mirror of
https://github.com/ZDoom/gzdoom.git
synced 2024-11-10 23:01:50 +00:00
- Added linear and nearest shadowmap filters (enabled with defines)
This commit is contained in:
parent
4afface97c
commit
a6d4bfc748
1 changed files with 48 additions and 7 deletions
|
@ -138,27 +138,57 @@ float R_DoomLightingEquation(float light)
|
||||||
|
|
||||||
#ifdef SUPPORTS_SHADOWMAPS
|
#ifdef SUPPORTS_SHADOWMAPS
|
||||||
|
|
||||||
float sampleShadowmap(vec2 dir, float v)
|
float shadowDirToU(vec2 dir)
|
||||||
{
|
{
|
||||||
float u;
|
|
||||||
if (abs(dir.x) > abs(dir.y))
|
if (abs(dir.x) > abs(dir.y))
|
||||||
{
|
{
|
||||||
if (dir.x >= 0.0)
|
if (dir.x >= 0.0)
|
||||||
u = dir.y / dir.x * 0.125 + (0.25 + 0.125);
|
return dir.y / dir.x * 0.125 + (0.25 + 0.125);
|
||||||
else
|
else
|
||||||
u = dir.y / dir.x * 0.125 + (0.75 + 0.125);
|
return dir.y / dir.x * 0.125 + (0.75 + 0.125);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (dir.y >= 0.0)
|
if (dir.y >= 0.0)
|
||||||
u = dir.x / dir.y * 0.125 + 0.125;
|
return dir.x / dir.y * 0.125 + 0.125;
|
||||||
else
|
else
|
||||||
u = dir.x / dir.y * 0.125 + (0.50 + 0.125);
|
return dir.x / dir.y * 0.125 + (0.50 + 0.125);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
float sampleShadowmap(vec2 dir, float v)
|
||||||
|
{
|
||||||
|
float u = shadowDirToU(dir);
|
||||||
float dist2 = dot(dir, dir);
|
float dist2 = dot(dir, dir);
|
||||||
return texture(ShadowMap, vec2(u, v)).x > dist2 ? 1.0 : 0.0;
|
return texture(ShadowMap, vec2(u, v)).x > dist2 ? 1.0 : 0.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
float sampleShadowmapLinear(vec2 dir, float v)
|
||||||
|
{
|
||||||
|
float u = shadowDirToU(dir);
|
||||||
|
float dist2 = dot(dir, dir);
|
||||||
|
|
||||||
|
vec2 isize = textureSize(ShadowMap, 0);
|
||||||
|
vec2 size = vec2(isize);
|
||||||
|
|
||||||
|
vec2 fetchPos = vec2(u, v) * size - vec2(0.5, 0.0);
|
||||||
|
if (fetchPos.x < 0.0)
|
||||||
|
fetchPos.x += size.x;
|
||||||
|
|
||||||
|
ivec2 ifetchPos = ivec2(fetchPos);
|
||||||
|
int y = ifetchPos.y;
|
||||||
|
|
||||||
|
float t = fract(fetchPos.x);
|
||||||
|
int x0 = ifetchPos.x;
|
||||||
|
int x1 = ifetchPos.x + 1;
|
||||||
|
if (x1 == isize.x)
|
||||||
|
x1 = 0;
|
||||||
|
|
||||||
|
float depth0 = texelFetch(ShadowMap, ivec2(x0, y), 0).x;
|
||||||
|
float depth1 = texelFetch(ShadowMap, ivec2(x1, y), 0).x;
|
||||||
|
return mix(step(dist2, depth0), step(dist2, depth1), t);
|
||||||
|
}
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
//
|
//
|
||||||
// Check if light is in shadow using Percentage Closer Filtering (PCF)
|
// Check if light is in shadow using Percentage Closer Filtering (PCF)
|
||||||
|
@ -168,6 +198,9 @@ float sampleShadowmap(vec2 dir, float v)
|
||||||
#define PCF_FILTER_STEP_COUNT 3
|
#define PCF_FILTER_STEP_COUNT 3
|
||||||
#define PCF_COUNT (PCF_FILTER_STEP_COUNT * 2 + 1)
|
#define PCF_COUNT (PCF_FILTER_STEP_COUNT * 2 + 1)
|
||||||
|
|
||||||
|
// #define USE_LINEAR_SHADOW_FILTER
|
||||||
|
#define USE_PCF_SHADOW_FILTER 1
|
||||||
|
|
||||||
float shadowmapAttenuation(vec4 lightpos, float shadowIndex)
|
float shadowmapAttenuation(vec4 lightpos, float shadowIndex)
|
||||||
{
|
{
|
||||||
if (shadowIndex >= 1024.0)
|
if (shadowIndex >= 1024.0)
|
||||||
|
@ -182,7 +215,11 @@ float shadowmapAttenuation(vec4 lightpos, float shadowIndex)
|
||||||
|
|
||||||
vec2 dir = ray / length;
|
vec2 dir = ray / length;
|
||||||
|
|
||||||
ray -= dir * 2.0; // margin
|
#if defined(USE_LINEAR_SHADOW_FILTER)
|
||||||
|
ray -= dir * 6.0; // Shadow acne margin
|
||||||
|
return sampleShadowmapLinear(ray, v);
|
||||||
|
#elif defined(USE_PCF_SHADOW_FILTER)
|
||||||
|
ray -= dir * 2.0; // Shadow acne margin
|
||||||
dir = dir * min(length / 50.0, 1.0); // avoid sampling behind light
|
dir = dir * min(length / 50.0, 1.0); // avoid sampling behind light
|
||||||
|
|
||||||
vec2 normal = vec2(-dir.y, dir.x);
|
vec2 normal = vec2(-dir.y, dir.x);
|
||||||
|
@ -194,6 +231,10 @@ float shadowmapAttenuation(vec4 lightpos, float shadowIndex)
|
||||||
sum += sampleShadowmap(ray + normal * x - bias * abs(x), v);
|
sum += sampleShadowmap(ray + normal * x - bias * abs(x), v);
|
||||||
}
|
}
|
||||||
return sum / PCF_COUNT;
|
return sum / PCF_COUNT;
|
||||||
|
#else // nearest shadow filter
|
||||||
|
ray -= dir * 6.0; // Shadow acne margin
|
||||||
|
return sampleShadowmap(ray, v);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in a new issue