I am doing shadow mapping for spotlights in a deferred OpenGL 4.3 renderer.
I've been trying to follow some tutorials on the subject, and modelled by fragment shader after it, but what I do not understand is the final comparison to calculate the shadow factor. The values that I sample from the depth map ("unifShadowTexture
") is in the range of [0, 1], since it is directly from the depth buffer but how is projCoords.z
clamped to [0, 1]? Is the division by .w
clamping it to [0,1]?
The issues I am facing is that a major part of the scene is shadowed even though it should not be, such as the ground floor, in the following picture(ignore the light artifacts, due to the lack of bias - the important point is the models are lit, but the ground floor isnt):
const std::string gDirLightFragmentShader =
"#version 430 \n \
\n \
layout(std140) uniform; \n \
\n \
uniform UnifDirLight \n \
{ \n \
mat4 mWVPMatrix; \n \
mat4 mVPMatrix; // light view-projection matrix, pre-multiplied by the bias-matrix \n \
vec4 mLightColor; \n \
vec4 mLightDir; \n \
vec4 mGamma; \n \
vec2 mScreenSize; \n \
} UnifDirLightPass; \n \
\n \
layout (binding = 2) uniform sampler2D unifPositionTexture; \n \
layout (binding = 3) uniform sampler2D unifNormalTexture; \n \
layout (binding = 4) uniform sampler2D unifDiffuseTexture; \n \
layout (binding = 5) uniform sampler2D unifShadowTexture; \n \
\n \
out vec4 fragColor; \n \
\n \
void main() \n \
{ \n \
vec2 texcoord = gl_FragCoord.xy / UnifDirLightPass.mScreenSize; \n \
\n \
vec3 worldPos = texture(unifPositionTexture, texcoord).xyz; \n \
vec3 normal = normalize(texture(unifNormalTexture, texcoord).xyz); \n \
vec3 diffuse = texture(unifDiffuseTexture, texcoord).xyz; \n \
\n \
vec4 lightClipPos = UnifDirLightPass.mVPMatrix * vec4(worldPos, 1.0); \n \
vec3 projCoords = lightClipPos.xyz / lightClipPos.w; \n \
\n \
float depthValue = texture(unifShadowTexture, projCoords.xy).x; \n \
float visibilty = 1.0; \n \
if (depthValue < (projCoords.z)) \n \
visibilty = 0.0; \n \
\n \
float angleNormal = clamp(dot(normal, UnifDirLightPass.mLightDir.xyz), 0, 1); \n \
\n \
fragColor = vec4(diffuse, 1.0) * visibilty * angleNormal * UnifDirLightPass.mLightColor; \n \
} \n";