WEBカメラで撮影した画像をリアルタイムでDCTをかけるプログラムを作成ました。
以下に二つのソースを掲載させていただきます。
一つ目は最初に実現し正常に動作したもので、二つ目が少しだけ変更して動作しないものです。
その原因がわかりません・・・・・。
ちなみに実行結果は元画像、元画像をグレイスケールにしたもの、DCT係数の3つのウィンドウが作成されます。
#include <opencv/cv.h>
#include <opencv/highgui.h>
#include <opencv/cxcore.h>
#include <ctype.h>
#include <stdio.h>
////////////////////////////////////////////////////////////////////////////////
/////DCT Transform////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////
void DCT(IplImage *src=0,IplImage *image=0,IplImage*dctImage=0){
int x,y;
cvCvtColor(src,image,CV_BGR2GRAY);
//DCT,IDCT用の行列作成(double)
CvMat*dct=0;
dct = cvCreateMat(image->height, image->width, CV_64FC1);
for(y=0; y<image->height; y++){
for(x=0; x<image->width; x++){
cvmSet(dct,
y,
x,
(double)(unsigned char)(image->imageData[image->widthStep
* y + x]));
}
}
cvDCT( dct, dct, CV_DXT_FORWARD);
for(y=0; y<dctImage->height; y++){
for(x=0; x<dctImage->width; x++){
dctImage->imageData[dctImage->widthStep * y + x] =(unsigned char)cvmGet(dct,y,x);
}
}
}
////////////////////////////////////////////////////////////////////////////////////////////////
///////フレーム処理////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////////////////////
int
main (int argc, char **argv)
{
CvCapture *capture = 0;
IplImage *frame = 0,*gray=0,*dct=0;
int c;
if (argc == 1 || (argc == 2 && strlen (argv[1]) == 1 && isdigit (argv[1][0])))
capture = cvCreateCameraCapture (argc == 2 ? argv[1][0] - '0' : 0);
frame = cvQueryFrame(capture);
gray=cvCreateImage(cvGetSize(frame), IPL_DEPTH_8U, 1);
dct=cvCreateImage(cvGetSize(frame), IPL_DEPTH_8U, 1);
cvNamedWindow ("Capture", CV_WINDOW_AUTOSIZE);
cvNamedWindow("Gray",CV_WINDOW_AUTOSIZE);
cvNamedWindow ("DCT係数", CV_WINDOW_AUTOSIZE);
while (1) {
frame = cvQueryFrame (capture);
DCT(frame,gray,dct);
cvShowImage ("Capture", frame);
cvShowImage("Gray",gray);
cvShowImage ("DCT係数", dct);
c = cvWaitKey (2);
if (c == '\x1b')
break;
}
cvDestroyWindow ("Capture");
cvDestroyWindow ("DCT係数");
cvDestroyWindow("Gray");
cvReleaseImage(&frame);
cvReleaseCapture (&capture);
return 0;
}
IplImage構造体のimage(元画をグレイスケールに変換したもの)
と
IplImage構造体のdctImage(dct後)
の二つをを取り出していたのですが後々のことを考えるとそれに加えて
dct後の行列の値も取り出しておきたいと思いました。
そこで以下のように
IplImageとCvMatの二つの変数からなる構造体を定義し、それを関数の引数としましたが
実行するとデバッグは通るものの動作が停止しましたと表示されて動きません。
構造体の中で構造体を定義するといけないのでしょうか?
もしお気づきになった方がいればご教授お願いしますm(__)m
#include <opencv/cv.h>
#include <opencv/highgui.h>
#include <opencv/cxcore.h>
#include <ctype.h>
#include <stdio.h>
////////////////////////////////////////////////////////
struct DCTmem{
IplImage*dctimage;
CvMat*dctmat;
};
////////////////////////////////////////////////////////////////////////////////////
/////////DCT Transform////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////
void DCT(IplImage *src=0,IplImage *image=0,struct DCTmem *dctmem1=0){
int x,y;
cvCvtColor(src,image,CV_BGR2GRAY);
//DCT,IDCT用の行列作成(double)
dctmem1->dctmat = cvCreateMat(image->height, image->width, CV_64FC1);
for(y=0; y<image->height; y++){
for(x=0; x<image->width; x++){
cvmSet(dctmem1->dctmat,
y,
x,
(double)(unsigned char)(image->imageData[image->widthStep
* y + x]));
}
}
cvDCT( dctmem1->dctmat, dctmem1->dctmat, CV_DXT_FORWARD);
for(y=0; y<dctmem1->dctimage->height; y++){
for(x=0; x<dctmem1->dctimage->width; x++){
dctmem1->dctimage->imageData[dctmem1->dctimage->widthStep * y + x] =(unsigned char)cvmGet(dctmem1->dctmat,y,x);
}
}
}
////////////////////////////////////////////////////////////////////////////////////////////////
///////メイン(フレーム処理)////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////////////////////
int
main (int argc, char **argv)
{
CvCapture *capture = 0;
IplImage *frame = 0,*gray=0;
DCTmem*dctmem1=0;
int c;
if (argc == 1 || (argc == 2 && strlen (argv[1]) == 1 && isdigit (argv[1][0])))
capture = cvCreateCameraCapture (argc == 2 ? argv[1][0] - '0' : 0);
frame = cvQueryFrame(capture);
gray=cvCreateImage(cvGetSize(frame), IPL_DEPTH_8U, 1);
dctmem1->dctimage=cvCreateImage(cvGetSize(frame), IPL_DEPTH_8U, 1);
dctmem1->dctmat=cvCreateMat(frame->height, frame->width, CV_64FC1);
cvNamedWindow ("Capture", CV_WINDOW_AUTOSIZE);
cvNamedWindow("Gray",CV_WINDOW_AUTOSIZE);
cvNamedWindow ("DCT係数", CV_WINDOW_AUTOSIZE);
while (1) {
frame = cvQueryFrame (capture);
DCT(frame,gray,dctmem1);
cvShowImage ("Capture", frame);
cvShowImage("Gray",gray);
cvShowImage ("DCT係数", dctmem1->dctimage);
c = cvWaitKey (2);
if (c == '\x1b')
break;
}
cvDestroyWindow ("Capture");
cvDestroyWindow ("DCT係数");
cvDestroyWindow("Gray");
cvReleaseImage(&frame);
cvReleaseCapture (&capture);
return 0;
}