c++ - 如何在光线追踪器中移动相机?

标签 c++ camera transformation raytracing

我目前正在研究光线追踪技术,我认为我做得很好;但是,我还没有覆盖相机。

到目前为止,我使用了一个位于 (-width/2, height/2, 200)(width/2, -height/2) 之间的平面片段作为 View 平面, 200) [200只是固定的z个数,可以改变]。

除此之外,我主要在 e(0, 0, 1000) 上使用相机,并且使用透视投影。

我从点e 发送光线到像素,并在计算像素颜色后将其打印到图像的相应像素。 enter image description here

这是我创建的图像。希望您可以通过查看图像猜出眼睛和 View 平面的位置。

我的问题从这里开始。是时候四处移动我的相机了,但我不知道如何将 2D View 平面坐标映射到规范坐标。是否有一个转换矩阵?

我认为该方法需要知道 View 平面上像素的 3D 坐标。我不确定这是正确的使用方法。那么,您有什么建议?

最佳答案

有多种方法可以做到这一点。这是我的做法:

  1. 选择一个点来表示相机位置 (camera_position)。
  2. 选择一个 vector 来指示相机的观察方向 (camera_direction)。 (如果你知道相机正在注视的一个点,你可以通过从那个点减去 camera_position 来计算这个方向 vector 。)你可能想要归一化(camera_direction),在在这种情况下,它也是图像平面的法 vector 。
  3. 选择另一个从相机的角度(camera_up)(大约)“向上”的归一化 vector 。
  4. camera_right = Cross(camera_direction, camera_up)
  5. camera_up = Cross(camera_right, camera_direction)(这纠正了“向上”选择中的任何倾斜。)

camera_position + camera_direction 处可视化图像平面的“中心”。向上和向右 vector 位于图像平面内。

您可以选择图像平面的矩形部分来对应您的屏幕。此矩形部分的宽度或高度与 camera_direction 的长度之比决定了视野。要放大,您可以增加 camera_direction 或减小宽度和高度。执行相反的操作以缩小。

因此给定一个像素位置 (i, j),您需要该像素在图像平面上的 (x, y, z)。您可以从中减去 camera_position 以获得光线 vector (然后需要对其进行归一化)。

Ray ComputeCameraRay(int i, int j) {
  const float width = 512.0;  // pixels across
  const float height = 512.0;  // pixels high
  double normalized_i = (i / width) - 0.5;
  double normalized_j = (j / height) - 0.5;
  Vector3 image_point = normalized_i * camera_right +
                        normalized_j * camera_up +
                        camera_position + camera_direction;
  Vector3 ray_direction = image_point - camera_position;
  return Ray(camera_position, ray_direction);
}

这只是说明性的,因此并未优化。

关于c++ - 如何在光线追踪器中移动相机?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13078243/

相关文章:

python - Python校准相机

java - 如何在 AppCompatButton 旋转时更改其背景?

cordova - PhoneGap 相机使应用程序崩溃

c++ - 更好地解释数组

c++ - 如何简单地调整指针的集合或映射排序谓词

java - 在 C++ 中将 Java long 转换为 int64

security - 如何通过软件连接到CCTV摄像机?

java - 基于规则构建转型引擎

c++ - 如何使用 GLSL 向简单三角形添加旋转?

c++ - 在基本类型上使用 std::declval