OpenCVを使用してカメラの撮影画像をキャプチャしjpgファイルに保存する

icon 項目のみ表示/展開表示の切り替え

概要

OpenCVでカメラを開きカメラで撮影した画像をMat型にコピーしウィンドウに表示しファイルjpgファイル保存するプログラムである。
1秒置きにキャプチャされ、連番のファイル名で保存されます。
画像の下部に撮影番号が表示される。
Visual C++ を対象としておりOpenCVのインストールが必要である。
プログラムを終了させるためにはいずれかのキーを押します。
以下は動作例です。ウィンドウの中の画像ははめ込み画像です。

キャプチャの解像度は320*240に設定しています。

テスト環境

コンパイラ

Visual C++ 2008 Express(32bit)/Standard(32/64bit) with OpenCV2.3.1
Visual C++ 2013 Express 32bit/64bit with OpenCV2.4.10

実行環境

Windows 7 32/64bit

OpenCVのインストール及び環境設定

プログラムソースの概要

#include の後の行からusing namespace cv;の手前までは、Visual C++のバージョン及びRelease/Debug 32bit/64bit 静的リンク/動的リンクに合わせてロードするLIBのファイル名を自動的に作成するために記述しています。
固定された環境であれば、簡素に記述可能です。
例えば Visual C++ 2013 32bit Release 動的リンクであれば、以下のように簡素に記述できます。

#pragma comment(lib, "c:/opencv2.4.10/opencv/build/vc12/x86/lib/opencv_core2410.lib")
#pragma comment(lib, "c:/opencv2.4.10/opencv/build/vc12/x86/lib/opencv_highgui2410.lib")
using namespace cv; により名前空間をcvにします。これを定義しない場合は、OpenCVの関数を使う場合には関数名の前にcv::を付加する必要があります。

_tWinMain

VideoCaptureのコンストラクタでカメラを開きます。引数はカメラ番号を示しています。複数のカメラが接続されている場合は、0より大きい数字が指定できます。
VideoCaptureのisOpend関数でカメラが開けない場合は、プログラムを終了させます。
解像度はset関数により320*240に設定しています。
カメラの選択及び解像度の変更をプログラム実行時に行うには、DirectShowを使用してカメラ名と解像度をリストボックスに表示しカメラと解像度の選択結果を表示するを参考にしてプログラムを修正すれば、キャプチャー前にカメラ番号を選択させることも可能となります。
namedWindow関数によりウィンドウを開きます。
cap >> frameによりカメラで撮影された画像をMat型変数imgへコピーします。
putTextによりimgに文字列を表示します。
imshow関数によりimgをウィンドウに表示します。
imwrite関数によりimgをファイルに保存します。
waitkey(1000)により1秒待機しキー入力があればプログラムを終了させます。

ソースコード


//      OpenCVを使用してカメラで1秒おきに撮影してjpgファイルに保存するサンプル
//      動画の上部に日時を表示
//
//      Open CV 2.3.1(Visual C++ 2008/2013)/2.4.10(Visual C++ 2013)
//      マルチバイト/UNICODE
//              VCのインクルードディレクトリに C:\opencv2.4.10\opencv\build\include; を付加してください。
//      動的リンクで作成した場合は、サンプルの実行には環境変数PATHに以下のフォルダーを登録する必要がある。
//              win64   C:\opencv2.4.10\opencv\build\x64\vc12\bin
//              win32   C:\opencv2.4.10\opencv\build\x86\vc12\bin
//              win64   C:\opencv2.3.1\opencv\build\x64\vc12\bin
//              win32   C:\opencv2.3.1\opencv\build\x86\vc12\bin
//      LIBファイルは本ソースのプラグマで設定しているので、CV_INST_DIR CV_INSt_DIR_SUBマクロでLIBファイルのパスを設定する必要がある。
//              本ソースは、c:\opencvメジャー番号.マイナー番号.サブマイナー番号\opencv\build を想定


#include <windows.h>
#include <opencv2/opencv.hpp>
#include <stdio.h>
#include <tchar.h>

#ifdef _DLL     //      動的リンク
#define CV_LINK_MODE "/lib/"
#else   //      静的リンク
#define CV_LINK_MODE "/staticlib/"
#endif

// バージョン取得
#define CV_VERSION_STR CVAUX_STR(CV_MAJOR_VERSION) CVAUX_STR(CV_MINOR_VERSION) CVAUX_STR(CV_SUBMINOR_VERSION)

#define CV_INST_SUB_DIR  "opencv" ## CVAUX_STR(CV_MAJOR_VERSION) ## "." CVAUX_STR(CV_MINOR_VERSION) ## "." CVAUX_STR(CV_SUBMINOR_VERSION)

#define CV_INST_DIR "c:/" ## CV_INST_SUB_DIR ## "/opencv/build"


//      32bit/64bit ランタイムのリンクモード等に応じてLIBファイルのフォルダー名(CV_LIB_DIR)を作成

#ifdef _WIN64
#ifdef _DLL
#define CV_LIB_DIR  CV_INST_DIR ## "/x64/" ## CV_MS_VER ## "/lib/"
#else
#define CV_LIB_DIR  CV_INST_DIR ## "/x64/" ## CV_MS_VER ## "/staticlib/"
#endif
#else
#ifdef _DLL
#define CV_LIB_DIR  CV_INST_DIR ## "/x86/" ## CV_MS_VER ## "/lib/"
#else
#define CV_LIB_DIR  CV_INST_DIR ## "/x86/" ## CV_MS_VER ## "/staticlib/"
#endif
#endif


#if _MSC_VER==1500
 #define VCVER 2008
 #define CV_MS_VER "vc9"
#endif

#if _MSC_VER==1600
 #define VCVER 2010
 #define CV_MS_VER "vc10"
#endif

#if _MSC_VER==1700
 #define VCVER 2012
 #define CV_MS_VER "vc11"
#endif

#if _MSC_VER==1800
 #define VCVER 2008
 #define CV_MS_VER "vc12"
#endif


#ifdef _DEBUG   //      デバック
 #define CV_EXT_STR "d.lib"
#else   //      リリース
 #define CV_EXT_STR ".lib"
#endif

#pragma comment(lib, CV_LIB_DIR "opencv_core"  CV_VERSION_STR CV_EXT_STR)
#pragma comment(lib, CV_LIB_DIR "opencv_highgui" CV_VERSION_STR CV_EXT_STR)

#ifdef _DLL     //      動的リンク

#else
 #pragma comment(lib,"comctl32.lib")
 #pragma comment(lib,"vfw32.lib")
 #pragma comment(linker, "/nodefaultlib:\"msvcprt"  CV_EXT_STR "\"")

 #if CV_MAJOR_VERSION==2 && CV_MINOR_VERSION==4 && CV_SUBMINOR_VERSION==10
  #pragma comment(lib, CV_LIB_DIR "IlmImf"  CV_EXT_STR )
 #endif
 #pragma comment(lib, CV_LIB_DIR "libjasper"  CV_EXT_STR )
 #pragma comment(lib, CV_LIB_DIR "libjpeg"  CV_EXT_STR )
 #pragma comment(lib, CV_LIB_DIR "libpng"  CV_EXT_STR )
 #pragma comment(lib, CV_LIB_DIR "libtiff"  CV_EXT_STR )
 #pragma comment(lib, CV_LIB_DIR "zlib"  CV_EXT_STR )
#endif

using namespace cv;

int WINAPI WinMain(HINSTANCE hCurInst, HINSTANCE hPrevInst, char* CmdLine, int nCmdShow){
        int cameraNum=0;        //      カメラ番号0を開く
        VideoCapture cap(CV_CAP_DSHOW + cameraNum);             //      DirectShowでキャプチャ
        if(!cap.isOpened()){
                MessageBox(0,_TEXT("カメラを開くことができませんでした。"),_TEXT("エラー"),MB_OK);
                return 1;
        }

        Mat frame;
        //      フレームレート
        int fps=1;
        //      キャプチャサイズの指定
        Size cap_size( 320 , 240 );
        cap.set(CV_CAP_PROP_FRAME_WIDTH , cap_size.width);
        cap.set(CV_CAP_PROP_FRAME_HEIGHT , cap_size.height);
        //      キャプチャフレームレートの設定
        cap.set(CV_CAP_PROP_FPS , fps);
        //      画像サイズに合わせてウィンドウを開く
        namedWindow("capture jsave",CV_WINDOW_AUTOSIZE);

        DWORD t=0;
        char buf[64];
        for(;;){
                cap >> frame;     //      カメラから1フレーム分の画像を取得
                sprintf_s(buf,sizeof(buf),"%6d",t );
                putText(frame,buf,Point(180,220),FONT_HERSHEY_SIMPLEX,1.2,Scalar(0,0,200),2,CV_AA);

                //画像ファイルに保存
                sprintf_s(buf,sizeof(buf),"img%5.5d.jpg",t );
                imwrite(buf, frame); 

                imshow("capture jsave",frame);        //      ウィンドウの更新
                if(waitKey(1000) >=0 )       //1000ms wait キー入力があった場合、文字コードを返す キー入力がない場合は-1が返る
                        break;
                ++t;
        }
        return 0;
}

実行ファイルとソースファイルのダウンロード(capture_jsave.zip)