FindChessboardCorners无法通过长焦距镜头检测非常大的图像上的棋盘

时间:2013-02-22 07:00:05

标签: c++ opencv computer-vision camera-calibration

我可以将FindChessboardCorners函数用于小于15万像素的图像,例如2k x 1.5k。但是当我在DSLR的图像上使用它时,分辨率为3700x5300,它不起作用。

我尝试使用resize()直接缩小图像大小,然后就可以了。

显然,OpenCV源代码中存在一些硬编码或错误。

你能帮我解决一下,还是指点一个补丁?

我发现有人在2006年发布了类似的问题,here,所以看起来问题仍然存在。

我使用的代码就像

found = findChessboardCorners( viewGray, boardSize, ptvec,
                                CV_CALIB_CB_ADAPTIVE_THRESH + CV_CALIB_CB_FILTER_QUADS + CV_CALIB_CB_NORMALIZE_IMAGE + CV_CALIB_CB_FAST_CHECK);

更新

就在这里澄清一下。我认为该算法适用于较大的图像分辨率,但当棋​​盘占据较大比例的图像时,它会失败。 例如,当我在相同的相机位置使用50mm固定镜头时,FindChessboardCorners永远不会失败。将其更改为100mm固定镜头后,该功能开始停止检测图案。我认为这与比例或焦距有关。

下图是100mm镜头效果。

更新2

我为大图片添加了锐化滤镜,它开始解决问题。

首先我用

//do a sharpen filter for the large resolution image
if (viewGray.cols > 1500)
{
  Mat temp ;
  GaussianBlur(viewGray,temp, Size(0,0), 105) ; //hardcoded filter size, to be tested on 50 mm lens
  addWeighted(viewGray, 1.8, temp, -0.8,0,viewGray) ; //hardcoded weight, to be tested.
//imwrite("test"+ imageList[k][i], viewGray) ;

}

found = findChessboardCorners( viewGray, boardSize, ptvec,
CV_CALIB_CB_ADAPTIVE_THRESH + CV_CALIB_CB_FILTER_QUADS + CV_CALIB_CB_NORMALIZE_IMAGE + CV_CALIB_CB_FAST_CHECK);

上传了图片

原始分辨率为3744 x 5616的jpg图像,如果此网站强制转换,请确保您使用的是正确的分辨率。

A jpg image at original resolution 3744 x 5616, if this site force convert, then make sure you are using at the correct resolution.

2 个答案:

答案 0 :(得分:24)

几点。

  1. 正如您所注意到的,缩小尺寸有助于探测器。这是因为在OpenCV中用于找到角落的角点检测滤波器具有固定的大小,并且卷积掩模的大小可能太小而无法检测到您的角落 - 全尺寸图像实际上可能在该尺度上看起来“平滑”,尤其是它有点模糊。但是,通过降尺度,您可以丢弃一些角落定位精度。
  2. 出于同样的原因,锐化也有帮助。然而,它也违背了准确性,因为它增加了角落的子像素位置的偏差 - 即使在没有噪声的理想情况下也是如此。为了让自己相信这种情况,请考虑一维模拟:角落周围的图像强度(在1D中,一个明显的黑白过渡)看起来像一个S形曲线(一个有光滑角落的斜坡),你想要的找到其拐点的位置。锐化会使曲线更陡峭,这通常会移动该点的位置。当你考虑到锐化通常会放大噪音时,情况会变得更糟。
  3. 可能正确的方法是以较低的分辨率(即缩小尺寸)开始,然后按比例放大所找到的角落的位置,并将它们用作全分辨率的cvFindCornersSubpix运行的初始估计值。

答案 1 :(得分:1)

如果您有权访问OpenCV源并可以重建它,那么您可以调试cvFindChessboardCorners的行为。

您必须#define DEBUG_CHESSBOARD,然后您将有一些帮助来理解算法。

我认为OpenCV 2.4具有此功能(例如参见https://github.com/Itseez/opencv/blob/2.4/modules/calib3d/src/calibinit.cpp)。

此外,即使它似乎不适用于您的情况,OpenCV doc也要求校准目标:

  

注意:该功能需要在电路板周围的白色空间(如方形厚边框,越宽越好)进行检测   在各种环境中更加强大。否则,如果没有边框   并且背景是黑暗的,外部的黑色方块不能   正确分割等方形分组和排序算法   失败。

http://docs.opencv.org/modules/calib3d/doc/camera_calibration_and_3d_reconstruction.html#findchessboardcorners

问题中的棋盘对于行(6个角)和列(8个角)都有偶数个内角,而reference OpenCV chessboard enter image description here具有偶数/奇数个角,即它是9x6,我不知道这可能是个问题。