64 lines
		
	
	
		
			2.4 KiB
		
	
	
	
		
			Python
		
	
	
		
			Executable File
		
	
			
		
		
	
	
			64 lines
		
	
	
		
			2.4 KiB
		
	
	
	
		
			Python
		
	
	
		
			Executable File
		
	
| import math
 | |
| import random
 | |
| import cv2
 | |
| import numpy as np
 | |
| 
 | |
| TOTAL_OFFSET = 8
 | |
| 
 | |
| def gen_outline(path, dest):
 | |
|     img = cv2.imread(path, cv2.IMREAD_GRAYSCALE)
 | |
|     img_contour = cv2.imread(dest, cv2.IMREAD_UNCHANGED)
 | |
| 
 | |
|     kernel_size = 1
 | |
|     sigma = 0.5
 | |
|     kernel = cv2.getGaussianKernel(kernel_size, sigma)
 | |
|     kernel = np.dot(kernel, kernel.T)
 | |
|     smoothed = cv2.filter2D(img, -1, kernel)
 | |
| 
 | |
|     _, thresh = cv2.threshold(smoothed, 1, 255, cv2.THRESH_BINARY)
 | |
|     contours, _ = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
 | |
| 
 | |
|     # 计算轮廓的总面积
 | |
|     total_area = 0
 | |
|     for contour in contours:
 | |
|         area = cv2.contourArea(contour)
 | |
|         total_area = total_area + area
 | |
| 
 | |
|     # 选择周长和面积满足条件的轮廓,过滤太小的轮廓
 | |
|     valid_contours = []
 | |
|     threshold = 0.5
 | |
|     idx = 0
 | |
|     while not (len(valid_contours) > 0 and idx == 0):
 | |
|         contour = contours[idx]
 | |
|         perimeter = cv2.arcLength(contour, True)
 | |
|         area = cv2.contourArea(contour)
 | |
|         # print(path, "周长 =", perimeter, "面积占比 =", area/total_area, threshold)
 | |
|         if perimeter > 0 and area/total_area > threshold:
 | |
|             # print("add =====> ")
 | |
|             valid_contours.append(contour)
 | |
|         idx = idx + 1
 | |
|         if idx >= len(contours):
 | |
|             threshold = threshold - 0.1
 | |
|             idx = 0
 | |
| 
 | |
|     start = random.randint(0, int(len(valid_contours[0])/3*2)-1)
 | |
|     start = 0
 | |
|     contour_points = valid_contours[0][start:(start + int(len(valid_contours[0])/3))]
 | |
|     contour_points = valid_contours[0][start:(start + len(valid_contours[0]))]
 | |
|     offset = (4, 4)
 | |
|     offset_contour_points = contour_points + offset
 | |
|     print("contour_points start = ", start, len(valid_contours[0]))
 | |
|     cv2.polylines(img_contour, [offset_contour_points], False, (255, 255, 255, 255), int(TOTAL_OFFSET - 1), lineType=cv2.LINE_AA)
 | |
|     cv2.polylines(img_contour, [offset_contour_points], False, (0, 0, 0, 255), int(TOTAL_OFFSET / 2 - 1), lineType=cv2.LINE_AA)
 | |
|     
 | |
|     # cv2.drawContours(img_contour, valid_contours, -1, (255, 255, 255, 255), 9, None, None, None, (5, 5))
 | |
|     # cv2.drawContours(img_contour, valid_contours, -1, (0, 0, 0, 255), 5, None, None, None, (5, 5))
 | |
|     # cv2.imwrite(dest, img_contour)
 | |
| 
 | |
|     cv2.imshow('Original Image', img)
 | |
|     cv2.imshow('Contour Image', img_contour)
 | |
|     cv2.waitKey(0)
 | |
|     cv2.destroyAllWindows()
 | |
| 
 | |
| if __name__ == "__main__":
 | |
|     gen_outline("./image.png", "./image-emt.png") |