16

我在 3D 空间中有 3 个点,我知道它们的确切位置。假设它们是(x0,y0,z0)(x1,y1,z1)(x2,y2,z2)

此外,我有一台正在查看这 3 个点的相机,并且我知道这三个点在相机视图平面上的 2D 位置。例如,从相机的角度来看,将会是,(x0,y0,z0)将会是(x0',y0'),并且将会(x1,y1,z1)是。(x1',y1')(x2,y2,z2)(x2',y2')

找到将这些 3D 点投影到相机视图平面上的 2D 点的投影矩阵的最简单方法是什么。我们对相机位置一无所知。

4

4 回答 4

12

这为您提供了两组,每组 3 个变量中的三个方程:

a*x0+b*y0+c*z0 = x0'
a*x1+b*y1+c*z1 = x1'
a*x2+b*y2+c*z2 = x2'

d*x0+e*y0+f*z0 = y0'
d*x1+e*y1+f*z1 = y1'
d*x2+e*y2+f*z2 = y2'

只需使用在您的情况下最容易解决联立方程的任何方法(“手动”解决这些问题甚至都不难)。那么你的变换矩阵就是 ((a,b,c)(d,e,f))。

...

实际上,这过于简化了,并假设相机指向您的 3D 坐标系的原点并且没有透视。

从角度来看,变换矩阵的工作原理更像:

               ( a, b, c, d )   ( xt )
( x, y, z, 1 ) ( e, f, g, h ) = ( yt )
               ( i, j, k, l )   ( zt )

( xv, yv ) = ( xc+s*xt/zt, yc+s*yt/zt ) if md < zt;

但是 4x3 矩阵比 12 自由度更受约束,因为我们应该有

a*a+b*b+c*c = e*e+f*f+g*g = i*i+j*j+k*k = 1
a*a+e*e+i*i = b*b+f*f+j*j = c*c+g*g+k*k = 1

因此,您可能应该有 4 个点来获得 8 个方程来涵盖相机位置和角度的 6 个变量以及 1 个用于缩放二维视点的变量,因为我们将能够消除“中心”坐标 (xc,yc )。

因此,如果您有 4 个点并将您的 2-D 视点转换为相对于显示器的中心,那么您可以获得 13 个变量的 14 个联立方程并求解。

不幸的是,其中六个方程不是线性方程。幸运的是,这些方程中的所有变量都限制在 -1 和 1 之间的值,因此求解方程仍然可能是可行的。

于 2008-09-25T01:07:10.307 回答
3

您的相机(至少)有 7 个自由度 - 3 个用于位置,3 个用于方向,1 个用于 FOV。如果我错了,我相信有人会纠正我,但似乎 3 分不足以获得完整的解决方案。

有关此问题的通用解决方案,请查看 Graphics Gems II 中的“查看相关性”。

于 2008-09-25T01:13:25.830 回答
2

您正在寻找的是所谓的姿势估计算法。看看 OpenCV 中的 POSIT 实现:http: //opencv.willowgarage.com/documentation/c/calib3d_camera_calibration_and_3d_reconstruction.html#posit

您将需要四个或更多点,它们可能不在同一平面上。

这个实现的教程在这里: http: //opencv.willowgarage.com/wiki/Posit

但请注意:在本教程中使用了方形视口,因此所有视图坐标都在 -1,-1 到 1,1 范围内。这导致人们假设这些应该在相机坐标系中(在宽高比校正之前)。情况并非如此,因此如果您使用纵横比为 4:3 的视口,那么您的输入坐标应该在 -1.3333,-1 到 1.3333,1 的范围内。

顺便说一句,如果您的点必须位于同一平面上,那么您也可以查看 OpenCV 中的 CameraCalibration 算法,但这需要更多的设置,并且需要更多的点作为输入。但是,它也会为您提供相机的失真信息和内在参数。

于 2011-02-14T09:35:35.630 回答
0

我认为没有足够的信息来找到最终的解决方案。在不知道相机位置和视图平面的情况下,有无数个矩阵可以解决这个问题。

于 2008-09-25T01:08:34.513 回答