假设你有一张如下所示的图片 

 你想点击图中书的四个顶点,然后得到正放的书:

该如何做?
利用Homography可以做到这点。
1.首先获取书本四个顶点的坐标 pts_src
2.然后我们需要知道书本的宽高比,此书的宽高比是3/4,所以可使输出图像的size 为300*400,就可设其四个点的坐标为(0,0),(299,0),(299,399),(0,399)保存在pts_dst中
3.通过pts_src和pts_dst 获取homography
4.对原图应用homography 得到输出


#include <opencv2/opencv.hpp> using namespace cv; using namespace std; struct userdata{ Mat im; vector<Point2f> points; }; void mouseHandler(int event, int x, int y, int flags, void* data_ptr) { if ( event == EVENT_LBUTTONDOWN ) { userdata *data = ((userdata *) data_ptr); circle(data->im, Point(x,y),3,Scalar(0,0,255), 5, CV_AA); imshow("Image", data->im); if (data->points.size() < 4) { data->points.push_back(Point2f(x,y)); } } } void main() { // Read source image. Mat im_src = imread("book1.jpg"); // Destination image. The aspect ratio of the book is 3/4 Size size(300,400); Mat im_dst = Mat::zeros(size,CV_8UC3); // Create a vector of destination points. vector<Point2f> pts_dst; pts_dst.push_back(Point2f(0,0)); pts_dst.push_back(Point2f(size.width - 1, 0)); pts_dst.push_back(Point2f(size.width - 1, size.height -1)); pts_dst.push_back(Point2f(0, size.height - 1 )); // Set data for mouse event Mat im_temp = im_src.clone(); userdata data; data.im = im_temp; cout << "Click on the four corners of the book -- top left first and" << endl << "bottom left last -- and then hit ENTER" << endl; // Show image and wait for 4 clicks. imshow("Image", im_temp); // Set the callback function for any mouse event setMouseCallback("Image", mouseHandler, &data); waitKey(0); // Calculate the homography Mat h = findHomography(data.points, pts_dst); // Warp source image to destination warpPerspective(im_src, im_dst, h, size); // Show image imshow("Image", im_dst); waitKey(0);
02-11 11:43