轮廓是什么
- 边缘检测能够测出边缘,但是边缘是不连续的,将边缘连接为一个整体,构成轮廓
注意事项
- 对象是二值图像。所以需要预先进行阈值分割或者边缘检测处理。
- 查找轮廓需要更改原始图像。因此,通常使用原始图像的一份拷贝操作。
- 在OpenCV中,是从黑色背景中查找白色图像。因此,对象必须是白色的,背景必须是黑色的。
使用函数
- 查找图像轮廓的函数 cv2.findContours()
- 函数 :
contours, hierarchy = cv2.findContours(image, mode, method)
- 参数
- image : 原始图像
- mode : 轮廓检索模式
- cv2.RETR_EXTERNAL : 表示只检测外轮廓
- cv2.RETR_LIST : 测试的轮廓不建立等级关系
- cv2.RETR_CCOMP : 建立两个等级的轮廓,上面的一层为外边界,里面一层为內孔的边界信息。如果内孔内还有一个连通物,这个物体的边界也在顶层
- cv2.RETR_TREE : 建立一个等级树结构的轮廓
- method : 轮廓的近似方法
- cv2.CHAIN_APPROX_NONE : 存储所有的轮廓殿,相邻的两个点的像素位置差不超过1,即 m a x ( a b s ( x 1 − x 2 ) , a b s ( y 2 − y 1 ) ) = = 1 max(abs(x1-x2), abs(y2-y1))==1 max(abs(x1−x2),abs(y2−y1))==1
- cv2.CHAIN_APPROX_SIMPLE : 压缩水平方向,垂直方向,对角线方向的元素,只保留该方向的终点坐标,例如一个矩形轮廓只需4个点来保存轮廓信息
- cv2.CHAIN_APPROX_TC89_L1 : 使用teh-Chinl chain近似算法
- cv2.CHAIN_APPROX_TC89_KCOS : 使用teh-Chinl chain近似算法
- 返回值
- contours : 轮廓
- hierarchy : 图像的拓扑信息(轮廓层次)
- 查找到的轮廓绘制到图像上 cv2.drawContours()
- 函数 :
r = cv2.drawContours(o, contours, contoursIdx, color[, thickness])
- 参数 :
- o : 原始图像
- contours : 需要绘制的边缘数组
- contoursIdx : 需要绘制的边缘索引,如果全部绘制则为 -1.
- color : 绘制的颜色,为BGR格式的Scalar
- thickness : 可选,绘制的密度,即绘制轮廓时所用的画笔粗细
- 返回值 :
实例
import cv2
o = cv2.imread("/home/forrest/图片/lena彩图.png")
cv2.imshow("original", o)
co = o.copy()
gray = cv2.cvtColor(co, cv2.COLOR_BGR2GRAY)
ret,binary = cv2.threshold(gray, 127, 255, cv2.THRESH_BINARY)
contours, hierachy = cv2.findContours(binary, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
r = cv2.drawContours(co, contours, -1, (0, 0, 0), 1)
co
cv2.imshow("result", r)
cv2.waitKey()
cv2.destroyAllWindows()
- 原始图像
- 绘制轮廓