在图片不被裁剪时opencv绕图片中任意点旋转任意角度

opencv绕图片中任意角度旋转任意角度

  最近在做项目需要把把图片绕图片中任意点旋转任意角度,考虑到自己旋转需要编写插值算法,所以想到了用opencv,但是网上都是围绕图片中点旋转任意角度的,都是向下面这样写的:

绕图片中心旋转图片不裁剪

#include"opencv.hpp"
#include
using namespace std;
using namespace cv;
int main() {
    Mat src = imread("timg.jpg");
    Mat des,m;
    Point2f center = Point(src.cols / 2, src.rows / 2);
    double angle = 50,scale=0.5;
    int w = src.cols, h = src.rows;
    int bound_w = (h * fabs(sin(angle * CV_PI / 180)) + w * fabs(cos(angle * CV_PI / 180))) * scale;
    int bound_h = (h * fabs(cos(angle * CV_PI / 180)) + w * fabs(sin(angle * CV_PI / 180))) * scale;
    m = getRotationMatrix2D(center, angle, scale);
    m.at(0, 2) += (bound_w - src.cols) / 2;
    m.at(1, 2) += (bound_h - src.rows) / 2;

    warpAffine(src,des,m,Size2i(bound_h,bound_w));
    imshow("image",des);
    waitKey();
    return 0;

旋转之后的效果: 

在图片不被裁剪时opencv绕图片中任意点旋转任意角度插图

但是遇到绕任意点旋转时,会产生问题,用这种方式还是会存在裁剪,如果要理解绕任意点旋转,需要先理解函数getRotationMatrix2D,这个函数处理过程如下面矩阵表示所示:

在图片不被裁剪时opencv绕图片中任意点旋转任意角度插图1

具体实现代码如下:

    Mat src = imread("/home/sss/1111.jpg", IMREAD_GRAYSCALE);
    Mat des, m;
//旋转的任意角度
    double angle = 45;
    int w = src.cols, h = src.rows;
    Point2f rorate_center;
//旋转的任意中心
    rorate_center.x = w;
    rorate_center.y = h;
//重新计算旋转后的宽和高
    int bound_w = ceil(h * fabs(sin(angle * CV_PI / 180.0)) + w * fabs(cos(angle * CV_PI / 180.0)));
    int bound_h = ceil(h * fabs(cos(angle * CV_PI / 180.0)) + w * fabs(sin(angle * CV_PI / 180.0)));
    m = getRotationMatrix2D(rorate_center, angle, 1.0);

//通过eigen计算旋转矩阵
    Eigen::Matrix3d T1;
    T1  left_top_p, right_top_p, right_bottom_p, left_botoom_p;
    left_top_p  max_x){
        max_x = left_top_p[0];
    }
    if(right_top_p[0] > max_x){
        max_x = right_top_p[0];
    }
    if(right_bottom_p[0] > max_x)
    {
        max_x = right_bottom_p[0];
    }
    if(left_botoom_p[0] > max_x){
        max_x = left_botoom_p[0];
    }

    //max_y
    if(left_top_p[1] > max_y){
        max_y = left_top_p[1];
    }
    if(right_top_p[1] > max_y){
        max_y = right_top_p[1];
    }
    if(right_bottom_p[1] > max_y)
    {
        max_y = right_bottom_p[1];
    }
    if(left_botoom_p[1] > max_y){
        max_y = left_botoom_p[1];
    }

    //将偏置添加到矩阵中
    m.at(0, 2) += -min_x;
    m.at(1, 2) += -min_y;

//变换,最后不会存在裁剪
    warpAffine(src, des , m , Size2i(bound_w , bound_h),
               INTER_LINEAR, 0, Scalar(100, 100, 100));
    imwrite("/home/sss/222.jpg", des);
    return 0;

经过变换过的图片不会存在裁剪:

在图片不被裁剪时opencv绕图片中任意点旋转任意角度插图

 

 

 

文章来源于互联网:在图片不被裁剪时opencv绕图片中任意点旋转任意角度

THE END
分享
二维码