From d9d6255107b40290ca5a2695dc417bdd1fca2d7a Mon Sep 17 00:00:00 2001 From: Frederic Bouvier Date: Sun, 22 Jul 2012 19:53:27 +0200 Subject: [PATCH 1/2] Fix 'Phong distortion' artifact on specular lighting and disappearing emission (due to undefined pow(0,0) called) in Rembrandt - forgotten shaders --- Shaders/sunlight-nofiltering.frag | 15 +++++++-------- Shaders/sunlight-noshadow.frag | 15 +++++++-------- 2 files changed, 14 insertions(+), 16 deletions(-) diff --git a/Shaders/sunlight-nofiltering.frag b/Shaders/sunlight-nofiltering.frag index af9d0699e..4a6c2e3a0 100644 --- a/Shaders/sunlight-nofiltering.frag +++ b/Shaders/sunlight-nofiltering.frag @@ -61,8 +61,6 @@ void main() { if ( spec_emis.a < 0.1 ) discard; vec3 normal = normal_decode(texture2D( normal_tex, coords ).rg); - float len = length(normal); - normal /= len; vec3 viewDir = normalize(ray); vec3 pos = position( viewDir, coords, depth_tex ); @@ -72,14 +70,15 @@ void main() { lightDir = normalize( lightDir ); vec3 color = texture2D( color_tex, coords ).rgb; vec3 Idiff = clamp( dot( lightDir, normal ), 0.0, 1.0 ) * color * fg_SunDiffuseColor.rgb; - vec3 halfDir = lightDir - viewDir; - len = length( halfDir ); + vec3 halfDir = normalize( lightDir - viewDir ); vec3 Ispec = vec3(0.0); vec3 Iemis = spec_emis.z * color; - if (len > 0.0001) { - halfDir /= len; - Ispec = pow( clamp( dot( halfDir, normal ), 0.0, 1.0 ), spec_emis.y * 128.0 ) * spec_emis.x * fg_SunSpecularColor.rgb; - } + + float cosAngIncidence = clamp(dot(normal, lightDir), 0.0, 1.0); + float blinnTerm = clamp( dot( halfDir, normal ), 0.0, 1.0 ); + + if (cosAngIncidence > 0.0) + Ispec = pow( blinnTerm, spec_emis.y * 128.0 ) * spec_emis.x * fg_SunSpecularColor.rgb; float matID = texture2D( color_tex, coords ).a * 255.0; if (matID >= 254.0) diff --git a/Shaders/sunlight-noshadow.frag b/Shaders/sunlight-noshadow.frag index 2045b0f1c..23ad141d0 100644 --- a/Shaders/sunlight-noshadow.frag +++ b/Shaders/sunlight-noshadow.frag @@ -17,22 +17,21 @@ void main() { if ( spec_emis.a < 0.1 ) discard; vec3 normal = normal_decode(texture2D( normal_tex, coords ).rg); - float len = length(normal); - normal /= len; vec3 viewDir = normalize(ray); vec3 lightDir = (fg_ViewMatrix * vec4( fg_SunDirection, 0.0 )).xyz; lightDir = normalize( lightDir ); vec3 color = texture2D( color_tex, coords ).rgb; vec3 Idiff = clamp( dot( lightDir, normal ), 0.0, 1.0 ) * color * fg_SunDiffuseColor.rgb; - vec3 halfDir = lightDir - viewDir; - len = length( halfDir ); + vec3 halfDir = normalize( lightDir - viewDir ); vec3 Ispec = vec3(0.0); vec3 Iemis = spec_emis.z * color; - if (len > 0.0001) { - halfDir /= len; - Ispec = pow( clamp( dot( halfDir, normal ), 0.0, 1.0 ), spec_emis.y * 255.0 ) * spec_emis.x * fg_SunSpecularColor.rgb; - } + + float cosAngIncidence = clamp(dot(normal, lightDir), 0.0, 1.0); + float blinnTerm = clamp( dot( halfDir, normal ), 0.0, 1.0 ); + + if (cosAngIncidence > 0.0) + Ispec = pow( blinnTerm, spec_emis.y * 128.0 ) * spec_emis.x * fg_SunSpecularColor.rgb; float matID = texture2D( color_tex, coords ).a * 255.0; if (matID >= 254.0) From 0604e3975bb725132cd5f2e946fc2f221f29e6bb Mon Sep 17 00:00:00 2001 From: Stuart Buchanan Date: Tue, 24 Jul 2012 22:12:11 +0100 Subject: [PATCH 2/2] Add an additional random rotation to trees so the quads are not all oriented N/S and E/W, helping to disguise the limited set of textures used. --- Shaders/tree.vert | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/Shaders/tree.vert b/Shaders/tree.vert index cdaa0ce09..65b3d2d7e 100644 --- a/Shaders/tree.vert +++ b/Shaders/tree.vert @@ -18,8 +18,12 @@ void main(void) float numVarieties = gl_Normal.z; float texFract = floor(fract(gl_MultiTexCoord0.x) * numVarieties) / numVarieties; texFract += floor(gl_MultiTexCoord0.x) / numVarieties; - float sr = sin(gl_FogCoord); - float cr = cos(gl_FogCoord); + + // Determine the rotation for the tree. The Fog Coordinate provides rotation information + // to rotate one of the quands by 90 degrees. We then apply an additional position seed + // so that trees aren't all oriented N/S + float sr = sin(gl_FogCoord + gl_Color.x); + float cr = cos(gl_FogCoord + gl_Color.x); gl_TexCoord[0] = vec4(texFract, gl_MultiTexCoord0.y, 0.0, 0.0); // scaling