本文将梳理一种单目摄像头标定和矫正的方法,在梳理的过程中,首先使用网上离线的图片数据跑通流程,然后接入自己的camera,手动采集标定图像,实时矫正相机的畸变,然后输出矫正后的图像。全文基于Opencv使用C++实现,文末附带相应的python代码。
1. 基本概念
1.1 什么是畸变
下面两张示意图可以让大家直观的感受摄像头的畸变效果,简单的讲摄像头的畸变会让人们看到的图像出现“拉伸”或“扭曲”的直观感受,出现“横不平,竖不直”的现象。虽然畸变现象改变了图像原有的面貌,但在日常生活中也有很多应用之处,比如转弯路口的凸透镜,汽车的左右后视镜等,利用畸变效果扩大视野。但自动驾驶中,往往需要利用图像进行测量或者识别,为了保证精度,在这种场景下,就需要尽量还原图像,也就是所说的“畸变矫正”。畸变效果示意图一
畸变效果示意图二
1.2 为什么会产生畸变
在进行畸变矫正之前,我们需要简单的理解产生畸变的原因。通常畸变可以分为两种,一种是径向畸变,一种是切向畸变,如下面两张图所示。
径向畸变有两种形态,即桶形畸变和枕形畸变,从效果上看一个突出,一个内凹。产生径像畸变的原因是光学镜头在生产制造的过程中,很难保证厚度的均匀,离透镜中心越远的地方光线弯曲越大,从而产生径向畸变。径向畸变(图片来源https://blog.csdn.net/waeceo/article/details/50580808)
切向畸变如下图所示,从效果上看,一个平直的物体在照片中看上去会有“倾斜”,“大小不一”的现象。出现切向畸变的原因是由于镜头与图像传感器不完全平行造成的(可理解为投影仪与影布不平行)。切向畸变(图片来源https://blog.csdn.net/waeceo/article/details/50580808)
1.3 什么是摄像头参数
1)相机矩阵:包括焦距(fx,fy),光学中心(Cx,Cy),完全取决于相机本身,是相机的固有属性,只需要计算一次,可用矩阵表示如下:[fx, 0, Cx; 0, fy, cy; 0,0,1];
2) 畸变系数:畸变数学模型的5个参数 D = (k1,k2, P1, P2, k3);
3)相机内参:相机矩阵和畸变系数统称为相机内参,在不考虑畸变的时候,相机矩阵也会被称为相机内参;
4) 相机外参:通过旋转和平移变换将3D的坐标转换为相机2维的坐标,其中的旋转矩阵和平移矩阵就被称为相机的外参;描述的是将世界坐标系转换成相机坐标系的过程。
1.4 摄像头标定的流程
相机的标定过程实际上就是在4个坐标系转化的过程中求出相机的内参和外参的过程。这4个坐标系分别是:世界坐标系(描述物体真实位置),相机坐标系(摄像头镜头中心),图像坐标系(图像传感器成像中心,图片中心,影布中心,单位mm),像素坐标系(图像左上角为原点,描述像素的位置,单位是多少行,多少列)。
(1)世界坐标系
相机坐标系:求解摄像头外参(旋转和平移矩阵);
(2)相机坐标系
图像坐标系:求解相机内参(摄像头矩阵和畸变系数);
(3) 图像坐标系
像素坐标系:求解像素转化矩阵(可简单理解为原点从图片中心到左上角,单位厘米变行列)
2. 摄像头标定与矫正实践
2.1 离线图片实现摄像头标定和矫正
1)Cmakelist 配置Open