资讯动态

Text-to-CAD实战:用Python将自然语言生成STEP与URDF模型

发布时间:2026/10/27 14:18:06 来源:尧图企业网站定制
1. 从一段文字到一张能加工的图纸这条路到底通不通第一次听到 text-to-cad 这个说法我脑子里蹦出来的画面是对着电脑敲一句“给我画一个 80 毫米见方的法兰盘中心开 30 毫米通孔四角各一个 M6 沉头孔”然后屏幕上就自动生成一张能直接丢进加工流程的三维模型。这个想法放在几年前基本属于科幻但这两年随着大模型能力外溢到结构化输出领域它已经变成了一个可以动手搭出来的工程问题。text-to-cad 的核心说白了就是把自然语言描述转换成 CAD 可识别的几何数据。它要解决的不是“画得好看”而是“画得对、能复用、能进下游流程”。传统做法是人打开 CAD 软件一根线一根线地画或者写脚本调 API 生成。前者慢且依赖熟练度后者门槛高、改一个参数要动代码。text-to-cad 想干的事是让中间那层“人肉翻译”消失——你说人话机器出几何。这件事适合谁看如果你是会写点 Python、又对机械结构或参数化建模有兴趣的开发者这篇内容能帮你把整条链路跑通如果你是做产品原型、教学演示、批量出图需求的工程师这里面的思路能直接搬去用哪怕你只是想搞明白“大模型到底能不能画图”这个疑问看完你也会有明确答案。我会把 STEP、URDF 这些格式为什么重要、Python 侧怎么落地、哪些坑一定会踩全部摊开讲。需要先泼一盆冷水text-to-cad 目前不是“一句话出成品”的魔法。它更像一个“自然语言到参数化脚本”的编译器真正的几何质量取决于你给它的约束够不够、下游的校验严不严。把它当成一个帮你省掉 70% 重复建模劳动的助手而不是替代设计师的黑盒心态就对了。2. 为什么输出格式选 STEP 和 URDF而不是随便导个 STL2.1 STEP 是工程界的“通用普通话”很多人第一反应是让模型输出 STL因为 STL 简单、到处都能读。但 STL 有个致命问题它只存三角面片不存拓扑关系、不存特征历史、不存单位语义。你拿到一个 STL想改孔径、想调壁厚基本等于重新建模。而 STEPISO 10303是带边界表示B-rep的实体模型格式它保留了面、边、顶点之间的拓扑结构圆柱面就是圆柱面孔就是孔下游的 CAD 软件能识别出这些特征并继续编辑。从 text-to-cad 的角度看选 STEP 意味着你的中间表示必须携带“特征级”信息而不是“网格级”信息。这就要求生成环节不能直接吐三角面而要先构造参数化的实体操作序列——比如拉伸、旋转、布尔运算——再交给几何内核去执行。这也是为什么 Python 生态里做这件事绕不开OpenCASCADE通过 pythonocc-core 或 cadquery这类内核。2.2 URDF 是机器人侧的“装配说明书”URDFUnified Robot Description Format是另一条线。它描述的不是单个零件的几何而是多个刚体之间的连接关系、关节类型、运动学树。如果你做的是机械臂、移动底盘、夹爪这类系统光有零件 STEP 是不够的你还得告诉仿真器“哪个零件是底座、哪个是连杆、它们之间是旋转关节还是固定连接、转轴在哪”。text-to-cad 在这里的价值就体现出来了你可以用自然语言描述“一个两连杆机械臂基座固定第一关节绕 Z 轴旋转第二关节绕 Y 轴旋转连杆长度分别是 200 和 150 毫米”然后让系统同时生成几何STEP和运动学描述URDF。这两者配合才能直接导入仿真环境跑起来。热词里出现的“urdf导入coppeliasim”正好说明这是真实需求——大家生成完 URDF 是要拿去用的不是摆着看的。2.3 格式选型对照表格式存什么能否编辑特征典型下游text-to-cad 生成难度STL三角面片否3D 打印、渲染低STEPB-rep 实体拓扑是机械 CAD、CAM中高URDF刚体关节运动学部分结构层面机器人仿真中OBJ网格材质否渲染、游戏低选型逻辑很直接要加工、要改就上 STEP要动、要仿真就加 URDF。STL 只在最终打印或展示时作为导出产物出现不该作为中间交换格式。3. 用 Python 把自然语言翻译成几何整条链路的拆解3.1 整体架构三段式而不是端到端我试过让大模型直接输出 STEP 文件内容结果惨不忍睹——STEP 是复杂的文本格式模型很容易在语法层面就崩掉。靠谱的做法是三段式语义解析段大模型把自然语言转成结构化的中间表示JSON里面是特征、尺寸、约束、装配关系。几何构造段Python 程序读取这个 JSON调用几何内核cadquery / pythonocc执行建模操作。格式导出段把构造好的实体导出成 STEP把装配关系导出成 URDF。这个拆分的意义在于每一段都可以单独测试和替换。语义解析错了你换提示词或换模型几何构造错了你调参数映射导出错了你查内核版本。端到端一把梭的话出了问题你根本不知道是哪一环。3.2 中间表示长什么样中间表示是整个系统的“合同”。我一般设计成类似这样的结构{ part_name: flange, units: mm, features: [ {type: box, length: 80, width: 80, height: 10}, {type: hole, diameter: 30, position: [40, 40], through: true}, {type: hole, diameter: 6.6, position: [[10,10],[70,10],[10,70],[70,70]], through: true} ], operations: [cut_all_holes] }这个结构的好处是特征和操作分离。特征描述“要什么”操作描述“怎么组合”。大模型只需要负责填特征组合逻辑由 Python 侧固定减少出错面。单位必须显式声明我踩过坑模型默认按英寸给数结果出来一个 80 英寸的怪物。3.3 几何内核的选择cadquery 还是 pythonocccadquery 是 pythonocc 的上层封装语法更接近“人话”适合快速出活import cadquery as cq result (cq.Workplane(XY) .box(80, 80, 10) .faces(Z).workplane() .hole(30) .rect(60, 60, forConstructionTrue) .vertices().hole(6.6)) cq.exporters.export(result, flange.step)pythonocc 更底层控制力强但代码量大。我的经验是90% 的常规零件用 cadquery 足够只有遇到复杂曲面、非标准布尔运算时才下沉到 pythonocc。热词里“python安装numpy库的方法”“python安装教程”说明很多人卡在环境这一步cadquery 依赖 OCCT 内核装的时候一定要用 conda 而不是裸 pip否则编译能折腾你一下午。3.4 从零件到装配URDF 的生成逻辑URDF 的生成不能靠几何内核得单独写映射。核心是把中间表示里的“装配关系”翻译成 link 和 jointdef build_urdf(assembly): links [] joints [] for comp in assembly[components]: links.append(flink name{comp[name]}/) for conn in assembly[connections]: joints.append( fjoint name{conn[name]} type{conn[type]} fparent link{conn[parent]}/ fchild link{conn[child]}/ faxis xyz{conn[axis]}/ f/joint ) return wrap_urdf(links, joints)这里的关键是关节类型和轴的语义必须和几何对齐。我见过生成的 URDF 里关节轴指向和实际孔位差了 90 度导入仿真后机械臂直接穿模。解决办法是让几何构造段和 URDF 生成段共享同一份坐标定义不要各写各的。4. 实测中一定会遇到的坑以及我是怎么绕过去的4.1 大模型给的尺寸“看起来对其实不自洽”最典型的场景你说“一个边长 100 的方板四角各留 10 的边距打孔”模型可能给你孔位在 (10,10)、(90,10)、(10,90)、(90,90)看起来没问题。但如果板厚是 5孔径是 8孔壁到边缘只剩 6 毫米某些材料下直接崩边。模型不懂工艺约束它只懂语言模式。我的做法是在中间表示之后加一层规则校验器用 Python 写死一批工程规则孔径与板厚比、孔边距最小值、壁厚最小值。校验不过就打回让模型重生成或者直接报错让人介入。这层校验器是 text-to-cad 从“玩具”变成“工具”的分水岭。4.2 单位、坐标系、原点三座大山单位问题前面提过。坐标系问题更隐蔽cadquery 默认 Z 轴向上很多机器人仿真环境默认 Z 轴向上但 X 轴朝向不同URDF 里又有一套自己的约定。三个环节三套约定不对齐就等着模型躺平。我的经验是在中间表示里强制声明一个全局坐标系约定所有生成环节都从这个约定出发做转换转换函数只写一次、集中测试。原点位置也要显式指定默认放在零件几何中心还是某个角点必须写进合同不能靠猜。4.3 复杂特征的布尔运算失败当你让模型生成“带倒角、带圆角、带异形孔”的零件时几何内核的布尔运算可能失败——面重叠、自相交、精度不够都会让 OCCT 抛异常。这不是 text-to-cad 独有的问题是 B-rep 建模的固有难点。应对策略是降级生成先出最简版本只有主体和通孔确认能导出 STEP再逐步加特征每加一个就校验一次。不要一次性把所有特征堆上去失败了很难定位是哪个特征的问题。我一般把特征按“主体→大特征→小特征→装饰特征”排序逐级构建。4.4 环境依赖的坑比算法还多热词里大量出现“python安装”“python环境变量配置”“cad安装”说明环境问题是真实门槛。cadquery 依赖 OCCTOCCT 在不同平台上的二进制包不一样。我的建议很直接用conda 或 mamba建独立环境不要污染系统 Python。装 cadquery 用conda install -c conda-forge cadquery别用 pip 硬编。如果非要用 pip先确认系统里有编译工具链否则 OCCT 编译能跑半小时。导出 STEP 后用 FreeCAD 或任意 CAD 软件打开验证一遍别只看文件大小。提示生成完 STEP 一定要做“回读验证”——用另一个库把 STEP 读回来检查实体数量、包围盒尺寸是否符合预期。只写不读等于没验证。5. 让生成结果真正可用的几个工程习惯5.1 把提示词当成“接口文档”来写很多人写提示词很随意结果模型输出飘忽。我的做法是把提示词结构化角色、任务、输出格式、约束、示例五段式。尤其是输出格式直接把 JSON schema 贴进去让模型照着填。约束里写清楚单位、坐标系、必填字段。这样出来的中间表示稳定性高很多。5.2 版本化你的中间表示中间表示是系统的核心资产一定要版本化。每次改 schema 都记一笔因为几何构造段和 URDF 生成段都依赖它。我吃过亏改了字段名没同步下游生成了一堆空零件排查了半天才发现是 key 对不上。5.3 批量生成时加队列和重试如果你要批量处理几十上百条描述别串行跑。用 Python 的队列热词里“python队列queue不堵塞”正好相关做并发每条任务独立重试。几何内核偶尔会抽风重试一次往往就好了。但要注意并发数别开太高OCCT 不是线程安全的多进程比多线程稳。5.4 给非技术用户留一个“人话校验”出口最终用这套系统的人可能不懂几何内核。我一般会额外生成一张尺寸标注图用 matplotlib 画个简图标上关键尺寸让人一眼能看出“这玩意儿是不是我要的”。这比让人去 CAD 里量尺寸快得多也避免了很多返工。6. 这套东西现在的边界在哪以及我会怎么继续用把 text-to-cad 跑通之后我对它的定位更清楚了它是一个“参数化建模的加速器”不是“设计师替代品”。对于标准件、简单结构件、教学示例、批量变体它非常好用一句话出图改个参数重跑就行。但遇到复杂曲面、自由造型、需要工程判断的场合它给的结果只能当草稿最终还得人来定。我目前最常用的场景是批量生成系列化零件比如一组不同孔径、不同孔距的法兰用自然语言描述变体规则让系统批量出 STEP再统一导入下游做装配验证。这个流程省掉的时间是实打实的。另一个场景是机器人教学让学生用文字描述一个简单机构系统生成 URDF 直接导入仿真学生能立刻看到自己描述的东西动起来反馈闭环非常短。后续我打算把校验层做得更厚把更多工艺规则、装配干涉检查、运动学可达性检查都塞进去。生成不是难点生成之后能不能用才是难点。谁把校验和反馈这一环做扎实谁的工具才真正站得住。最后分享一个我踩过的小坑生成 STEP 之后别急着删中间 JSON那个 JSON 才是你后续改参数、做变体的唯一依据。STEP 是结果JSON 是源头。源头丢了你就只能重新跟模型聊天了。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑