版本声明(全系列统一口径)
本篇基线为AVEVA E3D Design 3.1;帮助站可确认的文档版本线为1.1 / 2.1 / 3.1,docs.aveva.com的版本索引把当前版本列为 E3D Design 3.1。AVEVA PDMS 自 2024 年 4 月 1 日起不再销售、不再提供支持,本系列不把它作为新开发目标。
正文中的环境变量名、界面路径、文档入口均出自官方文档;凡来自 AVEVA Community 或第三方博客的内容一律标注来源性质;凡按官方 API 或环境变量名构造、未在本机跑通的代码一律标注**“需在本地 E3D Design 环境验证”**。官方未公开的项(官方示例下载页、独立 Core/Core3D API 参考站、公开免费试用或下载页)只写"官方未公开"。
一句话结论
开发前自检只解决四个问题——版本对不对、入口找不找得到、路径通不通、示例工程在不在;这四件事全部可以在 30 分钟内用一条 PowerShell 脚本加一个 PML 探针验完,而跳过它们的人通常会在写完几百行代码之后才发现"根因在环境"。
〇认知问题
- 我要装的到底是哪个版本?怎么确认我手上这套是 E3D Design 3.1 而不是别的什么东西?
- 官方让写 PML 的那个"命令行窗口",官方到底叫什么名字?为什么我在文档里搜 “PML Console” 一条都搜不到?
PMLLIB到底管什么?为什么我在别的机器上能跑的函数,搬到这台就不认了?- CAF 那四个环境变量分别控制什么?不设会怎样?
- 官方示例代码到哪里去找?网上搜到的示例仓库可信吗?
- 四本二次开发手册各管什么?我应该先翻哪一本?
一机制解析
1.1 版本线怎么确认(三轮验证,不靠记忆)
版本对齐是铁律,但"对齐"需要一个可执行的确认动作。建议做三轮:
第一轮,看文档版本号。打开 https://help.aveva.com/AVEVA_Everything3D/3.1/GS/GS_FP.html,URL 里的3.1就是文档版本。把3.1手工改成1.1、2.1也能打开,说明三代文档都在线上——这也正是不能凭"能打开就算存在"来判断版本的原因。要拿权威口径,看docs.aveva.com的版本索引,它把当前版本列为E3D Design 3.1(https://docs.aveva.com/bundle/system-platform-2023-r2-sp1)。
第二轮,看安装侧证据。环境变量AVEVA_DESIGN_EXE指向 E3D Design 安装目录(官方 NCUG 3.04.3 把它列为关键环境变量之一)。列出该目录下的可执行文件与版本信息,是最直接的现场证据。
第三轮,排除误判项。这一步专门用来打掉三种常见错觉:
- “我装的是 15.x”—— 15.x 是AVEVA Engineering的版本,不是 E3D Design。文档站在同一页会同时列出 “E3D Design 3.1” 与 “Engineering 15.8” 这类条目(https://docs.aveva.com/bundle/system-platform-2023-r2-sp1)。
- “帮助站页面能打开就等于这个版本存在”——
docs.aveva.com对版本化 slug(如/bundle/e3d-design-3-1)会统一返回 200 的 SPA 兜底页,但这些 slug 在 sitemap 中并不存在。200 不能作为版本存在的证据。 - “我装的是最新版”—— 官方发布页 https://www.aveva.com/en/info/e3d-design-releases/ 只回溯到 2022 年 2 月,2023–2026 的发布条目在公开页面未找到;能确认的是 3.1.4.0(2022-02,MultiCAD、Work Packs、Space Management、Rule Manager 扩展)与 3.1.5.0(2022-04,Graphical Explorer、通过 PMLNETCALLABLE 导入 ML.NET 模型)。
还有一条必须提前知道的授权前提:官方未公开E3D/PDMS 的公开免费试用或下载页(只有 Demo 申请渠道)。这直接影响你的开发方式——很多团队是"开发机一套、测试 MDB 一套",如果没有可写的测试库,写库操作只能在正式库上做,风险极高。
1.2 官方入口名是 Command Window,不是 “PML Console”
这是本系列第一个必须纠正的习惯用法,因为它会直接影响你的检索效率。
官方名称是 Command Window(命令窗口)。GS 手册原文给的是界面路径:Tools 标签 → Display 组 → 点击 Commands,打开 Command Window(https://help.aveva.com/AVEVA_Everything3D/3.1/GS/GS6.6.8.html)。实测在 3.1 版 GS 目录中检索 “Console”零命中。
为什么这件事重要?因为你在网上能看到大量"PML 控制台"的写法,一旦按这个词去搜官方文档,命中率会非常低,于是很多人转而依赖第三方教程,最终把未经核实的语法写进生产脚本。本篇之后的全部内容,一律统一写 “Command Window”。
1.3 环境变量:PMLLIB 与四个 CAF 变量
PMLLIB是 PML 的搜索路径环境变量,PML 的函数、表单、对象文件(按官方培训材料口径为.pmlfnc、.pmlfrm、.pmlobj)就靠它定位。它的典型症状非常好认:同一份代码在 A 机器能跑、在 B 机器报"找不到函数"。绝大多数情况下不是代码问题,而是 B 机器的PMLLIB少了一个路径段。
四个 CAF 环境变量(官方 NCUG 3.04.3,https://help.aveva.com/AVEVA_Everything3D/3.1/NCUG/NCUG3.04.3.html):
| 变量 | 作用 | 不设的后果 |
|---|---|---|
AVEVA_DESIGN_EXE | E3D Design 安装目录 | PML.NET 找不到要载入的程序集(其查找路径含%AVEVA_DESIGN_EXE%目录及其子目录) |
CAF_ADDINS_PATH | Addin 所在位置,覆盖<模块名>Addins.xml的默认位置(默认与可执行文件同目录) | 自定义 dll 不被加载,菜单点了没反应 |
CAF_UIC_PATH | 界面定义文件位置,按<模块名>Customisation.xml查找并列出.uic | 自定义菜单/工具栏不出现 |
AVEVA_CAF_TRACING | 开发期跟踪开关 | 出问题时没有跟踪信息,排错只能猜 |
其中CAF_ADDINS_PATH支持以;分隔多个路径,也支持UNC 路径(官方 NCUG 2.03.10,https://help.aveva.com/AVEVA_Everything3D/3.1/NCUG/NCUG2.03.10.html)。关于装载配置还有一条必须记住的规则:每个 CAF 应用有一个<模块名>Addins.xml,例如MODEL 模块对应DesignAddins.xml,默认与可执行文件同目录。
实践建议(本系列一致口径):所有环境变量统一在启动脚本里设好,不靠个人机器的系统属性。理由很直接——个人机器配置不可复现、不可审计,一旦换人接手,环境就"莫名失效"。
1.4 安装目录里的 Samples.zip 与"可信资源"边界
官方示例代码包的位置:安装目录(AVEVA_DESIGN_EXE所指向的目录)下的Samples.zip,内含 C# 源码与 Visual Studio 工程。官方文档中给出的示例工程名有:AttributeBrowserAddin、ExamplesAddin、FlexibleExplorerAddin、NetGridExample、PMLNetExample、PMLGridExample(https://help.aveva.com/AVEVA_Everything3D/3.1/NCUG/NCUG_FP.html、NCUG2.03.02.html)。
这里必须划一条线:AVEVA 官方 GitHub 组织下公开的 PML/.NET 示例仓库或示例下载页未找到;官方示例的确认渠道只有Samples.zip。因此任何声称"这是 AVEVA 官方 GitHub 示例库"的链接,都需要你自行核实来源性质。
可以引用的第三方资源(均明确标注为第三方,非官方):
- VS Code 扩展
mikhalchankasm/vscode-pml-aveva-e3d:AVEVA E3D PML 的 LSP 语言服务器 + VS Code 扩展(MIT 许可),提供 PML1/PML2 语法高亮、IntelliSense、表单/回调 CodeLens,支持.pml/.pmlobj/.pmlfnc/.pmlfrm/.pmlmac/.pmlcmd(https://github.com/mikhalchankasm/vscode-pml-aveva-e3d)。 - PyPI 包
pyavevae3dext:Python 侧访问 E3D 的桥接库,提供GetPmlString/GetPmlReal/GetPmlBool等取值方法(https://pypi.org/project/pyavevae3dext/)。
1.5 四本手册各管什么
| 手册 | 代号 | 什么时候翻它 |
|---|---|---|
| .NET Customisation User Guide | NCUG | 写 .NET Addin、Command、UIC、DbElement、PML.NET 时 |
| PML Customisation User Guide | PMLCG | 写 PML/PML2 时:控制逻辑、宏、表单、回调、命令、错误处理 |
| Software Customisation | SCRM | 查"这个对象有哪些成员和方法"时(对象/成员/方法总参考) |
| AVEVA CAF API 参考 | — | 查 CAF API 类型签名时(唯一公开的独立 API 参考站) |
PMLCG 的正式章节名可直接当检索关键词使用:Introduction、Variables/Objects/Functions and Methods、General Features of PML、PML Expressions、Control Logic、Arrays、Macros、Using PML in AVEVA Products、Errors and Error Handling、Developing PML Code、Form Concepts、Form and Gadget Callbacks、Forms、Commands、Form Layout、Menus、Frames、Gadgets and their Attributes、Alert Objects、FMSYS/CMSYS Object、PML Add-ins、Core Managed Objects、Flexible Explorer Control(https://help.aveva.com/AVEVA_Everything3D/3.1/PMLPUG/PMLCG_FP.html)。
SCRM 的章节为:Summary of Objects, Members and Methods / Methods Available to All Objects / Forms and Menus Objects / Summary of Gadget-Specific Methods / Gadget Syntax Graphs / Object Type Details。
另外三本常被忽略但很有用的手册:Getting Started(GS)、Database Management(DBRM,含 Expressions 章)、DRAW 参考(DRUGP)。
1.6 开发前自检清单
| # | 检查项 | 通过标准 | 不通过的处置 |
|---|---|---|---|
| 1 | 产品与版本 | 能说清"本机是 E3D Design 3.1 文档线",并能排除 15.x 误判 | 回到 1.1 的三轮验证 |
| 2 | Command Window | 能从 Tools → Display → Commands 打开,并能执行一行命令 | 确认模块已进入 Design/MODEL 环境 |
| 3 | PMLLIB | 探针宏能被$m/...调起;.pmlfnc里的函数能被调用 | 检查路径分隔与拼写,逐个路径段验证 |
| 4 | AVEVA_DESIGN_EXE | 变量可读,且指向真实存在的安装目录 | 在启动脚本里显式设置 |
| 5 | CAF_ADDINS_PATH/CAF_UIC_PATH | 变量可读,路径存在,;分隔正确 | 同上 |
| 6 | AVEVA_CAF_TRACING | 知道在哪打开、在哪看输出 | 查本地 NCUG 3.04.3 |
| 7 | Samples.zip | 在安装目录找到该压缩包,能列出官方示例工程名 | 联系本地管理员索取安装包 |
| 8 | 四本手册入口 | 四个 URL 均能打开且正文可读(优先help.aveva.com) | 换用docs.aveva.com做检索式跳转 |
| 9 | 测试 MDB | 有一个可写、可回退的测试模型库 | 没有测试库就不要做写库操作 |
| 10 | 版本控制 | 自定义 PML 与 dll 已入库 | 先建仓库,再写第一行代码 |
二完整代码与逐行剖析
2.1 PowerShell 环境自检脚本
把下面这段存成e3d-dev-check.ps1,在开发机上运行。它只做"读"和"打印",不改动任何系统设置。
# E3D 二次开发环境自检脚本(只读,不做任何系统改动)# 注意:路径请按本机实际安装位置修改# --- 1) 设置本次会话的环境变量(若已在启动脚本里设好,可跳过)---$env:PMLLIB ='D:\AVEVA\E3D31\PMLLIB'# PML 搜索路径,可用 ; 分隔多段$env:AVEVA_DESIGN_EXE ='C:\Program Files\AVEVA\E3D Design 3.1'# 安装目录$env:CAF_ADDINS_PATH ='D:\E3DDev\addins'# Addin 位置,覆盖默认(可 ; 分隔、可用 UNC)$env:CAF_UIC_PATH ='D:\E3DDev\uic'# UIC 界面定义文件位置# $env:AVEVA_CAF_TRACING = '...' # 开发期跟踪开关;启用值与输出位置请以本机 NCUG 3.04.3 为准# --- 2) 逐个检查变量是否可读、路径是否存在 ---$names='PMLLIB','AVEVA_DESIGN_EXE','CAF_ADDINS_PATH','CAF_UIC_PATH','AVEVA_CAF_TRACING'foreach($nin$names){$v=[Environment]::GetEnvironmentVariable($n)if([string]::IsNullOrWhiteSpace($v)){Write-Host("[未设置] {0}"-f$n)-ForegroundColor Yellowcontinue}# 某些变量是路径列表(; 分隔),逐个判断存在性$segs=$v-split';'foreach($sin$segs){if(Test-Path-LiteralPath$s){Write-Host("[ 存在] {0} -> {1}"-f$n,$s)-ForegroundColor Green}else{Write-Host("[ 不存在] {0} -> {1}"-f$n,$s)-ForegroundColor Red}}}# --- 3) 列出安装目录下的可执行文件与版本信息(不做任何推断)---$dir=$env:AVEVA_DESIGN_EXEif($dir-and(Test-Path-LiteralPath$dir)){Write-Host"`n安装目录下的可执行文件(取前 20 条):"-ForegroundColor CyanGet-ChildItem-LiteralPath$dir-Filter*.exe-File-ErrorAction SilentlyContinue|Select-Object-First 20|ForEach-Object{"{0,-45} {1}"-f$_.Name,$_.VersionInfo.FileVersion}}else{Write-Host"AVEVA_DESIGN_EXE 未指向有效目录,无法列表。"-ForegroundColor Red}# --- 4) 查找官方示例包 Samples.zip ---if($dir-and(Test-Path-LiteralPath$dir)){$zip=Get-ChildItem-LiteralPath$dir-Filter'Samples.zip'-File-Recurse-Depth 1-ErrorAction SilentlyContinueif($zip){Write-Host"`n找到官方示例包:"-ForegroundColor Green$zip|ForEach-Object{$_.FullName}}else{Write-Host"`n未在安装目录附近找到 Samples.zip,请向本机管理员确认安装包完整性。"-ForegroundColor Yellow}}逐段剖析:
- 第一段是会话级环境变量设置。放在脚本里而不是系统属性里,符合"环境可复现"的要求;
PMLLIB与CAF_ADDINS_PATH都支持;分隔多段。 - 第二段用
[Environment]::GetEnvironmentVariable读取进程级变量,逐个打印"存在 / 不存在"。这是把"我以为设了"变成"我看见了"的关键一步。 - 第三段列出安装目录下的
*.exe及其VersionInfo.FileVersion。这里刻意不做任何"版本 = x.y"的推断,只是把现场证据摆出来给你判断——因为 AVEVA 官方产品页并没有列出 PDMS 的版本号清单,凭文件名猜版本是常见的误判来源。 - 第四段查找
Samples.zip。官方示例的确认渠道就是它,找不到就说明安装包或环境有问题。 - 注意:脚本中的路径是占位示例,需在本地 E3D Design 环境下按实际安装位置修改并验证。
2.2 PML 侧探针宏
在PMLLIB覆盖的任一路径下建一个目录(比如probe),放两个文件。
第一个文件pmllibtarget.pmlfnc,用来验证"函数能不能被找到":
-- 文件:pmllibtarget.pmlfnc -- 用途:探针函数,用来验证 PMLLIB 是否包含本目录 -- 说明:本函数由教程按官方 .pmlfnc 写法构造,需在本地 E3D Design 环境验证 define function !!probeTag() is STRING return 'PMLLIB-OK' endfunction第二个文件selfcheck.mac,用$m/调起:
-- 文件:selfcheck.mac -- 用途:环境自检宏。逐行执行,观察 Command Window 的回显。 -- 来源:写法沿用官方培训材料中的宏调用与查询形式 P ---- begin selfcheck ---- -- 1) 验证 PMLLIB:能调起说明该路径已在 PMLLIB 中 !tag = !!probeTag() q var !tag -- 2) 导出当前元素的关键属性(这些属性名出自官方文档与培训材料的真实示例) q var !!ce.flnn q var !!ce.name q var !!ce.type q var !!ce.position P ---- end selfcheck ----逐行剖析:
P ...:PML 的输出命令,用于把后面这串内容打到 Command Window。本篇用它做分段与标签,是因为它在官方示例里出现过(官方控制逻辑示例中的P CE is Branch.)。!tag = !!probeTag():调用上面那个函数并把返回值赋给局部变量。这一行是探针的核心——如果PMLLIB里没有包含存放pmllibtarget.pmlfnc的目录,这一行就会失败,从而把"路径没配好"这件事变成一个可见的报错。写法上刻意只用两种已被官方示例证实的形态:函数调用与赋值(官方示例!area = !!area(12, 200)),不做行内$注入,避免把"未验证的组合写法"混进排错工具里。q var !tag:以"变量形式"打印!tag(官方示例q var !!ce.flnn、社区宏里的q var !q都是这个用法)。看到PMLLIB-OK就说明PMLLIB覆盖到了该目录。q var !!ce.flnn/q var !!ce.name/q var !!ce.type/q var !!ce.position:!!ce是跟踪当前元素的全局变量;flnn、name、type、position四个属性名均出自官方的真实示例代码(q var !!ce.flnn出现在官方表单示例的方法体里;!!ce.name、!!ce.type、!!ce.position出现在官方对象示例GETELEMENTINFORMATION中)。- 关于版本信息:在本篇所依据的官方材料范围内,没有找到"在 PML 侧直接打印产品版本号"的已核实命令或方法名。因此版本核验请放在系统侧完成(2.1 的脚本 + 帮助站 URL 版本号),不要在脚本里臆造一个打印版本的命令。
- 运行方式:按官方培训材料口径,
$M/%PDMSUI%\examples\simpleMac.mac或$m/FILENAME——把FILENAME换成你的selfcheck.mac全路径。
2.3 C# 侧读取 AVEVA_DESIGN_EXE
这一段用来验证"企业侧程序能否读到 AVEVA 环境"。它是一个普通控制台程序,不依赖 E3D 进程。
usingSystem;usingSystem.IO;// 用途:在企业侧程序里读取 AVEVA 关键环境变量,做"环境就绪"前置判断。// 说明:环境变量名取自官方 NCUG 3.04.3;本程序按标准 .NET 写法构造,// 需在本地 E3D Design 环境验证(尤其是变量是否在进程级可见)。classEnvProbe{staticvoidMain(){string[]names={"AVEVA_DESIGN_EXE","CAF_ADDINS_PATH","CAF_UIC_PATH","PMLLIB"};foreach(stringninnames){stringv=Environment.GetEnvironmentVariable(n);// 进程级读取if(string.IsNullOrWhiteSpace(v)){Console.WriteLine("[未设置] "+n);continue;}// CAF_ADDINS_PATH 与 PMLLIB 可能是 ; 分隔的路径列表foreach(stringseginv.Split(';')){strings=seg.Trim();if(s.Length==0)continue;Console.WriteLine((Directory.Exists(s)?"[ 存在]":"[不存在]")+" "+n+" -> "+s);}}}}逐行剖析:
Environment.GetEnvironmentVariable(n):读取当前进程可见的环境变量。这里有一个非常容易忽略的前提——从外部程序启动 E3D 时,环境变量必须在进程级就已经存在,否则读到的会是空字符串。这也是"启动脚本统一设变量"这一实践的直接理由。v.Split(';'):CAF_ADDINS_PATH官方支持;分隔多路径,PMLLIB同理。逐个路径判断存在性,比整体判断有用得多——因为只要有一段写错,加载就会静默失败。- 不要在这段程序里用
Directory.GetFiles去"猜"程序集名。程序集名请从官方文档取值(如Aveva.Core.Database.dll、Aveva.ApplicationFramework.dll),而不是靠搜索文件名匹配——历史上 PDMS 12.0 时代用的是Pdms.Database.dll、PDMSFilters.dll,靠模糊匹配极易把旧名当成新名。
三常见报错与排查
症状一:函数调用失败,提示找不到某个 PML 函数/对象。
- 现象:同样的
.pmlfnc,在同事机器上正常,在你机器上"找不到"。 - 原因:
PMLLIB未包含该文件所在目录;或目录在PMLLIB中但拼写/分隔符有误(;与空格混淆最常见)。 - 处置:用 2.2 的探针宏跑一次,确认
probe tag = PMLLIB-OK能打印出来;随后逐段核对PMLLIB(建议在脚本里把每个路径段单独Test-Path一次)。统一在启动脚本里设变量,不要依赖个人机器配置。
症状二:在官方文档里检索 “PML Console”、“Console” 零命中。
- 现象:想找"PML 命令行窗口"的官方说明,搜不到。
- 原因:官方没有这个名称。官方入口名是Command Window,路径为Tools 标签 → Display 组 → Commands(官方 GS 手册 GS6.6.8)。
- 处置:改用 “Command Window” 作为检索词;在团队文档里也统一用这个名称,避免新人在错误的路标上浪费半天。
症状三:自定义菜单/工具栏完全不出现。
- 现象:dll 编译通过,
<模块名>Addins.xml(MODEL 模块对应DesignAddins.xml)也放了,界面没有任何变化。 - 原因:
CAF_ADDINS_PATH没有指向 dll 所在目录(它覆盖默认的"与可执行文件同目录"),或CAF_UIC_PATH没有指向含.uic的目录,或<模块名>Customisation.xml的<UICustomizationFiles>里没列出你的 UIC(注意其中的$1会被当前工程名替换,路径写法必须考虑这一点)。 - 处置:先按 2.1 脚本确认两个变量的每一段路径都存在;再打开
AVEVA_CAF_TRACING(开发期跟踪)看加载日志;最后确认命令类的Key与 UIC 中的引用完全一致。
症状四:外部程序启动 E3D 之后,Addin 报了"读不到环境"的错。
- 现象:手工启动 E3D 一切正常,从企业系统里拉起来就异常。
- 原因:环境变量只设在了交互式 shell 里,没有进入被启动进程的环境块。
- 处置:把环境变量写进启动脚本或服务配置,用 2.3 的控制台程序在同一启动上下文里先跑一次验证;确认无
[未设置]再启动 E3D。
四动手练习
练习 1(15 分钟):把 2.1 的脚本按你本机路径改好并运行。合格判定:PMLLIB、AVEVA_DESIGN_EXE、CAF_ADDINS_PATH、CAF_UIC_PATH四个变量的每一段路径都打印为[存在];AVEVA_CAF_TRACING允许显示[未设置],但你必须能说清它在本地文档的哪一页说明。
练习 2(15 分钟):在 Command Window 里手工执行 2.2 的探针。合格判定:能看到PMLLIB-OK被打印出来;四个q var至少有三个打印出真实值(若当前元素为空,!!ce相关可能报错,这本身也是正确结果,记下报错原文即可)。
练习 3(10 分钟):在安装目录里找到Samples.zip,用解压工具列出其中的工程目录名,并核对是否包含官方文档列出的示例工程(AttributeBrowserAddin、ExamplesAddin、FlexibleExplorerAddin、NetGridExample、PMLNetExample、PMLGridExample)。合格判定:至少能对上 4 个名字;对不上的部分记录为"本机安装包版本差异"。
练习 4(10 分钟):做一次"来源性质标注"训练。打开 https://github.com/mikhalchankasm/vscode-pml-aveva-e3d 和 https://pypi.org/project/pyavevae3dext/,用一句话说清它们分别是什么、以及为什么它们不能被称为"官方工具"。合格判定:能明确指出它们是可核实的第三方开源资源,且官方示例的确认渠道只有安装目录下的Samples.zip。
五小结与下一篇预告
本篇把"环境"从"感觉"变成了"证据":版本要三轮验证(文档版本号、安装侧证据、排除 15.x 与 200 兜底页误判);官方唯一的 PML 交互入口是 Command Window(Tools → Display → Commands),文档里没有 “PML Console” 这个词;PMLLIB管 PML 文件搜索,四个 CAF 变量分别管安装目录、Addin 位置、UIC 位置与开发期跟踪;官方示例只随Samples.zip提供,官方 GitHub 示例库未找到。
下一篇《第一个 PML 宏:参数化宏与命令注入》会正式动手:宏的三种调用形式、“宏没有参数声明,参数就是行尾多写的东西”这一反直觉机制、以及如何把 PML 变量注入到命令字符串里去做参数化建模。
文末 FAQ
Q1:我要装的到底是哪个版本?怎么确认我手上这套是 E3D Design 3.1 而不是别的什么东西?
看文档版本号(如help.aveva.com/AVEVA_Everything3D/3.1/...中的3.1),并以docs.aveva.com版本索引为准——它把当前版本列为 E3D Design 3.1。帮助站上可确认的文档版本线是 1.1 / 2.1 / 3.1 三代,所以"能打开某代文档"不等于"你装的是那一代"。同时要在现场核对:读环境变量AVEVA_DESIGN_EXE找到安装目录,列出其中的可执行文件与版本信息作为现场证据。并且用排除法打掉误判:15.x 是 AVEVA Engineering 的版本而非 E3D;docs.aveva.com对不存在的版本化 slug 也会返回 HTTP 200 的 SPA 兜底页,所以"页面能打开"不能作为版本存在的证据。
Q2:官方让写 PML 的那个"命令行窗口",官方到底叫什么名字?为什么我在文档里搜 “PML Console” 一条都搜不到?
官方名称是Command Window(命令窗口),打开路径是Tools 标签 → Display 组 → 点击 Commands(官方 Getting Started 手册 GS6.6.8)。搜不到 “PML Console” 是因为官方根本没有这个名称——实测在 3.1 版 GS 目录中检索 “Console” 零命中。请统一使用 “Command Window” 作为书面与口头用词,这也是本系列的一致性要求。
Q3:PMLLIB到底管什么?为什么我在别的机器上能跑的函数,搬到这台就不认了?PMLLIB是 PML 的搜索路径环境变量,PML 的函数(.pmlfnc)、表单(.pmlfrm)、对象(.pmlobj)文件靠它定位。跨机器失效的最常见原因是目标机器的PMLLIB缺少某个路径段,或者路径列表的;分隔写错、把空格当成了分隔符。排查方法是写一个探针函数放进该目录、用$m/...调起宏来验证PMLLIB是否覆盖到该目录;更稳妥的做法是把PMLLIB统一写在启动脚本里,不依赖个人机器配置。
Q4:CAF 那四个环境变量分别控制什么?不设会怎样?
按官方 NCUG 3.04.3:AVEVA_DESIGN_EXE指向 E3D Design 安装目录(也影响 PML.NET 的程序集查找路径),不设则程序集可能载入失败;CAF_ADDINS_PATH指定 Addin 位置、覆盖默认的"与可执行文件同目录",不设则你的 dll 不会被加载;CAF_UIC_PATH指定界面定义文件位置、按<模块名>Customisation.xml查找并列出.uic,不设则自定义菜单/工具栏不出现;AVEVA_CAF_TRACING是开发期跟踪开关,不设则出问题时缺少跟踪信息。注意CAF_ADDINS_PATH支持;分隔多路径,也支持 UNC 路径。另外,每个 CAF 应用有一个<模块名>Addins.xml,MODEL 模块对应的是DesignAddins.xml。
Q5:官方示例代码到哪里去找?网上搜到的示例仓库可信吗?
官方示例的确认渠道是安装目录(AVEVA_DESIGN_EXE所指目录)下的Samples.zip,内含 C# 源码与 Visual Studio 工程;官方文档中出现的示例工程名有 AttributeBrowserAddin、ExamplesAddin、FlexibleExplorerAddin、NetGridExample、PMLNetExample、PMLGridExample。AVEVA 官方 GitHub 组织下公开的 PML/.NET 示例仓库或示例下载页未找到,因此任何以"官方 GitHub"名义出现的仓库都需要自行核实来源。可以核实的第三方资源有 MIT 许可的 VS Code 扩展mikhalchankasm/vscode-pml-aveva-e3d(PML LSP,支持.pml/.pmlobj/.pmlfnc/.pmlfrm/.pmlmac/.pmlcmd)和 PyPI 上的pyavevae3dext(提供GetPmlString/GetPmlReal/GetPmlBool)——它们都只能标注为第三方,不能写成官方工具。
Q6:四本二次开发手册各管什么?我应该先翻哪一本?
NCUG(.NET Customisation User Guide)管 .NET Addin、Command、UIC、DbElement、PML.NET;PMLCG(PML Customisation User Guide)管 PML/PML2 的语言与控制逻辑、宏、表单、回调、命令、错误处理;SCRM(Software Customisation)是对象/成员/方法总参考,用来查"这个对象有哪些成员和方法";另有唯一公开的独立 API 参考站是 AVEVA CAF API 参考(https://help.aveva.com/API/CAF/index.html)。入门顺序建议先 PMLCG(甚至只先看 Control Logic、Macros、Errors and Error Handling 三章),写界面时再翻 SCRM 与 NCUG。检索时优先用help.aveva.com的静态页(正文可直接抓取、可核对),用docs.aveva.com做跳转检索。