我正在尝试找到相机与棋盘的相对位置(或其他方式) - 我对在不同坐标系之间进行转换感到满意,例如这里所建议的。我决定在这个阶段不仅使用棋盘进行校准,而且还使用实际位置确定,因为我可以使用findChessboardCorners
来获取imagePoints
(并且这工作正常)。
我已经阅读了很多关于这个主题的内容,并且觉得我理解solvePnP
输出(即使我对openCV
计算机视觉完全陌生)。不幸的是,我从solvePnP
测试设置中得到的结果和物理测量结果是不同的:z 方向的平移大约偏离了。25%。x
和y
方向完全错误 - 几个数量级和不同的方向,而不是我读到的相机坐标系(x 指向图像,y 指向右侧,z 远离相机)。如果我在世界坐标中转换tvec
和rvec
相机姿势,差异仍然存在。
我的问题是:
- 相机和世界坐标系轴的方向是什么?
- 是否
solvePnP
以与我指定的相同单位输出翻译objectPoints
? - 我将世界原点指定为第一个
objectPoints
(棋盘角之一)。可以tvec
吗?是从相机坐标精确到那个点的平移吗?
这是我的代码(我附上它的形式,因为它不会引发任何异常等)。我在校准过程中使用灰度图像来获取相机内在矩阵和失真系数,因此决定也执行灰度定位。chessCoordinates
是相对于原点(角点之一)以毫米为单位的棋盘点位置列表。camMatrix
并distCoefficients
来自校准(使用相同的棋盘和 执行objectPoints
)。
camCapture=cv2.VideoCapture(0) # Take a picture of the target to get the imagePoints
tempImg=camCapture.read()
imgPts=[]
tgtPts=[]
tempImg=cv2.cvtColor(tempImg[1], cv2.COLOR_BGR2GRAY)
found_all, corners = cv2.findChessboardCorners(tempImg, chessboardDim )
imgPts.append(corners.reshape(-1, 2))
tgtPts.append(np.array(chessCoordinates, dtype=np.float32))
retval,myRvec,myTvec=cv2.solvePnP(objectPoints=np.array(tgtPts), imagePoints=np.array(imgPts), cameraMatrix=camMatrix, distCoeffs=distCoefficients)