2. 针孔相机模型:从物理世界到像素坐标的映射关系
相机标定这件事,说白了就是搞清楚「世界上的一个点,到底是怎么变成照片里的一个像素的」。
我刚开始做视觉的时候,觉得拍照嘛,镜头对着就完了。直到有一次做三维重建,发现重建出来的点云全是扭曲的,才意识到——不懂相机模型,你连照片都看不懂。
这一章,我们就从最经典的针孔相机模型讲起。它虽然简单,但几乎所有现代相机模型都是它的变体。
2.1 针孔相机模型:最简单的成像方式
想象一个密闭的盒子,前面戳一个小孔。光线从物体上反射,穿过小孔,在盒子后方的平面上形成一个倒立的像。
这就是针孔相机。它没有镜头,没有畸变,只有一个理想化的几何关系。
核心思想:针孔模型假设所有光线都直线传播,且只通过一个点(光心)。
这个模型里,有几个关键角色:
- 光心(O):小孔的位置,所有光线的交点。
- 成像平面:感光元件所在的位置,像落在这里。
- 焦距(f):光心到成像平面的距离。
- 主点(principal point):光轴与成像平面的交点。
嗯,这里要注意:真实相机是有镜头的,镜头会引入畸变。但针孔模型是我们理解一切的基础。先把这个搞懂,后面加畸变模型就是水到渠成的事。
2.2 从世界坐标到相机坐标:刚体变换
世界上的一个点,比如墙角那个点,它在世界坐标系里有一个坐标 (X_w, Y_w, Z_w)。
但相机有自己的坐标系——它以光心为原点,光轴为 Z 轴。要把世界点转到相机坐标系,需要做一次刚体变换:旋转 + 平移。
用数学表达就是:
| X_c | | R11 R12 R13 | | X_w | | t_x |
| Y_c | = | R21 R22 R23 | | Y_w | + | t_y |
| Z_c | | R31 R32 R33 | | Z_w | | t_z |
其中 R 是 3×3 旋转矩阵,t 是 3×1 平移向量。合起来,我们叫它外参(extrinsic parameters)。
我的习惯:外参描述的是「相机在世界中的位置和朝向」。每次标定完,我都会先看一眼外参——如果旋转矩阵的行列式不是 1(或者接近 1),那标定大概率有问题。
2.3 从相机坐标到图像坐标:透视投影
现在点已经在相机坐标系里了,接下来要把它投影到成像平面上。
根据相似三角形,相机坐标系下的点 (X_c, Y_c, Z_c) 在成像平面上的投影位置是:
x = f * X_c / Z_c
y = f * Y_c / Z_c
这里 (x, y) 是图像物理坐标,单位是毫米。注意 Z_c 在分母上——这就是透视效应:离得远的物体看起来小。
我遇到过不少新手,在这里卡住。他们问:「为什么不是 x = f * X_c?」
你想想看,如果真是那样,那一个物体不管远近,在图像上大小都一样——那还怎么判断距离?透视投影正是三维世界在二维平面上成像的本质。
2.4 从图像坐标到像素坐标:内参矩阵
物理坐标 (x, y) 是连续的,但像素是离散的。我们需要把它映射到像素坐标系 (u, v)。
这个映射涉及两个因素:
- 缩放:每个像素在 x 和 y 方向上的物理尺寸(dx, dy)。
- 平移:主点 (u0, v0) 在像素坐标系中的位置。
写成矩阵形式:
| u | | f/dx 0 u0 | | X_c |
| v | = | 0 f/dy v0 | | Y_c |
| 1 | | 0 0 1 | | Z_c |
这个 3×3 矩阵就是内参矩阵 K。它包含了焦距、像素尺寸、主点位置——这些都是相机的固有属性。
我曾经踩过的坑:有一次标定完,发现主点坐标偏离图像中心特别远。我以为是标定板没放好,折腾了半天。后来才发现——是相机传感器被装歪了。嗯,硬件问题也会反映在内参里。
2.5 齐次坐标:为什么要引入它?
你注意到没有,上面的投影公式里,Z_c 在分母上。这意味着从三维到二维的映射是非线性的。
非线性在数学上不好处理。尤其是当我们想把外参和内参串起来,写成一个统一的变换时,除法会让我们很头疼。
这时候,齐次坐标就派上用场了。
简单说,齐次坐标就是在普通坐标后面加一个维度:
- 三维点 (X, Y, Z) → 齐次坐标 (X, Y, Z, 1)
- 二维点 (u, v) → 齐次坐标 (u, v, 1)
有了齐次坐标,除法就变成了矩阵乘法。透视投影可以写成:
| u | | f_x 0 u0 0 | | X_w |
| v | = | 0 f_y v0 0 | | Y_w |
| 1 | | 0 0 1 0 | | Z_w |
| 1 |
等等,这里其实省略了外参。完整的公式是:
s * [u, v, 1]^T = K * [R | t] * [X_w, Y_w, Z_w, 1]^T
s 是一个缩放因子,它让等式两边齐次坐标的最后一个分量相等。
一句话总结:齐次坐标把「除法」变成了「乘法」,把「非线性」变成了「线性」。这是计算机视觉里最优雅的数学技巧之一。
2.6 完整映射流程
把上面所有步骤串起来,从世界点到像素点的完整流程是:
- 世界坐标 (X_w, Y_w, Z_w) → 通过外参 (R, t) → 相机坐标 (X_c, Y_c, Z_c)
- 相机坐标 (X_c, Y_c, Z_c) → 通过透视投影 → 图像物理坐标 (x, y)
- 图像物理坐标 (x, y) → 通过内参 (f_x, f_y, u0, v0) → 像素坐标 (u, v)
用齐次坐标,这三步可以合并成一个矩阵乘法:
s * [u, v, 1]^T = K * [R | t] * [X_w, Y_w, Z_w, 1]^T
这个公式,就是针孔相机模型的完整数学表达。你会在后面每一章里反复见到它。
下面这张图,把整个流程画了出来:
2.7 内参与外参:一张表说清楚
| 参数类型 | 符号 | 含义 | 自由度 | 是否随相机移动变化 |
|---|---|---|---|---|
| 内参 | f_x, f_y, u0, v0 | 焦距(像素单位)、主点位置 | 4 | 否(固定) |
| 外参 | R, t | 旋转矩阵、平移向量 | 6 | 是(随相机位姿变化) |
我的建议:标定的时候,内参只需要标一次。但外参每次移动相机都要重新算。所以如果你把相机固定在一个地方,内参标好了就别动它,只更新外参就行。
2.8 本章小结
针孔相机模型,是整个相机标定的基石。它告诉我们:
- 一个三维点,经过外参变换、透视投影、内参映射,最终变成一个像素。
- 齐次坐标让这个非线性过程变成了优雅的线性矩阵乘法。
- 内参是相机的固有属性,外参描述相机的位置和朝向。