Du bist nicht angemeldet.

Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!

Werbeanzeige

  • »Sebastian Müller« ist der Autor dieses Themas

Beiträge: 369

Wohnort: Freilingen [Rheinland-Pfalz]

Beruf: Schüler

  • Private Nachricht senden

1

09.02.2014, 12:25

Fehlerhafte Lichtberechnung mit Pointlight

Liebe Leser

Ich entwickle geraden einen eigene Beleuchtung-Shader. Ich habe viel im Internet recherchiert und viel darüber gelesen. Ich habe nun einen eigenen Shader geschrieben (Point light). Die Lichtberechnungen sind bis auf einen Punkt perfekt.

-> Falloff nur auf einer Seite perfekt

Jedoch sieht das Ergebnis bei meine Hütten-Modell etwas seltsam aus. Das Licht scheint nur in einer Richtung perfekt zu laufen. in der anderen hört es sofort auf zu leuchten.

Also die inerpolation oder der Falloff zwischen 100% licht und 0% licht läuft auf einer fälsche zwischen 0.05cm (geschätzt) und auf der anderen zwischen 50 (geschätzt). Genau so wie eingestellt. (Reichweite -> 50)

Ein Beispiel ist im anhang







Hier der shader

HLSL-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
// Dieser Effekt wurde automatisch vom TriBase-Tool ModelConverter generiert.
// Hinweis: um einen Tabulator einzufügen, drücken Sie <Strg+Tab>!

DWORD   NumTextures         = 1;
STRING  Texture1Filename    = "Wood_2.png";
DWORD   Texture1Type        = 1; // 1: 2D-Textur; 2: Würfel; 3: Volumen
DWORD   Texture1ColorKey    = 0x00000000;
TEXTURE Texture1;


struct  Lighting
{
float3  Position;
float4  Diffuse;
float4  Specular;
int Distance;
};

int     NumLight;
Lighting    Lights[3];

// Material
float3 CameraPos;
float4 DiffuseColor = {0.5, 0.5, 0.5, 1.0};
float4 EmissiveColor = {0.05, 0.05, 0.05, 1.0};
float4 SpecularColor = {0.5, 0.5, 0.5, 1.0};
float SpecularPower = 15.0;


// Matrizen
float4x4    World;
float4x4    View;
float4x4    Prj;


sampler Main_sp = sampler_state
{
Texture     = <Texture1>;
AddressU    = Wrap;
AddressV    = Wrap;
MIPFilter   = Linear;
MinFilter   = Linear;
MagFilter   = Linear;
};


struct VS_INPUT
{
float4 Position : POSITION;
float3 Normal   : NORMAL;
float2 TexCords : TEXCOORD0;
float4 Diffuse  : COLOR0;
};

struct VS_OUTPUT        // PS_INPUT
{
float4 Position : POSITION;
float2 TexCords : TEXCOORD0;
float3 Normal   : COLOR0;
float3 WorldPos : TEXCOORD1;
};

//  ***************************************************************************************************************
//  ************************************Vertex Shader *************************************************************

VS_OUTPUT VS_MAIN(VS_INPUT IN)
{

VS_OUTPUT OUTPUT = (VS_OUTPUT) (0);

// Matrizen herstellen
float4x4 WorldPrj = mul(World, View);
float4x4 Matrix    = mul(WorldPrj, Prj);

float4   TexCords  = {0.0, 0.0, 0.0, 0.0};
float4   OutPos    = {0.0, 0.0, 0.0, 0.0};

OUTPUT.Position = mul(IN.Position, Matrix);
OUTPUT.Normal  = mul(IN.Normal, (float3x3)World);
OUTPUT.TexCords = IN.TexCords;
OUTPUT.WorldPos = mul(IN.Position, World);

return OUTPUT;
}
//  ***************************************************************************************************************
//  ************************************Beleuchtungs Funktion *************************************************************

float4  LightFunktion(int Light, VS_OUTPUT input, float4 texel)
{

// Lichtrichtung ausrechnen
float3      LightDir = normalize(input.WorldPos - Lights[0].Position);

// Leuchtstärke berechnen
float       Diffuse_Light = saturate(input.Normal - LightDir );

// Lichtabschwäschung berechnen (Falloff)
Diffuse_Light *= (Lights[0].Distance / dot(Lights[Light].Position - input.WorldPos, Lights[0].Position - input.WorldPos));

// Specular vorberechnungen
float3 h = normalize(normalize(CameraPos - input.WorldPos) - LightDir);
float Specular_Light = pow(saturate(dot(h, input.Normal)), SpecularPower);



return float4(saturate(
    EmissiveColor +
    (texel.xyz * DiffuseColor * Lights[0].Diffuse * Diffuse_Light * 0.6) + 
    (SpecularColor * Lights[0].Specular * Specular_Light * 0.4)
    ), 1.0);


}
//  ***************************************************************************************************************
//  ************************************Pixel Shader  *************************************************************
float4 PS_MAIN(VS_OUTPUT IN) : COLOR0
{
// Farben [Oberfläschen]
float4 Texel = {0.0, 0.0, 0.0, 0.0};    // Grass

Texel = tex2D(Main_sp, IN.TexCords);

return LightFunktion(0, IN, Texel);
}

//  ***************************************************************************************************************
//  ************************************Technik - 1 **************************************************************
TECHNIQUE T1
{
    PASS P1
    {
        VertexShader = compile vs_3_0 VS_MAIN();
        PixelShader = compile ps_3_0 PS_MAIN();
    }
}
»Sebastian Müller« hat folgendes Bild angehängt:
  • Beispiel.png

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

2

09.02.2014, 13:05

Das hier kommt mir komisch vor:

HLSL-Quelltext

1
2
// Leuchtstärke berechnen
float       Diffuse_Light = saturate(input.Normal - LightDir );

Und das hier auch:

HLSL-Quelltext

1
2
// Lichtabschwäschung berechnen (Falloff)
Diffuse_Light *= (Lights[0].Distance / dot(Lights[Light].Position - input.WorldPos, Lights[0].Position - input.WorldPos));


;)

  • »Sebastian Müller« ist der Autor dieses Themas

Beiträge: 369

Wohnort: Freilingen [Rheinland-Pfalz]

Beruf: Schüler

  • Private Nachricht senden

3

09.02.2014, 13:08

Welche Werte werden normalerweise dafür berechnet

ich meine bei der Berechnung der Lichtstärke?

Ich glaube, dass es an der Falloff Berechnung hängt.

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »Sebastian Müller« (09.02.2014, 13:21)


dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

4

09.02.2014, 13:22

Ich glaube, dass es vor allem an der Berechnung von Diffuse_Light hängt... ;)
Überleg mal, was diese Formel, die du da hingeschrieben hast, eigentlich tut.

Beim Falloff kommt mir nur komisch vor, dass du im dot() unten einmal mit Lights[Light] und einmal mit Lights[0] rechnest...

  • »Sebastian Müller« ist der Autor dieses Themas

Beiträge: 369

Wohnort: Freilingen [Rheinland-Pfalz]

Beruf: Schüler

  • Private Nachricht senden

5

09.02.2014, 13:32

Wenn ich es so mache

float Diffuse_Light = saturate(input.Normal + LightDir );

Also mit + und nicht -, dann ist es umgedreht !!!

die andere Seite wird beleuchtet und die vorherige nicht.

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

6

09.02.2014, 13:35

Richtig und jetzt überleg mal, wieso das wohl so ist... ;)

  • »Sebastian Müller« ist der Autor dieses Themas

Beiträge: 369

Wohnort: Freilingen [Rheinland-Pfalz]

Beruf: Schüler

  • Private Nachricht senden

7

09.02.2014, 13:55

Ok ich denke.


Eine Frage. Die Funktion Saturate tut doch 2 werte in eine zahl zwischen 0 und 1 berechnen. oder?

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

8

09.02.2014, 14:06

saturate() tut einfach alle Komponenten des übergebenen Vektors auf den Bereich §[0, 1]§ stutzen.

http://msdn.microsoft.com/en-us/library/…p/bb509645.aspx

  • »Sebastian Müller« ist der Autor dieses Themas

Beiträge: 369

Wohnort: Freilingen [Rheinland-Pfalz]

Beruf: Schüler

  • Private Nachricht senden

9

09.02.2014, 14:14

OK. Tut mir leid ich komme immer noch nicht drauf.


Wenn ich es so sehe, wird der Winkel zwischen Lichtstrahl und Normalvektor berechnet. Wenn er großer als 0 und kleiner als 90° ist, wird dementsprechend beleuchtet.

Jedoch muss auch beleuchtet werden, wenn kleiner als 0 und größer als -90 ist.

Ich hänge hier fest.

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

10

09.02.2014, 14:20

Wo genau wird hier deiner Meinung nach ein Winkel berechnet?

Werbeanzeige