OpenCV 2.0 で AVI ファイルを AVI ファイルに書き出す(第2版)

OpenCV 2.0 用サンプル - 画像入出力,映像入出力 - BiBoLoG で書いていたコードを修整した.フレーム数を取得できない映像ファイルがあったから,これを直した.テストに使用した映像は OpenCV2.0 beta で mp4 や flv を処理する - BiBoLoG の1番目「[HTV技術実証機_H-IIBロケット試験機打ち上げ _ Launch of HTV-1_H-IIB TF1 [HD].flv」を使用した.

#include "stdafx.h"
#include <opencv/cv.h>
#include <opencv/highgui.h>

#ifdef _DEBUG
#pragma comment( lib, "cv200d.lib" )
#pragma comment( lib, "cxcore200d.lib" )
#pragma comment( lib, "highgui200d.lib" )
#else
#pragma comment( lib, "cv200.lib" )
#pragma comment( lib, "cxcore200.lib" )
#pragma comment( lib, "highgui200.lib" )
#endif

#define YOUTUBEROCKET "C:/Data/Video/YouTube/HTV技術実証機_H-IIBロケット試験機打ち上げ _ Launch of HTV-1_H-IIB TF1 [HD]/"
const char *IN_VIDEO = YOUTUBEROCKET"HTV技術実証機_H-IIBロケット試験機打ち上げ _ Launch of HTV-1_H-IIB TF1 [HD].flv";
//const char *IN_VIDEO = "c:/data/video/fez20091005-185827[000].avi";
//const char *IN_VIDEO = "c:/data/video/90frame.avi";
const char *OUT_VIDEO = "c:/data/video/testhfyu.avi";
const char *WINDOW_NAME = "preview window";
const int KEYCODE_ESC = 0x1b;

class video_property
{
private:
	int count;
	int width;
	int height;
	double  fps;
public:
	int get_count(void)  { return this->count;  }
	int get_width(void)  { return this->width;  }
	int get_height(void) { return this->height; }
	double get_fps(void)    { return this->fps; }
	video_property( cv::VideoCapture capture ) { set(capture); };
	void set( cv::VideoCapture capture)
	{
		if ( capture.isOpened() )
		{
			this->count  = (int) capture.get( CV_CAP_PROP_FRAME_COUNT  );
			this->width  = (int) capture.get( CV_CAP_PROP_FRAME_WIDTH  );
			this->height = (int) capture.get( CV_CAP_PROP_FRAME_HEIGHT );
			this->fps    = capture.get( CV_CAP_PROP_FPS );
		}else{
			this->count = this->width = this->height = 0;
			this->fps = 0.0;
		}
	}
	void print(void)
	{
		printf("%-26s: %d\n",  "CV_CAP_PROP_FRAME_COUNT",  this->count );
		printf("%-26s: %d\n",  "CV_CAP_PROP_FRAME_WIDTH",  this->width );
		printf("%-26s: %d\n",  "CV_CAP_PROP_FRAME_HEIGHT", this->height);
		printf("%-26s: %lf\n", "CV_CAP_PROP_FPS",          this->fps   );
	}
};

int _tmain(int argc, _TCHAR* argv[])
{
	cv::VideoCapture capture(IN_VIDEO);
	printf("%s\n", IN_VIDEO);
	if( capture.isOpened() )
	{
		video_property prop(capture);
		prop.print();
		cv::VideoWriter writer(
			OUT_VIDEO, CV_FOURCC('H','F','Y','U'),
			//OUT_VIDEO, CV_FOURCC_DEFAULT,
			prop.get_fps(), cv::Size(prop.get_width(), prop.get_height()));

		if( writer.isOpened() )
		{
			cv::namedWindow(WINDOW_NAME, CV_WINDOW_AUTOSIZE);
			int frame_count = prop.get_count();
			cv::Mat image;
			int key = 0;

			if( frame_count > 0 )
			{
				while( frame_count )
				{
					capture >> image;
					cv::imshow( WINDOW_NAME, image);
					key = cv::waitKey(1);
					writer << image;
					if( key == KEYCODE_ESC )
						break;
				}
			}else{
				frame_count = 0;
				while( 1 )
				{
					capture >> image;
					if( image.empty() )
						break;
					cv::imshow( WINDOW_NAME, image);
					key = cv::waitKey(1);
					writer << image;
					frame_count++;
					if( key == KEYCODE_ESC )
						break;
				}
			}
		}
	}

	return 0;
}