주의할 점은 cvLoadImage함수와 cvCreateImage함수 호출 시 인자 값 설정이다.
cvLoadImage에서 1은 color로 그림을 받아오겠다는 것이고 0은 흑백으로 받아온다는 것이다.
즉 1로 받아오면 rgb 레이어가 존재하고 0으로 받아오면 rgb레이어가 존재하지 않아서 widthStep으로 index를 계산하면 메모리 엑세스 에러가 떠서 프로그램이 동작하지 않는다.
cvCreateImage 또한 이미지를 생성할때 3을 넣으면 rgb레이어를 사용하는 3채널이고 1을 사용한다면 1채널으로 rgb 레이어가 존재하지 않는 것에 주의해야한다.
#include <opencv2\/opencv.hpp>
#include <opencv\cv.h>
#include <stdio.h>
using namespace cv;
void main()
{
IplImage* image = 0; // image 선언
image = cvLoadImage("img.jpg", 1); //img.jpg파일을 불러옴 1은 컬러로 받아옴, 0은 흑백으로 받아옴(rgb가 없음)
int width = image->width;
int height = image->height;
int index = image->widthStep;
int avg;
int thd = 90;
CvSize size = cvSize(width, height);
IplImage *newImage = cvCreateImage(size, IPL_DEPTH_8U, 3);//세번째 인자값 1: 1=1채널(rgb가 없음) , 3=3채널
IplImage *newImage2 = cvCreateImage(size, IPL_DEPTH_8U, 3);//세번째 인자값 1: 1=1채널(rgb가 없음) , 3=3채널
for(int i=0;i<height;i++)
for(int j=0;j<width;j++){
int index2 = i*index+j*3;
avg = ((unsigned char)image->imageData[index2+0]+(unsigned char)image->imageData[index2+1]+(unsigned char)image->imageData[index2+2])/3;
int avg2 = avg;
if(thd > avg2) avg2 = 255;
else avg2 = 0;
for(int k=0;k<3;k++)
{
newImage->imageData[index2+k] = avg;//gray scale
newImage2->imageData[index2+k] = avg2;//이진화
}
}
cvSaveImage("out.jpg",image);
cvSaveImage("out2.jpg",newImage);
cvSaveImage("out3.jpg",newImage2);
cvNamedWindow( "openCV", 1); // 윈도우 생성
cvNamedWindow( "openCV2", 1); // 윈도우 생성
cvNamedWindow( "openCV3", 1); // 윈도우 생성
cvShowImage( "openCV", image ); // 이미지를 보여줌
cvShowImage( "openCV2", newImage ); // 이미지를 보여줌
cvShowImage( "openCV3", newImage2 ); // 이미지를 보여줌
cvWaitKey(0); // 사용자의 키 입력을 기다림
cvDestroyWindow( "openCV" );
cvDestroyWindow( "openCV2" );
cvDestroyWindow( "openCV3" );
}
결과(원본, Gray scale, 이진화)

댓글 없음:
댓글 쓰기