经过了前面的两个相机的单目标定,分别得到了两个相机的内参和畸变系数。供本程序使用。
同时需要用到前面单目标定用到的两组图片(左摄像机的n张照片和右相机的n张照片)
本程序的最终目的是得到:两个相机的外参旋转矩阵(R)、平移矩阵(T)、重投影矩阵(Q)。
#include "stdafx.h"
#include "SemiGlobalMatching.h"
#include <chrono>
#include <fstream>
#include <vector>
using namespace std::chrono;
// opencv library
#include <opencv2/opencv.hpp>
#ifdef _DEBUG
#pragma comment(lib,"opencv_world310d.lib")
#else
#pragma comment(lib,"opencv_world310.lib")
#endif
/*
* ..\Data\my05\13left.jpeg ..\Data\my05\13right.jpeg ..\Data\my05\
*/
/**
*\先用单目标定得到内参(3*3的内参矩阵和5*1的畸变系数)
* 用这个工程得到R、T、F、E、Q这几个矩阵
* sprintf_s(filename, "../05left720p/%d.jpeg", goodFramCount);
* sprintf_s(filename, "../05right720p/%d.jpeg", goodFramCount);
* sprintf_s(saveName, "../Data/biaodin05/%dleft.png", goodFramCount);
* sprintf_s(saveName, "../Data/biaodin05/%dright.png", goodFramCount);
* 内外参矩阵
* \return
*/
/*通过findChessboardCorners找到棋盘上的所有角点,
*然后再通过调用cornerSubPix(image只能单通道)亚像素精确化,找到精确的角点坐标,
*然后调用drawChessboardCorner画出角点位置。
* stereoCalibrate
*/
void calRealPoint(std::vector<std::vector<cv::Point3f>>& obj, int boardWidth, int boardHeight, int imgNumber, int squareSize)
{
std::vector<cv::Point3f> imgpoint;
for (int rowIndex = 0; rowIndex < boardHeight; rowIndex++)
{
for (int colIndex = 0; colIndex < boardWidth; colIndex++)
{
imgpoint.push_back(cv::Point3f(rowIndex * squareSize, colIndex * squareSize, 0));
}
}
for (int imgIndex = 0; imgIndex < imgNumber; imgIndex++)
{
obj.push_back(imgpoint);
}
}
/*本项目需要先完成单目标定,再将标定好的内参拿进来*/
int main(int argv, char* argc[])
{
int goodFramCount = 0, framNumber = 17; //根据自己拍的照片定
//摄像头的分辨率
int imageWidth, imageHeight;
//左边摄像机所有照片角点的坐标集合
std::vector<std::vector<cv::Point2f>> imag