import cv2 import numpy as np class test_main(): def __init__(self): # 讀取原始影像 self.original_image = cv2.imread(r'D:\Code\Project\Medeologix\Python\Size\01_10fps_0.041ms_0db_1092\01.bmp') self.test() def test(self): # 複製原始影像 img = self.original_image.copy() o_img_black = img.copy() o_img_black[:, :, :] = 0 # 將影像填充為黑色 # 將圖片轉換為灰度圖 gray_image = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 使用 Canny 邊緣檢測 edges = cv2.Canny(gray_image, 250, 250) # 檢測直線 lines = cv2.HoughLinesP(edges, 1, np.pi / 180, threshold=100, minLineLength=100, maxLineGap=200) # 建立黑色影像 black_img = gray_image.copy() black_img[:, :] = 0 # 如果檢測到直線,繪製在黑色影像上 if lines is not None: for line in lines: x1, y1, x2, y2 = line[0] cv2.line(black_img, (x1, y1), (x2, y2), (255, 255, 0), 2) # 找出黑色影像中白色點的座標 y_list, x_list = np.where(black_img == 255) # 繪製紅色的兩條垂直線 cv2.line(o_img_black, (300, 0), (300, len(o_img_black)), (0, 0, 255), 2) cv2.line(o_img_black, (len(o_img_black[0]) - 300, 0), (len(o_img_black[0]) - 300, len(o_img_black)), (0, 0, 255), 2) # 像素大小(5.5μm) pixel_size_um = 5.5 # 找到 x 座標等於 300 的所有索引 indices_300 = np.where(x_list == 300)[0] # 從 y_list 中獲取這些索引對應的 y 值 y_values_300 = y_list[indices_300] # 找出最大和最小的 Y 值 max_y_300 = np.max(y_values_300) min_y_300 = np.min(y_values_300) print("For x = 300:") print("Max Y:", max_y_300, "Min Y:", min_y_300) # 計算相減結果 diff_300 = max_y_300 - min_y_300 # 將距離從像素轉換為毫米 diameter_300 = diff_300 * pixel_size_um / 1000 print("直徑:{:.3f} mm".format(diameter_300)) # 找到 x 座標等於 o_img_black.shape[1] - 300 的所有索引 indices_other = np.where(x_list == o_img_black.shape[1] - 300)[0] # 從 y_list 中獲取這些索引對應的 y 值 y_values_other = y_list[indices_other] # 找出最大和最小的 Y 值 max_y_other = np.max(y_values_other) min_y_other = np.min(y_values_other) print("For x =", o_img_black.shape[1] - 300) print("Max Y:", max_y_other, "Min Y:", min_y_other) # 計算相減結果 diff_other = max_y_other - min_y_other # 將距離從像素轉換為毫米 diameter_other = diff_other * pixel_size_um / 1000 print("直徑:{:.3f} mm".format(diameter_other)) # 從 y_list 中獲取這些索引對應的 y 值 intersection_points_300 = [(300, y_list[i]) for i in indices_300] intersection_points_other = [(o_img_black.shape[1] - 300, y_list[i]) for i in indices_other] # 合併所有相交的點 intersection_points = intersection_points_300 + intersection_points_other # 在原圖上標記相交的點並連接紅色垂直線 for point in intersection_points: cv2.circle(img, point, 10, (0, 255, 0), -1) # 在垂直相交點之間繪製紅線 for i in range(len(intersection_points_300) - 1): cv2.line(img, intersection_points_300[i], intersection_points_300[i + 1], (69, 27, 203), 2) for i in range(len(intersection_points_other) - 1): cv2.line(img, intersection_points_other[i], intersection_points_other[i + 1], (69, 27, 203), 2) # 將所有找到的點也標記出來 for i in range(len(x_list)): point = (x_list[i], y_list[i]) cv2.circle(o_img_black, point, 1, (102, 193, 134), -1) # 顯示直徑數據在原圖上 cv2.putText(img, "Diameter at 300: {:.3f} mm".format(diameter_300), (10, 100), cv2.FONT_HERSHEY_SIMPLEX, 2, (0, 0, 0), 2) cv2.putText(img, "Diameter at {}: {:.3f} mm".format(o_img_black.shape[1] - 300, diameter_other), (10, 170), cv2.FONT_HERSHEY_SIMPLEX, 2, (0, 0, 0), 2) # 顯示結果 black_img_resized = cv2.resize(o_img_black, (640, 640)) cv2.imshow('Black Image with Lines', black_img_resized) original_img_resized = cv2.resize(img, (1280, 1280)) cv2.imshow('Original Image with Diameter', original_img_resized) cv2.waitKey(0) cv2.destroyAllWindows() if __name__ == "__main__": test_main()