Ask Your Question

Revision history [back]

CalibrateCamera returns bad intrinsic Matrix

Hey there,

I'm currently working on a cameracalibration using a Chessboard. The cornerdetection works perfectly and everything runs without error, the return value of calibrateCamera() is somewhere ~0.2. From what i understood from the documentation is, that the intrinsic matrix returned by CalibrateCamera should look like this:

[fx,0,cx]
[0,fy,cy]
[0 ,0 ,1]

but what i get in return looks like this:

[~0 ,0, 0]
[~4,0, 0]
[0,~0*,0]

~0 -> not really zero but something with e-10 or more

*-> sometimes not zero but insanly large (e+15)

I'm using 40 samples, with a 10x6 Chessboard. Running on 1280x800 capture resolution. I don' set any Flags for calibrate Camera and thus i don't give it any preset intrinsic values, just an empty shell for the Matrix. The distortion-coeffs are alright.

important parts of the Code:

void camCalib() {

Mat intrinsic = Mat(3, 3, CV_32FC1);

Mat distCoeffs;
distCoeffs = Mat(1, 5, CV_64F);
vector<Mat> rvecs;
vector<Mat> tvecs;

VideoCapture cap = VideoCapture(0); // activate Camerahandle
cap.set(CV_CAP_PROP_FRAME_HEIGHT, 800);
cap.set(CV_CAP_PROP_FRAME_WIDTH, 1280);

Mat vidImg, vidImgBackup, greyMat, blurredMat, blurredMat2, binaryImg, conturImg, undistortedImg; // Varaibles to save different Imagestages
namedWindow("Video", WINDOW_AUTOSIZE); 
namedWindow("FilteredVideo", WINDOW_AUTOSIZE);
int xPoints = 6;
int yPoints = 10;
Size patternsize(yPoints, xPoints);
vector<Point2f> corners;
bool once = true;
Scalar color = Scalar(255, 0, 0);        // circle color
vector<vector<Point3f>> CalibPointWorldPositions;
vector<vector<Point2f>> CalibPointImagePositions;
vector<Mat> t_vec_col;
vector<Mat> r_vec_col;
int zPoints = 40;

[...] // fill WorldPosition Vector, all Points on the same z-Level 

Size ImageSize;
int counter = 0;
int buttonPressed = waitKey(1);
while (buttonPressed != 27)
{
    buttonPressed = waitKey(1);
    cap.read(vidImg);
    ImageSize = vidImg.size();
    cvtColor(vidImg, greyMat, CV_BGR2GRAY);
    imshow("Video", vidImg);
    if (buttonPressed == 13) // press Enter
    {

        bool patternfound = findChessboardCorners(vidImg, patternsize, corners,
            CALIB_CB_ADAPTIVE_THRESH + CALIB_CB_NORMALIZE_IMAGE
            + CALIB_CB_FAST_CHECK);
        TermCriteria criteria = TermCriteria(CV_TERMCRIT_EPS + CV_TERMCRIT_ITER, 100, 0.001);
        if (patternfound)
        {
            cout << "pattern found" << endl;
            drawChessboardCorners(vidImg, patternsize, Mat(corners), patternfound);
            cornerSubPix(greyMat, corners, Size(5,5), Size(-1,-1), criteria);
            CalibPointImagePositions.push_back(corners);

            counter++;
        }
        imshow("Video", vidImg);
        if (counter == zPoints)
        {
            if (once)
            {
                //once = !once;
                cout << "calibrating Camera..." << endl;
                TermCriteria criteria = TermCriteria(CV_TERMCRIT_EPS + CV_TERMCRIT_ITER, 10, 0.001);
                cout << calibrateCamera(CalibPointWorldPositions, CalibPointImagePositions, ImageSize, intrinsic, distCoeffs, rvecs, tvecs, 0,criteria) << endl;

//print intrinsic matrix:

cout << intrinsic.ptr<float>(0)[0] << " ;; " << intrinsic.ptr<float>(1)[0] << " ;; " << intrinsic.ptr<float>(2)[0] << endl; cout << intrinsic.ptr<float>(0)[1] << " ;; " << intrinsic.ptr<float>(1)[1] << " ;; " << intrinsic.ptr<float>(2)[1] << endl; cout << intrinsic.ptr<float>(0)[2] << " ;; " << intrinsic.ptr<float>(1)[2] << " ;; " << intrinsic.ptr<float>(2)[2] << endl;

[...] // rest of the code is not important }

Thanks in advance Captain_Obvious