【opencv】opencv画像透視変換と二値化処理


#include "highgui.h"
#include 
#include "cv.h"
#include 
#include 
#include  
#include 
using namespace cv;

#define max(a,b)  (((a) > (b)) ? (a) : (b))  
#define min(a,b)  (((a) < (b)) ? (a) : (b))  

#define ROAD "H:\kc.jpg"
#define WIN1 "win1"
#define WIDTH 300
#define HEIGHT 300

int mouse_x,mouse_y; 
int pointset[8];

void point(int mouseevent, int x, int y, int flags, void* param) ;
void getPoint(const char* win) ;
void get_four_points(int *pointset,IplImage* crw);
void PerspectiveTrans(IplImage* src, IplImage* dst,int* pointset ,CvMat *transmat);
void invert_to_binary(IplImage* img);

template class Image {
	public:
	IplImage* imgp;

	Image(IplImage* img=0) {imgp=img;}
	~Image(){imgp=0;}
	inline T* operator[](const int rowIndx) {return ((T *)(imgp->imageData + rowIndx*imgp->widthStep));}
};


typedef Image BwImage;

void cvThin (IplImage* src, IplImage* dst, int iterations) 
{
	cvCopyImage(src, dst);
	BwImage dstdat(dst);
	IplImage* t_image = cvCloneImage(src);
	BwImage t_dat(t_image);
	for (int n = 0; n < iterations; n++)
	for (int s = 0; s <= 1; s++) 
	{
		cvCopyImage(dst, t_image);
		for (int i = 0; i < src->height; i++)
		for (int j = 0; j < src->width; j++)
		if (t_dat[i][j]) 
		{
			int a = 0, b = 0;
			int d[8][2] = {{-1, 0}, {-1, 1}, {0, 1}, {1, 1},{1, 0}, {1, -1}, {0, -1}, {-1, -1}};
			int p[8];
			p[0] = (i == 0) ? 0 : t_dat[i-1][j];
			for (int k = 1; k <= 8; k++) 
			{
				if (i+d[k%8][0] < 0 || i+d[k%8][0] >= src->height || j+d[k%8][1] < 0 || j+d[k%8][1] >= src->width)
					p[k%8] = 0;
				else 
					p[k%8] = t_dat[ i+d[k%8][0] ][ j+d[k%8][1] ];
				if (p[k%8]) 
				{
					b++;
					if (!p[k-1]) a++;
				}
			}
			if (b >= 2 && b <= 6 && a == 1)
			if (!s && !(p[2] && p[4] && (p[0] || p[6])))
				dstdat[i][j] = 0;
			else 
				if (s && !(p[0] && p[6] && (p[2] || p[4])))
					dstdat[i][j] = 0;
		}
	}
	cvReleaseImage(&t_image);
};
int main()
{
	
	IplImage* crw = cvLoadImage(ROAD); //        ,          
	IplImage* transming		= cvCreateImage(cvSize(WIDTH,HEIGHT),IPL_DEPTH_8U,3);
	CvMat *transmat		 = cvCreateMat(3, 3, CV_32FC1);

	cvNamedWindow(WIN1); //            
	//CvMat* transmat = cvCreateMat(3,3,CV_32FC1);
	cvShowImage(WIN1, crw);
	


	get_four_points(pointset,crw);
	PerspectiveTrans(crw,transming,pointset,transmat);

	cvNamedWindow("PerspectiveTrans");
	cvShowImage("PerspectiveTrans", transming);

	invert_to_binary(transming);
	cvNamedWindow("binary");
	cvShowImage("binary", transming);

	cvThin(transming,transming,100);
	cvNamedWindow("thin");
	cvShowImage("thin", transming);

	cvWaitKey(0);
	cvReleaseImage(&crw);
	
	return 0;
}
void point(int mouseevent, int x, int y, int flags, void* param) 
{ 
	if (mouseevent == CV_EVENT_LBUTTONDOWN) //     
	{ 
		mouse_x = x; mouse_y = y; //      
	};
};
void getPoint(const char* win) 
{ 
	cvSetMouseCallback(win, point); //       
	cvWaitKey(); //           
};
void get_four_points(int *pointset,IplImage* crw)
{
	cout<height;
    width = img->width;
    step = img->widthStep;
    channls = img->nChannels;
    data = (uchar*)img->imageData;
    for (i=0;i

まず、画像上の4つの点を抽出し、パース変換します.
その後,透視後のピクチャを二値化処理し,細分化を継続できる経路を得た.
これは科創2 Bの第1部のほんの半分で、後で更新されます.
自分がまた一日頑張ったことに感謝します.