gpt4 book ai didi

c++ - 理解 OpenCV 的 undistort 函数

转载 作者:塔克拉玛干 更新时间:2023-11-02 23:37:59 26 4
gpt4 key购买 nike

我希望在不更改相机矩阵的情况下,使用我为相机计算的畸变系数来消除图像的畸变。这正是 undistort() 所做的,但我想将输出绘制到更大的 Canvas 图像上。

当我尝试这样做时:

Mat drawtransform = getOptimalNewCameraMatrix(cameraMatrix, distCoeffs, size, 1.0, size * 2);
undistort(inputimage, undistorted, cameraMatrix, distCoeffs, drawtransform);

它仍然写出相同大小的图像,但只有放大两倍且未失真结果的左上四分之一。 Like the documentation says , undistort 写入相同大小的目标图像。

很明显,我可以复制并重新实现一个略微调整的 undistort() 版本,但我在理解它在做什么时遇到了一些麻烦。这是来源:

void cv::undistort( InputArray _src, OutputArray _dst, InputArray _cameraMatrix,
InputArray _distCoeffs, InputArray _newCameraMatrix )
{
Mat src = _src.getMat(), cameraMatrix = _cameraMatrix.getMat();
Mat distCoeffs = _distCoeffs.getMat(), newCameraMatrix = _newCameraMatrix.getMat();

_dst.create( src.size(), src.type() );
Mat dst = _dst.getMat();

CV_Assert( dst.data != src.data );

int stripe_size0 = std::min(std::max(1, (1 << 12) / std::max(src.cols, 1)), src.rows);
Mat map1(stripe_size0, src.cols, CV_16SC2), map2(stripe_size0, src.cols, CV_16UC1);

Mat_<double> A, Ar, I = Mat_<double>::eye(3,3);

cameraMatrix.convertTo(A, CV_64F);
if( distCoeffs.data )
distCoeffs = Mat_<double>(distCoeffs);
else
{
distCoeffs.create(5, 1, CV_64F);
distCoeffs = 0.;
}

if( newCameraMatrix.data )
newCameraMatrix.convertTo(Ar, CV_64F);
else
A.copyTo(Ar);

double v0 = Ar(1, 2);
for( int y = 0; y < src.rows; y += stripe_size0 )
{
int stripe_size = std::min( stripe_size0, src.rows - y );
Ar(1, 2) = v0 - y;
Mat map1_part = map1.rowRange(0, stripe_size),
map2_part = map2.rowRange(0, stripe_size),
dst_part = dst.rowRange(y, y + stripe_size);

initUndistortRectifyMap( A, distCoeffs, I, Ar, Size(src.cols, stripe_size),
map1_part.type(), map1_part, map2_part );
remap( src, dst_part, map1_part, map2_part, INTER_LINEAR, BORDER_CONSTANT );
}
}

这里大约一半的行用于完整性检查和初始化输入参数。我感到困惑的是 map1map2 发生了什么。遗憾的是,这些名称的描述性不如大多数名称。我一定是遗漏了一些解释,也许它隐藏在一些介绍页面中,或者在另一个功能的文档下。

map1是双 channel 有符号短整数矩阵,map2是无符号短整数矩阵,都是维度(height, max(4096/width, 1) ).问题是,为什么?这些 map 将包含什么?这种 strip 化的意义和目的是什么?奇怪的条纹尺寸有什么意义和目的?

最佳答案

使用initUndistortRectifyMap获得您想要的比例转换,然后将其输出(您提到的两个矩阵)应用于 remap .

第一个映射用于计算每个像素位置的 x 坐标变换,第二个映射用于变换 y 坐标。

关于c++ - 理解 OpenCV 的 undistort 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19897414/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com