news 2026/9/16 12:54:19

Altium Designer交互式BOM插件:PCB装配数据可视化与高亮定位

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Altium Designer交互式BOM插件:PCB装配数据可视化与高亮定位

简介:这是一套面向 Altium Designer 的交互式 BOM 表导出插件,主要供硬件工程师、PCB 设计人员及需要处理元件清单的相关岗位使用。它针对传统 BOM 表格只能静态查看、不支持按封装/位号快速筛选和定位的痛点,通过内置脚本在 AD 中直接生成具备搜索、高亮、折叠分类等能力的 HTML 交互页面,方便生产、采购与维修环节高效查阅。资源包共包含 30 个文件,整体大小仅 139KB。文件以 JavaScript 脚本为主(17 个 js 文件),负责 BOM 数据处理与页面渲染;辅以 HTML/CSS 模板用于定义交互界面外观,另有批处理脚本用于快速初始化与卸载插件,以及工程脚本和窗体定义文件用于接入 AD 菜单与界面。目前已有 2304 人学习使用该资源。除了核心导出功能和可直接运行的批处理脚本外,包内还提供示例页面和用户自定义模块,便于使用者理解交互逻辑并做二次开发;整个包结构紧凑、无需复杂安装,适合希望替代传统 BOM 输出方式的工程师快速接入。

1. 交互 BOM:把 Altium Designer 的装配数据变成一张“能点的板子”

实际装配时最耗时的不是看表格,而是在 PCB 视图里找位号。传统 BOM 经 AD 导出成 Excel 或 PDF 后,与版图完全割裂:要确认某颗 0.1uF 电容贴在哪,得在表格里查位号,再回头用 Ctrl+F 在 PCB 上搜索。这个插件改变了工作流——它把 AD 的 PCB 数据导出成一个独立的交互式 HTML 文件,元件以图形化方式呈现,点击 BOM 行,对应器件在板图上高亮;点击板图上的器件,BOM 行同步定位。整个过程不依赖 AD 环境,浏览器打开就能用。

这套方案的底层是一组 Altium Designer 脚本工程(InteractiveHtmlBomForAD),由 Delphi 窗体脚本和 JavaScript 脚本混合组成。它适合需要频繁输出装配文档的硬件工程师、PCB 设计人员,以及需要跟产线、贴片厂对接 BOM 的工艺岗位。它解决的问题不是"生成 BOM 表",而是"让 BOM 表能跟 PCB 对上话"。

2. 脚本工作台解剖:InPcb API、坐标映射与 lz-string 数据链路

2.1 AD 脚本系统的运行机制:为什么插件要混用 Delphi 与 JS

Altium Designer 的脚本系统支持 DelphiScript、VB Script 和 JavaScript 三种语言,工程文件以.PrjScr结尾。这个插件的主工程文件是InteractiveHtmlBomForAD.PrjScr,从文件列表能看出它同时携带了.dfm(Delphi 窗体定义)和.js(JavaScript 逻辑)文件。mainWin.dfm定义的是导出参数对话框界面,而mainWin.js负责业务逻辑,这是 AD 脚本中很常见的"窗体骨架用 Delphi、逻辑用 JavaScript"的混合写法,因为 JS 处理字符串拼接和数组遍历更顺手。

插件通过 AD 的脚本运行接口获得当前 PCB 文档对象。InPcb.js是这一层的关键封装,它把 AD 内部 PCB API 包装成插件可调用的方法,比如遍历元件、读取坐标、获取网络名。AD10.js的存在说明插件兼容了 AD10 时代的 API 差异——Altium 从 AD10 到 AD20 虽然接口大体一致,但部分 PCB 对象属性在不同版本中有变化,插件单独保留一个版本适配文件就是为了处理这类兼容性问题。

脚本运行的典型时序是这样的:用户在 AD 里执行脚本 -> mainWin 窗体弹出 -> 用户选择导出路径和参数 -> 确认后脚本访问 PCBServer 接口枚举当前 PCB 的全部元件 -> 数据整理成 JSON -> 经 lz-string 压缩后嵌入 HTML 模板。

2.2 数据提取与坐标映射:从 AD 对象模型到 Canvas 渲染

AD 的 PCB 对象模型中,每个元器件(Component)至少包含以下属性:位号(Designator)、封装(Pattern/Footprint)、元件类型(LibReference/Value)、中心坐标(X/Y)、旋转角度(Rotation)、所在层(Layer)。插件要做的第一件事就是把它们读出来:

// 通过 AD 的 PCBServer 接口枚举 PCB 上的所有元件 var pcb = PCBServer.GetCurrentPCBBoard(); // 获取当前 PCB 文档 var iterator = pcb.BoardIterator_Create(); // 创建对象迭代器 iterator.AddFilter_ObjectSet(MkSet(ePCBComponent)); // 只遍历元件类对象 var comp = iterator.FirstPCBObject(); while (comp !== null) { var designator = comp.Designator.Text; // 位号,如 R12 var value = comp.Comment.Text; // 值/型号,如 10K var pattern = comp.Pattern; // 封装名,如 0402 var x = comp.X; // 坐标:AD 内部单位是 10nm var y = comp.Y; var rotation = comp.Rotation; // 旋转角度 var layer = comp.Layer; // TopLayer / BottomLayer iterator.Next(); } PCB.BoardIterator_Destroy(iterator);

这段代码中MkSet(ePCBComponent)是 AD 脚本里的标准过滤写法,告诉迭代器"我只要元器件,不要走线、过孔、铺铜"。坐标单位是 AD 内部单位,1 单位等于 10 纳米,导出前需要换算成 mil 或 mm,否则到 HTML 页面上坐标会差好几个数量级。comp.Layer用来区分顶层和底层元件,这个信息最终会体现在交互页面的镜像翻转逻辑里。

拿到原始数据后,下一步是建立 PCB 坐标到浏览器画布坐标的映射。PCB 的原点在板框外某个位置,而 HTML 画布的(0,0)在左上角。常见做法是先计算所有元件的包围盒(bounding box),得到板子整体的最小 X、最小 Y 值和宽高,再按比例缩放到画布尺寸,同时做居中处理。这一步如果算错,导出的板图会出现元件位置整体偏移或放大缩小比例不对。

2.3 数据封装与前端渲染:lz-string 压缩与 render.js

原始 BOM 数据量不大,一个千元件板子的 JSON 文本通常在几十 KB 量级,但插件要把整个 PCB 的元件布局也内嵌进 HTML,就会带来 JSON 体积膨胀。插件引入了lz-string.js做压缩,压缩后以字符串形式嵌进 HTML 的 script 标签里;浏览器加载页面时再用同样的库解压还原 JSON。这种单文件自包含的交付方式,方便直接发给产线或客户,不依赖任何外部服务器。

前端核心是ibom.jsrender.jsibom.html是页面骨架,ibom.css是样式,render.js负责把元件坐标渲染成 Canvas 图形。pep.js是 Pointer Events 的 polyfill,用来统一鼠标和触摸事件——这样在平板上打开导出的 HTML 也能正常交互。split.js用于实现 BOM 列表和板图之间的可拖拽分栏。

user.jsuser.cssuserheader.htmluserfooter.html这几个文件是留给使用者做自定义扩展的钩子,插件作者把用户可改的部分单独抽出来,避免升级时覆盖自定义内容。结构上这是相当成熟的做法:

文件职责
mainWin.dfm导出参数对话框的窗体定义
mainWin.js对话框逻辑、参数收集
InPcb.jsAD PCB API 封装
AD10.js老版本 API 兼容适配
ibom.js核心交互逻辑:点选、高亮、合集切换
render.jsCanvas 绘制板图与元件
util.js数组去重、字符串处理等工具函数
lz-string.js数据压缩/解压
newstroke_font.js矢量笔画字体,用于在 Canvas 上绘制文字
config.ini导出参数配置
Initialize.bat/UnInitialize.bat安装/卸载脚本

newstroke_font.js很有意思。Canvas 原生fillText依赖系统字体,不同电脑打开字体不一致会导致位号文字位置漂移;插件采用 stroke font(笔画字体)方案,把每个字符定义为一组线段坐标,绘制时逐笔画出来,保证了在任何设备上渲染结果完全一致。代价是中文支持有限,这也是很多用户反映位号中文显示异常的根本原因。

2.4 HTML 与 JS 的协作:交互高亮是怎么实现的

整个交互流程围绕"BOM 行 ↔ 板图元件"的双向绑定展开。左侧 BOM 表按 Value+Footprint 分组,每一组对应一类器件;右侧 Canvas 板图上每个元件绘制为一个小图形。当鼠标悬停在 BOM 行上,ibom.js会遍历该分组下所有元件,在 Canvas 上执行重绘:非目标元件降低透明度,目标元件用高亮色绘制边框。点击板图上的元件时,反向通过元件的唯一索引找到 BOM 分组,滚动列表并重点突出对应行。

网络高亮是交互 BOM 的另一项核心功能。用户点击某个焊盘,插件会找出该焊盘所属的网络,然后把同网络的所有走线、过孔、焊盘一并高亮显示。这个功能在审核阶段特别有用,能直观看到某个电源网络覆盖了哪些区域。实现上仍然走 Canvas 重绘,但需要 AD 端在导出时额外写入网络信息——这就是为什么插件读取数据时,不仅要遍历元件,还要遍历走线和过孔。

3. 安装与配置:从 Initialize.bat 到 config.ini 的逐项说明

3.1 Initialize.bat 做了什么:AD 脚本目录与工程注册

插件压缩包解压后,目录下有两个批处理文件:Initialize.batUnInitialize.bat。前者负责把脚本工程安装到 AD 能识别到的位置,最常见的方式是复制整个目录到C:\Users\Public\Documents\Altium Designer\AD 20\Scripts或用户文档目录下的 Scripts 文件夹,后者负责清理。

提示:AD 的脚本扫描路径可以在 DXP -> Preferences -> Scripting System 里查到。不同 AD 版本的默认脚本目录不一样,安装前先确认一下。

打开 Initialize.bat,典型的逻辑是:

@echo off rem ---------- InteractiveHtmlBomForAD 安装脚本 ---------- set SCRIPT_SRC=%~dp0 set TARGET_DIR=%PUBLIC%\Documents\Altium Designer\AD 20\Scripts\InteractiveHtmlBomForAD rem 目标目录不存在则创建 if not exist "%TARGET_DIR%" mkdir "%TARGET_DIR%" rem 将插件源码整体复制到脚本目录 xcopy "%SCRIPT_SRC%*" "%TARGET_DIR%" /E /I /Y rem 提示安装完成 echo Install done. Restart Altium Designer. pause

%~dp0获取当前批处理所在路径,/E表示复制所有子目录,/I表示目标路径按目录处理,/Y覆盖不提示。如果你的 AD 装在 D 盘或者脚本目录被改过,需要手动把TARGET_DIR改成实际路径。安装完成后要重启 AD,脚本才会出现在可执行列表里。

卸载脚本的逻辑正好相反:删除目标目录并提示用户。这里有一个细节,如果用户后续把自定义的 user.js 放进了脚本目录,卸载会一并删掉——我自己会在改完 user.js 后先把文件备份一份到压缩包外。

3.2 在 Altium Designer 中运行脚本的两种方式

安装完成后,运行方式有两种。第一种是通过菜单DXP -> Run Script(或文件 -> 运行脚本),在弹出的文件选择框里定位InteractiveHtmlBomForAD.PrjScr,选择要执行的函数入口。第二种是在脚本工程窗口中直接打开文件,选中入口函数点击运行按钮。插件通常在 mainWin.js 里暴露了入口,类似:

function main() { var dlg = new MainWin(); dlg.ShowModal(); }

ShowModal()让对话框以模态窗口运行,意味着必须关掉对话框才能回到 AD 主界面。这样设计是为了防止用户在导出过程中继续编辑 PCB,导致数据不一致。对话框出现后,你需要设置输出目录、文件名等参数,然后等待脚本执行完成。

首次运行时如果 AD 没有任何反应,最常见的两个原因:一是代码中访问了不存在的 PCB 文档(没有打开任何 .PcbDoc),二是脚本编译时抛出了语法错误。插件对网络和 PCB 对象有直接依赖,确保当前激活的文档是 PCB,而不是原理图。

3.3 config.ini 参数表:哪些配置影响导出结果

config.ini是插件的又一个用户配置入口,它的作用类似于"导出默认值"。插件读取配置后填入对话框,省去每次手动填写的麻烦。常见配置项包括:

配置项作用建议值
OutputDir导出文件保存目录绝对路径,如D:\BOM_Export
FileNamePrefix文件名前缀比如ProjectA_BOM
CompressData是否压缩内嵌数据true一般保持开启
IncludeBottomSide是否包含底层器件true,除非你对贴装顺序有特殊要求
ShowTopAssembly默认视图显示顶层装配图true
BoardOutlineOnly是否只绘制板框false大多数时候需要显示丝印

参数具体的键名在不同版本里会有差异,但思路一致。改完 config.ini 后需要重启 AD 才能生效,因为脚本在启动阶段一次性加载了配置。如果插件运行时报"无法读取配置文件",多半是路径中包含了中文字符,AD 的部分老版本脚本引擎对 Unicode 路径支持不好,我的做法是把整个工程路径统一改为纯英文。

3.4 完整导出流程与产物验证

安装配置完成后,导出一个实际项目大约需要三个步骤。先打开目标 PCB 文件,确认元件编号完整(Tools -> Design Rule Check 跑一遍,排除未布线或未标号元件)。然后运行脚本,设置输出目录和文件名,项目规模决定等待时间:一个 200 元件的小板子几秒钟就能完成;上千元件且铺铜复杂的板子可能需要十几秒。

关键点来了:输出的 HTML 文件是自包含的。拿到产物后,我强烈建议做一次"换机验证"——把 HTML 复制到一台没装 AD 也没有任何插件库的电脑上,用浏览器打开确认交互正常。因为所有数据已经压进了 HTML,所以只要浏览器能跑,就说明产物没问题。此时给工厂发出去的 BOM 就不只是一张表格了,它是一个可搜索、可定位、可镜像翻面的装配图。

4. 二次定制:把 user.js / user.css / config.js 变成自己的交付模板

4.1 user.css:改造导出页面的视觉识别度

交付给产线的 BOM 页面,默认视觉风格可能不够直观。user.css是 Custom 样式的扩展点,插件在加载完默认ibom.css之后再加载user.css,所以这里的规则可以覆盖前者。常见定制包括:把 BOM 分类表的表头改为深色底白字、增加打印排版适配、给高亮状态增加更强对比度。

/* user.css - 定义公司 BOM 模板样式 */ .bom-table th { background-color: #2d2d2d !important; color: #fff !important; position: sticky; /* 表头滚动吸顶,长列表方便看字段 */ top: 0; } .component-highlighted { stroke: #ff6a00 !important; /* 高亮描边改成醒目橙色 */ stroke-width: 2px !important; } @media print { .split-pane { display: block !important; } /* 打印时改为单栏 */ }

position: sticky配合top: 0让 BOM 表头在向下滚动时固定住,几百行列表时不用来回滚动找列名。打印模式下把分栏布局改成块状,避免板图和 BOM 表被拆分到不同页面。配色上注意不要只用颜色区分状态,丝印图和位号文字在黑白打印时会重叠,建议同时叠加线宽变化。

4.2 user.js:补充“供应商链接”和“复制位号”两个高价值功能

完全默认的 BOM 表格只包含位号、封装、值三层信息。实际交付中,采购需要的是物料编码,或者至少一键打开供应商搜索。在 user.js 里可以扩展一个"供应商链接"列,实现方式是先定义映射表,然后在表格渲染完成后执行插入逻辑。

// user.js - 在 BOM 表中注入供应商查询链接 var supplierMap = { "STM32F103C8T6": "https://item.szlcsc.com/global/search.html?q=", "AMS1117-3.3": "https://item.szlcsc.com/global/search.html?q=" }; window.enhanceBOMPanel = function () { // 找到 BOM 面板容器,插件默认会给一个 id var panel = document.getElementById("bom-panel"); if (!panel) return; // 遍历每个分组的 Value 单元格 panel.querySelectorAll(".bom-value").forEach(function (cell) { var value = cell.textContent.trim(); var url = supplierMap[value]; if (url) { var link = document.createElement("a"); link.href = url + encodeURIComponent(value); link.target = "_blank"; link.textContent = " 采购"; link.style.marginLeft = "6px"; cell.appendChild(link); } }); }; // 插件在数据加载完成后会调用用户钩子(如 onUserScriptLoaded) if (typeof onUserScriptLoaded === "function") { window.addEventListener("load", enhanceBOMPanel, false); }

这段代码的逻辑是在 BOM 面板渲染完成后,扫描每个分组的 Value 单元格,命中映射表就追加一个"采购"链接。encodeURIComponent用来转义物料关键字中的特殊字符,防止链接拼接出错。onUserScriptLoaded是插件预留的用户钩子,具体名称需要打开 ibom.js 源码确认,如果不确定,退而求其次是监听window.load事件。

另一个实用功能是"复制全部位号"。当某个分组有几十个位号时,用户想直接粘贴到邮件或表格工具里,手工一个个复制效率太低。常见做法是给分组的位号列加一个复制按钮:

var designators = dataItem.designators.join(","); navigator.clipboard.writeText(designators).then(function () { console.log("Designators copied:", designators); }).catch(function () { // 老浏览器没有 clipboard 的 fallback var ta = document.createElement("textarea"); ta.value = designators; document.body.appendChild(ta); ta.select(); document.execCommand("copy"); document.body.removeChild(ta); });

优先使用navigator.clipboardAPI,失败时退回document.execCommand("copy")。考虑到导出后的 HTML 可能在不同年代的浏览器上打开,这段兼容代码很有必要。

4.3 config.js:调整分组策略和默认视图

config.js是 IBD 页面端运行时参数,不同于提前读取的config.ini。它在 HTML 加载时生效,主要控制页面显示行为。比如默认按Value + Footprint分组,但如果你需要更细的拆分粒度,可以改成把位号前缀也纳入分组维度;或者设置打开页面时默认显示 BOM 列表面板。

值得注意的参数是:是否默认启用网络高亮、是否在加载时自动滚动到第一个元件、BOM 表初始排序方向(按值还是按位号)。这些设置直接影响一线操作者打开文件后的第一眼体验。我一般会关闭自动滚动,因为产线使用时通常是先搜索位号,而不是依赖加载顺序。

4.4 自定义输出模板的保存:防止升级覆盖

如果你花了不少时间调好了 user.css 和 user.js,请记住把它们单独保存一份到压缩包外。插件升级时通常替换整个目录,如果直接覆盖,你的定制就没了。我的做法是维护一个my-custom文件夹,里面放自己版本的 user.js 和 user.css,升级后把这两个文件复制回去,而不是在压缩包内直接修改原文件。

5. 实战排错:坐标漂移、中文显示、大板卡顿的三个典型坑

5.1 坐标偏移:原点不一致导致板图跑偏

板图整体偏移,最常见的成因是 PCB 原点不在板框左下角。AD 默认的绝对原点在图纸左下角,但设计者在布局时可能把原点挪到了板框内某个器件旁,导致导出的元件绝对坐标与板框相对位置产生固定差值。解决办法有两个层面:一是调整 PCB 原点位置后在导出前重新执行脚本,二是如果你不想动 PCB,就需要在生成 HTML 前对坐标做一次整体平移。

检查手段很简单:在 AD 里按快捷键EO把原点复位到板框左下角,重新导出,看坐标是否对齐。如果对齐了,那问题就出在原点。部分版本插件会在导出界面提供"固定偏移量"选项,这时直接填上原点到板框的相对偏移即可。设计上更稳妥的做法是:PCB 绘制期间原点固定在板框外固定位置,导出文档前强迫自己确认一次。

5.2 位号中文显示为线段:stroke font 的字符集边界

前文提到newstroke_font.js是为保证跨设备渲染一致性而引入的矢量字体,但它本质是一套笔画字体,只覆盖了 ASCII 字符集。如果你的位号含有中文(比如"U_电源模块"),交互页面会绘制出一些奇怪的线段拼凑图案,完全不可读。

这类场景我一般走两条路线:一是统一位号规范为纯英文,这本身也是行业规范;二是放弃笔画字体渲染,改用 Canvas 原生fillText绘制中文。第二种方案要改render.js中的字体渲染函数,风险是不同系统在没有安装对应中文字体时,页面上可能出现方框。折中思路是优先fillText,捕获到字体缺失异常时回退到 stroke font。

5.3 上千元件的大板卡顿:数据的体积瓶颈

元件数量达到 1500+ 时,HTML 文件体积可能达到 10~30 MB,原因是原始 JSON 包含坐标、位号、网络、封装等字段,即使经过 lz-string 压缩,数据体量依然不小。浏览器打开时要去压缩、解析、绘制,整个初始化过程会明显卡顿。

排查思路是分步确认瓶颈。先在 DevTools 的 Performance 面板查看是解析阶段慢还是绘制阶段慢。解析慢就减少内嵌数据:导出时过滤掉不必要的网络、隐藏层或机械层的对象;绘制慢则要降低 Canvas 重绘频率——render.js里常见的优化手法是维护一个脏标记,只有用户交互切到某个器件时才重绘这一层,而不是每次高亮都全量重绘。最简单的优化是导出时关闭不必要的铺铜显示,只保留板框、丝印和元件。

5.4 复用技巧:把交互 BOM 嵌入公司内部工艺系统

如果能跑通基本导出,这个项目的价值还能进一步放大。可以把它嵌入内部工艺文档系统:后端接收 AD 导出的 HTML 文件,解析其中的 BOM 数据,配合 ERP 中的物料编号做交叉匹配,前端在交互页面上直接展示库存状态。实现方式无需改动插件的 AD 端,只需要在前端写一个解析函数读取 lz-string 解压后的 JSON 结构。ISO 文件、工艺卡、首件确认单都能以这份 HTML 为核心载体,做到一物多用。

5.5 最后一步:用最小板子验证配置

换环境后所有功能失灵时,别急着找大项目测试,先做一个最小验证:新建一块空 PCB,只放一个电阻和一个电容,各加一个。导出 HTML,打开浏览器,确认两个元件都能高亮、网络能选中、BOM 分组正确,再把整目录迁移到新机器。小项目跑通能排除 80% 的路径、权限和配置问题,剩下的才是真正需要深挖的插件 bug。

本文还有配套的精品资源,点击获取

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/16 12:54:00

实验室直流电源使用技巧与多通道应用解析

1. 设备基础认知与核心参数解析这台型号为lPS 505N-MO的直流电源供应器,是典型的实验室级三通道输出设备。第一次接触它时,最让我惊讶的是其紧凑机身内竟能实现三组完全独立的输出通道——这意味着可以同时为不同电压需求的电路模块供电,比如…

作者头像 李华
网站建设 2026/9/16 12:53:40

LTX-Video 上手指南:文生视频、图生视频与多条件帧控制

LTX-Video 上手指南:文生视频、图生视频与多条件帧控制 【免费下载链接】LTX-Video Official repository for LTX-Video 项目地址: https://gitcode.com/GitHub_Trending/ltx/LTX-Video LTX-Video 是一个基于 DiT(Diffusion Transformer&#xff…

作者头像 李华
网站建设 2026/9/16 12:52:33

Claude Code实战:10分钟打造AI编程助手

1. Claude Code凯神实战指南:10分钟让AI成为你的编程助手作为一名长期与各类AI编程工具打交道的开发者,我见证了从早期代码补全插件到如今智能编程助手的进化历程。Claude Code的出现彻底改变了我的工作流——它不再只是简单的代码补全工具,而…

作者头像 李华
网站建设 2026/9/16 12:52:29

粒子群算法求解配电网储能优化配置:建模、实现与调参全流程

简介:面向配电网储能优化配置需求,提供了基于粒子群算法的完整Matlab实现方案,适合电力系统方向学生、科研人员及从事新能源并网或储能规划的工程师参考。资源针对配电网与单储能系统,构建了包含运行维护成本与容量配置成本的储能…

作者头像 李华
网站建设 2026/9/16 12:51:09

短视频平台RSA+AES加密接口逆向实战

1. 项目背景与需求分析最近在分析某短视频平台的视频解析接口时,发现其采用了RSAAES双重加密方案。这种组合加密方式在当今Web安全领域非常典型——RSA用于密钥交换,AES用于内容加密。作为爬虫开发者,我们需要逆向这套加密逻辑才能获取目标数…

作者头像 李华