Shadowmapping and sqrt() for maximum shadowmap resolution

Started by
3 comments, last by AndyTX 17 years, 5 months ago
Ok, I have posted this in the OpenGL forum but no luck with helping to understand how/why in the OpenGL Superbible 3rd edition they use a sqrt() to get the shadowmap to maximum resolution. Here is the code...

 GLfloat lightToSceneDistance, nearPlane, fieldOfView;
    GLfloat lightModelview[16], lightProjection[16];

    // Save the depth precision for where it's useful
    lightToSceneDistance = sqrt(lightPos[0] * lightPos[0] + 
                                lightPos[1] * lightPos[1] + 
                                lightPos[2] * lightPos[2]);
    nearPlane = lightToSceneDistance - 150.0f;
    if (nearPlane < 50.0f)
        nearPlane = 50.0f;
    // Keep the scene filling the depth texture
    fieldOfView = 17000.0f / lightToSceneDistance;

Any help would be great. I have tried this code in my own and my shadows disappear. I just don't get where they come up with the numbers. Maybe this code doesn't help me out with maximizing the depth texture... I am trying to get rid of my jagged edges on my shadows and thats with a 2048x2048 map. This is for a large outdoor terrain area. Thanks
Advertisement
All they are doing is working out how far the light is from the origin (0,0,0). The sqrt is just the one in "length(v) = sqrt(dot(v,v))".

So basically they are assuming that the scene is at the origin, and also that it has a maximum radius of 150 units (that's the - 150 in there). i.e. they're just putting the light's near plane as close to the scene as possible to save depth precision.

There are a few scene-specific constants and assumptions in there. What you want to do in the general case is probably to find a bounding sphere around your scene and use that instead.

i.e. something like:
lightToSceneVector = lightPos - boundingSphereCenter;lightToSceneDistance = length(lightToSceneVector);nearPlane = lightToSceneDistance - boundingSphereRadius;...


[Edited by - AndyTX on November 6, 2006 10:55:52 AM]
Quote:
lightToSceneDistance = sqrt(lightPos[0]*lightPos[0] + lightPos[1]*lightPos[1] + lightPos[2]*lightPos[2]);




I second that notion. Determination of length. l = sqrt(x*x + y*y + z*z)
So this only works with cameras that don't move? I am making a RTS game and so my camera moves around. And what is with the 17000.0 / lightToSceneDistance? And if this only moves the near plane closer one can just do this by hand correct and find the best placement for their engine correct?
This is relevant to *lights* actually, not cameras (since you're rendering the shadow map here).

It will work completely fine for moving lights, however you'll have to recompute it every time the light moves naturally.

Regarding the 17000 / lightToSceneDistance, that seems to be yet another scene-dependent constant constant rolled into the code. i.e. calculate the light field of view such that it covers the whole scene from the selected distance. The proper generic way would be to use the scene radius to compute the FOV (it'll be a single trig function).

This topic is closed to new replies.

Advertisement