不同颜色棋盘的 OpenCV 相机标定
OpenCV camera calibration with chessboard of different colours
今天早上我想到了一个疑问:findChessboardCorners
OpenCV 函数是否适用于不同颜色(例如蓝色)的棋盘?
如果不是这种情况,您认为非常简单的阈值设置是否可以解决问题?
您不能将彩色图像传递给 findChessboardCorners,因为正如 @api55 在他的评论中指出的那样,它只采用灰度图像。
您可能值得看一下提供的棋盘代码 here
// does a fast check if a chessboard is in the input image. This is a workaround to
// a problem of cvFindChessboardCorners being slow on images with no chessboard
// - src: input binary image
// - size: chessboard size
// Returns 1 if a chessboard can be in this image and findChessboardCorners should be called,
// 0 if there is no chessboard, -1 in case of error
int checkChessboardBinary(const cv::Mat & img, const cv::Size & size)
{
CV_Assert(img.channels() == 1 && img.depth() == CV_8U);
Mat white = img.clone();
Mat black = img.clone();
int result = 0;
for ( int erosion_count = 0; erosion_count <= 3; erosion_count++ )
{
if ( 1 == result )
break;
if ( 0 != erosion_count ) // first iteration keeps original images
{
erode(white, white, Mat(), Point(-1, -1), 1);
dilate(black, black, Mat(), Point(-1, -1), 1);
}
vector<pair<float, int> > quads;
fillQuads(white, black, 128, 128, quads);
if (checkQuads(quads, size))
result = 1;
}
return result;
}
主循环是:
CV_IMPL
int cvFindChessboardCorners( const void* arr, CvSize pattern_size,
CvPoint2D32f* out_corners, int* out_corner_count,
int flags )
是这个方法的主要实现。他们在这里
- 使用cvCheckChessboard判断图像中是否有棋盘
- 转换为二进制 (B&W) 并扩大以将角分开使用
- icvGenerateQuads 找到正方形。
因此,在回答您的问题时,只要您的图像在将其转换为灰度后有足够的对比度,它就可能有效,我想灰度蓝白图像就足够了,如果它是淡水绿色或黄色或其他你可能不经过更多处理就难以处理的颜色
今天早上我想到了一个疑问:findChessboardCorners
OpenCV 函数是否适用于不同颜色(例如蓝色)的棋盘?
如果不是这种情况,您认为非常简单的阈值设置是否可以解决问题?
您不能将彩色图像传递给 findChessboardCorners,因为正如 @api55 在他的评论中指出的那样,它只采用灰度图像。
您可能值得看一下提供的棋盘代码 here
// does a fast check if a chessboard is in the input image. This is a workaround to
// a problem of cvFindChessboardCorners being slow on images with no chessboard
// - src: input binary image
// - size: chessboard size
// Returns 1 if a chessboard can be in this image and findChessboardCorners should be called,
// 0 if there is no chessboard, -1 in case of error
int checkChessboardBinary(const cv::Mat & img, const cv::Size & size)
{
CV_Assert(img.channels() == 1 && img.depth() == CV_8U);
Mat white = img.clone();
Mat black = img.clone();
int result = 0;
for ( int erosion_count = 0; erosion_count <= 3; erosion_count++ )
{
if ( 1 == result )
break;
if ( 0 != erosion_count ) // first iteration keeps original images
{
erode(white, white, Mat(), Point(-1, -1), 1);
dilate(black, black, Mat(), Point(-1, -1), 1);
}
vector<pair<float, int> > quads;
fillQuads(white, black, 128, 128, quads);
if (checkQuads(quads, size))
result = 1;
}
return result;
}
主循环是:
CV_IMPL
int cvFindChessboardCorners( const void* arr, CvSize pattern_size,
CvPoint2D32f* out_corners, int* out_corner_count,
int flags )
是这个方法的主要实现。他们在这里
- 使用cvCheckChessboard判断图像中是否有棋盘
- 转换为二进制 (B&W) 并扩大以将角分开使用
- icvGenerateQuads 找到正方形。
因此,在回答您的问题时,只要您的图像在将其转换为灰度后有足够的对比度,它就可能有效,我想灰度蓝白图像就足够了,如果它是淡水绿色或黄色或其他你可能不经过更多处理就难以处理的颜色