OpenCV相机标定

4

你好,我正在进行一个图像三维重建的项目。目前我正在校准相机,这需要花费很长时间。但是当我编译代码并在相机前显示棋盘格时,它会直接出现未处理的异常错误。

当图片不在框架内时,没有错误,但一旦进入框架,就会出现未处理的错误,我不知道为什么。

我已经向很多人寻求帮助,但没有人能够解决这个问题。

以下是我的代码:

#include <cv.h>
#include <highgui.h>
#include <vector>
#include <stdlib.h>
#include <stdio.h>

using namespace cv;
using namespace std;

int main()
{
    int numBoards = 0;
    int numCornersHor;
    int numCornersVer;

    printf("Enter number of corners along width: ");
    scanf("%d", &numCornersHor);

    printf("Enter number of corners along height: ");
    scanf("%d", &numCornersVer);

    printf("Enter number of boards: ");
    scanf("%d", &numBoards);

    int numSquares = numCornersHor * numCornersVer;
    Size board_sz = Size(numCornersHor, numCornersVer);
    VideoCapture capture = VideoCapture(0);

    vector<vector<Point3d>> object_points;
    vector<vector<Point2d>> image_points;

    vector<Point2d> corners;
    int successes=0;

    Mat image;
    Mat gray_image;
    capture >> image;

    vector<Point3d> obj;
    for(int j=0;j<numSquares;j++)
        obj.push_back(Point3d(j/numCornersHor, j%numCornersHor, 0.0f));

    while(successes<numBoards)
    {
        cvtColor(image, gray_image, CV_BGR2GRAY);

        bool found = findChessboardCorners(image, board_sz, corners, CV_CALIB_CB_ADAPTIVE_THRESH | CV_CALIB_CB_FILTER_QUADS);

        if(found)
        {
            cornerSubPix(gray_image, corners, Size(11, 11), Size(-1, -1), TermCriteria(CV_TERMCRIT_EPS | CV_TERMCRIT_ITER, 30, 0.1));
            drawChessboardCorners(gray_image, board_sz, corners, found);
        }

        imshow("win1", image);
        imshow("win2", gray_image);

        capture >> image;

        int key = waitKey(1);

        if(key==27)
            return 0;

        if(key==' ' && found!=0)
        {
            image_points.push_back(corners);
            object_points.push_back(obj);
            printf("Snap stored!\n");

            successes++;

            if(successes>=numBoards)
                break;
        }
    }

    Mat intrinsic = Mat(3, 3, CV_32FC1);
    Mat distCoeffs;
    vector<Mat> rvecs;
    vector<Mat> tvecs;

    intrinsic.ptr<float>(0)[0] = 1;
    intrinsic.ptr<float>(1)[1] = 1;

    calibrateCamera(object_points, image_points, image.size(), intrinsic, distCoeffs, rvecs, tvecs);

    Mat imageUndistorted;
    while(1)
    {
        capture >> image;
        undistort(image, imageUndistorted, intrinsic, distCoeffs);

        imshow("win1", image);
        imshow("win2", imageUndistorted);

        waitKey(1);
    }

    capture.release();

    return 0;
}

我在控制台上看到的错误信息是

OpenCV ERROR: 断言失败 (ncorners >=0 && corners.depth() == CV_32F) ,文件位置 .....\src\opencv\modules\imgproc\src\cornersubpix.cpp, 第257行。

而错误对话框则显示:

basiccalibration.exe 中发生未处理的异常:Microsoft C++ 异常: cv::Exception,内存位置为 0x0021f51c。

希望能得到帮助。谢谢!


OpenCV包中有一个示例代码用于相机校准,你在使用吗? - Rui Marques
不,我想自己编写代码。我已经尝试过了,但是出现了太多错误,比如未定义的函数。 - Seif Sharif
我正在尝试运行与您相同的代码。实际上,我的代码有点不同,但我修改了它以获得与您接近的东西,并在这里尝试解决我的问题。一些问题: 在您的最终版本中,您真的使用了两次numCornersHor吗?为什么不使用numCornersVer作为第二个参数? 并且在声明它们时,您是否将两者都定义为float类型?感谢您的帮助! - user2414816
1个回答

3

请使用Point2f和Point3f,而不是Point2d和Point3d。请阅读断言文本。它要求一个CV_32F深度结构。


我是新手,所以不理解错误,也不知道你所说的需要CV_32F深度结构的意思。当我使用point2f和3f时,它会显示警告C4244:“参数”:从“int”转换为“float”,可能丢失数据,对于行“obj.push_back(Point3f(j/numCornersHor, j%numCornersHor, 0.0f));”,它会显示两次,因此构建失败,这就是我将其更改为point3d和point2d的原因。 - Seif Sharif
我遇到了错误。有什么建议吗?谢谢回复。希望能解决这个问题。 - Seif Sharif
你知道,警告是因为你正在将整数分配给浮点数的位置 (j/numCornersHor,j%cornersHor)。关于深度,可以在cv::Mat.depth()文档中找到相关信息。 - morynicz
所以我应该将numcornerver和hor更改为浮点数。 - Seif Sharif
断言在我将它们转换为浮点数后不再出现,但是断言错误中的代码不在我的代码中,而且这个矩阵需要深度为CV_32F,因为角落是我的程序中的向量。关于整数到浮点数的错误,我尝试将其转换为浮点数,但是出现了更多的错误。我该如何将它变成浮点数? - Seif Sharif
好的,我决定对int参数使用float(j/numcornershor),这似乎解决了问题,这是解决它的好方法还是有些低效呢?感谢您的帮助。 - Seif Sharif

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接