获取NX装配结构信息
最近在做一个项目,需要获取NX装配结构信息,这里把代码分享给大家,希望对各位有帮助,注意以下几点:
1)代码获取了PART的属性、表达式等,因此一些细节可能需要您根据实际情况修改。
2)读写XML用的pugixml,需要您包含到工程中,接口使用的是宽字符模式,所以在pugiconfig.hpp需要打开宽字符开关。

题外话,本人用过的解析XML的库有微软MSXML、markup、tinyxml、pugixml等,其中pugixml是最好用的,强烈推荐给大家,下载地址:pugixml。
3)代码功能是传入一个装配part,生成一个包含装配信息的xml。
4)代码采用ug open c实现,如果您需要在C#、Java等其他工程中调用,可将其包装成独立的exe,采用后台方式调用。
5)如果您不需要生成XML,可不生成,直接使用其内存对象即可。
6)该代码只是抛砖引玉,仅供参考。
VS后台传参如下:

由于装配结构嵌套可能非常多,生成的xml结构大致如下:

代码如下:
1 // GenarateAssemblyInfo.cpp : 定义控制台应用程序的入口点。
2 //
3
4 #include "stdafx.h"
5 #include "pugiconfig.hpp"
6 #include "pugixml.hpp"
7 #include <windows.h>
8 #include <stdlib.h>
9 #include <uf_attr.h>
10 #include <uf_modl.h>
11 #include <uf.h>
12 #include <uf_part.h>
13 #include <uf_assem.h>
14 #include <uf_ui_ugopen.h>
15 #include <map>
16 #include <vector>
17 #include <NXSigningResource.cpp>
18 using namespace std;
19
20 #ifndef SAFE_DELETE
21 #define SAFE_DELETE(p) do{ if(p){delete(p);(p)=NULL;} }while(0)
22 #endif
23 typedef struct _tagAssemblyInfo
24 {
25 _tagAssemblyInfo()
26 {
27
28 }
29
30 virtual ~_tagAssemblyInfo()
31 {
32 for (vector<_tagAssemblyInfo*>::iterator iter = children.begin(); iter != children.end(); ++iter)
33 {
34 SAFE_DELETE (*iter);
35 }
36 }
37
38 string path;//原型路径
39 map<string,map<string, string>> attr; //组,键值对
40 vector<_tagAssemblyInfo*> children;//子件
41 }AssemblyInfo;
42
43
44 string TCHAR2char( const TCHAR* STR)
45 {
46 string strchar;
47 if (!*STR)
48 {
49 return strchar;
50 }
51
52 //返回字符串的长度
53 int size = WideCharToMultiByte(CP_ACP, 0, STR, -1, NULL, 0, NULL, FALSE);
54
55 //申请一个多字节的字符串变量
56 char* str = new char[sizeof(char) * size];
57
58 //将STR转成str
59 WideCharToMultiByte(CP_ACP, 0, STR, -1, str, size, NULL, FALSE);
60 strchar = str;
61 delete (str);
62
63 return strchar;
64 }
65
66 TCHAR* char2TCAHR(const char* str)
67 {
68 int size = MultiByteToWideChar(CP_ACP, 0, str, -1, NULL, 0);
69
70 TCHAR* retStr = new TCHAR[size * sizeof(TCHAR)];
71
72 MultiByteToWideChar(CP_ACP, 0, str, -1, retStr, size);
73
74 return retStr;
75 }
76
77 void ReadExpression(AssemblyInfo* info,tag_t obj)
78 {
79 if ((NULL == info) || (NULL_TAG == obj))
80 {
81 return ;
82 }
83
84 int number_of_exps = 0;
85 tag_t *exps = NULL;
86 UF_MODL_ask_exps_of_part(obj,&number_of_exps,&exps);
87 char *name = "Exp";
88 for (int i = 0; i < number_of_exps; ++i)
89 {
90 tag_t expTag = *(exps + i);
91 char* expStr = NULL;
92 UF_MODL_ask_exp_tag_string(expTag, &expStr);
93 char* leftStr = NULL;
94 char* rightStr = NULL;
95 UF_MODL_dissect_exp_string(expStr, &leftStr, &rightStr,&expTag );
96 info->attr[name].insert(make_pair(leftStr,rightStr));
97 UF_free(expStr);
98 UF_free(leftStr);
99 UF_free(rightStr);
100 }
101
102 UF_free(exps);
103 }
104
105
106 void ReadAttribute(AssemblyInfo* info,tag_t obj)
107 {
108 if ((NULL == info) || (NULL_TAG == obj))
109 {
110 return ;
111 }
112
113 char* category[] = {"ParameterExpression","ParameterMapping", "FxPartThumbnail"}; //组名称
114
115 for (int i = 0; i < _countof(category); ++i)
116 {
117 int num_attributes = 0;
118 logical has_attribute = false;
119
120 UF_ATTR_info_t attr_info = {0};
121 UF_ATTR_init_user_attribute_info(&attr_info);
122
123 UF_ATTR_iterator_t query;
124 UF_ATTR_init_user_attribute_iterator(&query);
125 query.category = category[i];
126 query.check_category = true;
127 query.type = UF_ATTR_string;
128
129 UF_ATTR_get_user_attribute(obj,&query,&attr_info,&has_attribute);
130 while (has_attribute)
131 {
132 info->attr[query.category].insert(make_pair(attr_info.title,attr_info.string_value));
133 UF_ATTR_free_user_attribute_info_strings(&attr_info);
134 UF_ATTR_get_next_user_attribute(obj,&query,&attr_info,&has_attribute);
135 }
136 }
137 }
138
139 void GetAssembly(AssemblyInfo* info,tag_t occ)
140 {
141 if ((NULL == info) || (NULL_TAG == occ))
142 {
143 return ;
144 }
145 tag_t prototype = UF_ASSEM_ask_prototype_of_occ(occ);
146 UF_PART_set_display_part(prototype);
147
148 //根据obj获取路径及属性
149 char part_fspec [MAX_FSPEC_SIZE+1] = {0};
150 UF_PART_ask_part_name(prototype,part_fspec);
151 info->path = part_fspec;
152
153 //根据obj获取属性
154 ReadAttribute(info, prototype);
155
156 //根据obj获取表达式
157 ReadExpression(info, prototype);
158
159 //遍历子节点
160 tag_t *child_part_occs = NULL;
161
162 int number = UF_ASSEM_ask_part_occ_children(occ, &child_part_occs);
163 for (int i = 0; i < number; ++i)
164 {
165 AssemblyInfo* childInfo = new AssemblyInfo();
166 info->children.push_back(childInfo);
167 GetAssembly(childInfo, *(child_part_occs + i));
168 }
169
170 UF_free(child_part_occs);
171 }
172
173 void WriteNode(AssemblyInfo* info, pugi::xml_node parent)
174 {
175 if ((NULL == info) || (NULL == parent))
176 {
177 return ;
178 }
179 _TCHAR* tmpStr = NULL;
180 pugi::xml_node assembly = parent.append_child(_T("assembly"));
181 tmpStr = char2TCAHR(info->path.c_str());
182 assembly.append_attribute(_T("name")).set_value(tmpStr);
183 SAFE_DELETE(tmpStr);
184 pugi::xml_node attrs = assembly.append_child(_T("attrs"));
185
186 //属性
187 for (map<string,map<string, string>>::iterator iter = info->attr.begin(); iter != info->attr.end(); ++iter)
188 {
189 pugi::xml_node category = attrs.append_child(_T("category"));
190 tmpStr = char2TCAHR(iter->first.c_str());
191 category.append_attribute(_T("name")).set_value(tmpStr);
192 SAFE_DELETE(tmpStr);
193 map<string, string>& attrsMap = iter->second;
194 for (map<string, string>::iterator iterAttr = attrsMap.begin(); iterAttr != attrsMap.end(); ++iterAttr)
195 {
196 pugi::xml_node attr = category.append_child(_T("attr"));
197 tmpStr = char2TCAHR(iterAttr->first.c_str());
198 attr.append_attribute(_T("name")).set_value(tmpStr);
199 SAFE_DELETE(tmpStr);
200 tmpStr = char2TCAHR(iterAttr->second.c_str());
201 attr.append_attribute(_T("value")).set_value(tmpStr);
202 SAFE_DELETE(tmpStr);
203 }
204 }
205
206 //子节点
207 pugi::xml_node children = assembly.append_child(_T("children"));
208 for (int i = 0; i < info->children.size(); ++i)
209 {
210 WriteNode(info->children[i], children);
211 }
212 }
213
214 void WriteXml(AssemblyInfo* info,_TCHAR* xmlFile)
215 {
216 if ((NULL == info) || (NULL == xmlFile))
217 {
218 return ;
219 }
220
221 pugi::xml_document doc;
222 pugi::xml_node decNode = doc.append_child(pugi::node_declaration);
223 pugi::xml_attribute vAttr = decNode.append_attribute(_T("version"));
224 vAttr.set_value(_T("1.0"));
225 pugi::xml_attribute encAttr = decNode.append_attribute(_T("encoding"));
226 encAttr.set_value(_T("utf-8"));
227
228 pugi::xml_node root = doc.append_child(_T("root"));
229 WriteNode(info,root);
230
231 doc.save_file(xmlFile, _T("\t"), pugi::format_indent, pugi::encoding_utf8);
232 }
233
234 int _tmain(int argc, _TCHAR* argv[])
235 {
236 if (argc < 3)
237 {
238 return 0;
239 }
240
241 if (UF_initialize() != 0)
242 {
243 return 0;
244 }
245
246 const _TCHAR* prtPath = argv[1];
247 TCHAR* xmlFile = argv[2];
248 tag_t tag = NULL_TAG;
249 UF_PART_load_status_t status;
250 UF_PART_open(TCHAR2char(prtPath).c_str(),&tag,&status);
251 if (status.failed)
252 {
253 return 0;
254 }
255
256 tag_t occ = UF_ASSEM_ask_root_part_occ(tag);
257 AssemblyInfo* info = new AssemblyInfo();
258 if (NULL == info)
259 {
260 return 0;
261 }
262
263 GetAssembly(info, occ);
264 WriteXml(info,xmlFile);
265
266 UF_terminate();
267 delete info;
268 return 0;
269 }
获取NX装配结构信息的更多相关文章
- 使用JDBC connect获取数据库表结构信息
1.这是生成代码的关键 引入maven依赖 <dependency> <groupId>mysql</groupId> <artifactId>mysq ...
- NX二次开发-UF_ASSEM_ask_component_data获取装配部件的相关信息
NX9+VS2012 #include <uf.h> #include <uf_ui.h> #include <uf_assem.h> ], void* user_ ...
- c#通过oledb获取excel文件表结构信息
这个问题来自论坛提问,同理可以获得access等数据库的表结构信息. using System; namespace ConsoleApplication11 { class Program { pu ...
- NX二次开发-UFUN获取图层类别的信息UF_LAYER_ask_category_info
1 NX11+VS2013 2 3 #include <uf.h> 4 #include <uf_ui.h> 5 #include <uf_layer.h> 6 7 ...
- Postgresql 导出表结构信息
项目用了Postgresql 数据库,项目组要出表结构的文档,手写太麻烦,想用slq脚本导出一份.查了一番资料,似乎没有多好的方法.dump方式导出的脚本太乱,没法直接写在word文档里.只能自己写s ...
- sqlserver获取数据库表结构
SqlServer获取所有数据库,表,表结构 --获取所有数据库 SELECT * FROM Master..SysDatabases ORDER BY Name --获取test数据库下所有表 us ...
- ios获取CELLID,LAC等信息方法
搞了一个来月的这个东西了,还是没有完全解决问题,下面方法可以获取简单的Cell信息,方法一://CoreTelephony.h//主要就这两个结构体,其他需要的话,自己添加struct CTServe ...
- 获取SqlServer2005表结构(字段,主键,外键,递增,描述)
1.获取表的基本字段属性 --获取SqlServer中表结构 SELECT syscolumns.name,systypes.name,syscolumns.isnullable, syscolumn ...
- java中访问mysql数据库中的表结构信息
package cn.hncu.meta; import java.sql.Connection;import java.sql.DatabaseMetaData;import java.sql.Re ...
随机推荐
- 安装pyspider报错:ERROR: Complete output from command python setup.py egg_info:...
正在学习pyspider框架,安装过程并不顺利,随即百度了一下解决了问题,将解决方法记录备用 问题描述: 首先出现 pip版本低,根据提示升级即可 再次安装报错如下 解决过程: 第一步:首先安装wh ...
- 使用docker搭建redis集群
创建网卡 docker network create redis --subnet 172.20.0.0/ --gateway 172.20.0.1 通过脚本创建6个redis配置 for i in ...
- 保护wordpress后台登录地址
前几天有个群友的wordpress网站被后台入侵了,吓得我赶紧看了看网站日志,密密麻麻的404,扫描我的后台登录地址.还好之前有了安全措施: 纯代码保护后台登录地址,防止爆破 //保护后台登录add_ ...
- html行内块元素之间的缝隙
关于html行内块元素之间缝隙的那点儿事情 事情是这样子的,我起初打算验证使用transform属性的标签是否会影响其他的标签的布局,于是写了下面一段代码: <!DOCTYPE html> ...
- 超简单!基于Python搭建个人“云盘”
1. 简介 当我们想要从本地向云服务器上传文件时,比较常用的有pscp等工具,但避免不了每次上传都要写若干重复的代码,而笔者最近发现的一个基于Python的工具updog,可以帮助我们在服务器上搭建类 ...
- 开源基于lua gc管理c++对象的cocos2dx lua绑定方案
cocos2dx目前lua对应的c++对象的生命周期管理,是基于c++析构函数的,也就是生命周期可能存在不一致,比如c++对象已经释放,而lua对象还存在,如果这时候再使用,会有宕机的风险,为此我开发 ...
- 模拟CMOS集成电路-单级放大器增益直观理解
我们再看辅助定理: 这里,Gm是指输出与地短接时的跨导:Rout表示当输入电压为零时的输出电阻.这个是书上的原话,但是在推算公式时发现,这两个量的定义还不是完全完整,我 的理解是: 首先Gm是等效跨导 ...
- css动画是否会被js阻塞
css动画是否会被js阻塞 css的动画部分是会被js阻塞的,不过transform的动画则不会受影响. 下面举一个margin-left移动的动画下,启动js阻塞动画的性能图表 <style& ...
- directives 自定义指令
钩子函数 一个指令定义对象可以提供如下几个钩子函数 (均为可选): bind:只调用一次,指令第一次绑定到元素时调用.在这里可以进行一次性的初始化设置.基本数据类型如果发生改变,不会触发,但是引用数据 ...
- 11 vue 自定义全局方法
//global.js// 定义vue 全局方 // 定义vue 全局方法 建议自定义的全局方法加_ 以示区分 export default { install(Vue, options = ...