# [D3D9] Deferred Rendering: Point Lights (includes PICTURES)

This topic is 2578 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

##### Share on other sites
I'll bump this one single time as it has been 36 hours, almost 100 views and the thread is about to fall off the front page. Am I asking too much here? Not posting enough code? Does everything look correct code- and shader-wise? I'm not sure why the silence...

##### Share on other sites
I'll keep looking at this for a bit, but my first suggestion is to just use the world position passed in from the vertex shader instead of trying to compute the world matrix from the view matrix, since that just adds in extra complex computation that you don't need.

turn this:

{
float4 position : POSITION0;
float4 screen_position : TEXCOORD0;
};

to this:

{
float4 worldPos;
float4 position : POSITION0;
float4 screen_position : TEXCOORD0;
};

and this:

[font="Consolas,"]

[/font][font="Consolas,"]

{

[/font][font="Consolas,"]

[/font][font="Consolas,"]

[/font][font="Consolas,"]

//processing geometry coordinates

[/font][font="Consolas,"]

float4 world_position = mul(float4(input.position,1), mat_world);

[/font][font="Consolas,"]

float4 view_position = mul(world_position, mat_view);

[/font][font="Consolas,"]

output.position = mul(view_position, mat_projection);

[/font][font="Consolas,"]

output.screen_position = output.position;

[/font][font="Consolas,"]

[/font][font="Consolas,"]

return output;

[/font][font="Consolas,"]

}

[/font]

to this:

[font="Consolas,"]

[/font][font="Consolas,"]

{

[/font][font="Consolas,"]

[/font][font="Consolas,"]

[/font][font="Consolas,"]

//processing geometry coordinates

[/font][font="Consolas,"]

float4 world_position = mul(float4(input.position,1), mat_world);

[/font][font="Consolas,"]

float4 view_position = mul(world_position, mat_view);

[/font][font="Consolas,"]

output.[color="#1C2837"]worldPos = world_position;

[/font][font="Consolas,"]

output.position = mul(view_position, mat_projection);

[/font][font="Consolas,"]

output.screen_position = output.position;

[/font][font="Consolas,"]

[/font][font="Consolas,"]

return output;

[/font][font="Consolas,"]

}

[/font]
turn this:
[font="Consolas,"]

//transform to world space

[/font][font="Consolas,"]

position = mul(position, mat_invviewproj);

[/font][font="Consolas,"]

position /= position.w;

[/font]

to this:

[font="Consolas,"]

//transform to world space

[/font][font="Consolas,"]

position = input.[color="#1C2837"]worldPos;

[/font][font="Consolas,"]

[/font][font="Consolas,"]

Hope that helps

Oh yeah, and one other thing, to tell you the truth, I can't quite see whats wrong with your picture, it looks fine to me except maybe the walls and ceiling turn blue far off, is that what the problem is?

[/font]

##### Share on other sites
First of all, thanks a TON for writing! Really helps a lot.

I committed those changes but it didn't change anything (thanks for the simplification though). I guess I can also delete these lines?

 position.xy = input.screen_position.xy; position.z = depth_val; position.w = 1.0f; 

And I had to bind your float4 worldPos to TEXCOORD1 in order to get the shader to compile, I guess that's okay?

I have investigated further and I'm pretty sure the problem lies with the attenuation! That's the term that should make sure the stuff in the back, as can be seen in the shot in my first post, should NEVER be lit (as that stuff is too far away from the light and its radius) and it should also make sure the floor itself, which never gets lit currently, SHOULD be lit, right?

To answer your question, that's what is not working and making me think there's something wrong, the light sphere sits right on the floor plane of the environment, but it lights the background like a see-through sphere instead of leaving the background and point-lighting that floor.

Inverting the depth (which is stored in the alpha channel of my view-space normal render target in the G-Buffer just fine, I can check it in NVidia PerfHUD) like this doesn't change anything surprisingly:

 float depth_val = tex2D(smp_normal,tex_coord).a; depth_val = -depth_val + 1; 

My G-Buffer fill shader stores the depth like this:

 // in the vertex shader // get the position of the vertex in view-space, retrieve depth and pass it on float3 position_view = mul ( input.position, mat_worldview ); output.depth = position_view.z; // in the pixel shader // linear depth output.gbuffertex2.a = input.depth / render_distance; 

Since my render distance is large and that environment pretty small, the depth values stored in the G-Buffer are, according to PerfHUD, 0.00 and sometimes 0.01 - is that maybe a problem? I can lower the render distance and get much more variety between these numbers.

This might help.

##### Share on other sites
Hidden
try this maybe. Pass in a float 3 containing 3 attenuation factors, or modifiers, one is a constant modifier, another being the linear modifier, and the last being an exponential modifier.

Attenuation = att0 + (att1 * d) + (att2 * d²)

This is what i have for a pixel shader in my lesson on point lights, it could possibly be of use:

float4 PS(VS_OUTPUT input) : SV_TARGET
{
input.normal = normalize(input.normal);

float4 diffuse = ObjTexture.Sample( ObjSamplerState, input.TexCoord );

float3 finalColor = float3(0.0f, 0.0f, 0.0f);

//Create the vector between light position and pixels position
float3 lightToPixelVec = light.pos - input.worldPos;

//Find the distance between the light pos and pixel pos
float d = length(lightToPixelVec);

//Create the ambient light
float3 finalAmbient = diffuse * light.ambient;

//If pixel is too far, return pixel color with ambient light
if( d > light.range )
return float4(finalAmbient, diffuse.a);

//Turn lightToPixelVec into a unit length vector describing
//the pixels direction from the lights position
lightToPixelVec /= d;

//Calculate how much light the pixel gets by the angle
//in which the light strikes the pixels surface
float howMuchLight = dot(lightToPixelVec, input.normal);

//If light is striking the front side of the pixel
if( howMuchLight > 0.0f )
{
//Add light to the finalColor of the pixel
finalColor += howMuchLight * diffuse * light.diffuse;

//Calculate Light's Falloff factor
finalColor /= light.att[0] + (light.att[1] * d) + (light.att[2] * (d*d));
}

//make sure the values are between 1 and 0, and add the ambient
finalColor = saturate(finalColor + finalAmbient);

//Return Final Color
return float4(finalColor, diffuse.a);
}

I pass this in as the attenuation factor for the light (of course you will want to change it, and it can take a little time to find a good combination of attenuation factors:
light.att = XMFLOAT3(0.0f, 0.2f, 0.0f);

notice how i also use a variable for the range of the point light, you might consider doing that too, but if the attenuation lets the light go to far, then you can see a definite cut off at the range of the light (which can be useful sometimes)

(sorry if its hard to read without formatting, i can never get the code or source tags to work right...

[color="#cccccc"]

Yes, that link wasn't very helpful I'm afraid... Thanks for trying though!

Any other ideas, anyone?

##### Share on other sites
have a look at catalins xna blog here

i also made my baby-steps in deferred rendering based on his tutorial and it's really well written and rather easy to understand

##### Share on other sites

have a look at catalins xna blog here

i also made my baby-steps in deferred rendering based on his tutorial and it's really well written and rather easy to understand

This is even less helpful than the previous response. You have linked the same blog the OP was following.

@ op; I know how frustrating it is seeing the view count go up and the reply count stand dormant. I've looked at your post but as I'm still forward rendering I won't be as helpful as those with time in the trenches.

First, have you tried shrinking the size of your view frustum, there by increasing resolution in the Depth buffer? you had mentioned it in a previous post, and it struck me that this could be a depth issue( especially with the grainy vertical blue lines on the right of the second picture, although upon closer inspection it appears to be the pleats of the curtains). If you have and it wasn't the issue than I would try some simpler geometry that we can solve by pen and paper if need be. Maybe a sphere light with a simple box around it?

1. 1
2. 2
Rutin
16
3. 3
4. 4
5. 5

• 11
• 26
• 10
• 11
• 9
• ### Forum Statistics

• Total Topics
633722
• Total Posts
3013538
×