space-game001/resources/shaders/fog_shadow_web.fragment
2026-04-25 19:56:00 +03:00

77 lines
1.6 KiB
Plaintext

precision mediump float;
uniform sampler2D Texture;
uniform sampler2D uShadowMap;
uniform vec3 uLightDir;
varying vec2 texCoord;
varying vec4 fragPosLightSpace;
varying vec3 fragNormal;
varying float fogDistance;
float computeShadow(vec4 lightSpacePos, vec3 normal)
{
vec3 projCoords = lightSpacePos.xyz / lightSpacePos.w;
projCoords = projCoords * 0.5 + 0.5;
if (projCoords.x < 0.0 || projCoords.x > 1.0 ||
projCoords.y < 0.0 || projCoords.y > 1.0 ||
projCoords.z > 1.0)
{
return 0.0;
}
float currentDepth = projCoords.z;
float bias = 0.0004;
if (dot(normal, normal) > 0.001)
{
float cosTheta = dot(normalize(normal), -normalize(uLightDir));
bias = max(0.002 * (1.0 - cosTheta), 0.0002);
}
float shadow = 0.0;
float texelSize = 1.0 / 2048.0;
for (int x = -1; x <= 1; x++)
{
for (int y = -1; y <= 1; y++)
{
float pcfDepth = texture2D(uShadowMap, projCoords.xy + vec2(float(x), float(y)) * texelSize).r;
shadow += currentDepth - bias > pcfDepth ? 1.0 : 0.0;
}
}
shadow /= 9.0;
return shadow;
}
void main()
{
vec4 color = texture2D(Texture, texCoord);
if (color.a < 0.1)
discard;
float ambient = 0.4;
float diffuseStrength = 0.6;
float diffuse = 1.0;
vec3 n = fragNormal;
if (dot(n, n) > 0.001)
{
n = normalize(n);
diffuse = max(dot(n, -normalize(uLightDir)), 0.0);
}
float shadow = computeShadow(fragPosLightSpace, fragNormal);
float lighting = ambient + diffuseStrength * diffuse * (1.0 - shadow);
color.rgb *= lighting;
vec3 fogColor = vec3(0.53, 0.81, 0.92);
float fogFactor = clamp((fogDistance - 30.0) / 10.0, 0.0, 1.0);
color.rgb = mix(color.rgb, fogColor, fogFactor);
gl_FragColor = color;
}