【问题标题】:Crop and rotate picture OpenCV裁剪和旋转图片 OpenCV
【发布时间】:2012-11-29 16:02:30
【问题描述】:

我是 OpenCV 的新手,所以请宽容。 我正在做一个 Android 应用程序来识别正方形/矩形并裁剪它们。查找正方形/矩形的函数将找到的对象放入矢量>正方形。我只是想知道如何根据存储在vector> squares中的点中的数据裁剪图片,以及如何计算图片应该旋转的角度。感谢您的帮助

【问题讨论】:

    标签: opencv rotation crop


    【解决方案1】:

    这篇文章引用自OpenCV QA: Extract a RotatedRect area

    Felix Abecassis 有一篇很棒的文章,介绍了旋转和校正图像。这也向您展示了如何提取 RotatedRect 中的数据:

    您基本上只需要cv::getRotationMatrix2D 即可获得仿射变换的旋转矩阵,使用cv::warpAffinecv::getRectSubPix 裁剪旋转后的图像。我的应用程序中的相关行是:

    // This is the RotatedRect, I got it from a contour for example...
    RotatedRect rect = ...;
    // matrices we'll use
    Mat M, rotated, cropped;
    // get angle and size from the bounding box
    float angle = rect.angle;
    Size rect_size = rect.size;
    // thanks to http://felix.abecassis.me/2011/10/opencv-rotation-deskewing/
    if (rect.angle < -45.) {
        angle += 90.0;
        swap(rect_size.width, rect_size.height);
    }
    // get the rotation matrix
    M = getRotationMatrix2D(rect.center, angle, 1.0);
    // perform the affine transformation on your image in src,
    // the result is the rotated image in rotated. I am doing
    // cubic interpolation here
    warpAffine(src, rotated, M, src.size(), INTER_CUBIC);
    // crop the resulting image, which is then given in cropped
    getRectSubPix(rotated, rect_size, rect.center, cropped);
    

    【讨论】:

    • 虽然答案几乎是有效的,但这会在裁剪之前旋转您的整个图像。 高度那里的操作成本很高。
    【解决方案2】:

    周围有很多有用的帖子,我相信你可以做一个更好的搜索。

    作物:

    旋转:

    计算角度:

    【讨论】:

    【解决方案3】:

    虽然这个问题已经很老了,但我认为需要一个不像旋转整个图像那样昂贵的答案(请参阅@bytefish 的答案)。你需要一个边界矩形,出于某种原因rotatedRect.boundingRect() 对我不起作用,所以我不得不使用Imgproc.boundingRect(contour)。这是Android的OpenCV,其他环境的操作几乎一样:

    Rect roi = Imgproc.boundingRect(contour);
    // we only work with a submat, not the whole image:
    Mat mat = image.submat(roi); 
    RotatedRect rotatedRect = Imgproc.minAreaRect(new MatOfPoint2f(contour.toArray()));
    Mat rot = Imgproc.getRotationMatrix2D(rotatedRect.center, rotatedRect.angle, 1.0);
    // rotate using the center of the roi
    double[] rot_0_2 = rot.get(0, 2);
    for (int i = 0; i < rot_0_2.length; i++) {
        rot_0_2[i] += rotatedRect.size.width / 2 - rotatedRect.center.x;
    }
    rot.put(0, 2, rot_0_2);
    double[] rot_1_2 = rot.get(1, 2);
    for (int i = 0; i < rot_1_2.length; i++) {
        rot_1_2[i] += rotatedRect.size.height / 2 - rotatedRect.center.y;
    }
    rot.put(1, 2, rot_1_2);
    // final rotated and cropped image:
    Mat rotated = new Mat();
    Imgproc.warpAffine(mat, rotated, rot, rotatedRect.size);
    

    【讨论】:

      猜你喜欢
      • 2015-08-23
      • 1970-01-01
      • 2017-10-09
      • 1970-01-01
      • 2013-04-14
      • 2013-04-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多