5-4法线贴图

102 阅读1分钟

使用法线贴图来对所有fragement设置法线,决定物体的形状

使用一个2D纹理来储存法线向量,将xzy向量储存在rgb中,并将其映射在[0,1]范围内,并在像素着色器中使用

使用切线空间,使所有光照向量都和z进行变换,法线贴图向量只想正z方向

计算TBN矩阵构建空间 [TxBxTyByTzBz]=1ΔU1ΔV2−ΔU2ΔV1[ΔV2−ΔU2−ΔV1ΔU1][E1xE2xE1yE2yE1zE2z]

手工计算切线和副切线,首先计算三角形的边和deltaUV坐标

tangent1.x = f * (deltaUV2.y * edge1.x - deltaUV1.y * edge2.x); 
tangent1.y = f * (deltaUV2.y * edge1.y - deltaUV1.y * edge2.y);
tangent1.z = f * (deltaUV2.y * edge1.z - deltaUV1.y * edge2.z); 
tangent1 = glm::normalize(tangent1); 
bitangent1.x = f * (-deltaUV2.x * edge1.x + deltaUV1.x * edge2.x); 
bitangent1.y = f * (-deltaUV2.x * edge1.y + deltaUV1.x * edge2.y);
bitangent1.z = f * (-deltaUV2.x * edge1.z + deltaUV1.x * edge2.z);
bitangent1 = glm::normalize(bitangent1);

直接使用TBN矩阵将切线空间的向量转到世界坐标空间,直接传给像素着色器使用

或者使用TBN矩阵的逆矩阵,将世界坐标空间转到切线空间

然而计算切线向量时有共享顶点,对TBN向量进行重正交化

vec3 T = normalize(vec3(model * vec4(tangent, 0.0)));
vec3 N = normalize(vec3(model * vec4(normal, 0.0))); 
T = normalize(T - dot(T, N) * N); 
vec3 B = cross(T, N); 
mat3 TBN = mat3(T, B, N)