opencv calibration demo 阅读笔记

来源:互联网 发布:haproxy acl 端口复用 编辑:程序博客网 时间:2024/05/18 20:09

本文是在阅读opencv sample 所做的笔记。

fundamental

ctype.h

ctype.h character conversion macros and ctype macros
The ctype.h header file of the C Standard Library declares several functions that are useful for testing and mapping characters.

All the functions accepts int as a parameter, whose value must be EOF or representable as an unsigned char.

time

    time_t tt;    time(&tt);    struct tm *t2 = localtime(&tt);    char buf[1024];    strftime(buf, sizeof(buf) - 1, "%c", t2);    fs << "calibration_time" << buf;

time 函数返回秒数自午夜 (00:00 elapsed: 00), 1970 年一月 1 日,协调世界 (UTC)时 (utc),根据系统时钟。 返回值。 timer给定位置的存储。 ,在不存储情况下,此参数可以为 NULL返回值。

time 是 _time64 的包装,默认情况下,因此, time_t 与 __time64_t等效。 如果需要强制编译器解释 time_t 为旧 32 位 time_t,可以定义 _USE_32BIT_TIME_T。 这样做,因为应用程序可以在 2038 中,一月 18 日之后失败不建议使用;使用此宏在 64 位平台不允许的。

calib

calib3d moudle in opencv 包含了很多用来标定用的函数。

FileStorage

class FileStorage
XML/YAML file storage class that encapsulates all the information necessary for writing or reading data to/from a file.

All the functions return non-zero (true) if the argument c satisfies the condition described, and zero(false) if not.

main steps

code

1.print help and use instructions.

if (argc < 2){    help();    return 0;}

2.解析 输入命令行参数

for (i = 1; i < argc; i++){    const char* s = argv[i];    if (strcmp(s, "-w") == 0)    {        if (sscanf(argv[++i], "%u", &boardSize.width) != 1 || boardSize.width <= 0)            return fprintf(stderr, "Invalid board width\n"), -1;    }    else if (strcmp(s, "-h") == 0)    {        if (sscanf(argv[++i], "%u", &boardSize.height) != 1 || boardSize.height <= 0)            return fprintf(stderr, "Invalid board height\n"), -1;    }    else if (strcmp(s, "-pt") == 0)    {        i++;        if (!strcmp(argv[i], "circles"))            pattern = CIRCLES_GRID;        else if (!strcmp(argv[i], "acircles"))            pattern = ASYMMETRIC_CIRCLES_GRID;        else if (!strcmp(argv[i], "chessboard"))            pattern = CHESSBOARD;        else            return fprintf(stderr, "Invalid pattern type: must be chessboard or circles\n"), -1;    }    else if (strcmp(s, "-s") == 0)    {        if (sscanf(argv[++i], "%f", &squareSize) != 1 || squareSize <= 0)            return fprintf(stderr, "Invalid board square width\n"), -1;    }    else if (strcmp(s, "-n") == 0)    {        if (sscanf(argv[++i], "%u", &nframes) != 1 || nframes <= 3)            return printf("Invalid number of images\n"), -1;    }    else if (strcmp(s, "-a") == 0)    {        if (sscanf(argv[++i], "%f", &aspectRatio) != 1 || aspectRatio <= 0)            return printf("Invalid aspect ratio\n"), -1;        flags |= CALIB_FIX_ASPECT_RATIO;    }    else if (strcmp(s, "-d") == 0)    {        if (sscanf(argv[++i], "%u", &delay) != 1 || delay <= 0)            return printf("Invalid delay\n"), -1;    }    else if (strcmp(s, "-op") == 0)    {        writePoints = true;    }    else if (strcmp(s, "-oe") == 0)    {        writeExtrinsics = true;    }    else if (strcmp(s, "-zt") == 0)    {        flags |= CALIB_ZERO_TANGENT_DIST;    }    else if (strcmp(s, "-p") == 0)    {        flags |= CALIB_FIX_PRINCIPAL_POINT;    }    else if (strcmp(s, "-v") == 0)    {        flipVertical = true;    }    else if (strcmp(s, "-V") == 0)    {        videofile = true;    }    else if (strcmp(s, "-o") == 0)    {        outputFilename = argv[++i];    }    else if (strcmp(s, "-su") == 0)    {        showUndistorted = true;    }    else if (s[0] != '-')    {        if (isdigit(s[0]))            sscanf(s, "%d", &cameraId);        else            inputFilename = s;    }    else        return fprintf(stderr, "Unknown option %s", s), -1;}

分类处理输入图片和视频

if (inputFilename){    if (!videofile && readStringList(inputFilename, imageList))        mode = CAPTURING;    else        capture.open(inputFilename);}else    capture.open(cameraId);

准备读入图像数据

if (!capture.isOpened() && imageList.empty())    return fprintf(stderr, "Could not initialize video (%d) capture\n", cameraId), -2;if (!imageList.empty())    nframes = (int)imageList.size();if (capture.isOpened())    printf("%s", liveCaptureHelp);

读取图像

namedWindow("Image View", 1);for (i = 0;; i++)//main loop{    Mat view, viewGray;    bool blink = false;    if (capture.isOpened())    {        Mat view0;        capture >> view0;        view0.copyTo(view);    }    else if (i < (int)imageList.size())        view = imread(imageList[i], 1);//image list 读入mat     if (view.empty())    {        if (imagePoints.size() > 0)            runAndSave(outputFilename, imagePoints, imageSize,            boardSize, pattern, squareSize, aspectRatio,            flags, cameraMatrix, distCoeffs,            writeExtrinsics, writePoints);        break;    }//将一些标定的配置信息写入要输出的文件    imageSize = view.size();    if (flipVertical)        flip(view, view, 0);    vector<Point2f> pointbuf;    cvtColor(view, viewGray, COLOR_BGR2GRAY);///检测角点,    bool found;    switch (pattern)    {    case CHESSBOARD:        found = findChessboardCorners(view, boardSize, pointbuf,CALIB_CB_ADAPTIVE_THRESH | CALIB_CB_FAST_CHECK | CALIB_CB_NORMALIZE_IMAGE);        break;    case CIRCLES_GRID:        found = findCirclesGrid(view, boardSize, pointbuf);        break;    case ASYMMETRIC_CIRCLES_GRID:        found = findCirclesGrid(view, boardSize, pointbuf, CALIB_CB_ASYMMETRIC_GRID);        break;    default:        return fprintf(stderr, "Unknown pattern type\n"), -1;    }// improve the found corners' coordinate accuracy    if (pattern == CHESSBOARD && found) cornerSubPix(viewGray, pointbuf, Size(11, 11),        Size(-1, -1), TermCriteria(TermCriteria::EPS + TermCriteria::COUNT, 30, 0.1));    if (mode == CAPTURING && found &&        (!capture.isOpened() || clock() - prevTimestamp > delay*1e-3*CLOCKS_PER_SEC))    {        imagePoints.push_back(pointbuf);        prevTimestamp = clock();        blink = capture.isOpened();    }//标注检测出角点的位置    if (found)        drawChessboardCorners(view, boardSize, Mat(pointbuf), found);

开始标定

    string msg = mode == CAPTURING ? "100/100" :        mode == CALIBRATED ? "Calibrated" : "Press 'g' to start";    int baseLine = 0;    Size textSize = getTextSize(msg, 1, 1, 1, &baseLine);    Point textOrigin(view.cols - 2 * textSize.width - 10, view.rows - 2 * baseLine - 10);    if (mode == CAPTURING)    {        if (undistortImage)            msg = format("%d/%d Undist", (int)imagePoints.size(), nframes);        else            msg = format("%d/%d", (int)imagePoints.size(), nframes);    }    putText(view, msg, textOrigin, 1, 1,        mode != CALIBRATED ? Scalar(0, 0, 255) : Scalar(0, 255, 0));    if (blink)        bitwise_not(view, view);    if (mode == CALIBRATED && undistortImage)    {        Mat temp = view.clone();        undistort(temp, view, cameraMatrix, distCoeffs);    }    imshow("Image View", view);    int key = 0xff & waitKey(capture.isOpened() ? 50 : 500);    if ((key & 255) == 27)        break;///确认是否畸变矫正    if (key == 'u' && mode == CALIBRATED)        undistortImage = !undistortImage;    if (capture.isOpened() && key == 'g')    {        mode = CAPTURING;        imagePoints.clear();    }///进入标定主函数    if (mode == CAPTURING && imagePoints.size() >= (unsigned)nframes)    {        if (runAndSave(outputFilename, imagePoints, imageSize,            boardSize, pattern, squareSize, aspectRatio,            flags, cameraMatrix, distCoeffs,            writeExtrinsics, writePoints))            mode = CALIBRATED;        else            mode = DETECTION;        if (!capture.isOpened())            break;    }}//显示畸变矫正之后的参数if (!capture.isOpened() && showUndistorted){    Mat view, rview, map1, map2;    initUndistortRectifyMap(cameraMatrix, distCoeffs, Mat(),        getOptimalNewCameraMatrix(cameraMatrix, distCoeffs, imageSize, 1, imageSize, 0),        imageSize, CV_16SC2, map1, map2);    for (i = 0; i < (int)imageList.size(); i++)    {        view = imread(imageList[i], 1);        if (view.empty())            continue;        //undistort( view, rview, cameraMatrix, distCoeffs, cameraMatrix );        remap(view, rview, map1, map2, INTER_LINEAR);        imshow("Image View", rview);        int c = 0xff & waitKey();        if ((c & 255) == 27 || c == 'q' || c == 'Q')            break;    }}
0 0