轮廓发现findContours与轮廓绘制drawContours
/**
* 轮廓发现findContours
* findContours(
* Mat image, --输入图像,可以是灰度图,但更常用的是二值图像,一般是经过Canny、拉普拉斯等边缘检测算子处理过的二值图像;
* List<MatOfPoint> contours, --输出轮廓集合
* Mat hierarchy, --hiararchy向量内的元素和轮廓向量contours内的元素是一一对应的,向量的容量相同。
* int mode, --定义轮廓的检索模式:
* CV_RETR_EXTERNAL只检测最外围轮廓,包含在外围轮廓内的内围轮廓被忽略
* CV_RETR_LIST 检测所有的轮廓,包括内围、外围轮廓,但是检测到的轮廓不建立等级关
* 系,彼此之间独立,没有等级关系,这就意味着这个检索模式下不存在父轮廓或内嵌轮廓,
* 所以hierarchy向量内所有元素的第3、第4个分量都会被置为-1
* CV_RETR_CCOMP 检测所有的轮廓,但所有轮廓只建立两个等级关系,外围为顶层,若外围
* 内的内围轮廓还包含了其他的轮廓信息,则内围内的所有轮廓均归属于顶层
* CV_RETR_TREE 检测所有轮廓,所有轮廓建立一个等级树结构。外层轮廓包含内层轮廓,内
* 层轮廓还可以继续包含内嵌轮廓
* int method,
* Point offset=Point()
* );
*
* 轮廓绘制
* drawContours
* (
* Mat image, --目标图像
* List<MatOfPoint> contours, --输入的所有轮廓(每个轮廓以点集的方式存储)
* int contourIdx, --指定绘制轮廓的下标(若为负数,则绘制所有轮廓)
* Scalar, --绘制轮廓的颜色
* int thickness = 1, --绘制轮廓的线的宽度(若为负数,则填充轮廓内部)
* int lineType = LINE_8, --绘制轮廓的线型(4连通、8连通或者反锯齿)
* Mat hierarchy = noArray(), --关于层级的可选信息,仅用于当你想要绘制部分轮廓的时候
* int maxLevel = INT_MAX, --绘制轮廓的最大层级,若为0,则仅仅绘制指定的轮廓;若为1,则绘制该轮廓及其内嵌轮廓,
* 若为2,则绘制该轮廓、其内嵌轮廓以及内嵌轮廓的内嵌轮廓,依次类推。该参数只有在有层级信息输入时才被考虑。
* Point offset = Point(-1, -1) --可选的轮廓偏移参数,所有的轮廓将会进行指定的偏移
* )
*/
@Test
public void testContours() {
Mat src = GeneralUtils.converMat("C:\\图片\\test\\0001.jpg");
//去噪声与二值化
Mat gray = new Mat();
Mat binary = new Mat();
Imgproc.cvtColor(src, gray, Imgproc.COLOR_BGR2GRAY);
Imgproc.threshold(gray, binary, 0, 255, Imgproc.THRESH_BINARY | Imgproc.THRESH_OTSU);
//寻找轮廓
List<MatOfPoint> contours = new ArrayList<>();
Mat hierarchy = new Mat();
Imgproc.findContours(binary, contours, hierarchy, Imgproc.RETR_TREE, Imgproc.CHAIN_APPROX_SIMPLE, new Point(-1, -1));
//绘制轮廓
for (int i = 0; i < contours.size(); i++) {
Imgproc.drawContours(src, contours, i, new Scalar(0, 0, 255));
}
GeneralUtils.saveByteImg(src, "C:\\图片\\test\\findContours.jpg");
}
《中医基础理论》