[研究関連]]
linux環境ではlibcvを使うとどうやら一筋縄ではいかない模様.
libdcおよびlibrawを使用するとできる.
コンポーネント化もできました.
詳細は徐々に報告.
libdc1394は1394ベースのデジタルカメラの指定に合致するieee 1394の基づいたカメラを
制御したいアプリケーション開発者に高レベルプログラミングインターフェイスを提供するように
意図されていますライブラリです.
Intelが無料で提供している最強画像処理ライブラリ。==>OpenCV
ほとんどこれひとつで画像処理ができるため大人しくインストールすべし!!
サンプルプログラムが乏しいのが唯一の弱点?
OpenCVではgtk+2.0が必要。インストール前に以下を実行
# apt-get install gtk2 # apt-get install gtk2-devel
$ sudo apt-get install ffmpeg $ sudo apt-get install libgtk2.0-dev libavcodec-dev libavformat-dev libjpeg62-dev libtiff4-dev $ cd (OPENCV DIR) $ ./configure --prefix=[OPENCV-DIR] --enable-apps --enable-shared --with-ffmpeg --with-gnu-ld --with-x --without-quicktime CXXFLAGS=-fno-strict-aliasing
Check that the above produces no error and that in particular it reports ffmpeg as yes. If this is not the case there is no point in continuing! [#d273c353]
$ make (if you have tried making other configurations you could also do a make clean before make) $ sudo make install $ sudo vi /etc/ld.so.conf and add the line /opt/opencv/lib. Then sudo ldconfig
Edit (as root) /etc/bash.bashrc and add the lines:
PKG_CONFIG_PATH=$PKG_CONFIG_PATH:/opt/opencv/lib/pkgconfig export PKG_CONFIG_PATH
岩崎君がはまっている分野。 代表的なものを以下に
GML C++ Camera Calibration Toolbox? <== いち押し
MATLABを用いたカメラキャリブレーション
用語?
opencvのサイトにあるものと画像の読み込み部分だけ変更してみた結果、コンパイル成功。
#include <stdio.h> #include <cv.h> #include <highgui.h>
#define IMAGE_NUM (5) /* 画像数 */ #define PAT_ROW (6) /* パターンの行数 */ #define PAT_COL (8) /* パターンの列数 */ #define PAT_SIZE (PAT_ROW*PAT_COL) #define ALL_POINTS (IMAGE_NUM*PAT_SIZE) #define CHESS_SIZE (28.0) /* パターン1マスの1辺サイズ[mm] */
int main (void) { int i, j, k; int corner_count, found; int p_count[IMAGE_NUM]; IplImage *src_img[IMAGE_NUM], *src = 0; CvSize pattern_size = cvSize (PAT_ROW, PAT_COL); CvPoint3D32f objects[ALL_POINTS]; CvPoint2D32f *corners = (CvPoint2D32f *) cvAlloc (sizeof (CvPoint2D32f) * ALL_POINTS); CvMat object_points; CvMat image_points; CvMat point_counts; CvMat *intrinsic = cvCreateMat (3, 3, CV_32FC1); CvMat *rotation = cvCreateMat (1, 3, CV_32FC1); CvMat *translation = cvCreateMat (1, 3, CV_32FC1); CvMat *distortion = cvCreateMat (1, 4, CV_32FC1);
// (1)キャリブレーション画像の読み込み char file01[] = "./picture/calib_l/01.png"; char file02[] = "./picture/calib_l/02.png"; char file03[] = "./picture/calib_l/03.png"; char file04[] = "./picture/calib_l/04.png"; char file05[] = "./picture/calib_l/05.png"; src_img[0] = cvLoadImage (file01, CV_LOAD_IMAGE_COLOR); src_img[1] = cvLoadImage (file02, CV_LOAD_IMAGE_COLOR); src_img[2] = cvLoadImage (file03, CV_LOAD_IMAGE_COLOR); src_img[3] = cvLoadImage (file04, CV_LOAD_IMAGE_COLOR); src_img[4] = cvLoadImage (file05, CV_LOAD_IMAGE_COLOR);
// (2)3次元空間座標の設定 for (i = 0; i < IMAGE_NUM; i++) { for (j = 0; j < PAT_COL; j++) { for (k = 0; k < PAT_ROW; k++) { objects[i * PAT_SIZE + j * PAT_ROW + k].x = j * CHESS_SIZE; objects[i * PAT_SIZE + j * PAT_ROW + k].y = k * CHESS_SIZE; objects[i * PAT_SIZE + j * PAT_ROW + k].z = 0.0; } } } cvInitMatHeader (&object_points, ALL_POINTS, 3, CV_32FC1, objects);
// (3)チェスボード(キャリブレーションパターン)のコーナー検出 int found_num = 0; cvNamedWindow ("Calibration", CV_WINDOW_AUTOSIZE); for (i = 0; i < IMAGE_NUM; i++) { found = cvFindChessboardCorners (src_img[i], pattern_size, &corners[i * PAT_SIZE], &corner_count); cvFindChessboardCorners (src_img[i], pattern_size, &corners[i * PAT_SIZE], &corner_count); if (found) found_num++; // (4)コーナー位置をサブピクセル精度に修正,描画 IplImage *src_gray = cvCreateImage (cvGetSize (src_img[i]), IPL_DEPTH_8U, 1); cvCvtColor (src_img[i], src_gray, CV_BGR2GRAY); cvFindCornerSubPix (src_gray, &corners[i * PAT_SIZE], corner_count, cvSize (3, 3), cvSize (-1, -1), cvTermCriteria (CV_TERMCRIT_ITER | CV_TERMCRIT_EPS, 20, 0.03)); cvDrawChessboardCorners (src_img[i], pattern_size, &corners[i * PAT_SIZE], corner_count, found); p_count[i] = corner_count; cvShowImage ("Calibration", src_img[i]); cvWaitKey (0); } cvDestroyWindow ("Calibration");
if (found_num != IMAGE_NUM) return -1; cvInitMatHeader (&image_points, ALL_POINTS, 1, CV_32FC2, corners); cvInitMatHeader (&point_counts, IMAGE_NUM, 1, CV_32SC1, p_count);
// (5)内部パラメータ,歪み係数の推定 cvCalibrateCamera2 (&object_points, &image_points, &point_counts, cvSize (160, 120), intrinsic, distortion);
// (6)外部パラメータの推定 CvMat sub_image_points, sub_object_points; int base = 0; cvGetRows (&image_points, &sub_image_points, base, base + PAT_SIZE); cvGetRows (&object_points, &sub_object_points, base, base + PAT_SIZE); cvFindExtrinsicCameraParams2 (&sub_object_points, &sub_image_points, intrinsic, distortion, rotation, translation);
// (7)XMLファイルへの書き出し CvFileStorage *fs; fs = cvOpenFileStorage ("camera_l.xml", 0, CV_STORAGE_WRITE); cvWrite (fs, "intrinsic", intrinsic); cvWrite (fs, "rotation", rotation); cvWrite (fs, "translation", translation); cvWrite (fs, "distortion", distortion); cvReleaseFileStorage (&fs);
for (i = 0; i < IMAGE_NUM; i++) { cvReleaseImage (&src_img[i]); cvReleaseImage (&src); }
return 0; }
上のキャリブレーションのサンプルを行うために使用すると便利。
パターンの行・列数は変更してください.
#include <ctype.h> #include<cv.h> #include<highgui.h>
#define IMAGE_NUM (5) /* 画像数 */ #define PAT_ROW (6) /* パターンの行数 */ #define PAT_COL (8) /* パターンの列数 */ #define PAT_SIZE (PAT_ROW*PAT_COL) #define ALL_POINTS (IMAGE_NUM*PAT_SIZE) #define CHESS_SIZE (28.0) /* パターン1マスの1辺サイズ[mm] */
int main (void) { CvCapture *capture = 0; IplImage *frame = 0, *bayer = 0; IplImage *src_gray = 0, *src = 0;
int i, j, k; int corner_count, found; int p_count[IMAGE_NUM]; double w = 320, h = 240; int c; int count=0;
CvSize pattern_size = cvSize (PAT_ROW, PAT_COL); CvPoint3D32f objects[ALL_POINTS]; CvPoint2D32f *corners = (CvPoint2D32f *) cvAlloc (sizeof (CvPoint2D32f) * ALL_POINTS); CvMat object_points; CvMat image_points; CvMat point_counts; CvMat *intrinsic = cvCreateMat (3, 3, CV_32FC1); CvMat *rotation = cvCreateMat (1, 3, CV_32FC1); CvMat *translation = cvCreateMat (1, 3, CV_32FC1); CvMat *distortion = cvCreateMat (1, 4, CV_32FC1);
// (1)コマンド引数によって指定された番号のカメラに対するキャプチャ構造体を作成する capture = cvCreateCameraCapture (0);
/* この設定は,利用するカメラに依存する */ // (2)キャプチャサイズを設定する. frame = cvQueryFrame (capture); bayer = cvCreateImage (cvGetSize(frame), IPL_DEPTH_8U,1); src = cvCreateImage (cvGetSize(frame), IPL_DEPTH_8U,3);
cvNamedWindow ("Capture", 0);
// (3)カメラから画像をキャプチャする while (1) { frame = cvQueryFrame (capture); cvCvtColor(frame,bayer,CV_BGR2GRAY); cvCvtColor(bayer,frame,CV_BayerGB2BGR); int found_num = 0; src->origin=frame->origin;
cvCopy(frame,src,0);
for (i = 0; i < IMAGE_NUM; i++) { found = cvFindChessboardCorners (frame, pattern_size, &corners[i * PAT_SIZE], &corner_count); if (found) found_num++; // (4)コーナー位置をサブピクセル精度に修正,描画 src_gray = cvCreateImage (cvGetSize (frame), IPL_DEPTH_8U, 1); cvCvtColor (frame, src_gray, CV_BGR2GRAY); cvFindCornerSubPix (src_gray, &corners[i * PAT_SIZE], corner_count, cvSize (3, 3), cvSize (-1, -1), cvTermCriteria (CV_TERMCRIT_ITER | CV_TERMCRIT_EPS, 20, 0.03)); cvDrawChessboardCorners (frame, pattern_size, &corners[i * PAT_SIZE], corner_count, found); }
cvShowImage ("Capture", frame); c = cvWaitKey (10); if( (char)c == 27 ){ break; } if( (char)c == 115 ){ count++; switch(count){ case 1: cvSaveImage("./picture/calib_l/01.png",src); break; case 2: cvSaveImage("./picture/calib_l/02.png",src); break; case 3: cvSaveImage("./picture/calib_l/03.png",src); break; case 4: cvSaveImage("./picture/calib_l/04.png",src); break; case 5: cvSaveImage("./picture/calib_l/05.png",src); break; default: break; } if(count == 6){ break; } } }
cvReleaseCapture (&capture); cvDestroyWindow ("Capture");
return 0; }