#!/usr/bin/env python3 """ STP到GLB转换器类 使用XCAF直接保留装配结构,无需STL中间步骤 """ import os from typing import Callable, Optional, List, Dict, Literal from utils.network_helper import is_url, download_file, cleanup_downloaded_file # 导入XCAF转换器 try: from .converter_xcaf import XCAFConverter, check_xcaf_availability XCAF_AVAILABLE = True except ImportError: XCAF_AVAILABLE = False XCAFConverter = None class StpToGlbConverter: """STP到GLB转换器""" def __init__(self): """初始化转换器,使用XCAF管线""" self.progress_callback: Optional[Callable[[int, str], None]] = None self.downloaded_file_path: Optional[str] = None # 记录下载的临时文件路径 # 检查XCAF可用性 if not XCAF_AVAILABLE: raise RuntimeError("XCAF模块不可用,请检查pythonocc安装") self.xcaf_converter = XCAFConverter() if not self.xcaf_converter.is_available(): status = self.xcaf_converter.get_availability_status() raise RuntimeError(f"XCAF转换器不可用: {status['message']}") def set_progress_callback(self, callback: Callable[[int, str], None]) -> None: """设置进度回调函数""" self.progress_callback = callback if self.xcaf_converter: self.xcaf_converter.set_progress_callback(callback) def _update_progress(self, progress: int, message: str) -> None: """更新进度""" if self.progress_callback: self.progress_callback(progress, message) def _prepare_input_file(self, stp_path: str) -> str: """ 准备输入文件(下载URL或验证本地文件) Args: stp_path: STP文件路径或URL Returns: str: 本地文件路径 """ if is_url(stp_path): self._update_progress(1, f"检测到URL输入: {stp_path}") # 下载文件到临时位置 self.downloaded_file_path = download_file(stp_path, self.progress_callback) self._update_progress(95, f"文件下载完成: {self.downloaded_file_path}") return self.downloaded_file_path else: # 本地文件验证 self._update_progress(5, "检查本地输入文件...") if not os.path.isfile(stp_path): raise FileNotFoundError(f"找不到文件:{stp_path}") return stp_path def _cleanup_downloaded_file(self) -> None: """清理下载的临时文件""" if self.downloaded_file_path: cleanup_downloaded_file(self.downloaded_file_path) self.downloaded_file_path = None def convert(self, stp_path: str, glb_path: str, linear_deflection: float = 0.01, angular_deflection: float = 0.1, embed_textures: bool = True, y_up: bool = True, **kwargs) -> None: """ STP到GLB转换,直接保留装配结构 Args: stp_path: 输入STEP文件路径或URL(支持HTTP/HTTPS) glb_path: 输出GLB文件路径 linear_deflection: 线性偏差(控制网格精度) angular_deflection: 角度偏差(控制网格精度) embed_textures: 是否嵌入纹理 y_up: 是否使用Y向上坐标系 **kwargs: 忽略的其他参数(用于兼容性) """ try: # 准备输入文件(可能需要下载) local_stp_path = self._prepare_input_file(stp_path) # 使用XCAF转换,保留装配结构 self.xcaf_converter.convert_with_xcaf( local_stp_path, glb_path, embed_textures=embed_textures, y_up=y_up, linear_deflection=linear_deflection, angular_deflection=angular_deflection ) finally: # 清理下载的文件 self._cleanup_downloaded_file() def get_info(self) -> dict: """获取转换器信息""" status = self.xcaf_converter.get_availability_status() if self.xcaf_converter else {} return { "converter": "XCAF", "capabilities": { "assembly_hierarchy": True, "component_names": True, "colors": True, "materials": True, "instances": True }, "status": status }