功能:對一幅二值圖像進行旋轉,旋轉後圖像是傾斜的,而後再把傾斜圖像最小的外接矩形(邊界是水平垂直)區域取出來。基於這樣的需求,圖像旋轉的時候是取原圖像左上、左下和右上三個點,而後根據旋轉的角度計算這三個點在目標圖像上對應的點。ui
#include<stdio.h> #include<opencv2/core/core.hpp> #include<opencv2/highgui/highgui.hpp> #include<opencv2/imgproc/imgproc.hpp> using namespace cv; int main(int argc,char** argv) { Mat src = imread("t2.png",0); double angle = -90; int height = src.rows; int width = src.cols; Point2f srcTri[3],dstTri[3]; //取原圖像上的三個點,左上、左下和右上,根據旋轉角度計算出在目標圖像上對應的點 srcTri[0] = Point2f(0,0); srcTri[1] = Point2f(width-1,0); srcTri[2] = Point2f(0,height-1); //把角度化成弧度 double ang = fabs(angle)*CV_PI/180; double sina = sin(ang); double cosa = cos(ang); int newH,newW; //順時針旋轉的 if(angle < 0) { dstTri[0] = Point2f(height*sina,0); dstTri[1] = Point2f(dstTri[0].x + width * cosa,width * sina); dstTri[2] = Point2f(0,height * cosa); newW = dstTri[1].x; newH = dstTri[2].y + width*sina; } else //逆時針旋轉 { dstTri[0] = Point2f(0,width * sina); dstTri[1] = Point2f(width*cosa,0); dstTri[2] = Point2f(height*sina,dstTri[0].y + height*cosa); newH = dstTri[2].y; newW = dstTri[1].x + height*sina; } printf("dstTri[0]:(%f,%f) dstTri[1]:(%f,%f) dstTri[2]:(%f,%f)\n",dstTri[0].x,dstTri[0].y,dstTri[1].x,dstTri[1].y,dstTri[2].x,dstTri[2].y); //計算仿射變換矩陣 Mat warpMat = getAffineTransform(srcTri,dstTri); //dst這裏高和寬隨意設了一個很大的值 Mat dst(500,500,CV_8U); warpAffine(src,dst,warpMat,dst.size(),INTER_LINEAR,BORDER_CONSTANT,Scalar(255)); dst = dst(Rect(0,0,newW,newH)); //二值圖像旋轉後在黑白交界的地方因爲插值會變成黑色,爲了使旋轉後的圖像還是二值圖像,就把灰色像素置0 uchar *data = dst.data; int num = dst.cols*dst.rows; int i; Mat test(dst.rows,dst.cols,CV_8U,Scalar(255)); uchar *data1 = test.data; for(i=0;i<num;i++) { if(*(data+i) != 0 && *(data+i) != 255) { *(data1+i) = 0; } } imshow("src",src); imshow("dst",dst); imshow("test",test); waitKey(0); return 0; }