模型视图投影 - 如何在世界中移动对象
Posted
技术标签:
【中文标题】模型视图投影 - 如何在世界中移动对象【英文标题】:Model View Projection - How to move objects in a world 【发布时间】:2018-03-19 23:32:03 【问题描述】:我有一个 3D 世界,里面有一个立方体。我知道立方体的顶点被定义为立方体“质心”的坐标。
我想将立方体放置在远离我的位置,向右上方,所以我想将立方体放置在 (1,1,1)。我目前没有任何“相机”代码,所以假设我的观看位置是 (0,0,0)。
我需要翻译什么才能将立方体移动到新位置?
我对 View 和 Model 矩阵感到困惑。我认为 View 是相机视图/位置,而 Model 是 3D 世界中顶点的位置。
我下面的代码对 x 和 y 位置的工作方式与我预期的一样,但 z 进入屏幕(更远)是负数,正向/移出屏幕。我希望 z 是正的,对象离视点越远。
我做错了什么?
glm::mat4 Projection = glm::perspective( 45.0f, g_AspectRatio, 0.1f, 100.0f );
glm::mat4 View = glm::mat4(1.0);
glm::mat4 Model = glm::mat4(1.0);
// Move the object within the 3D space
Model = glm::translate( Model, glm::vec3( m_X, m_Y, m_Z ) );
glm::mat4 MVP;
MVP = Projection * View * Model;
MVP
被传递到 transform
制服中。
我的着色器:
char *vs3DShader =
"#version 140\n"
"#extension GL_ARB_explicit_attrib_location : enable\n"
"layout (location = 0) in vec3 Position;"
"layout (location = 1) in vec4 color;"
"layout (location = 2) in vec3 normal;"
"out vec4 frag_color;"
"uniform mat4 transform;"
"void main()"
""
" gl_Position = transform * vec4( Position.x, Position.y, Position.z, 1.0 );"
" // Pass vertex color to fragment shader.. \n"
" frag_color = color;"
""
;
【问题讨论】:
【参考方案1】:我下面的代码对 x 和 y 位置的工作方式与我预期的一样,但 z 进入屏幕(更远)是负数,正向/移出屏幕。我希望 z 为正值,对象离视点越远。
您可以通过设置一个镜像 Z 轴的视图矩阵来实现这一点:
glm::mat4 View = glm::scale(glm::mat4(1.0), glm::vec3(1.0f, 1.0f, -1.0f));
视图矩阵从世界空间转换到视图空间。您的视图矩阵是单位矩阵:
glm::mat4 View = glm::mat4(1.0);
这意味着世界空间等于视图空间。请注意,通常一个视图矩阵由glm::lookAt
设置。
Z 轴是 X 轴和 Y 轴的叉积。这意味着,如果在right handed system 中 X 轴指向左侧,Y 轴指向上方,则 Z 轴指向视口之外。 见Understanding OpenGL’s Matrices
我上面描述的坐标通常是right handed system 中的视图坐标,因为glm::glm::perspective
设置了一个右手投影矩阵,它将这个坐标转换为剪辑空间,这样 z 轴被反转并变成深度。
【讨论】:
非常感谢。 Z=-1 的比例让一切变得不同。我不确定为什么首选右手系统 - 这对我来说感觉违反直觉,但很高兴知道这一点。很好的答案。 也许Is OpenGL coordinate system left-handed or right-handed?可以带来进一步的澄清以上是关于模型视图投影 - 如何在世界中移动对象的主要内容,如果未能解决你的问题,请参考以下文章
AR 对象不应随 AR 相机 Vuforia Unity3d 移动