主要用到以下三个API
cv.Scharr,cv.findContours,cv.subtract
import cv2 as cv
import numpy as np
import os
import shutil
import time
讲一下大概的思路:
先检测外轮廓,然后填充,与原图相减就可以得到roi,然后在进行roi后续的处理
#global show22
def kifsk(src):
grad_x = cv.Scharr(src, cv.CV_32F, 1, 0) # 增强版(Sobel)图像
grad_y = cv.Scharr(src, cv.CV_32F, 0, 1)
gradx = cv.convertScaleAbs(grad_x) # 转变
grady = cv.convertScaleAbs(grad_y)
gradxy = cv.addWeighted(gradx, 1, grady, 2, 0)
#cv.imshow(“gradient”, gradxy)
gradxy = cv.blur(gradxy, (3, 3))
gradxy = cv.blur(gradxy, (3, 3))
gradxy = cv.GaussianBlur(gradxy, (7, 7), 0)
gradxy = cv.blur(gradxy, (3, 3))
gradxy = cv.cvtColor(gradxy, cv.COLOR_BGR2GRAY)
ret, binary = cv.threshold(gradxy, 0, 255, cv.THRESH_BINARY | cv.THRESH_OTSU)
binary = cv.GaussianBlur(binary, (7, 7), 0)
binary = cv.blur(binary, (3, 3))
#cv.imshow("binary image", binary)
kernel = cv.getStructuringElement(cv.MORPH_RECT, (40, 40))
binary1 = cv.morphologyEx(binary, cv.MORPH_CLOSE, kernel)
binary2 = cv.morphologyEx(binary, cv.MORPH_CLOSE, kernel)
#cv.imshow("close_op", binary1)
cloneImage, contours, heriachy = cv.findContours(binary2, cv.RETR_EXTERNAL, cv.CHAIN_APPROX_NONE)
area = []
are = 0
for j,i in enumerate (range(len(contours))):
are = cv.contourArea(contours[i])
area.append(are)
i = area.index(max(area))
contour =max(area)
dst333=cv.drawContours(src, contours, i, (0, 0, 255), 2)
cv.imshow('dst',dst333)
detyyy=dst333
return detyyy
def sobel_demo(src,detyyy111):
grad_x222 = cv.Scharr(src, cv.CV_32F, 1, 0) # 增强版(Sobel)图像
grad_y222 = cv.Scharr(src, cv.CV_32F, 0, 1)
gradx222 = cv.convertScaleAbs(grad_x222) # 转变
grady222 = cv.convertScaleAbs(grad_y222)
gradxy222 = cv.addWeighted(gradx222, 1, grady222, 2, 0)
#cv.imshow(“gradient”, gradxy)
gradxy222 = cv.blur(gradxy222, (3, 3))
gradxy222 = cv.blur(gradxy222, (3, 3))
gradxy222= cv.GaussianBlur(gradxy222,(7,7),0)
gradxy222 = cv.blur(gradxy222, (3, 3))
gradxy222 = cv.cvtColor(gradxy222, cv.COLOR_BGR2GRAY)
ret, binary222 = cv.threshold(gradxy222, 0, 255, cv.THRESH_BINARY | cv.THRESH_OTSU)
binary222 = cv.GaussianBlur(binary222, (7, 7), 0)
binary222 = cv.blur(binary222, (3, 3))
#cv.imshow("binary image", binary)
kernel222 = cv.getStructuringElement(cv.MORPH_RECT, (40, 40))
binary222 = cv.morphologyEx(binary222, cv.MORPH_CLOSE, kernel222)
# 需要检测的轮廓预处理
cloneImage, contours222, heriachy = cv.findContours(binary222, cv.RETR_EXTERNAL, cv.CHAIN_APPROX_NONE)
area222 = []
are1222 = 0
for j,i in enumerate (range(len(contours222))):
are1222 = cv.contourArea(contours222[i])
area222.append(are1222)
i = area222.index(max(area222))
contour222 =max(area222)
dst222=cv.drawContours(src, contours222, i, (255, 255, 255), cv.FILLED) # 3通道
#cv.imshow('filled_con',dst222)
dst1 = cv.subtract(dst222, src2)
#mask_inv = cv.bitwise_not(dst1) # 暂时不需要反转
#cv.imshow("subtract_demo", dst1)
gray=cv.cvtColor(dst1,cv.COLOR_BGR2GRAY)
ret,ser=cv.threshold(gray,170,255,cv.THRESH_BINARY)
#cv.imshow('saw',ser)
cloneIm, contours1, heriachy23 = cv.findContours(ser, cv.RETR_CCOMP, cv.CHAIN_APPROX_SIMPLE)
for i, conto in enumerate(contours1):
show22 = cv.drawContours(detyyy111, contours1, i, (0, 0, 255), 2)
#print(show22.shape[2])
#result
#cv.imshow("show22",show22) #3通道
return contours1
# area222=[]
# are111=0
# for i in range(len(contours1)):
# asda=cv.contourArea(contours1[i])
# area222.append(asda)
# print(area222)
# var_jian=[]
# for i in area222:
# if i <100000 and i >15:
# var_jian.append(i)
# shutil.move(os.path.join(path,file),'E:/cv_youwujiance_1_2000_ret/')
# time.sleep(0.1)
# print(var_jian)
src1 = cv.imread(“D:/opencv-yxd-code/opencv/os/1.tif”)
src = cv.resize(src1,(0,0),fx=0.3,fy=0.3)
src2 = cv.resize(src1,(0,0),fx=0.3,fy=0.3)
detyyy = kifsk(src2) #检测的外轮廓
#contours1=sobel_demo(src,detyyy) # 检测内部污点
#area222=[]
# are111=0
# for i in range(len(contours1)):
# asda=cv.contourArea(contours1[i])
# area222.append(asda)
# print(area222)
# var_jian=[]
# for i in area222:
# if i <100000 and i >15:
# var_jian.append(i)
# shutil.move(os.path.join(path,file),'E:/cv_youwujiance_1_2000_ret/')
# time.sleep(1)
# print(var_jian)
cv.waitKey()
cv.destroyAllWindows()