最终目标:获取位图(深度图)
过程:
1、单目标定(棋盘标定法)
2、双目标定,获取位图
一、单目标定
前期准备--两个摄像机固定到一起,镜头之间呈现一定的夹角,然后对准标定板,切换各种角度拍摄。为了方便,把棋盘图片和最终要测量的实物图一起拍完。
我的标定板一开始是用自制的,精度差的一批。后面买了个72*72毫米极小的标定板来标定。
首先标定左相机拍摄的图片,标定的目标是通过查找角点计算出相机的扭曲矩阵,内外参数矩阵。
可以将结果打印出来观察,画出角点,图片保存在提前创建好的show文件夹中。
注意代码中关于要修改棋盘格角点大小的多个位置。计算棋盘角点大小的方式一般是从左上角第一个格子黑色算起,这个格子开始计算黑白格子交点个数
import numpy as np
import cv2
import glob
import time
# 设置迭代终止条件
criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 30, 0.001)
# 设置 object points, 形式为 (0,0,0), (1,0,0), (2,0,0) ....,(6,5,0)
objp = np.zeros((8*10,3), np.float32) #我用的是8×10的棋盘格,可根据自己棋盘格自行修改相关参数
objp[:,:2] = np.mgrid[0:8,0:10].T.reshape(-1,2)
# 用arrays存储所有图片的object points 和 image points
objpoints = [] # 3d point in real world space
imgpoints = [] # 2d points in image plane.
#用glob匹配文件夹下所有文件名含有“.jpg"的图片
images = glob.glob(r"/home/ubuntu/Two_eyes/left/*.bmp")
t0 = time.time()
for fname in images:
print(time.time()-t0)
prefix=fname.split('/')[5]
img = cv2.imread(fname)
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
# 查找棋盘格角点
ret, corners = cv2.findChessboardCorners(gray, (8,10), None)
# 如果找到了就添加 object points, image points
if ret == True:
objpoints.append(objp)
corners2=cv2.cornerSubPix(gray,corners, (11,11), (-1,-1), criteria)
imgpoints.append(corners)
# 对角点连接画线加以展示
cv2.drawChessboardCorners(img, (8,10), corners2, ret)
cv2.imwrite('/home/ubuntu/Two_eyes/left/show/'+prefix, img)
cv2.namedWindow("img", 0)
cv2.resizeWindow("img", 1200, 800);
cv2.imshow('img', img)
cv2.waitKey(5)
cv2.destroyAllWindows()
# 标定
ret, mtx, dist, rvecs, tvecs = cv2.calibrateCamera(objpoints, imgpoints, gray.shape[::-1], None, None)
print(ret)
print("############")
print(mtx)
print("############")
print(dist)
print("############")
print(rvecs)
print("############")
print(tvecs)
#对所有图片进行去畸变,有两种方法实现分别为: undistort()和remap()
images = glob.glob(r"/home/ubuntu/Two_eyes/left/*.bmp")
for fname in images:
prefix=fname.split('/')[5]
img = cv2.imread(fname)
h, w = img.shap