模型矩阵畸形结果的 Opengl 翻译
Opengl Translation on Model Matrix malforms result
我正在尝试构建一个模型矩阵,我在其中应用了一些常见的变换,例如缩放、旋转和平移。我在这里学习教程:https://solarianprogrammer.com/2013/05/22/opengl-101-matrices-projection-view-model/。我知道矩阵不可交换,所以我想我注意获得正确的转换顺序。
但是当我尝试平移我的模型时,它被拉伸到相应的轴而不是平移。
外观如下:
如有任何帮助,我将不胜感激。 :)
顶点着色器
# version 330
in vec3 in_pos;
in vec3 in_col;
in vec3 in_norm;
// uniform wie eine konstante, kann einmal per frame geaender werden und gillt fuer alle vertices
uniform mat4 mvp; // mat4 = 4x4 Matrix
// out stream to fragment shader
out vec4 frag_pos;
out vec4 frag_col;
out vec4 frag_norm;
// column major
void main() {
gl_Position = mvp * vec4(in_pos, 1.0);
frag_pos = vec4(in_pos,1.0);
// transparent frag_col = vec4(in_col,0.5);
frag_col = vec4(in_col,1);
frag_norm = vec4(in_norm,1.0);
}
Java 转换
float aspectRatio = (float) HEIGHT /(float)WIDTH;
float[][] rotX = new float[][] {
{1.0f,0.0f,0.0f,0.0f},
{0.0f,(float)Math.cos(thetaX),(float)-Math.sin(thetaX),0.0f},
{0.0f,(float)Math.sin(thetaX),(float)Math.cos(thetaX),0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] rotY = new float[][] {
{(float)Math.cos(thetaY),0.0f,(float)Math.sin(thetaY),0.0f},
{0.0f,1.0f,0.0f,0.0f},
{(float)-Math.sin(thetaY),0.0f,(float)Math.cos(thetaY),0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] rotZ = new float[][] {
{(float)Math.cos(thetaZ),(float)-Math.sin(thetaZ),0.0f,0.0f},
{(float)Math.sin(thetaZ),(float)Math.cos(thetaZ),0.0f,0.0f},
{0.0f,0.0f,1.0f,0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] translation = new float[][] {
{1.0f,0.0f,0.0f,transX},
{0.0f,1.0f,0.0f,transY},
{0.0f,0.0f,1.0f,transZ},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] scaleMatrix = new float[][] {
{scale,0.0f,0.0f,0.0f},
{0.0f,scale,0.0f,0.0f},
{0.0f,0.0f,scale,0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] aspect = new float[][] {
{aspectRatio,0.0f,0.0f,0.0f},
{0.0f,1.0f,0.0f,0.0f},
{0.0f,0.0f,1.0f,0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] rotationMatrix = Matrix.matMult(rotZ,Matrix.matMult(rotY,rotX));
float[][] matrix = Matrix.matMult(translation,Matrix.matMult(rotationMatrix,scaleMatrix));
float[] model = Matrix.matrixToFloatVector(Matrix.matMult(matrix,aspect));
FloatBuffer fb = BufferUtils.createFloatBuffer(16);
fb.put(model);
fb.flip(); // Reset pointer
// "upload" to graphics card
glUniformMatrix4fv(uLocMVP, false, fb);
参见 The OpenGL Shading Language 4.6, 5.4.2 Vector and Matrix Constructors,第 110 页:
To initialize a matrix by specifying vectors or scalars, the components are assigned to the matrix elements in column-major order.
mat4(float, float, float, float, // first column
float, float, float, float, // second column
float, float, float, float, // third column
float, float, float, float); // fourth column
这意味着在设置 mat4
类型的统一变量之前必须转置矩阵。
这可以通过设置glUniformMatrix4fv
的第3个参数自动完成 true
:
glUniformMatrix4fv(uLocMVP, true, fb)
相反,您也可以转置初始化并交换矩阵乘法 (Matrix.matMult
)。
我正在尝试构建一个模型矩阵,我在其中应用了一些常见的变换,例如缩放、旋转和平移。我在这里学习教程:https://solarianprogrammer.com/2013/05/22/opengl-101-matrices-projection-view-model/。我知道矩阵不可交换,所以我想我注意获得正确的转换顺序。
但是当我尝试平移我的模型时,它被拉伸到相应的轴而不是平移。 外观如下:
如有任何帮助,我将不胜感激。 :)
顶点着色器
# version 330
in vec3 in_pos;
in vec3 in_col;
in vec3 in_norm;
// uniform wie eine konstante, kann einmal per frame geaender werden und gillt fuer alle vertices
uniform mat4 mvp; // mat4 = 4x4 Matrix
// out stream to fragment shader
out vec4 frag_pos;
out vec4 frag_col;
out vec4 frag_norm;
// column major
void main() {
gl_Position = mvp * vec4(in_pos, 1.0);
frag_pos = vec4(in_pos,1.0);
// transparent frag_col = vec4(in_col,0.5);
frag_col = vec4(in_col,1);
frag_norm = vec4(in_norm,1.0);
}
Java 转换
float aspectRatio = (float) HEIGHT /(float)WIDTH;
float[][] rotX = new float[][] {
{1.0f,0.0f,0.0f,0.0f},
{0.0f,(float)Math.cos(thetaX),(float)-Math.sin(thetaX),0.0f},
{0.0f,(float)Math.sin(thetaX),(float)Math.cos(thetaX),0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] rotY = new float[][] {
{(float)Math.cos(thetaY),0.0f,(float)Math.sin(thetaY),0.0f},
{0.0f,1.0f,0.0f,0.0f},
{(float)-Math.sin(thetaY),0.0f,(float)Math.cos(thetaY),0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] rotZ = new float[][] {
{(float)Math.cos(thetaZ),(float)-Math.sin(thetaZ),0.0f,0.0f},
{(float)Math.sin(thetaZ),(float)Math.cos(thetaZ),0.0f,0.0f},
{0.0f,0.0f,1.0f,0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] translation = new float[][] {
{1.0f,0.0f,0.0f,transX},
{0.0f,1.0f,0.0f,transY},
{0.0f,0.0f,1.0f,transZ},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] scaleMatrix = new float[][] {
{scale,0.0f,0.0f,0.0f},
{0.0f,scale,0.0f,0.0f},
{0.0f,0.0f,scale,0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] aspect = new float[][] {
{aspectRatio,0.0f,0.0f,0.0f},
{0.0f,1.0f,0.0f,0.0f},
{0.0f,0.0f,1.0f,0.0f},
{0.0f,0.0f,0.0f,1.0f}
};
float[][] rotationMatrix = Matrix.matMult(rotZ,Matrix.matMult(rotY,rotX));
float[][] matrix = Matrix.matMult(translation,Matrix.matMult(rotationMatrix,scaleMatrix));
float[] model = Matrix.matrixToFloatVector(Matrix.matMult(matrix,aspect));
FloatBuffer fb = BufferUtils.createFloatBuffer(16);
fb.put(model);
fb.flip(); // Reset pointer
// "upload" to graphics card
glUniformMatrix4fv(uLocMVP, false, fb);
参见 The OpenGL Shading Language 4.6, 5.4.2 Vector and Matrix Constructors,第 110 页:
To initialize a matrix by specifying vectors or scalars, the components are assigned to the matrix elements in column-major order.
mat4(float, float, float, float, // first column float, float, float, float, // second column float, float, float, float, // third column float, float, float, float); // fourth column
这意味着在设置 mat4
类型的统一变量之前必须转置矩阵。
这可以通过设置glUniformMatrix4fv
的第3个参数自动完成 true
:
glUniformMatrix4fv(uLocMVP, true, fb)
相反,您也可以转置初始化并交换矩阵乘法 (Matrix.matMult
)。