Robotics - Seneing - Coordinates
Pc=(X,Y,Z) 中的下标 cc 表示 camera。相机坐标系不是相机里画着的三根轴,而是人为固定在相机上的一个三维参考系。
通常这样建立:
- 原点 OcO_c:设在相机的等效光心(投影中心)。
- ZcZ_c 轴:沿相机光轴,指向相机前方。
- XcX_c 轴:与图像水平方向平行,指向图像右侧。
- YcY_c 轴:与图像垂直方向平行,指向图像下方。
对于 RealSense/OpenCV 常用的光学坐标约定:
Xc:右,Yc:下,Zc:前\boxed{ X_c:\text{右},\qquad Y_c:\text{下},\qquad Z_c:\text{前} }
因此,一个点:
Pc=(X,Y,Z)P_c=(X,Y,Z)
表示的是:
从相机光心出发,这个点向右 XX、向下 YY、向前 ZZ。
例如:
Pc=(0.1,0.05,1.0) mP_c=(0.1,0.05,1.0)\ \text{m}
表示这个点位于相机:
- 右侧 1010 cm;
- 下方 55 cm;
- 前方 11 m。
它与图像坐标的关系
因为 XcX_c 向右、YcY_c 向下,所以:
X>0⇒u>cxX>0 \Rightarrow u>c_x
点会出现在主点右边。
Y>0⇒v>cyY>0 \Rightarrow v>c_y
点会出现在主点下边。
Z>0Z>0
表示点位于相机前方,可以被相机看到。
因此投影公式可以直接写成:
u=fxXZ+cxu=f_x\frac{X}{Z}+c_x v=fyYZ+cyv=f_y\frac{Y}{Z}+c_y
相机坐标不是机身外壳坐标
这里的原点不是:
- 相机外壳中心;
- Sensor 左上角;
- USB 接口位置;
- D435 整台设备的几何中心。
而是该成像模型的等效光心。
对于 D435,还必须说明是哪个相机坐标系,因为它内部有多个相机:
- 左红外相机坐标系;
- 右红外相机坐标系;
- RGB 相机坐标系;
- 深度 stream 使用的光学坐标系。
它们的原点位置并不完全相同,相互之间通过外参转换。例如,一个点已经在深度相机坐标系中表示为 PdP_d,要转到 RGB 相机坐标系:
Prgb=Rrgb←dPd+trgb←dP_{\text{rgb}} = R_{\text{rgb}\leftarrow d}P_d + t_{\text{rgb}\leftarrow d}
相机是怎么知道 X,Y,ZX,Y,Z 的?
普通 RGB 相机从一个像素 (u,v)(u,v) 只能得到观察方向:
XZ=u−cxfx,YZ=v−cyfy\frac{X}{Z}=\frac{u-c_x}{f_x}, \qquad \frac{Y}{Z}=\frac{v-c_y}{f_y}
不知道具体距离 ZZ,所以无法单独确定 X,Y,ZX,Y,Z。
D435 通过双目计算出深度 ZZ 后,就可以反投影:
X=u−cxfxZ\boxed{ X=\frac{u-c_x}{f_x}Z } Y=v−cyfyZ\boxed{ Y=\frac{v-c_y}{f_y}Z } Z=Z\boxed{ Z=Z }
也就是说:
像素位置 (u,v)+深度 Z⟶相机坐标 (X,Y,Z)\text{像素位置 }(u,v)+\text{深度 }Z \longrightarrow \text{相机坐标 }(X,Y,Z)
最直观的理解是:
把相机光心当作你的一只眼睛:正前方是 ZZ,画面右边是 XX,画面下边是 YY。Pc=(X,Y,Z)P_c=(X,Y,Z) 就是在描述一个点相对于这只“眼睛”的位置。
这个跟2d lines不是一回事, 虽然都是3个数