我是 OpenCV 新手。 我有一个“简单”的邮票图像,我已经对其进行了一些处理,如下面的代码所示。 现在我遇到了裁剪图像以获得印章的问题。 边缘上的点和条纹会干扰我当前识别邮票的代码。 图像可能不同,因此无法修复图像的位置。
代码:
img = cv2.imread('./images/image.JPG')
img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
img_blur = cv2.GaussianBlur(img_gray, (3,3), 0)
edges = cv2.Canny(image=img_blur, threshold1=100, threshold2=200)
最佳答案
这是一个简单的方法:
获取二值图像。我们加载图像,转换为灰度、高斯模糊,然后进行 Otsu 阈值以获得二值图像。
消除小瑕疵和噪音。创建一个矩形结构元素并变形打开以消除小噪音。然后假设印章是单个轮廓,将各个轮廓合并为单个轮廓。
检测并提取印章 ROI。查找轮廓,使用轮廓区域和形状近似进行过滤。这个想法是,如果轮廓有四个顶点,那么它就是正方形。我们可以使用 Numpy 切片提取图章 ROI 并保存图章
提取的 ROI 结果
这是评论中另外两个输入图像的结果。假设对于每个图像,只有一个图章或一组相邻的图章。对于这些情况,我们按轮廓区域排序并假设最大的轮廓是印章。
代码
import cv2
# Load image, grayscale, Gaussian blur, Otsu's threshold
image = cv2.imread("1.jpg")
original = image.copy()
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
blur = cv2.GaussianBlur(gray, (5,5), 0)
thresh = cv2.threshold(blur, 0, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)[1]
# Morph operations to remove small artifacts and noise
open_kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3,3))
opening = cv2.morphologyEx(thresh, cv2.MORPH_OPEN, open_kernel, iterations=1)
close_kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (7,7))
close = cv2.morphologyEx(opening, cv2.MORPH_CLOSE, close_kernel, iterations=2)
# Find contours, filter using contour area, and shape approximation
cnts = cv2.findContours(close, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cnts = cnts[0] if len(cnts) == 2 else cnts[1]
cnts = sorted(cnts, key=cv2.contourArea, reverse=True)
for c in cnts:
peri = cv2.arcLength(c, True)
area = cv2.contourArea(c)
approx = cv2.approxPolyDP(c, 0.05 * peri, True)
# Assumption is if the contour has 4 vertices then its a square shape
# 2nd assumption is that there's only one stamp, or one group of stamps
if len(approx) == 4 and area > 100:
x,y,w,h = cv2.boundingRect(approx)
ROI = original[y:y+h, x:x+w]
cv2.imshow("ROI", ROI)
cv2.imwrite("ROI.png", ROI)
break
cv2.waitKey()
关于python - 如何使用 OpenCV 从图像中裁剪和提取图章?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/72020710/