Normal mapping / TBN problems

Started by
5 comments, last by programmer_tom 16 years, 2 months ago
hi all having some issues with my normal mapping. when I change the lighting angle, the normal mapping changes properly, but when i just rotate the object, the normal mapping is incorrect. somehow, the object's transformation matrix isn't being considered properly, so that the mapping stays on the same place on the object as it's rotated ('shadows' should point the same direction, not rotate with the object) here's the hlsl where the problems come from: vertex shader snippet:

float3 vecWorldToLight = normalize ( vecLightWorldPosition - vecWorldPosition );
float3x3 TBNMatrix = float3x3 ( vTangent, vBinormal, vNormal ); 
Out.oVecLight = normalize ( mul ( TBNMatrix, vecWorldToLight ) );
pixel shader snippet:

float3 vecNormalMap = 2.0f * tex2D ( samp1, In.oT1 ).rgb - 1.0f;
float fDiffuse = saturate ( dot ( vecNormalMap, In.oVecLight ) );
any ideas? -programmer_tom
Advertisement

Hi,

It seems that your TBN matrix transforms the light vector from object space to tangent space.

I think that you have forgotten to transform the light vector from world space to object space. So you'll need to transform the light vector by the inverse object/world matrix.

Best regards!
float3 vecNormalMap = 2.0f * tex2D ( samp1, In.oT1 ).rgb - 1.0f;

Isnt this line incorrect? Assuming your normals range from -1 to 1 I think the formula should be (tex2D().rgb + 1) * 0.5

float3 vecNormalMap = 2.0f * tex2D ( samp1, In.oT1 ).rgb - 1.0f;

Isnt this line incorrect? Assuming your normals range from -1 to 1 I think the formula should be (tex2D().rgb + 1) * 0.5

wouldn't that make the range 0.5 to 1?
You have to individually transform your normal, tangent, and binormals by your world matrix and then normalize them to ensure that they rotate along with the object being drawn.
Quote:Original post by schupf
float3 vecNormalMap = 2.0f * tex2D ( samp1, In.oT1 ).rgb - 1.0f;

Isnt this line incorrect? Assuming your normals range from -1 to 1 I think the formula should be (tex2D().rgb + 1) * 0.5


No that looks right. Typically normal maps are stored in 24bpp or 32bpp textures with unsigned 8-bit components. This means that the normals are compressed into the 0 to 1 range on the texture, and once read have to be expanded to the -1 to 1 range.

Quote:
You have to individually transform your normal, tangent, and binormals by your world matrix and then normalize them to ensure that they rotate along with the object being drawn.


weird you should say that...that's the exact solution we came up with...just like transforming the normal in regular shaders. the top of the test cube we're working with doesn't seem to be cooperating though hmmm....

This topic is closed to new replies.

Advertisement