如何将局部物体坐标转换为世界坐标?
我需要一种简单的方法将对象坐标转换为世界坐标,以便可以在该坐标系中定位它们并进行碰撞检测?
I need a simple way to convert my objects coordinate into world coordinates, so that a can locate them in that coordinate system and do collision detection?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
首先,一些背景知识。在 3D 图形中,您需要担心几个向量空间:
[-1, +1]
。坐标是均匀指定的,因此每个向量都有分量
(x, y, z, w)
,其中w
是缩放因子。您可以获得 3 空间中的坐标(x/w, y/w, z/w)
。某些变换(例如透视投影)需要缩放因子,而这对于非齐次坐标是不可能的。需要 4x4 矩阵将坐标从一个向量空间转换到另一向量空间。您可以拥有三个不同的矩阵:
您可以使用以下公式将坐标
C
投影到屏幕上:OpenGL内部维护两个矩阵:模型视图(模型和视图相乘)和投影。还有一个我们不用担心的纹理矩阵。当您调用
glMatrixMode
时,您正在这些矩阵之间进行切换。您可以使用glLoadIdentity 将当前矩阵替换为单位矩阵。您可以使用glTranslatef
、glRotatef
或gluProjection
等函数将转换应用于当前矩阵。这些函数中的每一个都只是创建一个 4x4 矩阵来实现特定的变换,然后将当前矩阵乘以它。您可以在OpenGL 2.1 参考页中查看变换矩阵的内容。现在给出实际的答案。您需要为场景中的每个对象维护一个 4x4 模型矩阵。模型矩阵将包含将模型坐标更改为世界坐标所需的所有转换。例如,每次调用
glTranslate
时,您都会更新模型矩阵:然后您可以使用模型矩阵将坐标获取到世界空间中(首先确保它们是同质坐标;只需设置
w = 1,如果不是):
由于您并行维护这些转换,因此实际上不再需要维护 OpenGL 模型视图矩阵。您可以将模型矩阵作为统一传递给着色器。您可以用类似的方式维护自己的视图和投影矩阵。这是最近版本的 OpenGL 所必需的;所有矩阵处理函数均已弃用。
First, some background. In 3D graphics, you need to worry about several vector spaces:
[-1, +1]
in each dimension.Coordinates are specified homogeneously, so each vector has components
(x, y, z, w)
, wherew
is a scaling factor. You can obtain coordinates in 3-space as(x/w, y/w, z/w)
. The scaling factor is needed for certain transformations like perspective projection that wouldn't be possible with non-homogenous coordinates.4x4 matrices are needed to transform coordinates from one vector space to another. You could have three different matrices:
You would project a coordinate
C
onto the screen using the formula:OpenGL internally maintains two matrices: modelview (model and view multiplied together), and projection. There is also a texture matrix we won't worry about. When you call
glMatrixMode
, you are switching between these matrices. You replace the current matrix with the identity matrix usingglLoadIdentity
. You apply transformations to the current matrix with functions likeglTranslatef
,glRotatef
, orgluProjection
. Each of these functions just creates a 4x4 matrix the implements that specific transformation, then multiplies the current matrix by it. You can see what the transformation matrices are in the OpenGL 2.1 reference pages.Now for the actual answer. You need to maintain a 4x4 model matrix for each object in your scene. The model matrix will contain all the transformations needed to change model coordinates into world coordinates. For instance, every time you call
glTranslate
, you would update your model matrix:You can then use your model matrix to get coordinates into world space (make sure they are homogenous coordinates first; just set
w = 1
, if they aren't):Since you are maintaining these transformations in parallel, you don't actually need to maintain the OpenGL modelview matrix anymore. You can pass in your model matrix as a uniform to your shaders. You can maintain your own view and projection matrices in similar ways. This is required in recent versions of OpenGL; all of the matrix handling functions are deprecated.
您可以使用虚拟相机视图矩阵的逆矩阵 (V-1) 乘以对象的模型视图矩阵 (V*M) 的乘积来获取世界坐标。
您可以在 gluLookAt() 函数之后使用以下命令获得 V:
glGetFloatv (GL_MODELVIEW_MATRIX, camViewMatrix),
然后反转矩阵并存储它(用于稍后在代码中进行乘法。)
您在要绘制的点处获得 V*M对象,就在使用相同 GL 函数的所有 glTranslatef()、glRotatef() 和 glScale() 命令之后:
glGetFloatv (GL_MODELVIEW_MATRIX,对象模型视图矩阵);
V-1 * ( V * M ) == M
然后乘以两个矩阵,结果矩阵包含位置 m12 = x、m13 = y 和 m14 = z
更多详细信息,C 代码位于:
You can use the product of the inverse of the virtual camera view matrix(V-1) times the ModelView Matrix (V*M) of the object to get World coordinates.
You get V just after the gluLookAt() function using:
glGetFloatv (GL_MODELVIEW_MATRIX, camViewMatrix)
then invert the matrix and store it, (used for multiply later in the code.)
You get V*M at the point where you are about to draw the object, just after all the glTranslatef(), glRotatef() and glScale() commands using the same GL function:
glGetFloatv (GL_MODELVIEW_MATRIX, objectsModelViewMatrix);
V-1 * ( V * M ) == M
Then multiple the two matrices, resulting matrix contains the position, m12 = x, m13 = y and m14 = z
more details with C code at:
https://sourceforge.net/p/openantz/wiki/Local_to_World_Coordinates/