gpt4 book ai didi

c++ - 通过转换矩阵而不是 glTranslate() 在 OpenGL 中移动模型

转载 作者:行者123 更新时间:2023-11-30 04:51:58 24 4
gpt4 key购买 nike

我的目标是通过按下箭头键来移动对象。为此,在回调中,我从某个偏移量创建平移矩阵,并将其乘以世界矩阵。但是它不起作用 - 立方体不会通过按键移动。我还注意到直接使用 glTranslate() 和设置的偏移量效果很好但看起来像拐杖。我的意思是,我应该只使用转换矩阵来进行任何模型转换。我的代码哪里出了问题?如何解决?为什么 glTranslate() 效果很好?最小代码示例:


glm::mat4 mWorldMatrix;
glm::mat4 mViewMatrix;
glm::mat4 mProjMatrix;

void onKeyCallback(GLFWwindow*, int key, int scan, int action, int mods)
{
switch (key)
{
case GLFW_KEY_UP:
{
auto translationMatrix = glm::translate(glm::mat4{}, glm::vec3{ 0, 1, 0 });
mWorldMatrix = mWorldMatrix * translationMatrix;
break;
}
case GLFW_KEY_DOWN:
{
auto translationMatrix = glm::translate(glm::mat4{}, glm::vec3{ 0, -1, 0 });
mWorldMatrix = mWorldMatrix * translationMatrix;
break;
}
case GLFW_KEY_LEFT:
{
auto translationMatrix = glm::translate(glm::mat4{}, glm::vec3{ -1, 0, 0 });
mWorldMatrix = mWorldMatrix * translationMatrix;
break;
}
case GLFW_KEY_RIGHT:
{
auto translationMatrix = glm::translate(glm::mat4{}, glm::vec3{ 1, 0, 0 });
mWorldMatrix = mWorldMatrix * translationMatrix;
break;
}
}
}


int main()
{
glfwInit();

const int weight = 640;
const int height = 480;
auto mWindow = glfwCreateWindow(weight, height, "TesT", nullptr, nullptr);
glfwMakeContextCurrent(mWindow);

glShadeModel(GL_SMOOTH);
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL);

mWorldMatrix = glm::mat4{ 1.0f };
mViewMatrix = glm::lookAt(glm::vec3{ 0, 0, -1 },
glm::vec3{ 0, 0, 0 },
glm::vec3{ 0, 1, 0 });
mProjMatrix = glm::perspective(glm::radians(45.0f),
static_cast<float>(weight) / height,
0.1f,
100.0f);

glfwSetKeyCallback(mWindow, onKeyCallback);

while (!glfwWindowShouldClose(mWindow)) {
glClearColor(0.5, 0.5, 0.5, 0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glViewport(0,0, weight, height);

auto modelViewMatrix = mViewMatrix * mWorldMatrix;
glMatrixMode(GL_MODELVIEW);
glLoadMatrixf(static_cast<const float*>(glm::value_ptr(modelViewMatrix)));

glMatrixMode(GL_PROJECTION_MATRIX);
glLoadMatrixf(static_cast<const float*>(glm::value_ptr(mProjMatrix)));

Cube cube{ glm::vec3{0.5, 0.5, 0.5}, 1 }; //cube with center in {0.5} and side length 1
auto vertices = cube.soup(); //vector of vertex

glTranslatef(0 /* + offset.x*/, 0/* + offset.y*/, -5); //Setting offset here is work good
glBegin(GL_TRIANGLES);
for (const auto& vertex : vertices)
{
glColor3f(vertex.position.x, vertex.position.y, vertex.position.z);
glVertex3f(vertex.position.x, vertex.position.y, vertex.position.z);
}
glEnd();

glfwSwapBuffers(mWindow);
glfwWaitEvents();
}

glfwTerminate();
return 0;
}

最佳答案

请注意,glBegin/glEnd 绘制的那幅画序列和固定函数矩阵堆栈和固定函数。参见 Fixed Function PipelineLegacy OpenGL .了解 Vertex SpecificationShader最先进的渲染方式。


投影矩阵应应用于投影矩阵堆栈,模型 View 矩阵应应用于模型 View 矩阵堆栈。

有两个问题。

  1. GL_PROJECTION_MATRIX 不是 glMatrixMode 的有效枚举常量并将导致 GL_INVALID_ENUM 错误。投影矩阵模式的有效枚举常量是 GL_PROJECTIONGL_PROJECTION_MATRIX 将用于通过 glGetFloatv 读取当前投影矩阵。 .

  2. 如果您想对模型应用额外的转换,那么您必须先选择GL_MODELVIEW 矩阵。如果 GL_PROJECTION 矩阵被“选中”,则此状态会一直保持到再次明确更改为止。

glMatrixMode(GL_MODELVIEW);
glLoadMatrixf(static_cast<const float*>(glm::value_ptr(modelViewMatrix)));

glMatrixMode(GL_PROJECTION); // <----- `GL_PROJECTION` instead of `GL_PROJECTION_MATRIX`
glLoadMatrixf(static_cast<const float*>(glm::value_ptr(mProjMatrix)));

// [...]

glMatrixMode(GL_MODELVIEW); // <-------- specify `GL_MODELVIEW`
glTranslatef(0 /* + offset.x*/, 0/* + offset.y*/, -5); //Setting offset here is work good

关于c++ - 通过转换矩阵而不是 glTranslate() 在 OpenGL 中移动模型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54669584/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com