视锥角不是预期的



我正试图编写一个方法,计算我正在工作的相机类的视图截锥角。我知道 MVP矩阵是正确的,因为它被推入我的顶点着色器,确实屏幕上的一切都是正确的,不仅如此,我从这个矩阵计算世界空间截锥体平面,它们是正确的。此外,这些方法在几种不同的相机配置中进行单元测试,并给出预期的结果。

我试图通过MVP矩阵的逆变换NDC角来计算截锥体角。

//  Fill with the corners in clip space.
QVector< Vector3f > corners( 8 );
corners[0] <<  1.0f,  1.0f,  1.0f;
corners[1] << -1.0f,  1.0f,  1.0f;
corners[2] <<  1.0f, -1.0f,  1.0f;
corners[3] << -1.0f, -1.0f,  1.0f;
corners[4] <<  1.0f,  1.0f, -1.0f;
corners[5] << -1.0f,  1.0f, -1.0f;
corners[6] <<  1.0f, -1.0f, -1.0f;
corners[7] << -1.0f, -1.0f, -1.0f;
//  Then transform back into worldspace.
for ( Vector3f& c : corners ) {
    c = mult( mvp.inverse(), c );
}

看起来足够体面,但是如果我输入我的MVP (column-major):

-1.68199   0.0       1.68199   0.0
-0.720796  3.00332  -0.720796  0.0
-0.671735 -0.322433 -0.671735  35.8534
-0.669589 -0.321403 -0.669589  37.3363

这是一个相机,近剪辑为0.8,远剪辑为500.0,FOV为35.0°,视口大小为800x600,定位在[25.0,12.0,25.0],看着原点(y是上轴)。我得到了这些角:

-0.988515,  0.00116634, -0.393982
-0.393982,  0.00116634, -0.988515
-0.845201, -0.595974,   -0.250669
-0.250669, -0.595974,   -0.845201
30.2115, 14.9772, 30.8061
30.8061, 14.9772, 30.2115
30.3548, 14.38,   30.9494
30.9494, 14.38,   30.3548

不要盯着这些数字看太久(你会发疯的),只要注意没有角,彼此之间有数百个单位,这是你期望的远平面为500.0。这个程序我有什么不明白的吗?

没有仔细看你的数字,我只是做一个大胆的猜测:

我希望你没有忘记在将变换角扩展到四维齐次坐标(通过添加一个1)并将它们乘以逆MVP后,将变换角除以它们的第四个分量。

这是必要的,因为MVP矩阵(实际上是投影部分)及其逆不是仿射变换,因此当应用于齐次向量时,结果是w -值而不是1。当你(或实际上你的着色器)在转换矢量时应用通常的前向MVP乘法时,这是相同的,只是固定功能图形硬件通过w为你做这个划分(所谓的透视划分,因为这实际上导致更远的对象在屏幕上更小)。

最新更新