赞
踩
opencv 这个效果差一点
- import cv2
- import numpy as np
- import os
- import time
-
- GAUSSIAN_BLUR_KERNEL_SIZE=(5,5)
- GAUSSIAN_BLUR_SIGMA_X=0
- CANNY_THRESHOLD1=60
- CANNY_THRESHOLD2=250
- LEEXING=4
-
- def get_gaussian_blur_image(image):
- return cv2.GaussianBlur(image,GAUSSIAN_BLUR_KERNEL_SIZE,GAUSSIAN_BLUR_SIGMA_X)
-
- def get_canny_image(image):
- return cv2.Canny(image,CANNY_THRESHOLD1,CANNY_THRESHOLD2)
-
- def get_contours(image):
- contours,_=cv2.findContours(image,cv2.RETR_CCOMP,cv2.CHAIN_APPROX_SIMPLE)
- return contours
-
- def lp(imgsss):
- img1=cv2.imread(imgsss,0)
- x1=cv2.Sobel(img1,cv2.CV_16S,1,0,ksize=-1)
- y1=cv2.Sobel(img1,cv2.CV_16S,0,1,ksize=-1)
- Scale_absX1=cv2.convertScaleAbs(x1)
- Scale_absY1=cv2.convertScaleAbs(y1)
- result1=cv2.addWeighted(Scale_absX1,0.5,Scale_absY1,0.5,0)
- return result1
-
- def ceshi1(imgsss):
- image_raw = cv2.imread(imgsss)
- h, w, _ = image_raw.shape
- mianji_MIN1 = 15000
- mianji_MAX1 = 40000
- zhouchang_min = 80
- zhouchang_max = 1800
-
- offset_min = 0.5 * image_raw.shape[1]
- offset_max = 0.95 * image_raw.shape[1]
-
-
- result1 = lp(imgsss)
- # 高斯去噪
- result2 = get_gaussian_blur_image(result1)
- # 均值
- result3 = cv2.blur(result2, (3, 3))
- # 提取輪廓
- image_canny = get_canny_image(result3)
-
- # 膨脹
- kernel = np.ones((3, 3), np.uint8)
- dige_dilate1 = cv2.dilate(image_canny, kernel, iterations=1)
- # 中值
- median = cv2.medianBlur(dige_dilate1, 5)
-
- contours = get_contours(median)
-
- image = cv2.imread(imgsss)
- contour = image.copy()
- cv2.drawContours(contour, contours, -1, (0, 255, 0), 2)
- count = 0 # 个数
- margin = 5 # 裁剪边距
- draw_rect = image.copy()
- for i, contour in enumerate(contours):
- area = cv2.contourArea(contour) # 计算包围形状的面积
- zhouchang = cv2.arcLength(contour, True)
- x2, y2, w2, h2 = cv2.boundingRect(contour)
- if area < mianji_MIN1: # 过滤面积小于15的形状
- continue
- if area > mianji_MAX1: # 过滤面积小于15的形状
- continue
- if zhouchang < zhouchang_min:
- continue
- if zhouchang > zhouchang_max:
- continue
- if x2 < offset_min:
- continue
- if x2 > offset_max:
- continue
-
- print('面積:', area, '周長:', zhouchang)
- count += 1
- rect = cv2.minAreaRect(contour) # 检测轮廓最小外接矩形,得到最小外接矩形的(中心(x,y), (宽,高), 旋转角度)
- box = np.int0(cv2.boxPoints(rect)) # 获取最小外接矩形的4个顶点坐标
- print(box)
- txt11=txt1(q=box,width=w,height=h)
- txt22=str(LEEXING)+' '+str(txt11[0])+' '+str(txt11[1])+' '+str(txt11[2])+' '+str(txt11[3])
- print(txt22)
-
- cv2.drawContours(draw_rect, [box], 0, (0, 0, 255), 2) # 绘制轮廓最小外接矩形
-
- h, w = image.shape[:2] # 原图像的高和宽
- rect_w, rect_h = int(rect[1][0]) + 1, int(rect[1][1]) + 1 # 最小外接矩形的宽和高
- if rect_w <= rect_h:
- x, y = int(box[1][0]), int(box[1][1]) # 旋转中心
- M2 = cv2.getRotationMatrix2D((x, y), rect[2], 1)
- rotated_image = cv2.warpAffine(image, M2, (w * 2, h * 2))
- y1, y2 = y - margin if y - margin > 0 else 0, y + rect_h + margin + 1
- x1, x2 = x - margin if x - margin > 0 else 0, x + rect_w + margin + 1
- rotated_canvas = rotated_image[y1: y2, x1: x2]
- else:
- x, y = int(box[2][0]), int(box[2][1]) # 旋转中心
- M2 = cv2.getRotationMatrix2D((x, y), rect[2] + 90, 1)
- rotated_image = cv2.warpAffine(image, M2, (w * 2, h * 2))
- y1, y2 = y - margin if y - margin > 0 else 0, y + rect_w + margin + 1
- x1, x2 = x - margin if x - margin > 0 else 0, x + rect_h + margin + 1
- rotated_canvas = rotated_image[y1: y2, x1: x2]
- print("rice #{}".format(count))
- # cv2.imshow("rotated_canvas", rotated_canvas)
- imgs = imgsss.split('\\')
- cv2.imwrite("./imgs/{}.jpg".format(imgs[-1]+str(count)), rotated_canvas)
- with open("./imgs/{}.txt".format(imgs[-1]+str(count)), 'w') as fp:
- fp.write(txt22)
- cv2.waitKey(0)
- cv2.imwrite("rect.jpg", draw_rect)
-
- def wenjian(path1):
- df_list=[]
- list212=os.listdir(path1)
- for i in list212:
- file_path=os.path.join(path1,i)
- df_list.append(file_path)
- return df_list
-
- def txt1(q,width,height):
- x1=q[1][0]
- x2=q[3][0]
- y1=q[1][1]
- y2=q[3][1]
- xmin_xishu, xmax_xishu =x1 / width, x2 / width
- ymin_xishu, ymax_xishu= y1 / height ,y2 / height
- width2=xmax_xishu-xmin_xishu
- height2=ymax_xishu-ymin_xishu
- x_centr_shu=xmin_xishu+width2/2
- y_centr_shu=ymin_xishu+height2/2
- return round(x_centr_shu, 6),round(y_centr_shu, 6),round(width2, 6),round(height2, 6)
-
- if __name__ == '__main__':
- a=time.time()
- path1 = r'E:\0908\1WVE' # 路径
- list1=wenjian(path1)
- for i in list1:
- ceshi1(i)
- b=time.time()
- c=b-a
- print(c)
这个效果可以
- import cv2
- import numpy as np
- import os
- import time
-
- GAUSSIAN_BLUR_KERNEL_SIZE=(5,5)
- GAUSSIAN_BLUR_SIGMA_X=0
- CANNY_THRESHOLD1=120
- CANNY_THRESHOLD2=250
- LEEXING=12 #要识别的类
-
- def get_gaussian_blur_image(image): #高斯去噪
- return cv2.GaussianBlur(image,GAUSSIAN_BLUR_KERNEL_SIZE,GAUSSIAN_BLUR_SIGMA_X)
-
- def get_canny_image(image): #找轮廓
- return cv2.Canny(image,CANNY_THRESHOLD1,CANNY_THRESHOLD2)
-
- def get_contours(image): #导出轮廓参数
- contours,_=cv2.findContours(image,cv2.RETR_CCOMP,cv2.CHAIN_APPROX_SIMPLE)
- return contours
-
- def lp(imgsss): #算轮廓
- img1=cv2.imread(imgsss,0)
- x1=cv2.Sobel(img1,cv2.CV_16S,1,0,ksize=-1)
- y1=cv2.Sobel(img1,cv2.CV_16S,0,1,ksize=-1)
- Scale_absX1=cv2.convertScaleAbs(x1)
- Scale_absY1=cv2.convertScaleAbs(y1)
- result1=cv2.addWeighted(Scale_absX1,0.5,Scale_absY1,0.5,0)
- return result1
-
- def ceshi1(imgsss):
- image_raw = cv2.imread(imgsss)
- h, w, _ = image_raw.shape
-
- mianji_MIN1 = 700000 #最小面积
- mianji_MAX1 = 1000000 #3最大面积
- zhouchang_min = 3000 #最小周长
- zhouchang_max = 5000 最大周长
- offset_min = 0.4 * image_raw.shape[1] #最小偏移量
- offset_max = 0.99 * image_raw.shape[1] #最大偏移量
-
-
-
- img = cv2.imread(imgsss)
- gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) #一个算子也可以改改成lp函数里的算子
- blurred = cv2.GaussianBlur(gray, (3, 3), 0)
- xgrad = cv2.Sobel(blurred, cv2.CV_16SC1, 1, 0)
- ygrad = cv2.Sobel(blurred, cv2.CV_16SC1, 0, 1)
- edge_output = cv2.Canny(xgrad, ygrad, 50, 150)
- rect_Kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (9, 3))
- image_tophat = cv2.morphologyEx(edge_output, cv2.MORPH_CLOSE, rect_Kernel)
-
- contours = get_contours(image_tophat)
-
- image = cv2.imread(imgsss)
- contour = image.copy()
- cv2.drawContours(contour, contours, -1, (0, 255, 0), 2)
- count = 0 # 个数
- margin = 5 # 裁剪边距
- draw_rect = image.copy()
- for i, contour in enumerate(contours):
- area = cv2.contourArea(contour) # 计算包围形状的面积
- zhouchang = cv2.arcLength(contour, True)
- x2, y2, w2, h2 = cv2.boundingRect(contour)
- if area < mianji_MIN1: # 过滤面积小于15的形状
- continue
- if area > mianji_MAX1: # 过滤面积小于15的形状
- continue
- if zhouchang < zhouchang_min:
- continue
- if zhouchang > zhouchang_max:
- continue
- if x2 < offset_min:
- continue
- if x2 > offset_max:
- continue
-
- print('面積:', area, '周長:', zhouchang)
- count += 1
- rect = cv2.minAreaRect(contour) # 检测轮廓最小外接矩形,得到最小外接矩形的(中心(x,y), (宽,高), 旋转角度)
- box = np.int0(cv2.boxPoints(rect)) # 获取最小外接矩形的4个顶点坐标
- # print(box)
- txt11=txt1(q=box,width=w,height=h)
- txt22=str(LEEXING)+' '+str(txt11[0])+' '+str(txt11[1])+' '+str(txt11[2])+' '+str(txt11[3])
- print(txt22)
-
- cv2.drawContours(draw_rect, [box], 0, (0, 0, 255), 2) # 绘制轮廓最小外接矩形
-
- h, w = image.shape[:2] # 原图像的高和宽
- rect_w, rect_h = int(rect[1][0]) + 1, int(rect[1][1]) + 1 # 最小外接矩形的宽和高
- if rect_w <= rect_h:
- x, y = int(box[1][0]), int(box[1][1]) # 旋转中心
- M2 = cv2.getRotationMatrix2D((x, y), rect[2], 1)
- rotated_image = cv2.warpAffine(image, M2, (w * 2, h * 2))
- y1, y2 = y - margin if y - margin > 0 else 0, y + rect_h + margin + 1
- x1, x2 = x - margin if x - margin > 0 else 0, x + rect_w + margin + 1
- rotated_canvas = rotated_image[y1: y2, x1: x2]
- else:
- x, y = int(box[2][0]), int(box[2][1]) # 旋转中心
- M2 = cv2.getRotationMatrix2D((x, y), rect[2] + 90, 1)
- rotated_image = cv2.warpAffine(image, M2, (w * 2, h * 2))
- y1, y2 = y - margin if y - margin > 0 else 0, y + rect_w + margin + 1
- x1, x2 = x - margin if x - margin > 0 else 0, x + rect_h + margin + 1
- rotated_canvas = rotated_image[y1: y2, x1: x2]
- print("rice #{}".format(count))
- # cv2.imshow("rotated_canvas", rotated_canvas)
- imgs = imgsss.split('\\')
- cv2.imwrite("./imgs/{}.jpg".format(imgs[-1]+str(count)), rotated_canvas)
- with open("./imgs/{}.txt".format(imgs[-1]+str(count)), 'w') as fp:
- fp.write(txt22)
- cv2.waitKey(0)
- cv2.imwrite("./imgs/{}.png".format(imgs[-1]+str(count)), draw_rect)
- # cv2.imwrite("rect.jpg", draw_rect)
-
- def wenjian(path1):
- df_list=[] #读取文件夹里的照片
- list212=os.listdir(path1)
- for i in list212:
- file_path=os.path.join(path1,i)
- df_list.append(file_path)
- return df_list
-
- def txt1(q,width,height): #计算出需要的参数
- x1=q[1][0]
- x2=q[3][0]
- y1=q[1][1]
- y2=q[3][1]
- xmin_xishu, xmax_xishu =x1 / width, x2 / width
- ymin_xishu, ymax_xishu= y1 / height ,y2 / height
- width2=xmax_xishu-xmin_xishu
- height2=ymax_xishu-ymin_xishu
- x_centr_shu=xmin_xishu+width2/2
- y_centr_shu=ymin_xishu+height2/2
- return round(x_centr_shu, 6),round(y_centr_shu, 6),round(width2, 6),round(height2, 6)
-
- if __name__ == '__main__':
- a=time.time()
- path1 = r'D:\AOI\18HP' # 路径
- list1=wenjian(path1)
- for i in list1:
- print(i)
- ceshi1(i)
- b=time.time()
- c=b-a
- print(c)
单独跑一张图片的
- import cv2 as cv
- import numpy as np
- import time
- from matplotlib import pyplot as plt
-
-
- # kernel = np.ones((3,3),np.uint8) #腐蝕
- # dige_erosion = cv.erode(image_canny,kernel,iterations = 1)
- #
- # kernel = np.ones((3,3),np.uint8) #膨脹
- # dige_dilate = cv.dilate(dige_erosion,kernel,iterations = 2)
-
- a=time.time()
-
- imgsss='1.jpg'
-
- CANNY_THRESHOLD1=60
- CANNY_THRESHOLD2=150
- GAUSSIAN_BLUR_KERNEL_SIZE=(5,5)
- GAUSSIAN_BLUR_SIGMA_X=0
-
-
- image_raw=cv.imread(imgsss)
-
- mianji_MIN1=700000
- mianji_MAX1=1000000
- zhouchang_min=3000
- zhouchang_max=5000
- offset_min=0.4*image_raw.shape[1]
- offset_max=0.99*image_raw.shape[1]
-
- #拉普算子
- def lp(imgsss):
- img1=cv.imread(imgsss,0)
- x1=cv.Sobel(img1,cv.CV_16S,1,0,ksize=-1)
- y1=cv.Sobel(img1,cv.CV_16S,0,1,ksize=-1)
- Scale_absX1=cv.convertScaleAbs(x1)
- Scale_absY1=cv.convertScaleAbs(y1)
- result1=cv.addWeighted(Scale_absX1,0.5,Scale_absY1,0.5,0)
- return result1
-
- def zhi():
- image = cv.imread(imgsss, cv.IMREAD_GRAYSCALE)
- thresh1 = cv.adaptiveThreshold(image, 255, cv.ADAPTIVE_THRESH_MEAN_C, cv.THRESH_BINARY, 11, 2)
- thresh2 = cv.adaptiveThreshold(image, 255, cv.ADAPTIVE_THRESH_MEAN_C, cv.THRESH_BINARY_INV, 11, 2)
- thresh3 = cv.adaptiveThreshold(image, 255, cv.ADAPTIVE_THRESH_GAUSSIAN_C, cv.THRESH_BINARY, 11, 2)
- thresh4 = cv.adaptiveThreshold(image, 255, cv.ADAPTIVE_THRESH_GAUSSIAN_C, cv.THRESH_BINARY_INV, 11, 2)
- return thresh1,thresh2,thresh3,thresh4
-
-
- def erzhi():
- # 读取第一张图像
- img = cv.imread(imgsss)
- # 获取图像尺寸
- h, w = img.shape[0:2]
- # 自定义空白单通道图像,用于存放灰度图
- gray = np.zeros((h, w), dtype=img.dtype)
- # 对原图像进行遍历,然后分别对B\G\R按比例灰度化
- for i in range(h):
- for j in range(w):
- gray[i, j] = max(img[i, j, 0], img[i, j, 1], img[i, j, 2]) # 求3通道中最大的值
- gray = cv.cvtColor(gray, cv.COLOR_BGR2RGB) # BGR转换为RGB显示格式,方便通过matplotlib进行图像显示
-
- ref_BINARY = cv.threshold(gray, 180, 255, cv.THRESH_BINARY_INV)[1] # 转换成二值图像
- return ref_BINARY
-
- '''高斯去噪'''
- def get_gaussian_blur_image(image): #高斯去噪
- return cv.GaussianBlur(image,GAUSSIAN_BLUR_KERNEL_SIZE,GAUSSIAN_BLUR_SIGMA_X)
-
- def get_canny_image(image):
- return cv.Canny(image,CANNY_THRESHOLD1,CANNY_THRESHOLD2)
-
- def get_contours(image):
- contours,_=cv.findContours(image,cv.RETR_CCOMP,cv.CHAIN_APPROX_SIMPLE)
- return contours
-
-
- img = cv.imread(imgsss)
- gray = cv.cvtColor(img, cv.COLOR_BGR2GRAY)
- blurred = cv.GaussianBlur(gray, (3, 3), 0)
- xgrad = cv.Sobel(blurred, cv.CV_16SC1, 1, 0)
- ygrad = cv.Sobel(blurred, cv.CV_16SC1, 0, 1)
- edge_output = cv.Canny(xgrad, ygrad, 50, 150)
- rect_Kernel = cv.getStructuringElement(cv.MORPH_RECT, (9, 3))
- image_tophat = cv.morphologyEx(edge_output, cv.MORPH_CLOSE, rect_Kernel)
-
- # #高斯去噪
- # result2=get_gaussian_blur_image(result1)
- # #均值
- # result3 = cv.blur(result2,(3,3))
- #提取輪廓
- # image_canny=get_canny_image(s1)
-
- #膨脹
- # kernel = np.ones((3,3),np.uint8)
- # dige_dilate1 = cv.dilate(image_canny,kernel,iterations = 1)
- #中值
- # median = cv.medianBlur(image_canny,5)
-
- contours=get_contours(image_tophat)
-
-
- image = cv.imread(imgsss)
- contour = image.copy()
- cv.drawContours(contour, contours, -1, (0, 255, 0), 2)
- count = 0 # 个数
- margin = 5 # 裁剪边距
- draw_rect = image.copy()
- for i, contour in enumerate(contours):
- area = cv.contourArea(contour) # 计算包围形状的面积
- zhouchang = cv.arcLength(contour, True)
- x2,y2,w2,h2=cv.boundingRect(contour)
- if area < mianji_MIN1: # 过滤面积小于15的形状
- continue
- if area >mianji_MAX1: # 过滤面积小于15的形状
- continue
- if zhouchang<zhouchang_min:
- continue
- if zhouchang>zhouchang_max:
- continue
- if x2 < offset_min:
- continue
- if x2 > offset_max:
- continue
-
- print('面積:',area ,'周長:',zhouchang)
- count += 1
- rect = cv.minAreaRect(contour) # 检测轮廓最小外接矩形,得到最小外接矩形的(中心(x,y), (宽,高), 旋转角度)
- box = np.int0(cv.boxPoints(rect)) # 获取最小外接矩形的4个顶点坐标
- # print(box)
- cv.drawContours(draw_rect, [box], 0, (0, 0,255), 2) # 绘制轮廓最小外接矩形
-
- h, w = image.shape[:2] # 原图像的高和宽
- rect_w, rect_h = int(rect[1][0]) + 1, int(rect[1][1]) + 1 # 最小外接矩形的宽和高
- if rect_w <= rect_h:
- x, y = int(box[1][0]), int(box[1][1]) # 旋转中心
- M2 = cv.getRotationMatrix2D((x, y), rect[2], 1)
- rotated_image = cv.warpAffine(image, M2, (w * 2, h * 2))
- y1, y2 = y - margin if y - margin > 0 else 0, y + rect_h + margin + 1
- x1, x2 = x - margin if x - margin > 0 else 0, x + rect_w + margin + 1
- rotated_canvas = rotated_image[y1: y2, x1: x2]
- else:
- x, y = int(box[2][0]), int(box[2][1]) # 旋转中心
- M2 = cv.getRotationMatrix2D((x, y), rect[2] + 90, 1)
- rotated_image = cv.warpAffine(image, M2, (w * 2, h * 2))
- y1, y2 = y - margin if y - margin > 0 else 0, y + rect_w + margin + 1
- x1, x2 = x - margin if x - margin > 0 else 0, x + rect_h + margin + 1
- rotated_canvas = rotated_image[y1: y2, x1: x2]
- print("rice #{}".format(count))
- # cv2.imshow("rotated_canvas", rotated_canvas)
- cv.imwrite("./imgs/{}.jpg".format(count), rotated_canvas)
- cv.waitKey(0)
- cv.imwrite("rect.jpg", draw_rect)
-
- b=time.time()
- c=b-a
- print(c)
- plt.figure()
- plt.imshow(image_tophat)
- plt.title("space")
- plt.show()
-
-
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。