API:
功能:近似于曲线的或与另一曲线/多边形的多边形用更少的顶点,使得它们之间的距离是小于或等于指定的精度
approxCurve=cv.approxPolyDP(curve, epsilon, closed[, approxCurve])
矩形:
BoundingRect是说,用一个最小的矩形,把找到的形状包起来。还有一个带旋转的矩形,面积会更小
minAreaRect函数返回矩形的中心点坐标,长宽,旋转角度[-90,0),当矩形水平或竖直时均返回-90
圆:
#include
#include
#include
using namespace std;
using namespace cv;
Mat src, gray_src, dst;
const char* output_title = "绘制结果";
const char* gray_title = "灰度图像";
int threshold_value = 50;
int threshold_max = 255;
void threshold_Demo(int, void*);
//在轮廓周围绘制矩形和圆形
int main(int argc, char ** argv)
{
src = imread("E://VS-pro//images//text.bmp");
if (!src.data)
{
printf("can not find .. \n");
return -1;
}
imshow("原图", src);
//变灰度
cvtColor(src, gray_src, COLOR_BGR2GRAY);
blur(gray_src, gray_src, Size(3, 3), Point(-1, -1));
imshow(gray_title, gray_src);
createTrackbar("threshold value: ", gray_title, &threshold_value, threshold_max, threshold_Demo);
threshold_Demo(0, 0);
waitKey(0);
return 0;
}
void threshold_Demo(int, void*)
{
Mat bin_src;
//转换为二值图像
threshold(gray_src, bin_src, threshold_value, threshold_max, THRESH_BINARY);
imshow("二值图像", bin_src);
vector> contours; //放轮廓点
vector hierachy; //图像的拓扑结构
//找轮廓
findContours(bin_src, contours, hierachy, RETR_TREE, CHAIN_APPROX_SIMPLE, Point(-1, -1));
//根据轮廓点找最小矩形和圆
vector> contours_ploy(contours.size()); //存放绘制矩形的点
vector ploy_rects(contours.size());
vector ccs(contours.size());//放圆心
vector radius(contours.size()); //放半径
vector minRects(contours.size());
vector myellipse(contours.size());
for (size_t i = 0; i < contours.size(); i++)
{
approxPolyDP(Mat(contours[i]), contours_ploy[i], 3, true); //减少多边形轮廓点数
ploy_rects[i] = boundingRect(contours_ploy[i]); //取矩形
minEnclosingCircle(contours_ploy[i], ccs[i], radius[i]);//圆
//另一种方法
if (contours_ploy[i].size() > 5) {
myellipse[i] = fitEllipse(contours_ploy[i]);
minRects[i] = minAreaRect(contours_ploy[i]);
}
}
//绘制
Mat drawImg;
RNG rng(12345);
// draw it
drawImg = Mat::zeros(src.size(), src.type());
Point2f pts[4];
for (size_t t = 0; t < contours.size(); t++) {
Scalar color = Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255));
//rectangle(drawImg, ploy_rects[t], color, 2, 8);
//circle(drawImg, ccs[t], radius[t], color, 2, 8);
if (contours_ploy[t].size() > 5) {
ellipse(drawImg, myellipse[t], color, 1, 8);//画圆
minRects[t].points(pts);
for (int r = 0; r < 4; r++) {
line(drawImg, pts[r], pts[(r + 1) % 4], color, 1, 8);//画矩形四条边
}
}
}
imshow(output_title, drawImg);
}