在让我的 GLSL 顶点着色器正确显示顶点几天后,我现在开始使用光照!无论如何,我对openGL光照/法线的理解都不是很好,所以请耐心等待。我不确定我需要对我的法线应用哪些翻译才能让它们正确显示。这是设置我的灯的应用程序代码:
final float diffuseIntensity = 0.9f;
final float ambientIntensity = 0.5f;
final float position[] = { 0f, 0f, 25000f, 0f};
gl.glLightfv(GL.GL_LIGHT0, GL.GL_POSITION, position, 0);
final float diffuse[] = { 0, diffuseIntensity, 0, 1f};
gl.glLightfv(GL.GL_LIGHT0, GL.GL_DIFFUSE, diffuse, 0);
final float ambient[] = { ambientIntensity, ambientIntensity, ambientIntensity, 1f};
gl.glLightfv(GL.GL_LIGHT0, GL.GL_AMBIENT, ambient, 0);
到目前为止相当标准的东西。现在由于应用程序的要求,这里是(有点奇怪的)顶点着色器:
void main()
{
// P is the camera matrix, model_X_matrices are the relative translation/rotation etc of the model currently being rendered.
vec4 pos = gl_ProjectionMatrix * P * modelTranslationMatrix * modelRotationMatrix * modelScaleMatrix * gl_Vertex;
gl_Position = pos;
gl_TexCoord[0] = gl_MultiTexCoord0;
gl_FrontColor = gl_Color;
}
我的理解是我需要将其转换gl_Normal
为世界坐标。对于我的着色器,我相信这将是:
vec4 normal = modelTranslationMatrix * modelRotationMatrix * modelScaleMatrix * vec4(gl_Normal);
然后我需要获取灯光的位置(已在世界空间的应用程序代码中声明)。我想我会这样做:
vec3 light_position = gl_LightSource[0].position.xyz;
然后通过求法线与光照位置的点积求出光照的漫反射值。
此外,我认为在片段着色器中,我只需要将颜色乘以这个漫反射值,它就可以工作了。我只是真的不确定如何正确转换法线坐标。我的假设是正确的还是我完全没有把握?
编辑:
在读到法线矩阵 ( gl_NormalMatrix
) 只是矩阵的 3x3 逆gl_ModelView
矩阵后,我猜想在世界空间中计算法线的正确方法是gl_Normal
乘以modelTranslationMatrix * modelRotationMatrix * modelScaleMatrix
? 我还需要将它乘以P
矩阵还是与正常计算无关?