机器视觉开发-图片转CAD
思路
获取图片,实现二值化,然后再利用使用高斯模糊来减少噪声,再利用canny获取轮廓,使用ezdxf进行描边。
代码
import cv2
import numpy as np
import ezdxf
import tkinter as tk
from tkinter import filedialog, messagebox
from PIL import Image, ImageTkclass ImageToDXFConverter:def __init__(self, root):self.root = rootself.root.title("图像转DXF工具")self.root.geometry("800x600")# 创建控件self.create_widgets()def create_widgets(self):# 输入图像路径self.input_label = tk.Label(self.root, text="输入图像:")self.input_label.pack(pady=5)self.input_entry = tk.Entry(self.root, width=50)self.input_entry.pack(pady=5)self.browse_button = tk.Button(self.root, text="浏览...", command=self.browse_image)self.browse_button.pack(pady=5)# 输出DXF路径self.output_label = tk.Label(self.root, text="输出DXF文件:")self.output_label.pack(pady=5)self.output_entry = tk.Entry(self.root, width=50)self.output_entry.pack(pady=5)self.save_button = tk.Button(self.root, text="另存为...", command=self.save_dxf)self.save_button.pack(pady=5)# 预览区域self.preview_label = tk.Label(self.root, text="图像预览:")self.preview_label.pack(pady=5)self.canvas = tk.Canvas(self.root, width=600, height=400, bg="gray")self.canvas.pack(pady=10)# 转换按钮self.convert_button = tk.Button(self.root, text="转换为DXF", command=self.convert_image, bg="green", fg="white")self.convert_button.pack(pady=10)def browse_image(self):file_path = filedialog.askopenfilename(filetypes=[("Image files", "*.jpg *.jpeg *.png *.bmp")])if file_path:self.input_entry.delete(0, tk.END)self.input_entry.insert(0, file_path)self.show_preview(file_path)def save_dxf(self):file_path = filedialog.asksaveasfilename(defaultextension=".dxf",filetypes=[("DXF files", "*.dxf")])if file_path:self.output_entry.delete(0, tk.END)self.output_entry.insert(0, file_path)def show_preview(self, image_path):try:# 读取并显示预览图像img = cv2.imread(image_path)img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)img = Image.fromarray(img)img.thumbnail((600, 400)) # 调整大小以适应画布self.tk_image = ImageTk.PhotoImage(img)self.canvas.create_image(300, 200, image=self.tk_image)except Exception as e:messagebox.showerror("错误", f"无法加载预览图像: {str(e)}")def convert_image(self):input_path = self.input_entry.get()output_path = self.output_entry.get()if not input_path or not output_path:messagebox.showwarning("警告", "请选择输入图像和输出DXF路径")returntry:# 调用原始转换函数image_to_dxf(input_path, output_path)messagebox.showinfo("成功", "DXF文件已成功生成!")except Exception as e:messagebox.showerror("错误", f"转换失败: {str(e)}")def image_to_dxf(image_path, dxf_path):# 读取图像image = cv2.imread(image_path, cv2.IMREAD_GRAYSCALE)# 图像反转flipped_image = cv2.flip(image, -1)flipped_image2 = cv2.flip(flipped_image, 1)if image is None:raise ValueError("无法读取图像文件")blurred = cv2.GaussianBlur(flipped_image2, (3, 3), 0)# 使用阈值处理来二值化图像_, thresholded = cv2.threshold(blurred, 211, 255, cv2.THRESH_BINARY)# 使用Canny边缘检测算法提取边缘edges = cv2.Canny(thresholded, 3, 20, apertureSize=7, L2gradient=True)# 找到轮廓contours, _ = cv2.findContours(edges, cv2.RETR_LIST, cv2.CHAIN_APPROX_NONE)# 创建新的DXF文档doc = ezdxf.new()msp = doc.modelspace()# 遍历轮廓并添加到DXF文件中for contour in contours:points = contour.reshape(-1, 2).tolist()msp.add_polyline2d(points)# 保存DXF文件doc.saveas(dxf_path)if __name__ == "__main__":root = tk.Tk()app = ImageToDXFConverter(root)root.mainloop()
效果