在做Nerf时对其中的一些原理感到困惑,因而把这些基础理论知识总结下来,方便后面的学习。
对于围绕某一物体拍出来的一组照片而言,我们首先需要弄清不同照片拍摄的方位,如下图所示。而相机的内外参就是用来表达相机位置的参数。其中,相机的位置和朝向由相机的外参(extrinsic matrix)决定,投影属性由相机的内参(intrinsic matrix)决定。
接下来我们逐一开始介绍:
相机外参是一个4x4的矩阵 M M M,其作用是将世界坐标系的点 P w o r l d = [ x , y , z , 1 ] P_{world}=[x,y,z,1] Pworld=[x,y,z,1] 变换到相机坐标系 P c a m e r a = M P w o r l d P_{camera}=MP_{world} Pcamera=MPworld下(注意此处为左乘)。我们也把相机外参叫做world-to-camera (w2c)矩阵。
补充:这里用到的是齐次坐标系,其定义如下:
如果一个点在无穷远处,这个点的坐标将会 ( ∞ , ∞ ) (\infty,\infty) (∞,∞),在欧氏空间中,这就变得没有意义。如果使用齐次坐标,平行线在透视空间的无穷远处交于一点,这样就实现了对于无穷点的表示。
简而言之,齐次坐标就是用N+1维来代表N维坐标
我们可以在一个2D笛卡尔坐标末尾加上一个额外的变量w来形成 2D齐次坐标。因此,一个在笛卡尔坐标系下的点 ( X , Y ) (X, Y) (X,Y)在齐次坐标里面变成了 ( x , y , w ) (x,y,w) (x,y,w),并且有:
X = x w ; Y = y w X=\frac{x}{w};Y=\frac{y}{w} X=wx;Y=wy
例如笛卡尔坐标系下(1,2),在齐次坐标系中可以表示为(1,2,1),如果点(1,2)移动到无限远处,在笛卡尔坐标下它变为 ( ∞ , ∞ ) (\infty,\infty) (∞,∞),然后它的齐次坐标表示为(1,2,0)。注意这样的话,我们可以不用 ” ∞ \infty ∞" 来表示一个无穷远处的点了。另外注意方向向量的齐次坐标第四维等于0,点坐标第四维等于1。
而NeRF主要使用camera-to-world (c2w),也就是相机外参的逆矩阵,其作用是把相机坐标系的点变换到世界坐标系。c2w矩阵是一个4x4的矩阵,左上角3x3是旋转矩阵R,又上角的3x1向量是平移向量T。有时写的时候可以忽略最后一行[0,0,0,1]。
[R,T]表示的c2w矩阵的值描述了相机坐标系的朝向和原点:
具体的,旋转矩阵的第一列到第三列分别表示了相机坐标系的X, Y, Z轴在世界坐标系下对应的方向;平移向量表示的是相机原点在世界坐标系的对应位置。
为了更通俗的理解c2w矩阵的内容,我们将c2w作用于相机坐标系中的x轴,也就是[1,0,0,0]上:
[R,T]*[1, 0, 0, 0]^T = [r11, r21, r31]^T
这也就是说相机坐标系下的x轴也就是世界坐标系中的 [r11, r21, r31],这也就是相机外参矩阵中的第一列内容。同理,将c2w作用到相机坐标系下的X轴[1, 0, 0, 0]、Y轴[0, 1, 0, 0]、 Z轴[0, 0, 1, 0]、以及原点[0, 0, 0, 1]我们会依次得到c2w的四列向量。
相机的内参矩阵K定义如下:
K = [ f x 0 c x 0 f y c y 0 0 1 ] K=\begin{bmatrix}f_x&&0&&c_x\\ 0&&f_y&&c_y\\ 0&&0&&1\end{bmatrix} K= fx000fy0cxcy1
内参矩阵K包含4个值:其中 f x f_x fx和 f y f_y fy是相机的水平和垂直焦距(对于理想的针孔相机,fx=fy)。焦距的物理含义是相机中心到成像平面的距离,长度以像素为单位。 c x c_x cx和 c y c_y cy是图像原点相对于相机光心的水平和垂直偏移量,可以用图像宽和高的1/2近似.
这里我们以针孔相机(Pinhole camera)为例介绍内参矩阵中的参数,首先引入我们熟知的小孔成像模型:
为了后面的分析方便,对小孔成像的模型进行进一步的调整,将成像平面画到镜头的对称位置,使得图像不再倒立。注意:这两者是等价的。
内参矩阵中的 f x 和 f y f_x 和f_y fx和fy也就是镜头到成像平面的距离。
之后我们讨论内参矩阵中的 c x c_x cx和 c y c_y cy,这两个参数主要用于将相机坐标系下的3D坐标映射到2D的图像平面。由于像素图片坐标原点一般设置在图片的左上角,不与相机光心重合,所以要表示某一个像素在相机坐标系中的位置时,要在像素坐标的基础上减去 c x 和 c y c_x和c_y cx和cy,同时结合下面这张图,像素点距离相机原点的z轴距离为焦距 f f f。我们可以得到:
对于像素图片坐标系中的某个点 ( i , j ) (i,j) (i,j),其在相机坐标系中被表示为 ( i − c x , j − c y , f ) (i-c_x,j-c_y,f) (i−cx,j−cy,f),由此构造出的一条射线的方向向量为: ( i − c x , j − c y , f ) − ( 0 , 0 , 0 ) = ( i − c x , j − c y , f ) (i-c_x,j-c_y,f)-(0,0,0)=(i-c_x,j-c_y,f) (i−cx,j−cy,f)−(0,0,0)=(i−cx,j−cy,f),将相机外参左乘这一方向向量也就得到了其在世界坐标系的坐标。
参考文献和资料:
[1] NeRF代码解读-相机参数与坐标系变换 - 知乎 (zhihu.com)
[2] 【3D目标检测】单目相机成像原理_单目相机原理_可乐大牛的博客-CSDN博客
[3] 机器视觉——相机标定(四个坐标系的关系)_相机坐标系和像素坐标系的关系_向暖阳呢的博客-CSDN博客
[4] 什么是齐次坐标系?为什么要用齐次坐标系? - 知乎 (zhihu.com)