First thank you guys for your help!
I've corrected my code now with your posted solutions in mind, but the strange thing is that if I don't comment out this line...
IN.vEyeRay.xyz /= IN.vEyeRay.z;
...I get a black screen?!
Also I noticed that the specular light seems to be wrong, because it's not centered at the light positon?!
I think something is wrong with the vReflection calculation, but what?!
Here is my final result:
And here an screenshot of all passes:
My corrected shader code now looks like this:
- Depth/Normal Pass
// Vertex shaderfloat4x4 matWorldViewProjection;float4x4 matWorldView;float4x4 matWorld;struct VS_INPUT { float3 Pos : POSITION0; float3 Normal : NORMAL;};struct VS_OUTPUT { float4 hPos : POSITION0; float4 Position : TEXCOORD0; float3 Normal : TEXCOORD1;};VS_OUTPUT vs_main(VS_INPUT Input){ VS_OUTPUT Output; Output.hPos = mul(float4(Input.Pos, 1.0), matWorldViewProjection); Output.Position = mul(float4(Input.Pos, 1.0), matWorldViewProjection); Output.Normal = mul(Input.Normal, (float3x3)matWorld); return Output; }// Pixel shaderfloat FarZ;struct VS_INPUT{ float4 hPos : POSITION0; float4 Position : TEXCOORD0; float3 Normal : TEXCOORD1;};struct VS_OUTPUT{ float4 Depth : COLOR0; float4 Normal : COLOR1;};VS_OUTPUT ps_main(VS_INPUT IN) : COLOR0{ VS_OUTPUT Output = (VS_OUTPUT)0; Output.Depth = IN.Position.z / IN.Position.w; Output.Normal = float4(normalize(IN.Normal) * 0.5f + 0.5f, 0); return Output;}
- One point light pass:
// Vertex shaderfloat4x4 matWorldViewProjection;float4x4 matViewInverse;float4x4 matWorldView;float4x4 matWorld;float FOV;float2 InvScreenDim;float2 ScreenDim;float3 ObjPos;float3 ObjSize;float3 LightPos0;struct VS_INPUT { float3 Position : POSITION0;};struct VS_OUTPUT { float4 Position : POSITION; float3 LightPos : TEXCOORD0; float4 vPos : TEXCOORD1; float3 vEyeRay : TEXCOORD2;};float4 ConvertToVPos(float4 p){ return float4(0.5 * (float2(p.x + p.w, p.w - p.y) + p.w * InvScreenDim.xy), p.zw);}float3 CreateEyeRay(float4 p){ float ViewAspect = ScreenDim.x / ScreenDim.y; float TanHalfFOV = tan(radians(FOV*0.5)); float3 ViewSpaceRay = float3(p.x * TanHalfFOV * ViewAspect, p.y * TanHalfFOV, p.w); return mul(ViewSpaceRay, (float3x3)matViewInverse);}VS_OUTPUT vs_main( VS_INPUT Input ){ VS_OUTPUT Output = (VS_OUTPUT)0; Output.Position = mul(float4(Input.Position, 1.0), matWorldViewProjection); Output.LightPos = mul(float4(LightPos0, 1.0), matWorld); Output.vPos = ConvertToVPos(Output.Position); Output.vEyeRay = CreateEyeRay(Output.Position); return Output;}// Pixel shadersampler2D DepthSampler;sampler2D NormalSampler;float4 EyePos;float4 LightColor0;float LightAttenuation0;float LightSpec0;float LightRadius0;struct VS_INPUT{ float4 Position : POSITION; float3 LightPos : TEXCOORD0; float4 vPos : TEXCOORD1; float4 vEyeRay : TEXCOORD2;};float4 ps_main(VS_INPUT IN) : COLOR0{ float LightIntensity = 1.0; float SpecularPower = 8.0; float SpecularIntensity = 1.0; float3 DiffColor = { 0.75, 0.75, 0.75 }; float Depth = tex2Dproj(DepthSampler, IN.vPos).r; float3 Normal = tex2Dproj(NormalSampler, IN.vPos).rgb; Normal = normalize(2.0f * Normal - 1.0f); // only works, when commented out?! //IN.vEyeRay.xyz /= IN.vEyeRay.z; // Compute pixel position float3 PixelWorldPos = (IN.vEyeRay.xyz) * Depth + EyePos; // Compute light attenuation and direction float3 vLight = IN.LightPos - PixelWorldPos; float Attenuation = saturate(1.0f - length(vLight)/LightRadius0); vLight = normalize(vLight); float NL = saturate(dot(Normal, vLight)); float3 Diffuse = NL * DiffColor.rgb; float3 vReflection = normalize(reflect(-vLight, Normal)); float3 vViewer = normalize(EyePos - PixelWorldPos); float Specular = SpecularIntensity * pow(saturate(dot(vReflection, vViewer)), SpecularPower); return Attenuation * LightIntensity * float4(Diffuse.rgb, Specular);}
Again... Thank you all for your great effort!
Cheers