《OpenCV3编程入门》学习笔记8 图像轮廓与图像分割修复(三)使用多边形将轮廓包围
8.3 使用多边形将轮廓包围
8.3.1 将轮廓包围的多边形函数
1.返回外部边界:boundingRect()函数
(1)作用:返回指定点集最外面的边界矩形(四个顶点)
(2)函数原型:Rect boundingRect(InputArray points)
2.寻找最小包围矩形:minAreaRect()函数
(1)作用:返回指定点集可旋转的最小面积的包围矩形(四个顶点)
(2)函数原型:RotatedRect minAreaRect(InputArray points)
3.寻找最小包围圆形:minEnclosingCircle()函数
(1)作用:利用一种迭代算法,返回指定点集的最小面积的包围圆形(圆心,半径)
(2)函数原型:void minEnclosingCircle(InputArray points, Point2f& center, float& radius)
(3)参数说明:输入二维点集,输出圆心,输出半径
4.用椭圆拟合二维点集:fitEllipse()函数
(1)作用:椭圆拟合二维点集
(2)函数原型:RotatedRect fitEllipse(InputArray points)
5.逼近多边形曲线:approxPolyDP()函数
(1)作用:用指定精度逼近多边形曲线
(2)函数原型:void approxPolyDP(InputArray curve, OutputArray approxCurve, double epsilon, bool closed)
(3)参数说明:
1)输入的二维点集
2)多边形逼近的结果
3)逼近的精度,为原始曲线和近似曲线间的最大值
4)取真时,近似的曲线为封闭曲线,取假时不封闭
8.3.2 综合示例
1.随机生成彩色点,调用多边形包围函数
#include<opencv2/opencv.hpp>
#include<opencv2/imgproc/imgproc.hpp>
#include<opencv2/highgui/highgui.hpp>
using namespace cv;
using namespace std;int main()
{//初始化变量和随机值Mat image(600, 600, CV_8UC3);Mat dstImage1, dstImage2, dstImage3, dstImage4;RNG& rng = theRNG();//循环,按下ESC键程序退出,否则一直更新while (1){//参数初始化int count = rng.uniform(3, 103);//随机生成点的数量vector<Point> points;//点值//随机生成点坐标for (int i = 0; i < count; i++){Point point;point.x = rng.uniform(image.rows / 4, image.rows * 3 / 4);point.y = rng.uniform(image.cols / 4, image.cols * 3 / 4);points.push_back(point);}//绘制出随机颜色的点image = Scalar::all(0);for (int i = 0; i < count; i++){circle(image, points[i], 3, Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)), FILLED, LINE_AA);}//【1】对指定点集寻找边界矩形Rect rect = boundingRect(Mat(points));//绘制边界矩形image.copyTo(dstImage1);rectangle(dstImage1, rect, Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)), 2, LINE_AA);//显示窗口imshow("【1】边界矩形窗口", dstImage1);//【2】对指定点集寻找最小面积的包围矩形RotatedRect box1 = minAreaRect(Mat(points));Point2f vertex2[4];box1.points(vertex2);//绘制最小面积的包围矩形image.copyTo(dstImage2);for (int i = 0; i < 4; i++){line(dstImage2, vertex2[i], vertex2[(i + 1) % 4], Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)), 2, LINE_AA);}//显示窗口imshow("【2】最小面积包围矩形窗口", dstImage2);//【3】对指定点集寻找最小面积的包围圆形Point2f center;float radius;minEnclosingCircle(Mat(points),center,radius);//绘制最小面积的圆形image.copyTo(dstImage3);circle(dstImage3, center, cvRound(radius), Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)), 2, LINE_AA);//显示窗口imshow("【3】最小面积包围圆形窗口",dstImage3);//【4】椭圆拟合指定点集RotatedRect box2 = fitEllipse(Mat(points));//绘制椭圆image.copyTo(dstImage4);ellipse(dstImage4, box2, Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255)), 2, LINE_AA);//显示窗口imshow("【4】椭圆形拟合窗口", dstImage4);char key = (char)waitKey();if(key == 27) break; }return 0;
}
运行效果:
2.载入图像,调用多边形包围函数
#include<opencv2/opencv.hpp>
#include<opencv2/highgui/highgui.hpp>
#include<opencv2/imgproc/imgproc.hpp>
using namespace cv;
using namespace std;
//定义辅助宏
#define WINDOW_NAME1 "【原始图窗口】"
#define WINDOW_NAME2 "【效果图窗口】"
//全局变量
Mat g_srcImage, g_grayImage;
int g_nThresh = 50;//阈值
int g_nMaxThresh = 255;//阈值最大值
RNG g_rng(12345);//随机数生成器
//全局函数
void on_ContoursChange(int, void*);int main()
{ //【1】载入原图g_srcImage = imread("Google.jpg");if (!g_srcImage.data){printf("载入原图失败~!\n");return false;}//【2】创建原始图窗口并显示namedWindow(WINDOW_NAME1,WINDOW_AUTOSIZE);imshow(WINDOW_NAME1, g_srcImage);//【3】得到原图的灰度图像并进行平滑cvtColor(g_srcImage, g_grayImage, COLOR_BGR2GRAY);blur(g_grayImage, g_grayImage, Size(3, 3));//【4】设置滚动条并调用一次回调函数createTrackbar("阈值:", WINDOW_NAME1, &g_nThresh, g_nMaxThresh, on_ContoursChange);on_ContoursChange(0, 0);waitKey(0);return 0;
}
void on_ContoursChange(int, void*)
{//定义一些参数Mat threshold_output;vector<vector<Point>> contours;vector<Vec4i> hierarchy;//使用Threshold检测边缘threshold(g_grayImage, threshold_output, g_nThresh, 255, THRESH_BINARY);//找出轮廓findContours(threshold_output, contours, hierarchy, RETR_TREE, CHAIN_APPROX_SIMPLE, Point(0, 0));//多边形逼近轮廓+获取矩形和圆形边界框vector<vector<Point>> contours_poly(contours.size());vector<Rect> boundRect(contours.size());vector<Point2f> center(contours.size());vector<float> radius(contours.size());//一个循环,遍历所有部分,进行本程序最核心的操作for (int i = 0; i < contours.size(); i++){approxPolyDP(Mat(contours[i]), contours_poly[i], 3, true);//用指定精度逼近多边形曲线boundRect[i] = boundingRect(Mat(contours_poly[i]));//计算点集的最外面矩形边界minEnclosingCircle(contours_poly[i], center[i], radius[i]);//对给定点集寻找最小面积的包围圆形}//绘制多边形轮廓+包围的矩形框+圆形框Mat dstImage = Mat::zeros(threshold_output.size(), CV_8UC3);for (int i = 0; i < contours.size(); i++){Scalar color = Scalar(g_rng.uniform(0, 255), g_rng.uniform(0, 255), g_rng.uniform(0, 255));//随即设置颜色drawContours(dstImage, contours_poly, i, color, 1, 8, vector<Vec4i>(), 0, Point());//绘制轮廓rectangle(dstImage, boundRect[i].tl(), boundRect[i].br(), color, 2, 8, 0);//绘制矩形circle(dstImage, center[i], (int)radius[i], color, 2, 8, 0);}//显示效果图窗口namedWindow(WINDOW_NAME2,WINDOW_AUTOSIZE);imshow(WINDOW_NAME2, dstImage);
}
运行效果:
《OpenCV3编程入门》学习笔记8 图像轮廓与图像分割修复(三)使用多边形将轮廓包围相关推荐
- 原创 OpenCV3编程入门 学习笔记(总)
版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明. 本文链接:https://blog.csdn.net/qq_36163358/article/ ...
- OpenCV3编程入门 学习笔记(总)
OpenCV3编程入门 学习笔记 2018.12.12-2018.12.29 此博客为在看过毛星云版<OpenCV3编程入门>后所总结的一本笔记,可供复习使用. 文章目录 OpenCV3编 ...
- Opencv3编程入门学习笔记(五)之通道分离(split)与合并(merge)
若要对Opencv中(BGR)颜色通道进行单一处理,那必然会涉及到通道分离(split)与合并(merge).那么本篇博客笔者记录了两个方法的使用方法和案例.案例来源于<Opencv3编程入门学 ...
- Opencv3编程入门学习笔记(三)之访问图像像素的三种方法
访问图像像素的三种方法:指针访问,迭代器访问,动态地址访问.访问最快的为指针访问,以下算法在几毫秒,但指针访问容易造成内存泄漏:其次为迭代器访问:最后为动态地址访问. 以下程序是根据<OpenC ...
- 【OpenCV3编程入门学习笔记】——第1章 邂逅OpenCV
邂逅OpenCV 文章目录 邂逅OpenCV 前言 1.1 OpenCV周边概念认知 1.1.1 图像处理.计算机视觉与OpenCV 1.1.2 OpenCV概述 1.1.3 起源及发展 1.1.4 ...
- 【OpenCV3编程入门学习笔记】——第3章 HighGUI图形用户界面初步
文章目录 前言 3.1 图形的载入.显示和输出到文件 3.1.1 OpenCV的命名空间 3.1.2 Mat类简析 3.1.3 图像的载入与显示概述 3.1.4 图像的载入:imread()函数 3. ...
- Opencv3编程入门学习笔记(四)之split通道分离Debug过程中0xC0000005内存访问冲突问题
这是笔者学习<Opencv3编程入门>的第四篇博客,这篇博客主要是解决在Windows系统下VS 2013中Debug含有split分离通道色彩函数时报出的0xC0000005内存访问冲突 ...
- Opencv3编程入门学习笔记(二)之显式创建Mat对象
以下总结是基于<Opencv3编程入门>一书4.1节总结的内容进行验证与总结,验证环境均为Windows10 ---VS2013 C++环境,验证Opencv3.0提供的开发包. 1. 方 ...
- 01.Java 编程入门学习笔记20210307
Java 编程入门学习笔记-day01 第0章:编程入门 1.计算机的概述 计算机 = 硬件 + 软件 1.1硬件:冯诺依曼体系 CPU: CPU的衡量标准:速度的计量单位是赫兹(Hz),1Hz相当于 ...
- Python快速编程入门#学习笔记01# |第一章 :Python基础知识 (Python发展历程、常见的开发工具、import模块导入)
全文目录 ==先导知识== 1 认识Python 1.1.1 Python的发展历程 1.1.2 Python语言的特点 2. Python解释器的安装与Python程序运行 1.2.1 安装Pyth ...
最新文章
- flask源码学习-helloworld与本地启动流程
- Python实例浅谈之五Python守护进程和脚本单例运行
- jradiobutton设置默认选项_JRadioButton(单选按钮)添加事件监听
- leetcode 497, 528. Random Point in Non-overlapping Rectangles | 497. 非重叠矩形中的随机点(Java)
- 记录一个相当好用的反编译工具下载地址
- 苹果CMS10 资源网模板
- php flush 逐行显示_PHP逐行输出(ob_flush与flush的组合)
- clock函数,计算程序运行时间
- GPCP全球月降水量数据下载与读取
- 旅行商问题(TSP) 中国34个城市 经纬度平面坐标
- PDF转HTML常用方法分享
- 网络神偷 v7.6 免费
- 备份手机相册----syncthing (一劳永逸式解决方案)
- 电脑扬声器耳机已拔出
- 计算机网络存在的漏洞,常见的计算机网络安全漏洞有哪些
- 跨域请求传递Cookie
- xnio-nio解决方法
- TCP/IP 协议详解内容总结
- 酒醉之后你最思念谁?
- java学习日记-接口