I am trying to implement a shadow mapping technique and I have some problems to make it works.
I have a camera in the light's position and this is the shadow map I get. All the vertex have been multiplied by each modelViewProjectionMatrix
.
I also have a texture with the world positions of the vertex. It's a GL_RGBA32F
texture because all the points have been multiplied by each ModelMatrix
to have the points in world space.
And the shader:
layout(binding=5) uniform sampler2D shadowMap;
layout(binding=6) uniform sampler2D positionMap;
in vec2 texcoord;
uniform mat uViewProjectionMatrix;
out vec4 color;
void main() {
vec4 pos = texture(positionMap, texcoord);
vec4 ShadowCoord = uViewProjectionMatrix * pos;
ShadowCoord.xy = ShadowCoord.xy * vec2(0.5,0.5) + vec2(0.5,0.5);
float a = texture(shadowMap, ShadowCoord.xy).z;
color = vec4(a, a, a, 1.0);
}
The output (the camera is almost in the same position of the light):
I am just trying to see if the projection of each vertex is right from the camera's position but looks like it's not. The point of all this is to compare:
if ( texture(shadowMap, ShadowCoord.xy).z < ( ShadowCoord.z-bias ) )
but it also doesn't work.
I would appreciate any help. Thank you.
You are missing the perspective divide and you seem to be completely ignoring depth range.
The general idea here is to get
ShadowCoord.xyz
into the range [0,1] (for texture lookup and depth comparison). Your code operates under the assumption thatuViewProjectionMatrix * pos
(clip-space coordinates) is in the range [-1,1] but that is not really guaranteed unless you divide byw
(NDC coordinates).I would consider something like this instead:
After this,
ShadowCoord.xy
will be a texture coordinate to lookup in your shadow map, andShadowCoord.z
will be the current fragment's depth from your light's point of view. You can useShadowCoord.z
for comparison versus the sampled depth.In fact, you might even consider using a
sampler2DShadow
to do this more efficiently. For an example of that, see this related question and answer