From 3e440fd88d58bd91f50e1a6e9e3cb3c991a0e7c8 Mon Sep 17 00:00:00 2001 From: auria Date: Sat, 3 Dec 2011 20:09:08 +0000 Subject: [PATCH] Improve how normal maps work on movimng objects git-svn-id: svn+ssh://svn.code.sf.net/p/supertuxkart/code/main/trunk@10312 178a84e3-b1eb-0310-8ba1-8eac791a3b58 --- data/shaders/normalmap.frag | 5 ++++- data/shaders/splatting.frag | 6 +++++- src/graphics/material.cpp | 7 ++++++- 3 files changed, 15 insertions(+), 3 deletions(-) diff --git a/data/shaders/normalmap.frag b/data/shaders/normalmap.frag index 6628f77f3..87881d505 100644 --- a/data/shaders/normalmap.frag +++ b/data/shaders/normalmap.frag @@ -8,6 +8,9 @@ uniform sampler2D BumpTex; //The bump-map varying vec3 LightDir; //Receiving the transformed light direction void main() { + vec4 LightDirTransformed4 = gl_ProjectionMatrix * gl_ModelViewMatrix * vec4(LightDir[0], LightDir[1], LightDir[2], 0); + vec3 LightDirTransformed = vec3(LightDirTransformed4[0], LightDirTransformed4[1], LightDirTransformed4[2]); + //Get the color of the bump-map vec3 BumpNorm = vec3(texture2D(BumpTex, gl_TexCoord[0].xy)); //Get the color of the texture @@ -15,7 +18,7 @@ uniform sampler2D BumpTex; //The bump-map //Expand the bump-map into a normalized signed vector BumpNorm = (BumpNorm -0.5) * 2.0; //Find the dot product between the light direction and the normal - float NdotL = max(dot(BumpNorm, LightDir), 0.0) / 3.0 * 2.1 + 0.5; + float NdotL = max(dot(BumpNorm, LightDirTransformed), 0.0) / 3.0 * 2.1 + 0.5; //Calculate the final color gl_FragColor vec3 diffuse = NdotL * passcolor.xyz * DecalCol; //Set the color of the fragment... If you want specular lighting or other types add it here diff --git a/data/shaders/splatting.frag b/data/shaders/splatting.frag index a080313b2..fcc5e6ce1 100644 --- a/data/shaders/splatting.frag +++ b/data/shaders/splatting.frag @@ -5,6 +5,7 @@ uniform sampler2D tex_detail0; uniform sampler2D tex_detail1; uniform sampler2D tex_detail2; uniform sampler2D tex_detail3; +uniform sampler2D tex_detail4; void main() { @@ -13,8 +14,11 @@ void main() vec4 detail1 = texture2D(tex_detail1, gl_TexCoord[1].st); vec4 detail2 = texture2D(tex_detail2, gl_TexCoord[1].st); vec4 detail3 = texture2D(tex_detail3, gl_TexCoord[1].st); + vec4 detail4 = texture2D(tex_detail4, gl_TexCoord[1].st); + gl_FragColor = layout.r * detail0 + layout.g * detail1 + layout.b * detail2 + - (1.0 - layout.r - layout.g - layout.b) * detail3; + (1.0 - layout.r - layout.g - layout.b) * detail3 + + (1.0 - layout.a) * detail4; } diff --git a/src/graphics/material.cpp b/src/graphics/material.cpp index 14f93f5df..98a1f8b7c 100644 --- a/src/graphics/material.cpp +++ b/src/graphics/material.cpp @@ -60,7 +60,12 @@ public: services->setPixelShaderConstant("BumpTex", (float*)&bumptex, 1); // TODO: check the position of the sun - const float lightdir[] = {0.5f, 0.5f, 1.0f}; + /* + You have to calculate the light position in (model)view Space. It can be done, by transforming the light positions and rotations + with the modelviewmatrix, after the camera is set. You should do this calculations before the shader runs, but it is also possible + to pass the camera matrix (calculation in modelviewspace) or ModelMatrix (calculation in WorldSpace) to a shader. + */ + const float lightdir[] = {-0.5f, -0.5f, -1.0f}; services->setVertexShaderConstant("lightdir", lightdir, 3); } };