关于ObjectARX中自定义对象的OPM代码细节

开发OPM的技术规格如下

1,是一个ATL-COM项目

1.1 是DLL库,引用了COM的代码内容

1.2也可以使用DBX类型作为输出,并且让它做一些DBX库的工作

 

2 关于stdafx文件

2.1 需要包括的COM文件

常规的情况下,使用CComModule得到一个 COM对象,这样不需要在项目中引用ATL

在引用ATL的情况下,可以通过CAtlDllModuleT创建COM对象

2.2 关于_ATL_NO_UUIDOF

项目中有包含,也有不包含的,作用待定

 2.3 包括AC的文件

#include "acadi.h"
#include "dbmain.h"
#include "dbents.h"
#include "dbsymtb.h"
#include "dbobjptr.h"
#include "rxregsvc.h"

 

3 导出函数

3.1 至少要包括COM的标准

    DllCanUnloadNow
    DllGetClassObject
    DllRegisterServer
    DllUnregisterServer

这四个函数都有基本的模板,几乎可以直接使用。

3.2 如果作为DBX,还要有
    acrxEntryPoint
    acrxGetApiVersion


4 建立 COMWrapper

主要工作是完成,将自定义对象的属性等接口转换成COM类型的接口;

可以参照 已经有类进行编写,函数内部基本同常规规则

 

5 IDL接口文件

COM的接口文件,用来表示COM的输出接口、GUID等内容

同时IDL文件会自动生成为多个文档,包括

x_i.h :会在COMWrapper中引用,是COM接口的C语言头文件

x_i.c :在dllmain 中引用,是COM中C语言的实现

x.tlb :在资源文件中被使用

上述文件的位置原则上可以自主安排,sample中,输出到$(ProjectDir)中

出于分离临时文件的原则,我选择输出到$(IntDir)中,可以视情况具体安排,只要包含目录中添加即可

 

5 在资源文件中

5.1 在资源中增加 RGS文件,作为注册表资源,该信息会被用于安装和卸载

5.2 在资源包括中增加一条编译命令,用于将TLB文件包含在资源内

1 TYPELIB "idloutputname.tlb"

注意:idloutputname是固定的硬编码,包括路径;不必非是$(ProjName),只要是是IDL输出的名字即可

这里我在项目资源属性中,增加$(IntDir)作为额外的包含路径

 

6 RGS文件

是一种注册表信息文件,只不过这种注册表文件需要存在资源中,外部程序可以根据其中信息对COM组件进行注册和卸载

基本的操作就是使用模板即可,替换GUID

但要注意,不同的sample中,内容会有一些不同,注意版本匹配即可

 

7 注册表文件

REG文件,将最后的DLL文件注册到系统中,这部分是完全独立的。只要按照模板写对GUID和路径即可

向操作系统注册可以通过另外一个方法解决——将OPM的DLL包装成DBX完成,但不是必须的

OPM-DLL只要向系统注册之后,即可使用,不必ACAD载入。

在任何情况下,注册操作都需要管理员权限。

具体如何合适的注册,直接看下面的文档

http://otb.manusoft.com/2011/10/registering-an-arxbrx-module-as-a-com-server.htm

 

8 还有几个没明白的地方

8.1 APARTMENT_THREADED

DllMain中的  DisableThreadLibraryCalls(hInstance);

stdafx中的  _ATL_APARTMENT_THREADED

RGS中的    val ThreadingModel = s 'Apartment'

暂时保持原状即可

8.2 对ACAD库的引用

从理论上分析COMWrapper.dll是可以不依赖ACAD的库的,

但实际在做接口转换的时候,由于底层的实体接口都是AcGe、AcDb等类,所以需要使用到相应的ACAD库

 

posted @ 2014-07-31 15:46  kevinzhwl  阅读(...)  评论(... 编辑 收藏