繁体中文
设为首页
加入收藏
当前位置:技术首页 >> 开发 >> Delphi >> Delphi使用VB编写的ActiveX控件全攻略

Delphi使用VB编写的ActiveX控件全攻略

2006-10-11 17:38:35  作者:admin  来源:赛迪网  浏览次数:118  文字大小:【】【】【
关键字:Delphi
 前言

在最近几周的工作里,始终被一个头疼的问题所困扰,那就是VB6编写的ActiveX控件在Delphi环境下存在着诸多稀奇古怪的问题,几经周折,终于在搜索了几乎全部的论坛、资料后,找到了针对不同Delphi版本发生的问题的解决办法。

 

Delphi 5 莫名其妙的致命异常之一

首先,我们来看看VB写的ActiveX控件在Delphi 5下面的奇怪表现。

例如:我们用VB编写了一个控件UserTest(为简单起见,我们只导出一个类即用户控件),一个属性TestName,一个方法TestMethod。然后将其编译成一个ActiveX控件,注册并导入Delphi5的开发环境(以上步骤如有未清楚之处,请查阅各类参考资料,肯定有标准答案),到目前为止,看来一切正常。

然后,我们习惯的把控件拖放到窗体上,调整大小,在属性窗口中为属性赋值,或者在代码中也是一样,非常正常,好用的很。但是,下面问题来了,如果您兴致勃勃的去调用了那个TestMethod,那么您将得到一个古怪的异常 “Ole Error 800a01a9”,然后程序退出,而且非常不幸的是,您将无法跟踪到这个异常,在Delphi中或是VB中都是,当然如果您对汇编很在行的话,您可以跟着Delphi的调试窗口一步一步往下……

当我第一次碰到这个问题的时候,我几乎是愤怒的,因为无论是MicroSoft或是Borland,对该错误都没有任何解释,也没有任何可以查找的资料。我只好跑到常去的几个论坛,当然最主要的还是CSDN,在VB版和Delphi版中四处搜索类似的问题,然后非常遗憾的是,只有类似的问题,而没有答案,一个大客户就用的这个开发工具,我在测试了几乎所有Windows上的开发工具和开发环境(包括桌面和WEB)后,惟独将Delphi忘记了。

剩下的两天里,我几乎是满世界乱跑,给所有的朋友打电话,询问Delphi方面的高手是否知道这个情况,最后,我从Google上搜到了一个链接,可惜的是现在我忘记了那个链接的具体位置,但是我得到了一个近乎Magic的方法(发现者是这么称呼它的):

 

一个手工修改Delphi导入VB ActiveX控件后产生的代理类型库XXX_TLB.PAS(这里XXX指的是控件的类名)文件的方法可以解决这一问题。举例说明:

 

有一个VB 写的控件 UserControl1 ,在Delphi中导入后产生两个文件,其中一个UserControl1_TLB.PAS 就是我们所要修改的文件。

在文件中查找 类似

 

FintF: _UserControl1;

Function GetControlInterface:_UserControl1;

 

 

property ControlInterface: _UserControl1 read GetControlInterface;

 

GetControlInterface;

以及

 

procedure TUserControl1.CreateControl;

procedure DoCreate;

begin

Finf:=IUnknown(OleObject) as _UserControl1;

End;

Begin

If Finf=nil then DoCreate;

End;

 

Function TUserControl1.GetControl1Interface: _UserControl1;

 

Begin

CreateControl;

Result:=Finfl;

End;

 

请注意:这里红色标出的 _UserControl1 要 全部换成 _ UserControl1Disp,如果编译不成功的话,请将编译警告中报出的_UserControl1 全部换成 _UserControl1Disp,编译即可,这样在调用控件的方法时便不会出现上述的致命错误。

 

感谢这个伟大的发现,我只能这么形容它,否则可能到现在我还要在这个圈子里套不出来,或者就是使用另外的工具重新开发这个控件(我难以想象这个工作量会有多大,又或者它可能还会存在其他的兼容性问题)。

Delphi 5 莫名其妙的致命异常之二

但是,Delphi并没有在我绕开这个限制之后而穒rtual machine handle

 

  moveax, flags// message box flags

 

  movecx, message// address of message text

 

  movedi, caption// address of caption text

 

  movesi, callback// address of callback

 

  movedx, referencedata// reference data for callback

 

 int20h// vxdcall

 

  dd 170004h// shell_message

 

end;

 

function sysdynamicdeviceinit : integer;

 

begin

 

  shellmessage(0, $10, copyright, ’sysdyninit: hello from delphi vxd !!!’, nil, nil);

 

  result := vxd_success;

 

end;

 

function sysdynamicdeviceexit : integer;

 

begin

 

  shellmessage(0, $10, copyright, ’sysdyndevexit: bye from delphi vxd !!!’, nil, nil);

 

  result := vxd_success;

 

end;

 

function w32deviceiocontrol(dwservice : integer;

 

dwddb : integer;

 

hdevice : integer;

 

lpdiocparms : pointer) : integer;

 

begin

 

  shellmessage(0, $10, copyright, ’w32devioctl’, nil, nil);

 

 if (dwservice = dioc_open) then

 

  begin

 

  result := no_error;

 

  end

 

  else if (dwservice = dioc_closehandle) then

 

  begin

 

  result := vxd_success;

 

  end

 

  else if (dwservice > max_pasvxd_w32_api) then

 

  begin

 

  result := error_not_supported;

 

  end

 

else

 

  begin

 

  result := vxd_success; 

 

  end;

 

end;

 

...

 

 

 

 

 

[译者:好了,简单的 vxd 设备驱动程序编写完毕了。你可以将它当作一个写 vxd 设备驱动程序的模板。]


点击收藏到

责任编辑:admin

本文引用地址: http://tech.itzero.com/2006/1011/862.html 请粘贴到你的QQ/MSN上推荐给你的好友

相关文章
在delphi.net的VCL.net里使用Ado.net
用Delphi开发Web服务数据库程序
Delphi程序实现对光驱盘盒的开关控制
Delphi中动态链接库(DLL)的建立和使用
在delphi.net的VCL.net里使用Ado.net
Delphi中优秀的字符串分割函数
在Delphi中如何维护COM+的状态信息
用Delphi编写VxD设备驱动程序
Delphi使用VB编写的ActiveX控件全攻略
在delphi中使用xml文档的两种方法
 

最新文章

更多

· Delphi使用VB编写的Acti...
· 在delphi.net的VCL.net里...
· 用Delphi开发Web服务数据...
· Delphi程序实现对光驱盘...
· Delphi中动态链接库(DLL...
· 在delphi.net的VCL.net里...
· Delphi中优秀的字符串分...
· 在Delphi中如何维护COM+...
· 用Delphi编写VxD设备驱动...
· Delphi使用VB编写的Acti...

热点文章

更多

其它推荐