相机模型与成像过程:深入解析相机内参、外参及标定方法
引言
相机作为图像采集的重要设备,在图像处理、计算机视觉及机器视觉等领域扮演着核心角色。了解相机的成像原理、模型参数及标定方法,对于提升图像质量和后续处理效果至关重要。本文将详细解析相机模型与成像过程,包括相机内参、外参的概念,以及相机标定的具体步骤和示例代码。
相机模型与成像过程
相机模型
相机模型是描述相机成像原理和图像生成过程的一个数学模型,常见的模型包括针孔相机模型(Pinhole Camera Model)和透视相机模型(Perspective Camera Model)。这里以针孔相机模型为例进行说明。
在针孔相机模型中,相机被看作是一个理想的针孔,光线从外界进入相机后通过针孔投影到成像平面上,形成图像。设成像平面的坐标系为像平面坐标系(x’, y’),相机坐标系为(X, Y, Z),物体坐标系为(x, y, z),则针孔相机模型的公式为:
x ′ = − f ⋅ X Z 和 y ′ = − f ⋅ Y Z x' = -f \cdot \frac{X}{Z} \quad \text{和} \quad y' = -f \cdot \frac{Y}{Z} x′=−f⋅ZX和y′=−f⋅ZY
其中,f为相机的焦距,表示相机的对焦距离。这个公式通过三角形相似原理,将三维空间中的点投影到二维成像平面上。
透视相机模型
在实际应用中,相机通常表现出一定的畸变,特别是当镜头为广角时,畸变现象更为明显。透视相机模型通过引入径向畸变和切向畸变参数来描述这些畸变,典型的径向畸变系数包括 k 1 k_1 k1、 k 2 k_2 k2、 k 3 k_3 k3,切向畸变系数为 p 1 p_1 p1、 p 2 p_2 p2。校正畸变后的图像坐标可以通过以下公式得到:
x c o r r e c t e d = x ⋅ ( 1 + k 1 ⋅ r 2 + k 2 ⋅ r 4 + k 3 ⋅ r 6 ) + 2 ⋅ p 1 ⋅ x ⋅ y + p 2 ⋅ ( r 2 + 2 ⋅ x 2 ) x_{corrected} = x \cdot (1 + k_1 \cdot r^2 + k_2 \cdot r^4 + k_3 \cdot r^6) + 2 \cdot p_1 \cdot x \cdot y + p_2 \cdot (r^2 + 2 \cdot x^2) xcorrected=x⋅(1+k1⋅r2+k2⋅r4+k3⋅r6)+2⋅p1⋅x⋅y+p2⋅(r2+2⋅x2)
y c o r r e c t e d = y ⋅ ( 1 + k 1 ⋅ r 2 + k 2 ⋅ r 4 + k 3 ⋅ r 6 ) + p 1 ⋅ ( r 2 + 2 ⋅ y 2 ) + 2 ⋅ p 2 ⋅ x ⋅ y y_{corrected} = y \cdot (1 + k_1 \cdot r^2 + k_2 \cdot r^4 + k_3 \cdot r^6) + p_1 \cdot (r^2 + 2 \cdot y^2) + 2 \cdot p_2 \cdot x \cdot y ycorrected=y⋅(1+k1⋅r2+k2⋅r4+k3⋅r6)+p1⋅(r2+2⋅y2)+2⋅p2⋅x⋅y
其中, r 2 = x 2 + y 2 r^2 = x^2 + y^2 r2=x2+y2表示未校正图像点到光心的距离。
成像过程
相机的成像过程可以概括为四个坐标系的转换:世界坐标系(UVW)-> 相机坐标系(XYZ)-> 图像坐标系(x, y)-> 像素坐标系(u, v)。
-
世界坐标到相机坐标:通过旋转和平移变换(即相机的外部参数),将世界坐标系中的点转换为相机坐标系中的点。
[ X Y Z 1 ] = [ R t 0 1 ] [ U V W 1 ] \begin{bmatrix} X \\ Y \\ Z \\ 1 \end{bmatrix} = \begin{bmatrix} R & t \\ 0 & 1 \end{bmatrix} \begin{bmatrix} U \\ V \\ W \\ 1 \end{bmatrix} XYZ1 =[R0t1] UVW1
其中, R \mathbf{R} R是3x3的旋转矩阵, t \mathbf{t} t是3x1的平移向量。
-
相机坐标到图像坐标:通过透视投影,将相机坐标系中的点投影到图像坐标系上。这一步仅与焦距f有关。
x = f ⋅ X Z , y = f ⋅ Y Z x = f \cdot \frac{X}{Z}, \quad y = f \cdot \frac{Y}{Z} x=f⋅ZX,y=f⋅ZY
-
图像坐标到像素坐标:通过仿射变换,将图像坐标系中的点转换为像素坐标系中的点。这一步涉及光心位置、像素分辨率和偏斜角等相机内部参数。
u = α x + u 0 , v = β y + v 0 u = \alpha x + u_0, \quad v = \beta y + v_0 u=αx+u0,v=βy+v0
其中, α \alpha α和 β \beta β是x和y方向上的缩放因子, u 0 u_0 u0和 v 0 v_0 v0是图像中心像素坐标。
相机内参和外参
内参
相机内参是描述相机内部特性的参数,主要包括焦距f、光心位置( u 0 , v 0 u_0, v_0 u0,v0)、像素分辨率(dx, dy)和偏斜角等。内参矩阵K通常表示为:
K = [ f x 0 u 0 0 f y v 0 0 0 1 ] K = \begin{bmatrix} f_x & 0 & u_0 \\ 0 & f_y & v_0 \\ 0 & 0 & 1 \end{bmatrix} K= fx000fy0u0v01
其中, f x = α ⋅ f f_x = \alpha \cdot f fx=α⋅f, f y = β ⋅ f f_y = \beta \cdot f fy=β⋅f。
外参
相机外参描述了相机在世界坐标系中的位置和朝向。外参由旋转矩阵 R \mathbf{R} R 和平移向量 t \mathbf{t} t 组成,它们将世界坐标系中的点转换为相机坐标系中的点:
( X c Y c Z c ) = R ( X w Y w Z w ) + t \begin{pmatrix} X_c \\ Y_c \\ Z_c \end{pmatrix} = \mathbf{R} \begin{pmatrix} X_w \\ Y_w \\ Z_w \end{pmatrix} + \mathbf{t} XcYcZc =R XwYwZw +t
这个公式描述了如何将世界坐标系中的三维点 ( X w , Y w , Z w ) (X_w, Y_w, Z_w) (Xw,Yw,Zw) 转换为相机坐标系中的三维点 ( X c , Y c , Z c ) (X_c, Y_c, Z_c) (Xc,Yc,Zc)。其中:
- R \mathbf{R} R 是旋转矩阵,表示相机的旋转姿态。
- t \mathbf{t} t 是平移向量,表示相机在世界坐标系中的位置。
相机标定
相机标定是通过已知的世界坐标和对应的像素坐标,计算相机的内参和外参的过程。标定过程通常涉及以下步骤:
-
采集标定图像:使用相机从不同角度拍摄标定板(如棋盘格),确保每张图像中标定板完整且清晰可见。
-
检测角点:利用图像处理算法(如OpenCV的
cv2.findChessboardCorners
)检测每张图像中标定板的角点,并获取这些角点在图像坐标系中的坐标。 -
计算内参、畸变参数及外参:利用检测到的角点坐标和已知的标定板角点在世界坐标系中的坐标,通过
cv2.calibrateCamera
等函数计算相机的内参、畸变参数及外参。 -
优化和验证:通过优化算法(如最小二乘法)对计算得到的内参和外参进行进一步优化,以提高标定精度。同时,使用未参与标定的图像对标定结果进行验证,确保标定参数的准确性和可靠性。
-
应用标定结果:标定完成后,可以将得到的内参、外参及畸变参数应用于后续的图像处理、三维重建等任务中,以提高处理效果和精度。
畸变校正的示例代码
在相机标定完成后,可以使用计算出的畸变参数对图像进行畸变校正。以下是一个使用OpenCV进行畸变校正的示例代码:
import cv2
import numpy as np
# 假设已经计算得到了相机的内参矩阵 mtx 和畸变系数 dist
# 读取一张需要校正的图像
img = cv2.imread('calibration_images/distorted_image.jpg')
h, w = img.shape[:2]
# 获取校正映射
newcameramtx, roi = cv2.getOptimalNewCameraMatrix(mtx, dist, (w, h), 1, (w, h))
# 校正图像
dst = cv2.undistort(img, mtx, dist, None, newcameramtx)
# 裁剪图像
x, y, w, h = roi
dst = dst[y:y+h, x:x+w]
# 显示校正后的图像
cv2.imshow('Undistorted Image', dst)
cv2.waitKey(0)
cv2.destroyAllWindows()
标定误差评估
在标定完成后,通过计算重投影误差来评估标定结果的准确性。重投影误差是指将三维世界坐标点通过标定得到的内参和外参投影到图像平面上的点与实际检测到的图像坐标点之间的距离。较小的重投影误差表明标定精度较高。
mean_error = 0
for i in range(len(objpoints)):
imgpoints2, _ = cv2.projectPoints(objpoints[i], rvecs[i], tvecs[i], mtx, dist)
error = cv2.norm(imgpoints[i], imgpoints2, cv2.NORM_L2)/len(imgpoints2)
mean_error += error
total_error = mean_error/len(objpoints)
print(f"Total re-projection error: {total_error}")
在实际应用中,重投影误差一般要求在亚像素级别(如小于0.5像素),以保证标定结果的可靠性。
相机标定的实际应用场景
相机标定在许多计算机视觉和图像处理任务中具有广泛应用。以下是几个典型的应用场景:
-
三维重建:通过标定相机获取精确的内参和外参,可以将二维图像中的点映射到三维空间,从而进行三维模型的重建。
-
增强现实(AR):在增强现实应用中,相机标定用于将虚拟物体准确地叠加在真实世界中,实现虚实融合的效果。
-
无人驾驶:在无人驾驶技术中,摄像头标定是实现环境感知和障碍物检测的重要步骤,标定的精度直接影响自动驾驶的安全性和可靠性。
结论
本文详细介绍了相机模型、成像过程、内参与外参的概念,以及相机标定的具体步骤和误差评估方法。通过深入理解这些基础知识,可以为计算机视觉和图像处理领域的实际应用奠定坚实的基础。在未来的应用中,这些知识将帮助我们更好地处理复杂的视觉任务,提高系统的整体性能和稳定性。