Pro/Toolkit、Pro/J-link和Pro/Web.link是PTC提供给客户的三种客制化工具,其中以Pro/Toolkit的功能最为强大,能访问大部分Pro/E底层资源,也是当前国内研究得最多的开发方式。目前国内对Pro/Toolkit的运作方式和核心技术进行了深入研究,并取得了丰硕的成果,但由于Pro/Toolkit 是从Unix系统移植过来的,且PTC提供的开发文档和范例是采用MakeFile模式进行,这些都提高了Pro/Toolkit开发门槛,限制了Pro/Toolkit开发的发展。另外,虽然Pro/Toolkit支持MFC DLL开发模式,但仍需要做诸多改动才可以编译出正确的DLL文件。
本文基于应用程序快速开发(Rapid Application Development, RAD)的思想,主要讨论利用VS2005 自定义向导功能,制作能快速开发Pro/Toolkit程序的向导(Wizard)。同时阐述如何通过VS编译事件实现代码和资源的自动编码,实现简单高效开发。
1 使用VS2005自定义向导,建立Pro/Toolkit程序模板
1.1 建立标准MFC DLL项目
基于VS2005 MFC DLL模板,使用共享规则快速建立一个ProToolkit_Wizard项目。在解决方案中将获得9个文件,其中主要文件为ProToolkit_Wizard.cpp和ProToolkit_Wizard.h文件,编译后可以生成一个标准的Windows DLL库文件。
1.2 扩展成Pro/Toolkit DLL项目
要成功编译Pro/Toolkit程序,须正确设置包含文件和库文件的路径,由于项目可能在不同的环境下编译,因此需要将包含文件和库文件的路径都设置在项目属性中。并在项目中新建一个ProeLoadpoint(Pro/E安装路径)宏,便于实现不同版本Pro/Toolkit程序的快速转换。可以在“项目属性\配置属性\C/C++\常规\附加包含目录”中设置包含文件路径,在“项目属性\配置属性\连接器\常规\附加库目录”中设置库文件路径(目录中可以引用ProeLoadpoint宏,比如"$(ProeLoadPoint)\protoolkit\includes")。
环境配置完成后,接下来添加一些Pro/Toolkit专用代码。首先建立一个TKInclude.h文件,将所有可能用到的Pro/Toolkit头文件都包含在这个文件中,然后在ProToolkit_Wizard.cpp中引用TKInclude.h文件,并添加两个函数extern"C"int user_initialize()和extern"C"void user_terminate()。做到这一步,一个Pro/Toolkit项目的基本框架就建立好了,便可以在user_initialize函数中写一些Pro/Toolkit API函数来测试。
然而,做到这一步还缺少一个非常重要的功能——程序菜单。为给程序添加菜单,先建立一个ProToolkit_Menu.txt文件用于菜单需要用到的文本资源,然后将菜单功能函数模块化来实现菜单的快速设计。在此新建4文件,其名称及作用如下:
TK_Menu_Strct.h………菜单资源数组申明,将菜单资源定义为一个结构体,并将创建菜单所有需要的信息都包含该结构体中。
TK_Menu_Array.h………菜单资源数组定义,包含TK_Menu_Strct.h和TK_Menu_Fuc.h,并在ProToolkit_Wizard.cpp包含它,用户可以在此完善菜单数组的定义。
TKMenuData MenuArray[]={
{"ProToolkit_Wizard_Menu","Menu1","-Menu1","-Menu1_1 Help",PRO_B_FALSE,"redo.bif",(uiCmdCmdActFn) Menu1_fun,NULL }}
TK_Menu_Fuc.h…………菜单回调函数申明,声明如下
int Menu1_fun();
TK_Menu_Fuc.cpp………菜单回调函数定义TK_Menu_Fuc.h,定义如下
int Menu1_fun(){AfxMessageBox("Menu1_fun");return 0;}
在ProToolkit_Wizard.cpp文件user_initialize()函数中添加下面代码,创建菜单:
ProStringToWstring (UserMenuMsg,"ProToolkit_Wizard_menu.txt");
status=ProMenubarMenuAdd("ProToolkit_Wizard_Menu","-ProToolkit_Wizard",
"Utilities",PRO_B_FALSE,UserMenuMsg);
//通过for循环读取MenuArray数组中的信息创建菜单
for(int i=0;i
{
if(!MenuArray[i].SubMenu);
{
//建立菜单
}else
{
//建立子菜单
}
}

到此,一个相对完整的Pro/Toolkit项目框架便已建立,且程序能自动创建菜单项,将代码写在TK_Menu_Fuc.cpp相应的函数中(比如:Menu1_fun),即能通过菜单执行。
1.3 项目改进点
利用上述框架工作时,程序代码结构清晰,易于扩展,也为下一步自动生成代码创建了条件。除此之外,该项目框架还获得以下改善:
(1)规范菜单设计方法,用户需要添加菜单,修改TK_Menu_Array.h菜单资源数组即可;
(2)规范包含文件和库文件的设置,将其设置在项目属性中并引入ProeLoadpoint宏变量,方便不同用户和开发环境的切换。
1.4 升级为模板
作为Pro/Toolkit开发的用户或者初学者需要频繁建立项目,反复重复上述动作是费时费力的工作。采用VS2005开发环境提供自定义向导功能,可一劳永逸地解决这个问题。
先用VS2005建立一个“自定义向导”项目,采用UI支持,便于获得不同版本Pro/Toolkit开发所需信息;然后将前面建立的文件拷贝到“自定义向导”项目中,并对部分文件进行必要的编辑。如果希望后续所建项目能自动更名,则将要变动的地方包括文件名改为VS指定的关键字(比如root、[!output CLASS_NAME]等),便可以实现在新项目中适当位置自动转换。“自定义向导”项目的Templates.inf文件控制了需要添加到新项目中的文件,所有需要添加到新项目的文件名都需要写入该文件。
工作做到这一步,便已建立了新的代码框架,但程序无法通过编译,因此最后需要为其设置Pro/Toolkit开发环境。开发环境的设置有两种方法:一种是建立一个用户属性表,在属性表中设置开发环境,新建项目可以通过自动继承项目属性表来完成;另一种是通过“自定义向导”项目的default.js(语法为Jscript,非JavaScript)文件AddConfig函数来设置。下面给出js代码示例,详细设计可以参考MSDN:
function AddConfig(proj,strProjectName)
{
//General
var config=proj.Object.Configurations(’Debug’);//Debug环境
config.InheritedPropertySheets=".\\user_macro.vsprops";//自动添加user_macro
//Compiler
var CLTool = config.Tools(’VCCLCompilerTool’);
//Add linker dependencies
var LinkTool=config.Tools(’VCLinkerTool’);
LinkTool.IgnIgnoreDefaultLibraryNames="msvcrt.lib";//忽略msvcrt.lib,否则会产生一个warning
}

通过以上工作,用户在Pro/Toolkit开发建立项目时,只需要选择Pro/E版本,向导即能重新生成前面完成的框架,不需要编写一行代码,程序就可以通过编译。
2 通过VS编译事件提高开发效率
2.1 ro/Toolkit菜单可视化设计
在前面的工作中,已经规范了菜单设计,然而这种菜单设计还是一种文本式编辑模式。若菜单比复杂时,仅靠手工来定义这些数组,仍需较大工作量来完成。这一点可通过菜单的可视化设计得到改善,VS开发环境已经提供一个菜单可视化编辑器,需要做的只是如何利用这个可视化编辑器来设计Pro/Toolkit菜单。通过研究VS的菜单资源文件(ProToolkit_Wizard.rc)发现VS的菜单资源是用非常简单的语法组织起来的,可利用编译前处理事件在程序编译前将其解析为菜单数组,就能把VS2005菜单转换为Pro/Toolkit菜单,从而实现代码和资源的自动编码。下面是VS菜单资源代码定义:
IDR_TK_MENU MENU
BEGIN
POPUP"Demo"
BEGIN
POPUP"Menu1"
BEGIN
MENUITEM"Menu1_1",ID_32772
MENUITEM"Menu1_1",ID_32773
END
POPUP"Menu2"
BEGIN
MENUITEM"menu2_1",ID_32776
END
END
END

从这些信息中可获得菜单名称和菜单结构(层级关系),但这些信息还不足以设计Pro/Toolkit菜单。还需将Pro/Toolkit菜单的标签和提示信息进行规范:规定菜单标签=“-Menu Name”、菜单帮助=“-Menu Name Help”,然后将Pro/Toolkit菜单回调函数、菜单图标、菜单权限函数定义在VS菜单属性的“prompt”属性中(可以在StringTable中获得)。StringTable结构如下:
STRINGTABLE
BEGIN
ID_32772"fuc1_1,edit.gif,FullAccessAvailable"
ID_32773"fuc1_2,,"
ID_32774"fuc1_3,,"
END
通过上述操作,可获得设计Pro/Toolkit菜单相当完整的信息,但要实现转换工作则需要另外一个程序(create_menu_src.exe,该程序不在本文讨论)来实现,并在程序编译前执行它即可。编译前事件设置: "$(VCInstallDir)\VCWizards\ProTK_Wizard\Bin\create_menu_src.exe"$(ProjectDir)TK_Menu.h)
2.2 Pro/Toolkit代码的自动实现
create_menu_src程序除了可以生成菜单数组和对应的菜单资源外,还可以根据从StringTable获得的信息,自动实现函数的申明和定义,从而实现代码的快速设计。默认代码为:
TK_Menu_Fuc.h………int MenuName_fun();
TK_Menu_Fuc.cpp……int MenuName _fun(){AfxMessageBox("MenuName_fun");return 0;}
3 总结
本文是VS2005 Wizard技术在Pro/Toolkit开发中的实践经验总结,通过客制化的向导快速建立代码框架清晰、功能完整、易于扩展的Pro/Toolkit项目。Pro/Toolkit程序菜单快速设计方法、菜单回调函数的自动声明和定义的应用,大大提高了开发效率,促进了Pro/Toolkit开发的发展。


