forked from OctaForge/OctaCore
689 lines
32 KiB
INI
689 lines
32 KiB
INI
////////////////////////////////////////////////
|
|
//
|
|
// deferred shading
|
|
//
|
|
////////////////////////////////////////////////
|
|
|
|
msaadetectedges = [
|
|
result [{
|
|
@(if (glext "GL_EXT_shader_samples_identical") [result [
|
|
if(textureSamplesIdenticalEXT(tex1, ivec2(gl_FragCoord.xy)))
|
|
{
|
|
@arg1
|
|
}
|
|
else
|
|
]])
|
|
|
|
{
|
|
vec4 e = texelFetch(tex1, ivec2(gl_FragCoord.xy), 0);
|
|
e.xyz -= 0.5;
|
|
float maxdiff = 0.98*0.98*dot(e.xyz, e.xyz);
|
|
|
|
@(loopconcat+ i 1 (- $msaasamples 1) [result [
|
|
vec4 e@i = texelFetch(tex1, ivec2(gl_FragCoord.xy), @i);
|
|
e@i.xyz -= 0.5;
|
|
if(abs(e.w-e@i.w) <= 2.0/255.0 && pow(dot(e@i.xyz, e.xyz), 2.0) >= maxdiff*dot(e@i.xyz, e@i.xyz))
|
|
{
|
|
]])
|
|
|
|
@arg1
|
|
|
|
@(loopconcat+ i 1 (- $msaasamples 1) [result [
|
|
}
|
|
]])
|
|
}
|
|
}]
|
|
]
|
|
|
|
lazyshader 0 msaaedgedetect [
|
|
attribute vec4 vvertex;
|
|
void main(void)
|
|
{
|
|
gl_Position = vvertex;
|
|
}
|
|
] [
|
|
@(? (glext "GL_EXT_shader_samples_identical") [
|
|
#extension GL_EXT_shader_samples_identical : enable
|
|
])
|
|
uniform sampler2DMS tex1;
|
|
|
|
void main(void)
|
|
{
|
|
@(msaadetectedges [discard;])
|
|
}
|
|
]
|
|
|
|
// deferredlighttype:
|
|
// p -> point-light shadow (default cubemap)
|
|
// c -> CSM
|
|
// a -> AO
|
|
// A -> AO sun
|
|
// r -> radiance hints
|
|
// G -> 5x5 weighted gather filter
|
|
// g -> 3x3 weighted gather filter
|
|
// E -> 5x5 weighted bilinear filter
|
|
// F -> 3x3 weighted bilinear filter
|
|
// f -> 4x rotated grid filter
|
|
// m -> minimap
|
|
// M -> multisampled
|
|
// O -> sample 1
|
|
// R -> manual resolve
|
|
// S -> sample shading
|
|
// T -> edge detection
|
|
// n -> tile batching
|
|
// s -> spotlights
|
|
// t -> transparent
|
|
// b -> combined base/light variants
|
|
// d -> avatar shadow dist bias variants
|
|
// D -> disable dist bias
|
|
// z -> spec toggle
|
|
dlopt = [ >= (strstr $deferredlighttype $arg1) 0 ]
|
|
|
|
unpacknormbias = 0.005
|
|
unpacknormscale = (+f 1 (*f 2 $unpacknormbias))
|
|
unpacknorm = [
|
|
result [
|
|
@arg1 = clamp(@arg1 * @(divf $unpacknormscale 0.5) - @(+f (*f $unpacknormscale (divf 0.25 0.5)) $unpacknormbias), 0.0, 1.0);
|
|
]
|
|
]
|
|
|
|
unpackspec = [
|
|
result [
|
|
vec3 camdir = normalize(camera - pos.xyz);
|
|
float facing = 2.0*dot(normal.xyz, camdir);
|
|
float specscale = min(3.0*(diffuse.a + 0.5/255.0), 2.999), gloss = floor(specscale);
|
|
specscale -= gloss;
|
|
specscale = (0.35 + 0.15*gloss) * specscale / (1.5 - specscale);
|
|
gloss = 5.0 + 17.0*gloss;
|
|
]
|
|
]
|
|
|
|
unpackdistbias = [
|
|
cond [$avatar] [result [
|
|
#define distbias -@avatarshadowbias
|
|
]] [|| $transparent [dlopt "d"] [dlopt "D"] [dlopt "m"]] [result [
|
|
#define distbias 0.0
|
|
]] [result [
|
|
float distbias = -@avatarshadowbias * @(? (dlopt "a") [avatarmask] [step(fogcoord, @avatarshadowdist) * @(? $msaasamples [step(0.75, normal.a)] [normal.a])]);
|
|
]]
|
|
]
|
|
|
|
deferredlightvariantshader = [
|
|
local deferredlighttype
|
|
deferredlighttype = $arg3
|
|
numsplits = (+ $arg4 0)
|
|
numrh = (+ $arg5 0)
|
|
numlights = (+ $arg6 0)
|
|
baselight = (< (mod $arg2 4) 2)
|
|
spotlight = (>= (mod $arg2 8) 4)
|
|
transparent = (<= 8 $arg2 16)
|
|
avatar = (<= 17 $arg2 31)
|
|
variantshader 0 $arg1 $arg2 (? (< $arg2 0) [
|
|
attribute vec4 vvertex;
|
|
uniform mat4 lightmatrix;
|
|
void main(void)
|
|
{
|
|
gl_Position = lightmatrix * vvertex;
|
|
}
|
|
]) [
|
|
@(? (&& (dlopt "S") [< $glslversion 400]) [
|
|
#extension GL_ARB_sample_shading : enable
|
|
])
|
|
@(? (&& (dlopt "T") [glext "GL_EXT_shader_samples_identical"]) [
|
|
#extension GL_EXT_shader_samples_identical : enable
|
|
])
|
|
@(if (dlopt "M") [result [
|
|
uniform sampler2DMS tex0, tex1, tex3 @(? $transparent [, tex2]);
|
|
]] [result [
|
|
uniform sampler2DRect tex0, tex1, tex3 @(? $transparent [, tex2]);
|
|
]])
|
|
@(if (|| (dlopt "p") (dlopt "c")) [
|
|
if (|| (dlopt "g") (dlopt "G")) [if (> $usetexgather 1) [result [
|
|
uniform sampler2DShadow tex4;
|
|
]] [result [
|
|
uniform sampler2D tex4;
|
|
]]] [result [
|
|
uniform sampler2DRectShadow tex4;
|
|
]]
|
|
])
|
|
@(if $numlights [result [
|
|
uniform vec4 lightpos[@@numlights];
|
|
uniform vec4 lightcolor[@@numlights];
|
|
@(if $spotlight [result [
|
|
uniform vec4 spotparams[@@numlights];
|
|
]])
|
|
@(if (dlopt "p") [result [
|
|
uniform vec4 shadowparams[@@numlights];
|
|
uniform vec2 shadowoffset[@@numlights];
|
|
]])
|
|
]])
|
|
@(if $numsplits [result [
|
|
uniform vec4 csmtc[@@numsplits];
|
|
uniform vec3 csmoffset[@@numsplits];
|
|
uniform vec2 csmz;
|
|
]])
|
|
@(if (dlopt "c") [result [
|
|
uniform mat3 csmmatrix;
|
|
uniform vec3 sunlightdir;
|
|
uniform vec3 sunlightcolor;
|
|
@(if (dlopt "r") [result [
|
|
uniform vec3 skylightcolor;
|
|
uniform float giscale, rhnudge, rhbounds;
|
|
uniform vec4 rhtc[@@numrh];
|
|
uniform sampler3D tex6, tex7, tex8, tex9;
|
|
]])
|
|
]])
|
|
uniform vec3 camera;
|
|
uniform mat4 worldmatrix;
|
|
uniform vec4 fogdir;
|
|
uniform vec3 fogcolor;
|
|
uniform vec2 fogdensity;
|
|
uniform vec4 radialfogscale;
|
|
uniform vec2 shadowatlasscale;
|
|
uniform vec4 lightscale;
|
|
@(? (&& (dlopt "a") [! $avatar] [! $transparent]) [uniform sampler2DRect tex5; uniform vec2 aoscale; uniform vec4 aoparams;])
|
|
@(gdepthunpackparams)
|
|
fragdata(0) vec4 fragcolor;
|
|
|
|
@(if (dlopt "p") [
|
|
? $spotlight [
|
|
vec3 getspottc(vec3 dir, float spotdist, vec4 spotparams, vec4 shadowparams, vec2 shadowoffset, float distbias)
|
|
{
|
|
vec2 mparams = shadowparams.xy / max(spotdist + distbias, 1e-5);
|
|
return vec3((dir.xy - spotparams.xy*(spotdist + (spotparams.z > 0.0 ? 1.0 : -1.0)*dir.z)*shadowparams.z) * mparams.x + shadowoffset, mparams.y + shadowparams.w);
|
|
}
|
|
] [
|
|
vec3 getshadowtc(vec3 dir, vec4 shadowparams, vec2 shadowoffset, float distbias)
|
|
{
|
|
vec3 adir = abs(dir);
|
|
float m = max(adir.x, adir.y), mz = max(adir.z, m);
|
|
vec2 mparams = shadowparams.xy / max(mz + distbias, 1e-5);
|
|
vec4 proj;
|
|
if(adir.x > adir.y) proj = vec4(dir.zyx, 0.0); else proj = vec4(dir.xzy, 1.0);
|
|
if(adir.z > m) proj = vec4(dir, 2.0);
|
|
return vec3(proj.xy * mparams.x + vec2(proj.w, step(0.0, proj.z)) * shadowparams.z + shadowoffset, mparams.y + shadowparams.w);
|
|
}
|
|
]
|
|
])
|
|
|
|
@(if (|| (dlopt "p") [dlopt "c"]) [
|
|
cond [dlopt "G"] [result [
|
|
@(? (> $usetexgather 1) [
|
|
#define shadowgather(center, xoff, yoff) textureGatherOffset(tex4, center, shadowtc.z, ivec2(xoff, yoff))
|
|
] [
|
|
#define shadowgather(center, xoff, yoff) step(shadowtc.z, textureGatherOffset(tex4, center, ivec2(xoff, yoff)))
|
|
])
|
|
float filtershadow(vec3 shadowtc)
|
|
{
|
|
vec2 offset = fract(shadowtc.xy - 0.5), center = (shadowtc.xy - offset)*shadowatlasscale;
|
|
vec4 group1 = shadowgather(center, -2, -2);
|
|
vec4 group2 = shadowgather(center, 0, -2);
|
|
vec4 group3 = shadowgather(center, 2, -2);
|
|
vec4 group4 = shadowgather(center, -2, 0);
|
|
vec4 group5 = shadowgather(center, 0, 0);
|
|
vec4 group6 = shadowgather(center, 2, 0);
|
|
vec4 group7 = shadowgather(center, -2, 2);
|
|
vec4 group8 = shadowgather(center, 0, 2);
|
|
vec4 group9 = shadowgather(center, 2, 2);
|
|
vec4 locols = vec4(group1.ab, group3.ab);
|
|
vec4 hicols = vec4(group7.rg, group9.rg);
|
|
locols.yz += group2.ab;
|
|
hicols.yz += group8.rg;
|
|
vec4 midcols = vec4(group1.rg, group3.rg) + vec4(group7.ab, group9.ab) +
|
|
vec4(group4.rg, group6.rg) + vec4(group4.ab, group6.ab) +
|
|
mix(locols, hicols, offset.y);
|
|
vec4 cols = group5 + vec4(group2.rg, group8.ab);
|
|
cols.xyz += mix(midcols.xyz, midcols.yzw, offset.x);
|
|
return dot(cols, vec4(1.0/25.0));
|
|
}
|
|
]] [dlopt "g"] [result [
|
|
@(? (> $usetexgather 1) [
|
|
#define shadowgather(center, xoff, yoff) textureGatherOffset(tex4, center, shadowtc.z, ivec2(xoff, yoff))
|
|
] [
|
|
#define shadowgather(center, xoff, yoff) step(shadowtc.z, textureGatherOffset(tex4, center, ivec2(xoff, yoff)))
|
|
])
|
|
float filtershadow(vec3 shadowtc)
|
|
{
|
|
vec2 offset = fract(shadowtc.xy - 0.5), center = (shadowtc.xy - offset)*shadowatlasscale;
|
|
vec4 group1 = shadowgather(center, -1, -1);
|
|
vec4 group2 = shadowgather(center, 1, -1);
|
|
vec4 group3 = shadowgather(center, -1, 1);
|
|
vec4 group4 = shadowgather(center, 1, 1);
|
|
vec4 cols = vec4(group1.rg, group2.rg) + vec4(group3.ab, group4.ab) + mix(vec4(group1.ab, group2.ab), vec4(group3.rg, group4.rg), offset.y);
|
|
return dot(mix(cols.xyz, cols.yzw, offset.x), vec3(1.0/9.0));
|
|
}
|
|
]] [dlopt "E"] [result [
|
|
#define shadowval(xy, xoff, yoff) float(shadow2DRect(tex4, vec3(xy + vec2(xoff, yoff), shadowtc.z)))
|
|
float filtershadow(vec3 shadowtc)
|
|
{
|
|
vec2 offset = fract(shadowtc.xy - 0.5);
|
|
vec4 center = vec4(shadowtc.xy - offset + 0.5, shadowtc.xy - offset*0.5);
|
|
vec4 size = vec4(offset + 1.0, 2.0 - offset);
|
|
return (1.0/25.0)*dot(size.zxzx*size.wwyy,
|
|
vec4(shadowval(center.zw, -1.5, -1.5),
|
|
shadowval(center.zw, 2.0, -1.5),
|
|
shadowval(center.zw, -1.5, 2.0),
|
|
shadowval(center.zw, 2.0, 2.0))) +
|
|
(2.0/25.0)*dot(size,
|
|
vec4(shadowval(center.zy, 2.0, 0.0),
|
|
shadowval(center.xw, 0.0, 2.0),
|
|
shadowval(center.zy, -1.5, 0.0),
|
|
shadowval(center.xw, 0.0, -1.5))) +
|
|
(4.0/25.0)*shadowval(center.xy, 0.0, 0.0);
|
|
}
|
|
]] [dlopt "F"] [result [
|
|
#define shadowval(center, xoff, yoff) float(shadow2DRect(tex4, center + vec3(xoff, yoff, 0.0)))
|
|
float filtershadow(vec3 shadowtc)
|
|
{
|
|
vec2 offset = fract(shadowtc.xy - 0.5);
|
|
vec3 center = shadowtc;
|
|
//center.xy -= offset;
|
|
//vec4 size = vec4(offset + 1.0, 2.0 - offset), weight = vec4(2.0 - 1.0 / size.xy, 1.0 / size.zw - 1.0);
|
|
//return (1.0/9.0)*dot(size.zxzx*size.wwyy,
|
|
// vec4(shadowval(center, weight.zw),
|
|
// shadowval(center, weight.xw),
|
|
// shadowval(center, weight.zy),
|
|
// shadowval(center, weight.xy)));
|
|
center.xy -= offset*0.5;
|
|
vec4 size = vec4(offset + 1.0, 2.0 - offset);
|
|
return (1.0/9.0)*dot(size.zxzx*size.wwyy,
|
|
vec4(shadowval(center, -0.5, -0.5),
|
|
shadowval(center, 1.0, -0.5),
|
|
shadowval(center, -0.5, 1.0),
|
|
shadowval(center, 1.0, 1.0)));
|
|
}
|
|
]] [dlopt "f"] [result [
|
|
#define shadowval(center, xoff, yoff) float(shadow2DRect(tex4, center + vec3(xoff, yoff, 0.0)))
|
|
float filtershadow(vec3 shadowtc)
|
|
{
|
|
return dot(vec4(0.25),
|
|
vec4(shadowval(shadowtc, -0.4, 1.0),
|
|
shadowval(shadowtc, -1.0, -0.4),
|
|
shadowval(shadowtc, 0.4, -1.0),
|
|
shadowval(shadowtc, 1.0, 0.4)));
|
|
}
|
|
]] [result [
|
|
#define filtershadow(shadowtc) float(shadow2DRect(tex4, shadowtc))
|
|
]]
|
|
])
|
|
|
|
@(if (dlopt "c") [result [
|
|
vec3 getcsmtc(vec3 pos, float distbias)
|
|
{
|
|
vec3 tc, offset;
|
|
pos = csmmatrix * pos;
|
|
pos.z -= distbias;
|
|
tc.z = csmz.x + pos.z*csmz.y;
|
|
@(loopconcat j $numsplits [result [
|
|
tc.xy = csmtc[@@j].xy + pos.xy*csmtc[@@j].z;
|
|
offset = csmoffset[@@j];
|
|
if(max(abs(tc.x), abs(tc.y)) >= csmtc[@@j].w)
|
|
{
|
|
]])
|
|
offset = vec3(-16384.0);
|
|
@(loopconcat j $numsplits [result [
|
|
}
|
|
]])
|
|
return tc + offset;
|
|
}
|
|
|
|
@(if (dlopt "r") [result [
|
|
vec4 getrhlight(vec3 pos, vec3 norm)
|
|
{
|
|
vec3 tc;
|
|
float offset;
|
|
pos += norm*rhnudge;
|
|
@(loopconcat j $numrh [result [
|
|
tc = rhtc[@@j].xyz + pos*rhtc[@@j].w;
|
|
offset = @(divf (+f 0.5 $j) $numrh);
|
|
if(max(max(abs(tc.x), abs(tc.y)), abs(tc.z)) >= rhbounds)
|
|
{
|
|
]])
|
|
tc = vec3(4.0);
|
|
@(loopconcat j $numrh [result [
|
|
}
|
|
]])
|
|
tc.xy += 0.5;
|
|
tc.z = tc.z * @(divf 1 $numrh) + offset;
|
|
vec4 shr = texture3D(tex6, tc), shg = texture3D(tex7, tc), shb = texture3D(tex8, tc), sha = texture3D(tex9, tc);
|
|
shr.rgb -= 0.5;
|
|
shg.rgb -= 0.5;
|
|
shb.rgb -= 0.5;
|
|
sha.rgb -= 0.5;
|
|
vec4 basis = vec4(norm*-(1.023326*0.488603/3.14159*2.0), (0.886226*0.282095/3.14159));
|
|
return clamp(vec4(dot(basis, shr), dot(basis, shg), dot(basis, shb), min(dot(basis, sha), norm.z + 1.0)), 0.0, 1.0);
|
|
}
|
|
]])
|
|
]])
|
|
|
|
void main(void)
|
|
{
|
|
@(if (dlopt "M") [
|
|
if (dlopt "R") [result [
|
|
@(if (dlopt "T") [result [
|
|
bool shouldresolve = true;
|
|
@(msaadetectedges [shouldresolve = false;])
|
|
]])
|
|
|
|
#define gfetch(sampler, coords) texelFetch(sampler, ivec2(coords), sampleidx)
|
|
|
|
vec4 resolved = vec4(0.0);
|
|
#define accumlight(light) resolved.rgb += light
|
|
#define accumalpha(alpha) resolved.a += alpha
|
|
|
|
@(if (&& [dlopt "a"] [! $avatar] [! $transparent]) [result [
|
|
float ao = texture2DRect(tex5, gl_FragCoord.xy*aoscale).r;
|
|
]])
|
|
|
|
for(int sampleidx = 0; sampleidx < @msaasamples; sampleidx++)
|
|
{
|
|
]] [result [
|
|
@(if (dlopt "T") [msaadetectedges [discard;]])
|
|
|
|
#define gfetch(sampler, coords) texelFetch(sampler, ivec2(coords), @(? (dlopt "S") [gl_SampleID] (? (dlopt "O") 1 0)))
|
|
|
|
#define accumlight(light) fragcolor.rgb = light
|
|
#define accumalpha(alpha) fragcolor.a = alpha
|
|
]]
|
|
] [result [
|
|
#define gfetch(sampler, coords) texture2DRect(sampler, coords)
|
|
|
|
#define accumlight(light) fragcolor.rgb = light
|
|
#define accumalpha(alpha) fragcolor.a = alpha
|
|
]])
|
|
|
|
@(if (|| $baselight [> $numlights 1]) [result [
|
|
vec4 normal = gfetch(tex1, gl_FragCoord.xy);
|
|
|
|
@(if $transparent [result [
|
|
@(? (! $ghasstencil) [
|
|
if(normal.x + normal.y == 0.0) discard;
|
|
])
|
|
|
|
normal.xyz = normal.xyz*2.0 - 1.0;
|
|
@(if $usepacknorm [result [
|
|
float alpha = dot(normal.xyz, normal.xyz);
|
|
normal.xyz *= inversesqrt(alpha);
|
|
@(if $baselight [unpacknorm alpha])
|
|
]] [result [
|
|
#define alpha normal.a
|
|
]])
|
|
|
|
vec4 diffuse = gfetch(tex0, gl_FragCoord.xy);
|
|
@(? $baselight [
|
|
vec3 glow = gfetch(tex2, gl_FragCoord.xy).rgb;
|
|
])
|
|
]] [result [
|
|
@(? $baselight [
|
|
float alpha = float(normal.x + normal.y != 0.0);
|
|
] [
|
|
#define alpha 1.0
|
|
])
|
|
|
|
normal.xyz = normal.xyz*2.0 - 1.0;
|
|
@(if $usepacknorm [result [
|
|
float glowscale = dot(normal.xyz, normal.xyz);
|
|
normal.xyz *= inversesqrt(glowscale);
|
|
@(unpacknorm glowscale)
|
|
]] [result [
|
|
#define glowscale normal.a
|
|
]])
|
|
|
|
vec4 diffuse = gfetch(tex0, gl_FragCoord.xy);
|
|
@(? $baselight [
|
|
vec3 glow = diffuse.rgb * (1.0 - glowscale);
|
|
])
|
|
diffuse.rgb *= glowscale;
|
|
]])
|
|
]])
|
|
|
|
@(if (dlopt "m") [if (+ $numlights (dlopt "c")) [
|
|
gdepthunpackortho depth [gfetch(tex3, gl_FragCoord.xy)] [
|
|
vec3 pos = (worldmatrix * vec4(gl_FragCoord.xy, depth, 1.0)).xyz;
|
|
]
|
|
]] [if (+ $numlights (dlopt "c")) [result [
|
|
@(gdepthunpack depth [gfetch(tex3, gl_FragCoord.xy)] [
|
|
vec3 pos = (worldmatrix * vec4(depth*gl_FragCoord.xy, depth, 1.0)).xyz;
|
|
] [
|
|
vec4 pos = worldmatrix * vec4(gl_FragCoord.xy, depth, 1.0);
|
|
pos.xyz /= pos.w;
|
|
])
|
|
@(? (|| $baselight [> $numlights 1]) [
|
|
float fogcoord = length(camera - pos.xyz);
|
|
])
|
|
@(if (> (+ $numlights (dlopt "c")) 1) [unpackspec])
|
|
]] [result [
|
|
@(gdepthunpack depth [gfetch(tex3, gl_FragCoord.xy)])
|
|
@(? $baselight [
|
|
float fogcoord = -depth*length(vec3(gl_FragCoord.xy*radialfogscale.xy + radialfogscale.zw, 1.0));
|
|
])
|
|
]]])
|
|
|
|
@(if $baselight [result [
|
|
vec3 light = lightscale.rgb;
|
|
@(? (dlopt "r") [
|
|
vec4 rhlight = getrhlight(pos.xyz, normal.xyz);
|
|
light += rhlight.a * skylightcolor;
|
|
])
|
|
light *= diffuse.rgb;
|
|
|
|
@(if (&& (dlopt "a") [! $avatar] [! $transparent]) [result [
|
|
@(? (! (&& (dlopt "M") [dlopt "R"])) [
|
|
float ao = texture2DRect(tex5, gl_FragCoord.xy*aoscale).r;
|
|
])
|
|
@(if (dlopt "d") [result [
|
|
#define aomask ao
|
|
]] [result [
|
|
float avatarmask = step(fogcoord, @avatarshadowdist) * @(? $msaasamples [step(0.75, normal.a)] [normal.a]);
|
|
float aomask = clamp(ao + avatarmask, 0.0, 1.0);
|
|
]])
|
|
light *= aoparams.x + aomask*aoparams.y;
|
|
]])
|
|
light += glow * lightscale.a;
|
|
]] [result [
|
|
vec3 light = vec3(0.0);
|
|
]])
|
|
|
|
@(if (> (+ (? (dlopt "p") $numlights) (dlopt "c")) 1) [unpackdistbias])
|
|
|
|
@(if (dlopt "c") [result [
|
|
@(? (dlopt "r") [
|
|
vec3 sunlight = rhlight.rgb * giscale * diffuse.rgb;
|
|
])
|
|
float sunfacing = dot(sunlightdir, normal.xyz);
|
|
if(sunfacing > 0.0)
|
|
{
|
|
@(if (= (+ (? (dlopt "p") $numlights) (dlopt "c")) 1) [unpackdistbias])
|
|
vec3 csmtc = getcsmtc(pos.xyz, distbias);
|
|
float sunoccluded = filtershadow(csmtc);
|
|
@(if (dlopt "m") [result [
|
|
light += diffuse.rgb*sunfacing * sunlightcolor * sunoccluded;
|
|
]] [result [
|
|
@(if (= (+ $numlights (dlopt "c")) 1) [unpackspec])
|
|
float sunspec = pow(clamp(sunfacing*facing - dot(camdir, sunlightdir), 0.0, 1.0), gloss) * specscale;
|
|
@(if (dlopt "r") [result [
|
|
sunlight += (diffuse.rgb*sunfacing + sunspec) * sunoccluded;
|
|
]] [result [
|
|
@(? (&& (dlopt "A") [! $avatar] [! $transparent]) [
|
|
sunoccluded *= aoparams.z + aomask*aoparams.w;
|
|
])
|
|
light += (diffuse.rgb*sunfacing + sunspec) * sunoccluded * sunlightcolor;
|
|
]])
|
|
]])
|
|
}
|
|
@(if (dlopt "r") [result [
|
|
@(? (&& (dlopt "A") [! $avatar] [! $transparent]) [
|
|
sunlight *= aoparams.z + aomask*aoparams.w;
|
|
])
|
|
light += sunlight * sunlightcolor;
|
|
]])
|
|
]])
|
|
|
|
@(loopconcat j $numlights [result [
|
|
vec3 light@[j]dir = lightpos[@@j].xyz - pos.xyz * lightpos[@@j].w;
|
|
float light@[j]dist2 = dot(light@[j]dir, light@[j]dir);
|
|
if(light@[j]dist2 < 1.0)
|
|
{
|
|
@(if (= (+ $numlights $baselight) 1) [result [
|
|
vec4 normal = gfetch(tex1, gl_FragCoord.xy);
|
|
@(? (&& $transparent [! $ghasstencil]) [
|
|
if(normal.x + normal.y == 0.0) discard;
|
|
])
|
|
normal.xyz = normal.xyz*2.0 - 1.0;
|
|
@(? $usepacknorm [
|
|
float glowscale = dot(normal.xyz, normal.xyz);
|
|
normal.xyz *= inversesqrt(glowscale);
|
|
] [
|
|
#define glowscale normal.a
|
|
])
|
|
]])
|
|
float light@[j]facing = dot(light@[j]dir, normal.xyz);
|
|
if(light@[j]facing > 0.0)
|
|
{
|
|
float light@[j]invdist = inversesqrt(light@[j]dist2);
|
|
@(if $spotlight [result [
|
|
float spot@[j]dist = dot(light@[j]dir, spotparams[@@j].xyz);
|
|
float spot@[j]atten = 1.0 - (1.0 - light@[j]invdist * spot@[j]dist) * spotparams[@@j].w;
|
|
if(spot@[j]atten > 0.0)
|
|
{
|
|
]])
|
|
float light@[j]atten = 1.0 - light@[j]dist2 * light@[j]invdist;
|
|
@(? (&& (= (+ $numlights $baselight) 1) [! (dlopt "m")]) [
|
|
float fogcoord = length(camera - pos.xyz);
|
|
])
|
|
@(if (= (+ (? (dlopt "p") $numlights) (dlopt "c")) 1) [unpackdistbias])
|
|
@(if $spotlight [
|
|
if (dlopt "p") [result [
|
|
vec3 spot@[j]tc = getspottc(light@[j]dir, spot@[j]dist, spotparams[@@j], shadowparams[@@j], shadowoffset[@@j], distbias * lightpos[@@j].w);
|
|
light@[j]atten *= spot@[j]atten * filtershadow(spot@[j]tc);
|
|
]] [result [
|
|
light@[j]atten *= spot@[j]atten;
|
|
]]
|
|
] [
|
|
if (dlopt "p") [result [
|
|
vec3 shadow@[j]tc = getshadowtc(light@[j]dir, shadowparams[@@j], shadowoffset[@@j], distbias * lightpos[@@j].w);
|
|
light@[j]atten *= filtershadow(shadow@[j]tc);
|
|
]]
|
|
])
|
|
@(if (= (+ $numlights $baselight) 1) [result [
|
|
vec4 diffuse = gfetch(tex0, gl_FragCoord.xy);
|
|
@(if (! $transparent) [result [
|
|
@(if $usepacknorm [unpacknorm glowscale])
|
|
diffuse.rgb *= glowscale;
|
|
]])
|
|
]])
|
|
light@[j]facing *= light@[j]invdist;
|
|
@(if (dlopt "m") [result [
|
|
light += diffuse.rgb*light@[j]facing * lightcolor[@@j].rgb * light@[j]atten;
|
|
]] [result [
|
|
@(if (= (+ $numlights (dlopt "c")) 1) [unpackspec])
|
|
float light@[j]spec = pow(clamp(light@[j]facing*facing - light@[j]invdist*dot(camdir, light@[j]dir), 0.0, 1.0), gloss) * specscale;
|
|
@(if (dlopt "z") [result [
|
|
light@[j]spec *= lightcolor[@@j].a;
|
|
]])
|
|
light += (diffuse.rgb*light@[j]facing + light@[j]spec) * lightcolor[@@j].rgb * light@[j]atten;
|
|
@(? (= (+ $numlights $baselight) 1) [
|
|
float foglerp = clamp(exp2(fogcoord*fogdensity.x)*fogdensity.y, 0.0, 1.0);
|
|
light *= foglerp;
|
|
])
|
|
]])
|
|
@(? $spotlight [}])
|
|
}
|
|
}
|
|
]])
|
|
@(if (dlopt "m") [if $baselight [result [
|
|
accumlight(light);
|
|
accumalpha(alpha);
|
|
]] [result [
|
|
accumlight(light);
|
|
accumalpha(0.0);
|
|
]]] [if (|| $baselight [> $numlights 1]) [result [
|
|
float foglerp = clamp(exp2(fogcoord*fogdensity.x)*fogdensity.y, 0.0, 1.0);
|
|
@(? $baselight [
|
|
accumlight(mix(fogcolor*alpha, light, foglerp));
|
|
accumalpha(alpha);
|
|
] [
|
|
accumlight(light*foglerp);
|
|
accumalpha(0.0);
|
|
])
|
|
]] [result [
|
|
accumlight(light);
|
|
accumalpha(0.0);
|
|
]]])
|
|
|
|
@(if (dlopt "R") [result [
|
|
@(? (dlopt "T") [if(!shouldresolve) break;])
|
|
}
|
|
|
|
@(? (dlopt "T") [if(shouldresolve)]) resolved *= @(divf 1 $msaasamples);
|
|
fragcolor = resolved;
|
|
]])
|
|
}
|
|
] $arg7
|
|
]
|
|
|
|
deferredlightshader = [
|
|
deferredlighttype = (concatword $arg1 $arg2 $arg3)
|
|
shadername = (concatword "deferredlight" $deferredlighttype)
|
|
basevariants = (* (max $arg6 1) 2 (? (dlopt "b") 2 1) (? (dlopt "s") 2 1))
|
|
maxvariants = $basevariants
|
|
if (dlopt "t") [maxvariants = (+ $maxvariants $basevariants 1)]
|
|
if (dlopt "d") [maxvariants = (+ $maxvariants $basevariants 1)]
|
|
deferredlightvariantshader $shadername -1 (concatword $arg1 $arg3) $arg4 $arg5 0 $maxvariants // base shader, no points lights, sunlight
|
|
if (dlopt "t") [
|
|
deferredlightvariantshader $shadername 16 (concatword $arg1 $arg3) $arg4 $arg5 0 $maxvariants // row 16, trasparency, base shader, no points lights, sunlight
|
|
]
|
|
if (dlopt "d") [
|
|
deferredlightvariantshader $shadername 17 (concatword $arg1 $arg3) $arg4 $arg5 0 $maxvariants // row 17, avatar, base shader, no points lights, sunlight
|
|
]
|
|
loop+ i 1 (max $arg6 1) [
|
|
if (dlopt "b") [
|
|
deferredlightvariantshader $shadername 0 (concatword $arg1 $arg3) $arg4 $arg5 $i $maxvariants // row 0, point lights, sunlight
|
|
deferredlightvariantshader $shadername 1 (concatword $arg1 $arg2 $arg3) $arg4 $arg5 $i $maxvariants // row 1, shadowed point lights, sunlight
|
|
]
|
|
deferredlightvariantshader $shadername 2 $arg1 $arg4 $arg5 $i $maxvariants // row 2, point lights
|
|
deferredlightvariantshader $shadername 3 (concatword $arg1 $arg2) $arg4 $arg5 $i $maxvariants // row 3, shadowed point lights
|
|
if (dlopt "s") [
|
|
if (dlopt "b") [
|
|
deferredlightvariantshader $shadername 4 (concatword $arg1 $arg3) $arg4 $arg5 $i $maxvariants // row 4, spot lights, sunlight
|
|
deferredlightvariantshader $shadername 5 (concatword $arg1 $arg2 $arg3) $arg4 $arg5 $i $maxvariants // row 5, shadowed spot lights, sunlight
|
|
]
|
|
deferredlightvariantshader $shadername 6 $arg1 $arg4 $arg5 $i $maxvariants // row 6, spot lights
|
|
deferredlightvariantshader $shadername 7 (concatword $arg1 $arg2) $arg4 $arg5 $i $maxvariants // row 7, shadowed spot lights
|
|
]
|
|
if (dlopt "t") [
|
|
if (dlopt "b") [
|
|
deferredlightvariantshader $shadername 8 (concatword $arg1 $arg3) $arg4 $arg5 $i $maxvariants // row 8, transparent, point lights, sunlight
|
|
deferredlightvariantshader $shadername 9 (concatword $arg1 $arg2 $arg3) $arg4 $arg5 $i $maxvariants // row 9, transparent, shadowed point lights, sunlight
|
|
]
|
|
deferredlightvariantshader $shadername 10 $arg1 $arg4 $arg5 $i $maxvariants // row 10, transparent, point lights
|
|
deferredlightvariantshader $shadername 11 (concatword $arg1 $arg2) $arg4 $arg5 $i $maxvariants // row 11, transparent, shadowed point lights
|
|
if (dlopt "s") [
|
|
if (dlopt "b") [
|
|
deferredlightvariantshader $shadername 12 (concatword $arg1 $arg3) $arg4 $arg5 $i $maxvariants // row 12, transparent, spot lights, sunlight
|
|
deferredlightvariantshader $shadername 13 (concatword $arg1 $arg2 $arg3) $arg4 $arg5 $i $maxvariants // row 13, transparent, shadowed spot lights, sunlight
|
|
]
|
|
deferredlightvariantshader $shadername 14 $arg1 $arg4 $arg5 $i $maxvariants // row 14, transparent, spot lights
|
|
deferredlightvariantshader $shadername 15 (concatword $arg1 $arg2) $arg4 $arg5 $i $maxvariants // row 15, transparent, shadowed spot lights
|
|
]
|
|
]
|
|
if (dlopt "d") [
|
|
if (dlopt "b") [
|
|
deferredlightvariantshader $shadername 24 (concatword $arg1 $arg3) $arg4 $arg5 $i $maxvariants // row 24, avatar, point lights, sunlight
|
|
deferredlightvariantshader $shadername 25 (concatword $arg1 $arg2 $arg3) $arg4 $arg5 $i $maxvariants // row 25, avatar, shadowed point lights, sunlight
|
|
]
|
|
deferredlightvariantshader $shadername 26 $arg1 $arg4 $arg5 $i $maxvariants // row 26, avatar, point lights
|
|
deferredlightvariantshader $shadername 27 (concatword $arg1 $arg2) $arg4 $arg5 $i $maxvariants // row 27, avatar, shadowed point lights
|
|
if (dlopt "s") [
|
|
if (dlopt "b") [
|
|
deferredlightvariantshader $shadername 28 (concatword $arg1 $arg3) $arg4 $arg5 $i $maxvariants // row 28, avatar, spot lights, sunlight
|
|
deferredlightvariantshader $shadername 29 (concatword $arg1 $arg2 $arg3) $arg4 $arg5 $i $maxvariants // row 29, avatar, shadowed spot lights, sunlight
|
|
]
|
|
deferredlightvariantshader $shadername 30 $arg1 $arg4 $arg5 $i $maxvariants // row 30, avatar, spot lights
|
|
deferredlightvariantshader $shadername 31 (concatword $arg1 $arg2) $arg4 $arg5 $i $maxvariants // row 31, avatar, shadowed spot lights
|
|
]
|
|
]
|
|
]
|
|
]
|
|
|