OpenGL - 在相机空间中绘制后将模型放置在世界空间中?

时间:2017-03-09 22:22:05

标签: c++ opengl camera

OpenGL中是否有一种方法可以在相机空间绘制一个物体并让它在移动后保持在世界空间中的那个位置?

我想离开子弹,让它留在世界空间,而不是在相机空间,并且无论我走到哪里都连接到相机。

有没有办法做到这一点,还是我做错了?我不认为我可以在世界空间中绘制物体,因为我可以面向任何方向。 感谢。

1 个答案:

答案 0 :(得分:2)

子弹与你世界上的任何物体都没有什么不同。物体与其他物体的区别在于它在同一空间中的坐标
在摄像机坐标中有一个物体意味着你可以避免乘以"模型"和"查看"矩阵,仅使用"投影"矩阵。

如果您拥有相机坐标中的子弹,则可以通过将它们乘以" View * Model"的倒数得到它的世界坐标。矩阵。

我们假设您使用代码设置项目符号相对于相机

glm::mat4 BulletRotationMatrix = glm::toMat4(bulletRotation);
// Offset so that it appears after the barrel of the gun
glm::mat4 BulletTranslationMatrix = translate(mat4(), glm::vec3(0.35, 0, -3));
glm::mat4 BulletScaleMatrix = scale(mat4(), glm::vec3(0.1f, 0.1f, 0.1f));
glm::mat4 ModelMatrix = BulletTranslationMatrix * BulletRotationMatrix * BulletScaleMatrix;
glm::mat4 MVP = ProjectionMatrix * ModelMatrix;

您选择的名称' ModelMatrix'可能与用于在世界空间中设置对象的矩阵相混淆,而不是相对于相机。所以最好重命名它:

glm::mat4 BulletInCameraMatrix = BulletTranslationMatrix * BulletRotationMatrix * BulletScaleMatrix;
glm::mat4 CameraAndProj = ProjectionMatrix * BulletInCameraMatrix ;

我们可以说,子弹局部坐标中的子弹xyz点被转换为相机空间

glm::vec4 bulletViewCoords = CameraAndProj * glm::vec4(x, y, z, 1.0);

其余的对象遭受矩阵VM = View * Model从局部空间到相机(视图)空间的转换。现在我们想在世界空间中找到一颗子弹。因此,只需撤消CameraAndProj并查看转换:

glm::mat4 BulletToWorld = glm::_inverse(CameraAndProj * View);
//bullet coordinates in world space
glm::vec4 bulletWorldCoords = BulletToWorld * glm::vec4(x, y, z, 1.0);

请注意,逐步撤消操作为inv(CameraAndProj),然后是inv(View)。矩阵代数告诉我们它等于inv(CameraAndProj * View)