作者:莪鈈稀罕rn | 来源:互联网 | 2023-06-13 14:32
http:blog.sina.com.cnsblog_4298002e0100e7zx.html创建视景体的glFrustum函数的形式为:glFrustum(left,right
http://blog.sina.com.cn/s/blog_4298002e0100e7zx.html
创建视景体的glFrustum函数的形式为: glFrustum(left,right,bottom,top,near,far),前4个参数表示坐标,可正可负,后两个参数表示距离,为正数.大多数OpenGL的参考文献都只是简单的介绍了一下glFrustum的语法和作用,而并不详细介绍该函数的每个参数如何确定.但是,在增强现实中,往往需要把计算出来的内参数矩阵指定给GL,而不能随便设定.那么怎么把内参数矩阵转化为glFrustum的参数,这就是下面要讨论的问题.
摄像机的内参数矩阵K的形式是:

假设图像的高度和宽度分别为height和width,这里near和far可以任意设定(比如near=100, far=10000).我们用两种方法来推导.
(一)几何推导
如下图,这是视景体的近裁剪面上的顶点在像平面上的投影.

图中长为top的线段被映射成长度为v0的线段,而长为-bottom(图中bottom的坐标值为负,加负号才表示长度)的线段被映射成长度为height-v0的线段.根据相似三角形的关系,可以直接得到:
top/v0 = near/fy;
-bottom/(height-v0) = near/fy;
于是得到参数top和bottom的计算公式:
top = v0*near/fy (1)
bottom = (v0-height)*near/fy (2)
类似地,从下图可以很容易得到left和right:

left = -u0*near/fx (3)
right = (width-u0)*near/fx (4)
上面的(1)-(4)式就是从内参数矩阵K计算glFrustum函数的参数的公式.
(二)代数推导
现在我们从代数上来推导这四个公式,以证明其正确性.
我们知道,在计算机视觉中,内参数矩阵K将摄像机坐标系下的三维点(X,Y,Z)投影到摄像机的像平面上成像,即:

化简得到:
x = fx*X/Z + u0;
y = fy*Y/Z + v0;
GL中所用的摄像机坐标系与计算机视觉中使用的摄像机坐标系不同,正好绕x轴旋转了180度,即y,z两轴反号.所以在GL中,对上式中的YZ取负号,变为:
x = -fx*X/Z + u0;
y = fy*Y/Z + v0;
对于视景体左上角的点,坐标为(left, top, -near),被映射成(0,0,1),所以:
0 = -fx*left/(-near) + u0;
0 = fy*top/(-near) + v0; 即:
left = -u0*near/fx,即为(3)式;
top = v0*near/fy,即为(1)式.
对于视景体右下角的点,坐标为(right, bottom, -near),被映射成(width,height,1),所以:
width = -fx*right/(-near) + u0;
height = fy*bottom/(-near) + v0; 即:
right = (width-u0)*near/fx,即为(4)式;
bottom = (v0-height)*near/fy,即为(2)式.
从上面可以看出,代数方法和几何方法推导出来的公式都一样.
综上,从摄像机的内参数矩阵K计算函数glFrustum的参数的公式为:
top = v0*near/fy;
bottom = (v0-height)*near/fy;
left = -u0*near/fx;
right = (width-u0)*near/fx.
反之,如果已知视景体和图像尺寸,也可以由此公式推导出内参数矩阵K.