摄像机标定
来源:互联网 发布:mac可以用盗版软件 编辑:程序博客网 时间:2024/06/03 00:32
主要是学习OPENCV一书中的例程,例程有部分错误,已修改过来了:
#include "cv.h"
#include "highgui.h"
#include <stdio.h>
#include <stdlib.h>
int n_boards = 0; //will be set by input list
const int board_dt = 20; //wait 20 frames per chessboard view
int board_w;
int board_h;
int main(int argc, char** argv)
{
if (argc != 4)
{
printf("ERROR: Wrong number of input parameters\n");
return -1;
}
board_w = atoi(argv[1]);
board_h = atoi(argv[2]);
n_boards = atoi(argv[3]);
int board_n = board_w * board_h;
CvSize board_sz = cvSize(board_w, board_h);
CvCapture* capture = cvCreateCameraCapture(0);
if (!capture)
{
printf("不能从摄影像头获取图像\n");
return -1;
}
// assert (capture);
cvNamedWindow("calibration");
//allocate storage
CvMat* image_points = cvCreateMat(n_boards * board_n, 2, CV_32FC1);
CvMat* object_points = cvCreateMat(n_boards * board_n, 3, CV_32FC1);
CvMat* point_counts = cvCreateMat(n_boards, 1, CV_32SC1);
CvMat* intrinsic_matrix = cvCreateMat(3, 3, CV_32FC1);
CvMat* distortion_coeffs = cvCreateMat(5, 1, CV_32FC1);
CvPoint2D32f* corners = new CvPoint2D32f[board_n];
int corner_count;
int successes = 0;
int step;
int frame =0;
IplImage* image = cvQueryFrame(capture);
IplImage* gray_image = cvCreateImage(cvGetSize(image), 8, 1);
//CAPTURE CORNER VIEWS LOOP UNTIL WE'VE GOT n_boards
//SUCCESSFUL CAPTURES (ALL CORNERS ON THE BOARD ARE FOUND)
//
while(successes < n_boards)
{
//skip every board_dt frames to allow user to move chessboard
if (frame++ % board_dt == 0)
{
//find chessboard corners:
int found = cvFindChessboardCorners(image, board_sz, corners, &corner_count,
CV_CALIB_CB_ADAPTIVE_THRESH | CV_CALIB_CB_FILTER_QUADS);
//get subpixel accuracy on those corners
cvCvtColor(image, gray_image, CV_RGB2GRAY);
cvFindCornerSubPix(gray_image, corners, corner_count, cvSize(11, 11), cvSize(-1, -1),
cvTermCriteria(CV_TERMCRIT_EPS + CV_CALIB_CB_FILTER_QUADS, 30, 0.1));
//draw it
cvDrawChessboardCorners(image, board_sz, corners, corner_count, found);
cvShowImage("calibration", image);
//if we got a good board, add it to our data
if (corner_count == board_n)
{
step = successes * board_n;
for (int i = step, j = 0; j < board_n; ++i, ++j)
{
CV_MAT_ELEM(*image_points, float, i, 0) = corners[j].x;
CV_MAT_ELEM(*image_points, float, i, 1) = corners[j].y;
CV_MAT_ELEM(*object_points, float, i, 0) = (float)(j/board_w);
CV_MAT_ELEM(*object_points, float, i, 1) = (float)(j%board_w);
CV_MAT_ELEM(*object_points, float, i, 2) = 0.0f;
}
CV_MAT_ELEM(*point_counts, int, successes, 0) = board_n;
successes++;
}
} // end skip board_dt between chessboard capture
//handle pause/unpause and esc
int c = cvWaitKey(15);
if (c == 'p')
{
c = 0;
while(c != 'p' && c != 27)
{
c = cvWaitKey(250);
}
}
if (c == 27)
{
return 0;
image = cvQueryFrame(capture); //get next image
}
} //end collection while loop
// allocate matrices according to how many chessboards found
CvMat* object_points2 = cvCreateMat(successes * board_n, 3, CV_32FC1);
CvMat* image_points2 = cvCreateMat(successes * board_n, 2, CV_32FC1);
CvMat* point_counts2 = cvCreateMat(successes, 1, CV_32SC1);
//transfer the points into ther correct size matrices
//below, we weite out the details in the next two loops.we could instead have written:
//image_points->rows = object_points->rows = siccesses*board_n; point_counts->rows = successes;
for (int i = 0; i < successes * board_n; ++i)
{
CV_MAT_ELEM(*image_points2, float, i, 0) = CV_MAT_ELEM(*image_points, float, i, 0);
CV_MAT_ELEM(*image_points2, float, i, 1) = CV_MAT_ELEM(*image_points, float, i, 1);
CV_MAT_ELEM(*object_points2, float, i, 0) = CV_MAT_ELEM(*image_points, float, i, 0);
CV_MAT_ELEM(*object_points2, float, i, 1) = CV_MAT_ELEM(*image_points, float, i, 1);
CV_MAT_ELEM(*object_points2, float, i, 2) = CV_MAT_ELEM(*image_points, float, i, 2);
}
for (i = 0; i < successes; ++i)
{
CV_MAT_ELEM(*point_counts2, int, i, 0) = CV_MAT_ELEM(*point_counts, int, i, 0);
}
cvReleaseMat(&object_points);
cvReleaseMat(&image_points);
cvReleaseMat(&point_counts);
// at this point we have all of the chessboard corners we need
//initialize the intrinsic matrix such that the two focal
//lengths have aratio of 1.0
//
CV_MAT_ELEM(*intrinsic_matrix, float, 0, 0) = 1.0f;
CV_MAT_ELEM(*intrinsic_matrix, float, 1, 1) = 1.0f;
//calibrate the camera!
cvCalibrateCamera2(object_points2, image_points2, point_counts2, cvGetSize(image),
intrinsic_matrix, distortion_coeffs, NULL, NULL, 0);
//save the intrinsics and distortions
cvSave("intrinsics.xml", intrinsic_matrix);
cvSave("distortion.xml", distortion_coeffs);
//example of loading these matrices back in :
CvMat* intrinsic = (CvMat*)cvLoad("intrinsics.xml");
CvMat* distortion = (CvMat*)cvLoad("distortion.xml");
//build the undistort map that we will use for all
//subsequent frames.
//
IplImage* mapx = cvCreateImage(cvGetSize(image), IPL_DEPTH_32F, 1);
IplImage* mapy = cvCreateImage(cvGetSize(image), IPL_DEPTH_32F, 1);
cvInitUndistortMap(intrinsic, distortion, mapx, mapy);
//just run the camera to the screen, now showing the raw and the undistorted image.
//
cvNamedWindow("undistort");
while(image)
{
IplImage* t = cvCloneImage(image);
cvShowImage("calibration", image); //show raw image
cvRemap(t, image, mapx, mapy); //undistort image
cvReleaseImage(&t);
cvShowImage("undistort", image); //show corrected image
//handle pause/unpause and esc
int c = cvWaitKey(15);
if (c == 'p')
{
c = 0;
while(c != 'p' && c != 27)
{
c = cvWaitKey(250);
}
}
if (c == 27)
{
break;
}
image = cvQueryFrame(capture);
}
return 0;
}
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 摄像机标定
- 表和索引在数据压缩前后空间占用情况的对比
- HDU 1524 A Chess Game (有向无环图SG博弈)
- 用C语言实现函数void * memmove(void *dest, const void *src, size_t n)。
- 堆算法排序 结构定义 link2005
- aspx如何获取aspx.cs中定义的变量、方法;
- 摄像机标定
- 抽象类和接口的区别,例子经典
- 2012网络电视有效MMS地址大全(2012-3-9 9:05更新)3TV标清地址
- JS—判断手机号和邮政编码
- 实时Java简介
- ReadProcessMemory
- 合并DataTable
- 华为boss力荐公司高层看的一篇文章,真的很经典!【转载于m13666368773的一篇博客】
- [MSSQL]循环遍历字符串