Pulled SSAO out into its own shader to support running at a lower-than-native framebuffer resolution (defaults at half-resolution [SHRenderSSAOResolutionScale=.5] ). This doesn't improve the slow ssao/shadow softening, however, as that bit remains unchanged.
This commit is contained in:
@@ -32,6 +32,7 @@ out vec4 frag_color;
|
||||
|
||||
//class 2 -- shadows and SSAO
|
||||
|
||||
uniform sampler2DRect diffuseRect;
|
||||
uniform sampler2DRect depthMap;
|
||||
uniform sampler2DRect normalMap;
|
||||
uniform sampler2DShadow shadowMap0;
|
||||
@@ -40,16 +41,12 @@ uniform sampler2DShadow shadowMap2;
|
||||
uniform sampler2DShadow shadowMap3;
|
||||
uniform sampler2DShadow shadowMap4;
|
||||
uniform sampler2DShadow shadowMap5;
|
||||
uniform sampler2D noiseMap;
|
||||
//uniform sampler2D noiseMap;
|
||||
|
||||
|
||||
// Inputs
|
||||
uniform mat4 shadow_matrix[6];
|
||||
uniform vec4 shadow_clip;
|
||||
uniform float ssao_radius;
|
||||
uniform float ssao_max_radius;
|
||||
uniform float ssao_factor;
|
||||
uniform float ssao_factor_inv;
|
||||
|
||||
VARYING vec2 vary_fragcoord;
|
||||
|
||||
@@ -66,6 +63,8 @@ uniform float shadow_offset;
|
||||
uniform float spot_shadow_bias;
|
||||
uniform float spot_shadow_offset;
|
||||
|
||||
uniform float downsampled_depth_scale;
|
||||
|
||||
vec2 encode_normal(vec3 n)
|
||||
{
|
||||
float f = sqrt(8 * n.z + 8);
|
||||
@@ -96,61 +95,6 @@ vec4 getPosition(vec2 pos_screen)
|
||||
return pos;
|
||||
}
|
||||
|
||||
vec2 getKern(int i)
|
||||
{
|
||||
vec2 kern[8];
|
||||
// exponentially (^2) distant occlusion samples spread around origin
|
||||
kern[0] = vec2(-1.0, 0.0) * 0.125*0.125;
|
||||
kern[1] = vec2(1.0, 0.0) * 0.250*0.250;
|
||||
kern[2] = vec2(0.0, 1.0) * 0.375*0.375;
|
||||
kern[3] = vec2(0.0, -1.0) * 0.500*0.500;
|
||||
kern[4] = vec2(0.7071, 0.7071) * 0.625*0.625;
|
||||
kern[5] = vec2(-0.7071, -0.7071) * 0.750*0.750;
|
||||
kern[6] = vec2(-0.7071, 0.7071) * 0.875*0.875;
|
||||
kern[7] = vec2(0.7071, -0.7071) * 1.000*1.000;
|
||||
|
||||
return kern[i];
|
||||
}
|
||||
|
||||
//calculate decreases in ambient lighting when crowded out (SSAO)
|
||||
float calcAmbientOcclusion(vec4 pos, vec3 norm)
|
||||
{
|
||||
vec2 pos_screen = vary_fragcoord.xy;
|
||||
vec2 noise_reflect = texture2D(noiseMap, vary_fragcoord.xy/128.0).xy;
|
||||
|
||||
// We treat the first sample as the origin, which definitely doesn't obscure itself thanks to being visible for sampling in the first place.
|
||||
float points = 1.0;
|
||||
float angle_hidden = 0.0;
|
||||
|
||||
// use a kernel scale that diminishes with distance.
|
||||
// a scale of less than 32 is just wasting good samples, though.
|
||||
float scale = max(32.0, min(ssao_radius / -pos.z, ssao_max_radius));
|
||||
|
||||
// it was found that keeping # of samples a constant was the fastest, probably due to compiler optimizations (unrolling?)
|
||||
for (int i = 0; i < 8; i++)
|
||||
{
|
||||
vec2 samppos_screen = pos_screen + scale * reflect(getKern(i), noise_reflect);
|
||||
vec3 samppos_world = getPosition(samppos_screen).xyz;
|
||||
|
||||
vec3 diff = samppos_world - pos.xyz;
|
||||
|
||||
if (diff.z < ssao_factor && diff.z != 0.0)
|
||||
{
|
||||
float dist = length(diff);
|
||||
float angrel = max(0.0, dot(norm.xyz, diff/dist));
|
||||
float distrel = 1.0/(1.0+dist*dist);
|
||||
float samplehidden = min(angrel, distrel);
|
||||
|
||||
angle_hidden += (samplehidden);
|
||||
points += 1.0;
|
||||
}
|
||||
}
|
||||
|
||||
angle_hidden /= points;
|
||||
float rtn = (1.0 - angle_hidden);
|
||||
return (rtn * rtn);
|
||||
}
|
||||
|
||||
float pcfShadow(sampler2DShadow shadowMap, vec4 stc, float scl, vec2 pos_screen)
|
||||
{
|
||||
stc.xyz /= stc.w;
|
||||
@@ -301,7 +245,7 @@ void main()
|
||||
}
|
||||
|
||||
frag_color[0] = shadow;
|
||||
frag_color[1] = calcAmbientOcclusion(pos, norm);
|
||||
frag_color[1] = texture2DRect(diffuseRect,vary_fragcoord*downsampled_depth_scale);
|
||||
|
||||
spos = vec4(shadow_pos+norm*spot_shadow_offset, 1.0);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user