Calculating scissor region for deferred lighting

Started by
18 comments, last by Nairou 12 years, 6 months ago

That article is self-contained. The only assumptions it makes is that you know what a plane is and what a dot product is, and it does not pull in equations from out of nowhere. If you really want to understand how to calculate the proper scissor rectangle for a light source, then that article is the right place to look.

I have no doubt that the article is sound, I'm just having a hard time understanding it. For example, it mentions that, in order to calculate the coordinates for the planes bounding the light, the following two equations must be satisfied:

eq_24.gif
eq_25.gif

But so far I don't have the slightest idea where these two conditions come from. I did some reading on dot products today to see if it had some other property I didn't know of, and found the geometric form which might be what the first equation is using, but other than that I'm still swimming in the dark. Again, no fault of the article, just a lack in my understanding. I just haven't yet found what I'm missing for it to make sense.
Advertisement
The dot product between a normalized plane and a point gives you the signed perpendicular distance from the point to the plane. The equation T * L = r means that the distance between the tangent plane T and the light position L is equal to the radius r of the light source. The equation Nx^2 + Nz^2 = 1 just means that the normal to the plane is unit length, where we left out the y coordinate because it is known to be zero.

The dot product between a normalized plane and a point gives you the signed perpendicular distance from the point to the plane. The equation T * L = r means that the distance between the tangent plane T and the light position L is equal to the radius r of the light source. The equation Nx^2 + Nz^2 = 1 just means that the normal to the plane is unit length, where we left out the y coordinate because it is known to be zero.

Wow... awesome, thank you for that explanation! That is the first I've read of a dot product doing that. I will start through the article again with that in mind.
What you're describing is using stencil testing, right?[/quote]
No. I think deferred is a bit over your head. In no offense, the reason your not getting a lot of stuff is that your skipping from beginner to advanced with no intermediate.

As I said and the whole optimization of what everyone here including you are talking about is: For each light, I dont want to run a pixel shader on pixels that are not affected by the light. How do you do that? Simplest way, know how big of a 3d area in the world your light effects. So draw a sphere in your world, any surfaces that collide with that sphere (use GL_DEPTH_TEST as GL_GREATER), the sphere ("light") will actually be hitting a surface. Since the sphere is drawn right over the screen those are the exact pixels you need to light. So while you draw your sphere, you arent drawing the sphere, you still run your pixel shader and pass the light position etc, but the pixel shader only draws the triangles being sent (The ones from the lights sphere that collide and hit surfaces).

look up some more tutorials, i swear every one i read talked about that. Your scissor test is going to do NOTHING faster than the first method I posted UNLESS you actually figure out and do method 2 and compute lighting in grid regions for each light in 1 pass for multiple lights. Just do the method we told you and ur fine. All you have to do is draw a 3d sphere at the lights position and scale it big enough. If its a small desk lamp draw the sphere like 3 units, a streetlight 50 units etc.

NBA2K, Madden, Maneater, Killing Floor, Sims http://www.pawlowskipinball.com/pinballeternal

dpadam450:

Which do you think would be faster, drawing a 16 triangle sphere where each vertex has to be multiplied by a set of matrices?
or computing the edges of the scissor region by taking the light position and adding in the strafe and up direction the radius of the light to get the top and right edges of the light's volume of affect projected onto 2d space?

I agree that drawing spheres to set a stencil region is fairly easy... perhaps I'll do a test, here's the code I was thinking of...



glm::mat4 view_matrix = camera->GetViewMatrix();
glm::mat4 projection_matrix = camera->GetProjectionMatrix();
glm::vec3 right_vector = glm::normalize(glm::vec3(view_matrix[0][0], view_matrix[1][0], view_matrix[2][0]));
glm::vec3 up_vector = glm::normalize(glm::vec3(view_matrix[0][1], view_matrix[1][1], view_matrix[2][1]));

for (unsigned int i = 0; i < light_count; i++){
light = lights;
glm::vec3 light_position = light->GetPosition();
float light_radius = light->GetRadius();

glm::vec3 right_side = projection_matrix * view_matrix * (light_position + (right_vector * light_radius));
glm::vec3 up_side = projection_matrix * view_matrix * (light_position + (up_vector * light_radius));

float scissor_left, scissor_right, scissor_up, scissor_down;
scissor_right = right_side.x;
scissor_up = up_side.y;
scissor_left = up_side.x - (right_side.x - up_side.x);
scissor_down = right_side.y - (up_side.y - right_side.y);
}


If someone could just double check my math, but I believe that will get you the scissor region, you could then just draw a rectangle that size in ortho mode into a light fbo and you should be set.
Douglas Eugene Reisinger II
Projects/Profile Site

As I said and the whole optimization of what everyone here including you are talking about is: For each light, I dont want to run a pixel shader on pixels that are not affected by the light. How do you do that? Simplest way, know how big of a 3d area in the world your light effects. So draw a sphere in your world, any surfaces that collide with that sphere (use GL_DEPTH_TEST as GL_GREATER), the sphere ("light") will actually be hitting a surface. Since the sphere is drawn right over the screen those are the exact pixels you need to light. So while you draw your sphere, you arent drawing the sphere, you still run your pixel shader and pass the light position etc, but the pixel shader only draws the triangles being sent (The ones from the lights sphere that collide and hit surfaces).

look up some more tutorials, i swear every one i read talked about that. Your scissor test is going to do NOTHING faster than the first method I posted UNLESS you actually figure out and do method 2 and compute lighting in grid regions for each light in 1 pass for multiple lights. Just do the method we told you and ur fine. All you have to do is draw a 3d sphere at the lights position and scale it big enough. If its a small desk lamp draw the sphere like 3 units, a streetlight 50 units etc.

The reason for my confusion is that I've already tried restricting light rendering to small regions of the screen using scissor testing, and achieved better performance. This article on deferred shading uses scissor testing, but never mentions rendering spheres around the light sources. All lights are rendered as fullscreen quads, but the scissor test limits shader execution to the portion of the screen where the light is located.

I'm certainly not opposed to trying the sphere method, as it sounds fairly simple, I just don't understand why you think both are required for deferred shading to work.

You mention that the method you describe doesn't use stencil testing. How else would you limit shader execution to an area of the screen masked by the rendered sphere? I've tried looking up more tutorials, as you suggest, but the only alternative I've found to scissor regions is using stencil testing, using an extra pass to render the light sphere to the stencil buffer, and then doing stencil failure tests to determine which pixels to run the shaders on. I'd love to see the tutorials you refer to.
[color="#1C2837"]Which do you think would be faster, drawing a 16 triangle sphere where each vertex has to be multiplied by a set of matrices?[/quote]
[color="#1C2837"]
I'm certainly not opposed to trying the sphere method, as it sounds fairly simple,[/quote]
[color="#1C2837"]
[color="#1C2837"]No, what I'm getting at is that it is easier for his perspective, I use what I know vs copying a function that doesn't make any sense to me. But in the theory of deferred shading, yes they will be the EXACT same time, unless your doing the 1,000+ disco lights. Also Pablo, the original method is faster (the one I'm proposing) IF IF IF your doing your stencil region 1 light at a time. How many operations does it take to project a low poly sphere say 100 polys: 100*32 instructions = 3200 instructions. Lets say his lighting shader is 32 instructions per pixel, and that includes pixels in his scissor test that are still NOT even receving light. So if your scissor region has more than 100 pixels that still wont receive light (which is going to happen), then your still running your pixel shader on pixels that equate to nothing, AND still wasting the blending operation which is the biggest concern for performance.
[color="#1C2837"]
[color="#1C2837"]
[color="#1C2837"]As to your question of the sphere. Well I have nothing to do at work atm, so damn if you dont get this then I give up.
[color="#1C2837"]

NBA2K, Madden, Maneater, Killing Floor, Sims http://www.pawlowskipinball.com/pinballeternal

Further, the scissor test is trying to solve the issue of not blending the pixel shader with the current framebuffer because it is slow NOT to determine what pixels the light source actually hits, those are 2 problems. You can still draw sphere to a stencil buffer and compute those same areas and shade them at once. So if there was another light on the right side of the box, you could draw that intersection as well and run the pixel shader on both regions at once. That way you only ADD to the framebuffer once. Thats all I got. But I have no benchmarks for performance, and to me the scissor test is overkill. Most real world lights dont overlap. If your using like school type industrial lights that are on the ceiling, then your non-sphere rendering would be F'd because all those lights would have basically fullscreen scissor regions. Where the actual method of doing deferred gives you just the pixels that intersect with the light, IE the ones actually on the ceiling can't be light by a light that only casts downward, etc. Not drawing spheres is horrible.

NBA2K, Madden, Maneater, Killing Floor, Sims http://www.pawlowskipinball.com/pinballeternal

Hmm... good point. Now I suppose I have to experiment myself and run a vs test. Although, when there are large amounts of collisions, your method seems a lot better, I must say. Thanks for the help!
Douglas Eugene Reisinger II
Projects/Profile Site

The dot product between a normalized plane and a point gives you the signed perpendicular distance from the point to the plane. The equation T * L = r means that the distance between the tangent plane T and the light position L is equal to the radius r of the light source. The equation Nx^2 + Nz^2 = 1 just means that the normal to the plane is unit length, where we left out the y coordinate because it is known to be zero.

After this explanation and a bit more reading, I am having a much easier time understanding the math used in the article. The only question I have at this point is more abstract.

Why is a quadratic equation being used to determine the extents of the light in screen space? I know what a quadratic equation looks like, and I understand how the shape makes sense for finding the two equation solutions that define the two sides of the light source. What I'm looking for is the proof or explanation that shows why the quadratic equation gives valid results for this use. I want to actually understand how this works as much as possible. Most of the quadratic equations I've seen are curved, but I would assume this calculation to require straight lines from the camera to the light edges. I'm guessing there is a variation on quadratic equations that mimics this?

I've been reading what I can find on quadratic equations all evening, but haven't found much beyond the typical curve examples from math class. Any information or links to explain how/why they are being used here would be awesome.

This topic is closed to new replies.

Advertisement