3. NX对象模型基础
在NX二次开发中,几乎所有代码都围绕“对象”展开。与普通面向对象编程不同,NX的绝大多数核心对象并不是由开发者用new创建的,而是由NX进程在启动、打开部件、创建界面时自动构建,开发者只是通过API“获取引用”并操作它们。理解这些对象的获取方式与生命周期,是写出稳定、不崩溃代码的前提。
一、NX对象模型的分层结构
NX的.NET API(NXOpen)大致可分为四层:最顶层是Session,代表当前NX进程的会话;其下是Part(部件)与UI(用户界面)两条主线;Part之下是各类几何与特征对象(Body、Feature、Sketch等),UI之下是各类对话框、菜单、选择控件;而Display(显示)则横跨两者,负责视图、图层、颜色、高亮等可视化状态。它们的关系可以用下图表示。
二、Session:一切操作的入口
Session是NX进程的根对象,通过NXOpen.Session.GetSession()获取。它本身不承载几何数据,而是提供访问Part、UI、Display以及各类全局工具的入口。典型用法如下:
using NXOpen;
Session theSession = Session.GetSession();
Part workPart = theSession.Parts.Work; // 当前工作部件
Part displayPart = theSession.Parts.Display; // 当前显示部件
UI theUI = UI.GetUI(); // 获取UI对象
Session的生命周期与NX进程一致:进程启动时创建,进程退出时销毁。因此不需要(也无法)手动释放Session。但要注意,Session是单例,任何时刻只有一个实例,多线程环境下应避免并发访问。
三、Part:文档级对象与工作/显示部件
Part代表一个已打开的NX部件文件(.prt)。NX中同时可以打开多个Part,但只有一个是工作部件(Work Part),只有一个是显示部件(Display Part)。工作部件是建模操作的目标,显示部件是当前窗口中显示的部件,两者可以不同。例如在装配中,工作部件可能是某个子零件,而显示部件是总装配。
获取Part的常见方式有三种:
theSession.Parts.Work:获取当前工作部件,若没有打开任何部件则返回null。theSession.Parts.Display:获取当前显示部件。theSession.Parts.FindObject("部件名"):按名称查找已加载的部件。
Part的生命周期由NX的打开/关闭操作管理。当用户关闭一个Part时,该Part对象即失效,继续访问其下的几何对象会抛出异常。因此代码中应始终在使用前检查workPart != null,并在长事务中避免缓存Part引用跨越多轮用户交互。
Session.GetSession()和theSession.Parts.Work,这正是因为它们是所有后续操作的起点。理解这一点,就能读懂大部分录制代码的结构。四、UI:交互对象的获取与对话框生命周期
UI对象通过UI.GetUI()获取,负责创建对话框、菜单、选择控件、消息框等。UI本身也是进程级单例,但其下创建的对话框(如BlockDialog)具有明确的生命周期:
- 创建:调用
theUI.CreateDialog("对话框名")或通过BlockDialog构造。 - 显示:调用
dialog.Show(),此时对话框进入交互状态。 - 响应:通过
dialog.GetBlock("blockID")获取控件,读取或设置值。 - 销毁:用户点击确定/取消后,调用
dialog.Dispose()释放资源。
关键点在于:对话框对象在Dispose()之后不可再访问,否则会引发内存访问异常。此外,Show()是模态阻塞调用,代码会停在Show()处等待用户操作,因此对话框的后续处理逻辑通常写在Show()返回之后,或通过回调函数处理。
五、Display:可视化状态的控制
Display对象通过theSession.DisplayManager或theUI相关接口访问,用于控制视图刷新、图层可见性、对象颜色、高亮显示等。它不是数据对象,而是“视图状态”的操作接口。常见操作包括:
theSession.DisplayManager.NewDisplay():创建新的显示窗口。theSession.DisplayManager.Refresh():刷新当前视图。- 通过
Part.Layers设置图层可见性,通过DisplayableObject设置颜色与高亮。
Display的操作通常不改变模型数据,只改变显示状态。因此它没有严格的生命周期约束,但频繁刷新会影响性能,建议在批量修改后统一调用一次刷新。
六、生命周期管理的实践要点
综合来看,NX对象模型的生命周期可以归纳为:Session贯穿进程,Part随文档开关,UI随对话框创建销毁,Display随视图状态变化。在实际开发中,应遵循以下原则:
- 不要缓存Part引用跨越多轮用户操作,每次操作前重新获取
theSession.Parts.Work。 - 对话框使用完毕后必须
Dispose(),避免内存泄漏和句柄残留。 - 访问任何对象前先判空,尤其是
Parts.Work和Parts.Display。 - Display刷新放在逻辑末尾,避免在循环中反复刷新导致界面卡顿。
- 在异常处理中释放已创建的对话框资源,保证UI对象不残留。
Show()返回后继续访问对话框内的控件。此时对话框可能已被销毁,正确做法是在Show()返回前通过回调或GetBlock读取所需值,或使用dialog.GetInteger("blockID")在Show()返回后立即取值(部分版本支持),但更稳妥的方式是在Update回调中处理。掌握这些对象的获取方式与生命周期边界,就能在后续的特征创建、装配操作、自动化批处理中避免大部分“对象已失效”或“空引用”类错误,为更复杂的二次开发打下坚实基础。