Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/71.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/opengl/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C opengl视图、投影和正交纵横比_C_Opengl_Viewport_Aspect Ratio - Fatal编程技术网

C opengl视图、投影和正交纵横比

C opengl视图、投影和正交纵横比,c,opengl,viewport,aspect-ratio,C,Opengl,Viewport,Aspect Ratio,有很多关于opengl 3D投影矩阵的优秀教程,但我不做3D。我真的很难按照自己的喜好设置正交投影 整数宽度=320; 内部高度=480 我使用这些设置创建视图投影矩阵 //eyex, eyey, eyez, centerx, centery, centerz, upx, upy, upz// matrix view = (0, 0, -20, 0, 0, -1, 0, 1, 0); matrix projection = (0, width, 0, height, 1, 100); glVi

有很多关于opengl 3D投影矩阵的优秀教程,但我不做3D。我真的很难按照自己的喜好设置正交投影

整数宽度=320; 内部高度=480

我使用这些设置创建视图投影矩阵

//eyex, eyey, eyez, centerx, centery, centerz, upx, upy, upz//
matrix view = (0, 0, -20, 0, 0, -1, 0, 1, 0);

matrix projection = (0, width, 0, height, 1, 100);
glViewport(0, width, 0, -height);
创建此视图和投影矩阵并将其传递给gpu后

然后我创建了一个从
-1,-1到1,1的四元组,使其原点位于中心

然后我为四边形做了一个比例矩阵,这样我就可以在屏幕上看到它了。它呈现为一个完美的正方形,但当然,视口或透视矩阵不应该是正方形。它应该是矩形的

如何设置glViewport和透视矩阵,以便保持纵横比

例如,我现在有宽高比,即宽度/高度。如何将其与投影矩阵和视口一起使用

@Reto可能是对的,我想得太多了,但opengl应用程序接口对我来说有点棘手

编辑 我画了一幅图,希望有助于澄清问题

假设我希望视口为320x480像素。我想要两种不同的缩放模式,我可以选择。要么保持一个固定的高度 其中,宽度将增长以显示更多水平视图,或固定宽度,高度将增长以显示更多垂直视图

这是图片

比如说,我设计了一个320x480左右的场景,我把所有的东西都布置好,我知道我想放大宽度,但保持一个固定的高度


如何从纵横比中使用glViewport和正交投影矩阵实现这一点?

使用正交投影时,您可以简单地将正交矩阵视为在xy平面中定义某个轴对齐的2D矩形,该矩形描述映射到视口的场景区域。如果该矩形的纵横比与视口的纵横比不匹配,则图像将相应地偏离

让我们使用以下定义:

V: aspect of the viewport:
  V = viewport_width / viewport_height
P: aspect of the ortho projection:
  P = (right - left) / (top - bottom)
O: aspect of some axis-aligned rectangle which is drawn
  O = (x_max - x_min) / (y_max - y_min)
应用变换时,对象将在屏幕上显示纵横比
O/p*V

通常,当谈到“保持纵横比”时,我们设置
p==V
,以便
V/p
在上述公式中相互抵消,并且对象以其在眼睛空间中绘制的纵横比显示

这正是您使用代码所得到的:

然后我创建了一个从
-1,-1到1,1的四元组,使其原点位于中心

这是一个正方形,我想知道,在保持纵横比的情况下,你怎么能期望它变成一个矩形

从您的图像可以清楚地看出,您感兴趣的对象是一个纵横比为2/3的矩形。所以你也应该把它画成这样一个长宽比的矩形。实现这一点有多种方法。由于视口大小似乎是给定的,因此可以调整
O
P
或两者

然而,在我看来,你似乎完全是把事情复杂化了。如果我没弄错的话,你有一些320x480像素的“设计空间”,这是你的“感兴趣区域”,无论视口大小如何,你都希望它在屏幕上可见。要实现这一点,您可以执行以下操作:

float target_width = 320.f;
float target_height = 480.f;
float A = target_width / target_height; // target aspect ratio 
// ... calculate V as above
if (V >= A) {
    // wide viewport, use full height
    ortho(-V/A * target_width/2.0f, V/A * target_width/2.0f, -target_height/2.0f, target_height/2.0f, ...);
} else {
    // tall viewport, use full width
    ortho(-target_width/2.0f, target_width/2.0f, -A/V*target_height/2.0f, A/V*target_height/2.0f, ...);
}

现在,您可以在像素的“设计范围”内工作。在该示例中,始终可见的范围将从
(-160,-240)
到(160,240)`,如果您使用该坐标精确绘制矩形,则它将与图像中的蓝色框在任何视口中匹配。如果你不想让原点在中间,你当然可以翻译它。

你想达到什么目的?二维图形要使用什么坐标范围?你可能把这个问题弄得太复杂了,但我不清楚你到底想做什么。@RetoKoradi我给这个问题添加了一张图片和一些细节。谢谢你的回答。这是我在这个问题上见过的最详细的一次。特别是在3个不同的地方,纵横比可以发挥作用。当你说如果你不想原点在中心,你可以平移它,这就是平移视图投影吗?还有没有一本书像你在这里做的那样,以简洁的方式详细介绍了这三个不同的方面?我真的需要理解这一点,这样我才能继续使用我的opengl,因为无论你渲染得多么好,如果它不可见,这仍然是一个问题。好吧,你在哪个矩阵中放置的翻译几乎是一个哲学问题。这将取决于如何想象这些事情。您可以直接将其放入投影矩阵(这相当于直接更改这些参数),以便移动眼睛空间中的视图体积,也可以将其放入视图矩阵中,以便在世界空间中的视图体积移动时,您的“虚拟摄影机”位置仍然代表视图矩形的中心。或者你可以移动所有物体。谢谢,这是一个很好的解释,但我发现了一个错误。应该是:正交(-target\u width/2.0f,target\u width/2.0f,-A/v目标高度/2.0f,A/v目标高度/2.0f,…);这是没有“-”的顶部@Umka:谢谢你发现了这个,修复了它。