diff options
author | Dmitry Kostenko <codeforsmile@gmail.com> | 2022-02-14 09:00:55 +0100 |
---|---|---|
committer | x2048 <codeforsmile@gmail.com> | 2022-03-07 23:45:26 +0100 |
commit | 25c1974e0d734b6e80d128b325e8e6b506a7401b (patch) | |
tree | 7cec8aae9b7b5e4336133208f641b2ce820c5536 | |
parent | 12896b22d8e30689c57ef17c23ec3165abaa7de7 (diff) | |
download | minetest-25c1974e0d734b6e80d128b325e8e6b506a7401b.tar.gz minetest-25c1974e0d734b6e80d128b325e8e6b506a7401b.tar.bz2 minetest-25c1974e0d734b6e80d128b325e8e6b506a7401b.zip |
Change normal bias for entities to avoid shadow acne
-rw-r--r-- | client/shaders/object_shader/opengl_fragment.glsl | 10 | ||||
-rw-r--r-- | client/shaders/object_shader/opengl_vertex.glsl | 13 |
2 files changed, 12 insertions, 11 deletions
diff --git a/client/shaders/object_shader/opengl_fragment.glsl b/client/shaders/object_shader/opengl_fragment.glsl index 48066adc3..fdfcec0c8 100644 --- a/client/shaders/object_shader/opengl_fragment.glsl +++ b/client/shaders/object_shader/opengl_fragment.glsl @@ -56,12 +56,6 @@ vec4 getPerspectiveFactor(in vec4 shadowPosition) return shadowPosition; } -// assuming near is always 1.0 -float getLinearDepth() -{ - return 2.0 * f_shadowfar / (f_shadowfar + 1.0 - (2.0 * gl_FragCoord.z - 1.0) * (f_shadowfar - 1.0)); -} - vec3 getLightSpacePosition() { vec4 pLightSpace; @@ -69,8 +63,7 @@ vec3 getLightSpacePosition() #if DRAW_TYPE == NDT_PLANTLIKE pLightSpace = m_ShadowViewProj * vec4(worldPosition, 1.0); #else - float offsetScale = (0.0057 * getLinearDepth() + normalOffsetScale); - pLightSpace = m_ShadowViewProj * vec4(worldPosition + offsetScale * normalize(vNormal), 1.0); + pLightSpace = m_ShadowViewProj * vec4(worldPosition + normalOffsetScale * normalize(vNormal), 1.0); #endif pLightSpace = getPerspectiveFactor(pLightSpace); return pLightSpace.xyz * 0.5 + 0.5; @@ -544,6 +537,5 @@ void main(void) float clarity = clamp(fogShadingParameter - fogShadingParameter * length(eyeVec) / fogDistance, 0.0, 1.0); col = mix(skyBgColor, col, clarity); - gl_FragColor = vec4(col.rgb, base.a); } diff --git a/client/shaders/object_shader/opengl_vertex.glsl b/client/shaders/object_shader/opengl_vertex.glsl index 9ca5ef0f3..12078f532 100644 --- a/client/shaders/object_shader/opengl_vertex.glsl +++ b/client/shaders/object_shader/opengl_vertex.glsl @@ -36,6 +36,8 @@ const vec3 artificialLight = vec3(1.04, 1.04, 1.04); varying float vIDiff; const float e = 2.718281828459; const float BS = 10.0; +const float bias0 = 0.9; +const float bias1 = 1.0 - bias0; #ifdef ENABLE_DYNAMIC_SHADOWS // custom smoothstep implementation because it's not defined in glsl1.2 @@ -104,8 +106,15 @@ void main(void) #ifdef ENABLE_DYNAMIC_SHADOWS vec3 nNormal = normalize(vNormal); cosLight = dot(nNormal, -v_LightDirection); - float texelSize = 767.0 / f_textureresolution; - float slopeScale = clamp(1.0 - abs(cosLight), 0.0, 1.0); + + // Calculate normal offset scale based on the texel size adjusted for + // curvature of the SM texture. This code must be change together with + // getPerspectiveFactor or any light-space transformation. + float distanceToPlayer = length((eyePosition - worldPosition).xyz) / f_shadowfar; + float perspectiveFactor = distanceToPlayer * bias0 + bias1; + float texelSize = 1.0 / f_textureresolution; + texelSize *= f_shadowfar * perspectiveFactor / (bias1 / perspectiveFactor - texelSize * bias0) * 0.15; + float slopeScale = clamp(pow(1.0 - cosLight*cosLight, 0.5), 0.0, 1.0); normalOffsetScale = texelSize * slopeScale; if (f_timeofday < 0.2) { |