Vulkan 应用程序中 (glm::) 正交相机的行为

问题描述 投票:0回答:1

我在 Vulkan 中有一个 3D 应用程序,其中正在渲染一个简单的 3D 模型。通常,我使用 glm 的透视投影,如下所示:

// Vulkan-trick because GLM was written for OpenGL, and Vulkan uses
// a right-handed coordinate system instead. Without this correction,
// geometry will be y-inverted in screen space, and the coordinate space
// will be left-handed. Described at:
// https://matthewwellings.com/blog/the-new-vulkan-coordinate-system/
glm::mat4 correction(
        glm::vec4(1.0f,  0.0f, 0.0f, 0.0f),
        glm::vec4(0.0f, -1.0f, 0.0f, 0.0f),
        glm::vec4(0.0f,  0.0f, 0.5f, 0.0f),
        glm::vec4(0.0f,  0.0f, 0.5f, 1.0f));

camera->projectionMatrix = correction * glm::perspectiveFov(fov, w, h, near, far);

这个效果很好。

所以,现在尝试使用正交投影:

float aspect = h / w; // window height/width in pixels
camera->projectionMatrix = correction * glm::ortho(-1.0f, 1.0f, -aspect, aspect, near, far);

3D 模型仍然会渲染,尽管它比以前更大,所以我可能在创建正交投影矩阵时犯了错误。

但问题是相机现在无法在场景中向前/向后移动,这在透视投影中效果很好。底层设置如下所示:

// called every frame if up arrow key is pressed
void camera_move_forward(Camera* camera, float distance)
{
    camera->position += camera->front * distance;
}

// called every frame
static void update(Camera* camera)
{
    const glm::quat& q = camera->orientation;
    camera->viewMatrix = glm::translate(glm::mat4_cast(q), camera->position);

    camera->front = glm::rotate(glm::conjugate(q), glm::vec3(0.0f, 0.0f, 1.0f));
    camera->up = glm::rotate(glm::conjugate(q), glm::vec3(0.0f, 1.0f, 0.0f));
    camera->right = glm::normalize(glm::cross(-camera->up, camera->front));
}

可观察到的行为是

camera_move_forward
不会改变屏幕上 3D 对象的大小。但是,如果我长时间按住向上/向下箭头键,我可以看到近/远平面工作正常,因为模型开始“剪切”。

这通常是如何完成的?我以前没有使用过正交投影。

c++ camera vulkan glm-math orthographic
1个回答
0
投票

这篇帖子提供了一个很好的答案。简而言之,它正在按设计工作。 3D 场景以平行方式投影到 2D,因此移动相机位置不会改变对象的大小,因为对象的范围始终看起来相距相同的距离。因此,“并行”。为了“放大”或缩小对象,您必须更改正交范围或以其他方式修改变换堆栈。

© www.soinside.com 2019 - 2024. All rights reserved.