下面列出了法线贴图的着色器代码。然而,由于生成的图像不正确,代码有问题。法线似乎已关闭。其他功能似乎工作正常,所以我认为问题在于着色器。什么想法可能是错的?
顶点着色器
#version 150
in vec3 position;
in vec2 texcoord;
in vec3 normal;
in vec3 tangent;
in vec3 bitangent;
out vec2 Texcoord;
out vec3 VertexPos_World;
out vec3 LightDir_Tan;
uniform vec3 lightPos0_World;
uniform mat4 model;
uniform mat4 view;
uniform mat4 proj;
void main()
{
gl_Position = proj * view * model * vec4(position, 1.0);
Texcoord = texcoord;
VertexPos_World = (model * vec4(position, 1.0)).xyz;
vec3 normal_Cam = (view * model * vec4(normal, 1.0)).xyz;
vec3 tangent_Cam = (view * model * vec4(tangent, 1.0)).xyz;
vec3 bitangent_Cam = (view * model * vec4(bitangent, 1.0)).xyz;
mat3 TBN = transpose(mat3(tangent_Cam, bitangent_Cam, normal_Cam));
vec3 lightDir_Cam = lightPos_Cam - vertexPos_Cam;
LightDir_Tan = TBN * lightDir_Cam;
}
片段着色器
#version 150
in vec2 Texcoord;
in vec3 VertexPos_World;
in vec3 LightDir_Tan;
out vec4 outColor;
uniform vec3 lightPos0_World;
uniform vec3 lightColor0;
uniform float lightPower0;
uniform vec3 ambientColor;
uniform vec3 diffuseColor;
uniform sampler2D tex0;
uniform sampler2D tex0normal;
void main()
{
float lightDistance = length(lightPos0_World - VertexPos_World);
vec3 materialDiffuseColor = texture(tex0, Texcoord).xyz * diffuseColor;
vec3 materialAmbientColor = ambientColor * materialDiffuseColor;
vec3 n = normalize(texture(tex0normal, Texcoord).rgb * 2.0 - 1.0);
vec3 l = normalize(LightDir_Tan);
float diff = clamp(dot(n,l), 0, 1);
outColor.rgb =
materialAmbientColor +
materialDiffuseColor * lightColor0 * lightPower0 * diff / (lightDistance * lightDistance);
}
答案 0 :(得分:3)
这可能不是唯一的问题,但在你的着色器中你有:
vec3 normal_Cam = (view * model * vec4(normal, 1.0)).xyz;
vec3 tangent_Cam = (view * model * vec4(tangent, 1.0)).xyz;
vec3 bitangent_Cam = (view * model * vec4(bitangent, 1.0)).xyz;
这应该是:
vec3 normal_Cam = (view * model * vec4(normal, 0.0)).xyz;
vec3 tangent_Cam = (view * model * vec4(tangent, 0.0)).xyz;
vec3 bitangent_Cam = (view * model * vec4(bitangent, 0.0)).xyz;
使用0.0
代替1.0
,因为它们是方向向量,而不是位置,因此您要忽略矩阵中的翻译。
此外,您应该在应用程序中将这些矩阵相乘并在着色器中使用统一的view_model(否则,您将按顶点而不是每个模型执行此工作)。
答案 1 :(得分:1)
你的法线很可能非常不合适。确保不是提交具有8个顶点的立方体,而是提交每个面具有4个顶点的立方体,以便您可以为每个面发送正确的法线。否则,插值器将简单地使用索引相邻三角形的法线,这就是导致该问题的原因。