• Advertisement
Sign in to follow this  

Normal mapping w/ texture mirroring

This topic is 4674 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I'm trying to implement normal mapping with meshes that utilize texture mirroring. I've calculated the tangent space basis vectors using this method: http://www.terathon.com/code/tangent.html But I can't get the mirrored portions of the meshes to appear correctly. I've tried negating some axis depending on the handedness. Using a pure white texture as the bump map, I result in the mirrored and unmirrored portions as black and white. Can I even do normal mapping that consists of texture mirroring? Or do I need to duplicate vertices that are on the seams?

Share this post


Link to post
Share on other sites
Advertisement
What's the purpose of mirroring normal texture and then negating X/Y components based on whether its mirrored or not fragment?

Just like your regular diffuse texture will be mirrored (supposedly), your normal map should be mirrored too and no negating is required here. It should work.

Negating coordinates in normal map would only make it inconsistent with diffuse texture map.

[Edit: typo]

[Edited by - MickeyMouse on April 27, 2005 5:24:20 AM]

Share this post


Link to post
Share on other sites
What you say by "mirror" is for example a car with only the left half textured, and the second one use the texture ?

Then if you computed your normal map in tangent space, there shouldn't be any diffrence between mirrored and unmirrored part, that's quite odd.

Can you post your shader ?

.:: Paic Citron ::.

Share this post


Link to post
Share on other sites
Yes, my real normal map texture will be the same mirroring as the diffuse texture.

By mirroring I mean, the model is unwrapped and any meshes that are symmetrical are textured half, where having the two halves of the mesh point to the same space in the texture. ie A human head can be textured with symmetry.

ie If I have 4 vertices, v1, v2, v3, v4: v1-v2-v3, v2-v3-v4 are triangles, with v2-v3 the common edge


v2(1,0)
v1(0,0) | v4(0,0)
v3(1,1)


ie texture mirroring to make effecient use of texture space
However, some meshes aren't mirrored all along one axis, though. Perhaps they are rotated to fit into the texture, I'm not sure.

But all I'm doing is that I'm taking the basis tangents and transforming the light vector into tangent space in my vertex shader. My tangents should be correct? Or do I need to take into account "mirrored UVs"?

There shouldn't be anything more I need to do, like negate the binormal (bitangent) axis?


My vertex shader:

mul BONEINDICES, VERTEX_BONES, c[CONST256].yyyy ; re-expand indices from 0.0-1.0 to 0-255

LOADBONEINDEX(BONEINDICES.z) ; bone 1
SKIN_VERT(TEMP0, VERTEX_POS)
mov TEMP0.w, c[CONST0123].y
mul POSACCUM, TEMP0, VERTEX_WEIGHTS.x

SKIN_NORMAL(TEMP0, VERTEX_NORMAL)
mul NORMACCUM, TEMP0, VERTEX_WEIGHTS.x

SKIN_NORMAL(TEMP0, VERTEX_S); ; texture basis
mul S_WORLD, TEMP0, VERTEX_WEIGHTS.x
SKIN_NORMAL(TEMP0, VERTEX_T);
mul T_WORLD, TEMP0, VERTEX_WEIGHTS.x
SKIN_NORMAL(TEMP0, VERTEX_SxT);
mul SxT_WORLD, TEMP0, VERTEX_WEIGHTS.x


LOADBONEINDEX(BONEINDICES.y) ; bone 2
SKIN_VERT(TEMP0, VERTEX_POS)
mad POSACCUM, TEMP0, VERTEX_WEIGHTS.y, POSACCUM

SKIN_NORMAL(TEMP0, VERTEX_NORMAL)
mad NORMACCUM, TEMP0, VERTEX_WEIGHTS.y, NORMACCUM

SKIN_NORMAL(TEMP0, VERTEX_S); ; texture basis
mad S_WORLD, TEMP0, VERTEX_WEIGHTS.y, S_WORLD
SKIN_NORMAL(TEMP0, VERTEX_T);
mad T_WORLD, TEMP0, VERTEX_WEIGHTS.y, T_WORLD
SKIN_NORMAL(TEMP0, VERTEX_SxT);
mad SxT_WORLD, TEMP0, VERTEX_WEIGHTS.y, SxT_WORLD


LOADBONEINDEX(BONEINDICES.x) ; bone 3
SKIN_VERT(TEMP0, VERTEX_POS)
mad POSACCUM, TEMP0, VERTEX_WEIGHTS.z, POSACCUM

SKIN_NORMAL(TEMP0, VERTEX_NORMAL)
mad NORMACCUM, TEMP0, VERTEX_WEIGHTS.z, NORMACCUM

SKIN_NORMAL(TEMP0, VERTEX_S); ; texture basis
mad S_WORLD, TEMP0, VERTEX_WEIGHTS.z, S_WORLD
SKIN_NORMAL(TEMP0, VERTEX_T);
mad T_WORLD, TEMP0, VERTEX_WEIGHTS.z, T_WORLD
SKIN_NORMAL(TEMP0, VERTEX_SxT);
mad SxT_WORLD, TEMP0, VERTEX_WEIGHTS.z, SxT_WORLD

; transform light direction to texture space
dp3 TEMP1.x, S_WORLD.xyz, c[DIRLIGHTDIR1]
dp3 TEMP1.y, T_WORLD.xyz, c[DIRLIGHTDIR1]
dp3 TEMP1.z, SxT_WORLD.xyz, c[DIRLIGHTDIR1]

; Normalize the light vector and store it in oD0
dp3 TEMP1.w, TEMP1, TEMP1
rsq TEMP1.w, TEMP1.w
mul TEMP1, TEMP1, TEMP1.w
mov oD1.xyz, TEMP1

NORMALIZE3(NORMACCUM)

dp4 oPos.x, POSACCUM, c[WORLDTOCLIP0] ; position to clip transform
dp4 oPos.y, POSACCUM, c[WORLDTOCLIP1]
dp4 oPos.z, POSACCUM, c[WORLDTOCLIP2]
dp4 oPos.w, POSACCUM, c[WORLDTOCLIP3]

dp4 oFog.x, POSACCUM, c[FOGTRANSFORM]

mov oT0, VERTEX_UV0 ; bump tex coords
mov oT1, VERTEX_UV0 ; base tex coords

; calc charlight UVs
dp3 oT2.xy, NORMACCUM, -c[DIRLIGHTDIR0]

; Lighting (skip DIRLIGHT0 -- charlight, and DIRLIGHT1 -- bumpLight)
LIGHT_BEGIN
PARALLEL_LIGHT(DIRLIGHTDIR2, DIRLIGHTCOLOR2, NORMACCUM)
LIGHT_END


Share this post


Link to post
Share on other sites
The problem is that you have to split the vertex at the mirrored point because tangent space is different on each side. Looking at it in 1D lets say you have the coordinates 1 -- 0 -- 1, you would split it like this 1 -- 0/0 -- 1, then calculate the correct tangent space vectors for the 4 vertices. Let me know if I'm being unclear.

Share this post


Link to post
Share on other sites
Quote:
Original post by blue_knight
The problem is that you have to split the vertex at the mirrored point because tangent space is different on each side. Looking at it in 1D lets say you have the coordinates 1 -- 0 -- 1, you would split it like this 1 -- 0/0 -- 1, then calculate the correct tangent space vectors for the 4 vertices. Let me know if I'm being unclear.


But won't that only solve creases on hard edge vertices?

I don't see how that would affect it if I have a mesh that has many, many more vertices?

v5 v2(1,0) v7
v1(0,0) | v4(0,0)
v6 v3(1,1) v8



And would I need to do anything special with the different tangent spaces? Or do I calculate it differently due to the reverse order of the UVs?


[Edited by - XBoy on April 28, 2005 12:13:25 PM]

Share this post


Link to post
Share on other sites
My suggestion (which you may not like) stop using mirrored textures. 3d tools have problems creating normal maps with mirrored textures, it takes extra effort to deal with the calculation of the tangent space (since the mirrored uvs cause the tangent and bitangent to vary quite a bit compared to non mirrored uvs), and you need to figure out (based on the "normal" of the texture face) which faces are based on mirrored coordinates.

If you really wanted to deal with it, I've pretty much laid out how to figure out when you need to change your tangent space basis calculation, and it's a pretty small change to calculate the tangent space for these faces (some negations).

Share this post


Link to post
Share on other sites
Turns out the problem was with the normal mapping vertex and pixel shaders, which wasn't written by me. I've corrected them and everything looks great. :)


I did everything right, in fact texture mirroring works wonderfully. There's no reason to avoid it; you just need to calculate the correct basis vectors.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement