如何在平行视图中保持良好的纵横比
How to keep good aspect ratio in parallel view
我目前正在开发一个提供两种类型视图的 STL 文件查看器。
透视图(效果很好):
和平行视图(光计算在这个上有问题但不是主题):
如您所见,平行视图变形了。这是我计算视图矩阵的方法:
float distance = glm::distance(focus,transform.GetPosition())* (ScreenSize.cx/ScreenSize.cy);
float distanceY = glm::distance(focus,transform.GetPosition())* (ScreenSize.cy/ScreenSize.cx);
return glm::ortho(-distance ,distance ,-distanceY ,distanceY, 0.00001f, 10000.0f);
我必须解释一下这段代码:
- 焦点是我正在查看的模型的中心点(0 0 0)
- transform.GetPosition() return相机的实际位置
- glm::distance(...) return 两个矢量之间的长度(相机矢量可以缩放或缩小到焦点)
我避免失真的想法是获取我的 OpenGL 上下文的实际比例的屏幕大小(存储在 ScreenSize 中)并将我的距离乘以它以保持兔子无论屏幕大小如何,都保持不变。但它不起作用,兔子仍然被拉伸或压碎。
如何防止我的 3D 模型在平行视图中无论屏幕尺寸如何都变形?
删除一个屏幕尺寸位?现在,如果您的 window 的高度是宽度的 3/4,那么高度就是高度的 3/4(到目前为止还不错)但是您还将宽度设为 4/3。您需要做其中之一,但不能同时做。
大多数电脑游戏似乎都保持相同的高度 - 因此垂直视距始终为 1(例如) - 并调整宽度:
float distance = glm::distance(focus,transform.GetPosition())*(ScreenSize.cx/ScreenSize.cy);
// delete this part vvvvvvvvvvvvvvvvvvvvvvvvvvvvvv
float distanceY = glm::distance(focus,transform.GetPosition())*(ScreenSize.cy/ScreenSize.cx);
我目前正在开发一个提供两种类型视图的 STL 文件查看器。
透视图(效果很好):
和平行视图(光计算在这个上有问题但不是主题):
如您所见,平行视图变形了。这是我计算视图矩阵的方法:
float distance = glm::distance(focus,transform.GetPosition())* (ScreenSize.cx/ScreenSize.cy);
float distanceY = glm::distance(focus,transform.GetPosition())* (ScreenSize.cy/ScreenSize.cx);
return glm::ortho(-distance ,distance ,-distanceY ,distanceY, 0.00001f, 10000.0f);
我必须解释一下这段代码:
- 焦点是我正在查看的模型的中心点(0 0 0)
- transform.GetPosition() return相机的实际位置
- glm::distance(...) return 两个矢量之间的长度(相机矢量可以缩放或缩小到焦点)
我避免失真的想法是获取我的 OpenGL 上下文的实际比例的屏幕大小(存储在 ScreenSize 中)并将我的距离乘以它以保持兔子无论屏幕大小如何,都保持不变。但它不起作用,兔子仍然被拉伸或压碎。
如何防止我的 3D 模型在平行视图中无论屏幕尺寸如何都变形?
删除一个屏幕尺寸位?现在,如果您的 window 的高度是宽度的 3/4,那么高度就是高度的 3/4(到目前为止还不错)但是您还将宽度设为 4/3。您需要做其中之一,但不能同时做。
大多数电脑游戏似乎都保持相同的高度 - 因此垂直视距始终为 1(例如) - 并调整宽度:
float distance = glm::distance(focus,transform.GetPosition())*(ScreenSize.cx/ScreenSize.cy);
// delete this part vvvvvvvvvvvvvvvvvvvvvvvvvvvvvv
float distanceY = glm::distance(focus,transform.GetPosition())*(ScreenSize.cy/ScreenSize.cx);