minAreaRect
的主要作用是获取一个多边形(就是有很多个点组成的一个图形)的最小旋转矩形(旋转矩形就是我们平常见到的水平框带了角度)。
OpenCV中使用vector<Point>
可以组成多个点的多边形,或者四个点的带角度的矩形。
C++中,带角度的矩形可以通过这种方式拿到:
vector<Point> ployPoints{Point(x1,y1),Point(x2,y2),Point(x3,y3),Point(x4,y5)};
RotatedRect rotated_rect = minAreaRect(ployPoints);
而python中是这样的,其中segmentation是这样的:[x1, y1, x2, y2, x3, y3, x4, y4]
:
segmentation = segmentation.reshape([-1, 2])
rect1 = cv2.minAreaRect(segmentation)
x, y, w, h, theta = rect1[0][0], rect1[0][1], rect1[1][0], rect1[1][1], rect1[2]
举个实际的例子:
# [x1, y1, x2, y2, x3, y3, x4, y4]
ployPoints = np.array([283.30, 72.65, 309.21, 72.90, 309.07, 87.79, 283.16, 87.54])
ployPoints = ployPoints.reshape([-1, 2]).astype(np.int32)
print(ployPoints)
rect1 = cv2.minAreaRect(ployPoints)
x, y, w, h, theta = rect1[0][0], rect1[0][1], rect1[1][0], rect1[1][1], rect1[2]
print(x,y,w,h,theta)
#
[[283 72]
[309 72]
[309 87]
[283 87]]
296.0 79.5 15.0 26.0 90.0
需要注意一点,看下图那就是这个角度是按照第一个找到的边做width,这个width可能是长边可能也不是!这点需要注意,是个坑!
发一下OpenCV-C++源码对RotatedRect的表述:
class CV_EXPORTS RotatedRect
{
public:
//! various constructors
RotatedRect();
RotatedRect(const Point2f& center, const Size2f& size, float angle);
RotatedRect(const CvBox2D& box);
//! returns 4 vertices of the rectangle
void points(Point2f pts[]) const;
//! returns the minimal up-right rectangle containing the rotated rectangle
Rect boundingRect() const;
//! conversion to the old-style CvBox2D structure
operator CvBox2D() const;
Point2f center; //< the rectangle mass center
Size2f size; //< width and height of the rectangle
float angle; //< the rotation angle. When the angle is 0, 90, 180, 270 etc., the rectangle becomes an up-right rectangle.
};