C#内置带事件的签名ActiveX组件

使用C#构建带事件的签名ActiveX组件具体方法:

   初步创建ActiveX项目

  使用Visual Studio 2008,文件->新建->项目,选择类库,创建一个类库项目。打开Visual Studio 2008,使用.NET语言编写的ActiveX控件的主体就是一个类库,首先我们来创建这个类库项目。

  创建ActiveX项目

  第二步编写ActiveX主体

  ActiveX的主体包括方法定义接口,事件定义接口(可选),实现这些接口的ActiveX主体类三个部分。下面是笔者原创的演示。

  首先,我们创建方法定义接口:

  /// <摘要>

  ///该接口定义了ActiveX的方法

  /// </ summary>

  [

  Guid(“ F3BD342F-14E1-4347-BFBD-F449DD070DF9”),

  InterfaceType(ComInterfaceType.InterfaceIsDual),

  ComVisible(true)]

  publicinterfaceIBosnMaActiveX

  {

  [DispId(1)]

  void Start();

  [DispId(2)]

  无效Stop();

  }

  该接口内部的成员会暴露给外部调用。这里我们提供两个简单方法启动和停止。使用工具(Visual Studio->工具->创建GUID)生成自己的GUID。

  接下来定义事件接口:

  /// <摘要>

  ///该接口定义了ActiveX的事件

  /// </ summary>

  [ComVisible(true)]

  [Guid(“ C4F9F24F-B860-4e79-945D-B9A281950C82”)]

  [InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]

  publicinterfaceBosnMaActiveXEvents

  {

  [DispId(21)]

  void OnRecorderStarted();

  [DispId(22)]

  void OnRecorderStopped();

  [DispId(23)]

  void OnRecorderVolumeChanged(int value);

  }

  这里我们为ActiveX定义三个事件,分别为OnRecorderStarted,OnRecorderStopped,OnRecorderVolumeChanged(带一个int参数)。
最后我们编写了集成方法接口和事件接口的ActiveX主体类:

  [

  引导(“ 78E683CE-EC77-40b0-B0C3-4060FFC70A93”),

  ProgId(“ ActiveXOfBosnMa.BosnMaActiveX”),

  ClassInterface(ClassInterfaceType.None),

  ComDefaultInterface(typeof(IBosnMaActiveX)),

  ComSourceInterfaces(typeof(BosnMaActiveXEvents)),

  ComVisible(真)

  ]

  publicclassBosnAcX:IBosnMaActiveX,IObjectSafety

  {

  #region事件,处理程序,实例

  publicdelegatevoidVolumeChangedHandler(int value);

  publicdelegatevoidSimpleHandler();

  publiceventVolumeChangedHandler OnRecorderVolumeChanged;

  publiceventSimpleHandler OnRecorderStarted;

  publiceventSimpleHandler OnRecorderStopped;

  #endregion

  #region IBosnMaActiveX的实现

  /// <摘要>

  ///调用该方法将引发OnRecorderStarted事件,并在3秒后引发OnRecorderVolumeChanged

  /// </ summary>

  publicvoid Start()

  {

  OnRecorderStarted();

  SimpleHandler d =工作;

  d.BeginInvoke(null,null);

  }

  publicvoid Work()

  {

  Thread.Sleep(3000);

  OnRecorderVolumeChanged(53);

  }

  /// <摘要>

  ///调用该方法将引发OnRecorderStopped事件

  /// </ summary>

  publicvoid Stop()

  {

  OnRecorderStopped();

  }

  #endregion

  }

  这里要注意主体类的事件名称要与事件接口(在上例中为BosnMaActiveXEvents)中的方法名相同。在BosnAcX中我们实现了IBosnMaActiveX中的方法,当调用Start()时引发一个OnRecorderStarted事件,并在3秒后引发一个OnRecorderVolumeChanged事件,在调用Stop()时引发一个OnRecorderStopped事件。

  编译并注册ActiveX

  编译整个项目将输出dll。

  图2编译ActiveX项目生成dll文件

  然后我们启动命令行CMD(如果是Vista / Win7使用管理员方式打开),使用以下命令注册控件。

  C:\> D://转到.dll所在目录,笔者为了方便将.dll复制到了D盘根目录

  D:\> regasm activexofbosnma.dll /代码库/ tlb

  * regasm命令在%systemroot%\ Microsoft.NET \ Framework \ v2.x.xxxx \目录下,将目录注册到用户环境变量中即可不使用完全定义名运行该命令。

  *使用regasm activexofbosnma.dll / codebase / tlb / unregister可以反注册,在ActiveX代码变更时重编译后,需要先反注册再注册。

  图3注册商标和反注册ActiveX控件

  测试ActiveX

  最后我们创建一个html页面来测试该ActiveX。

  <html>

  <headrunat =“ server”>

  <title> </ title>

  <objectid =“ myAcX” name =“ myAcX” classid =“ clsid:78E683CE-EC77-40b0-B0C3-4060FFC70A93”>

  </ object>

  <scriptlanguage =“ javascript” for =“ myAcX” type =“ text / javascript” event =“ OnRecorderVolumeChanged(v);”>

  MyDiv.innerHTML ='在javascript中:获取音量:'+ v;

  </ script>

  <scriptlanguage =“ javascript” for =“ myAcX” type =“ text / javascript” event =“ OnRecorderStarted”>

  MyDiv.innerHTML ='在javascript中:OnRecorderStarted';

  </ script>

  <scriptlanguage =“ javascript” for =“ myAcX” type =“ text / javascript” event =“ OnRecorderStopped”>

  MyDiv.innerHTML ='在javascript中:OnRecorderStopped';

  </ script>

  </ head> 
<body>

  <表格>

  <scriptlanguage =“ javascript” type =“ text / jscript”>

  函数Button1_onclick(){

  myAcX.Start();

  }

  函数Button2_onclick(){

  myAcX.Stop();

  }

  函数RecorderVolumeChanged(v){

  alert('volume:'+ v);

  }

  </ script>

  <divid =“ MyDiv”>什么都没发生</ div>

  <p>

  <inputid =“ Button1” type =“ button” value =“ Start” onclick =“ Button1_onclick()” />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;

  <inputid =“ Button2” type =“ button” value =“ Stop” onclick =“ Button2_onclick()” /> </ p>

  </ form>

  </ body>

  </ html>

  测试效果

  首先使用IE打开测试页面

  允许ActiveX交互后进入主界面,单击开始按钮会收到ActiveX返回的OnRecorderStarted事件。

  三秒过后收到VolumeEvent

  最后点击停止按钮会收到OnRecorderStopped事件。

  安全性

  为了标记ActiveX控件为安全的(避免点击“该控件是不安全的”警告),需要实现IObjectSafety接口。

  使用系统;

  使用System.Collections.Generic;

  使用System.Runtime.InteropServices;

  使用System.ComponentModel;

  使用System.Text;

  命名空间ActiveXOfBosnMa

  {

  [

  可序列化

  ComVisible(真)

  ]

  publicenumObjectSafetyOptions

  {

  INTERFACESAFE_FOR_UNTRUSTED_CALLER = 0x00000001,

  INTERFACESAFE_FOR_UNTRUSTED_DATA = 0x00000002,

  INTERFACE_USES_DISPEX = 0x00000004,

  INTERFACE_USES_SECURITY_MANAGER = 0x00000008

  };

  //

  // MS IObjectSafety接口定义

  //

  [

  ComImport(),

  Guid(“ CB5BDC81-93C1-11CF-8F20-00805F2CD064”),

  InterfaceType(ComInterfaceType.InterfaceIsIUnknown)

  ]

  publicinterfaceIObjectSafety

  {

  [PreserveSig]

  长GetInterfaceSafetyOptions(refGuid iid,outint pdwSupportedOptions,outint pdwEnabledOptions);

  [PreserveSig]

  长SetInterfaceSafetyOptions(refGuid iid,int dwOptionSetMask,int dwEnabledOptions);

  };

  //

  //为提供默认的实现

  //安全脚本。

  //这基本上意味着IE不会抱怨

  // ActiveX对象不安全

  //

  publicclassIObjectSafetyImpl:IObjectSafety

  {

  privateObjectSafetyOptions m_options =

  ObjectSafetyOptions.INTERFACESAFE_FOR_UNTRUSTED_CALLER |

  ObjectSafetyOptions.INTERFACESAFE_FOR_UNTRUSTED_DATA;

  #region [IObjectSafety实现]

  publiclong GetInterfaceSafetyOptions(refGuid iid,outint pdwSupportedOptions,outint pdwEnabledOptions)

  {

  pdwSupportedOptions =(int)m_options;

  pdwEnabledOptions =(int)m_options;

  返回0;

  }

  publiclong SetInterfaceSafetyOptions(refGuid iid,int dwOptionSetMask,int dwEnabledOptions)

  {

  返回0;

  }

  #endregion

  };

  }

  并实现以下两个方法:

  #region IObjectSafety的实现

  privateObjectSafetyOptions m_options =

  ObjectSafetyOptions.INTERFACESAFE_FOR_UNTRUSTED_CALLER |

  ObjectSafetyOptions.INTERFACESAFE_FOR_UNTRUSTED_DATA;

  publiclong GetInterfaceSafetyOptions(refGuid iid,outint pdwSupportedOptions,outint pdwEnabledOptions)

  {

  pdwSupportedOptions =(int)m_options;

  pdwEnabledOptions =(int)m_options;

  返回0;

  }

  publiclong SetInterfaceSafetyOptions(refGuid iid,int dwOptionSetMask,int dwEnabledOptions)

  {

  返回0;

  }

  #endregion

  使用C#构建带事件的签名ActiveX组件具体方法:

   初步创建ActiveX项目

  使用Visual Studio 2008,文件->新建->项目,选择类库,创建一个类库项目。打开Visual Studio 2008,使用.NET语言编写的ActiveX控件的主体就是一个类库,首先我们来创建这个类库项目。

  创建ActiveX项目

  第二步编写ActiveX主体

  ActiveX的主体包括方法定义接口,事件定义接口(可选),实现这些接口的ActiveX主体类三个部分。下面是笔者原创的演示。

  首先,我们创建方法定义接口:

  /// <摘要>

  ///该接口定义了ActiveX的方法

  /// </ summary>

  [

  Guid(“ F3BD342F-14E1-4347-BFBD-F449DD070DF9”),

  InterfaceType(ComInterfaceType.InterfaceIsDual),

  ComVisible(true)]

  publicinterfaceIBosnMaActiveX

  {

  [DispId(1)]

  void Start();

  [DispId(2)]

  无效Stop();

  }

  该接口内部的成员会暴露给外部调用。这里我们提供两个简单方法启动和停止。使用工具(Visual Studio->工具->创建GUID)生成自己的GUID。


接下来定义事件接口:

  /// <摘要>

  ///该接口定义了ActiveX的事件

  /// </ summary>

  [ComVisible(true)]

  [Guid(“ C4F9F24F-B860-4e79-945D-B9A281950C82”)]

  [InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]

  publicinterfaceBosnMaActiveXEvents

  {

  [DispId(21)]

  void OnRecorderStarted();

  [DispId(22)]

  void OnRecorderStopped();

  [DispId(23)]

  void OnRecorderVolumeChanged(int value);

  }

  这里我们为ActiveX定义三个事件,分别为OnRecorderStarted,OnRecorderStopped,OnRecorderVolumeChanged(带一个int参数)。
最后我们编写了集成方法接口和事件接口的ActiveX主体类:

  [

  引导(“ 78E683CE-EC77-40b0-B0C3-4060FFC70A93”),

  ProgId(“ ActiveXOfBosnMa.BosnMaActiveX”),

  ClassInterface(ClassInterfaceType.None),

  ComDefaultInterface(typeof(IBosnMaActiveX)),

  ComSourceInterfaces(typeof(BosnMaActiveXEvents)),

  ComVisible(真)

  ]

  publicclassBosnAcX:IBosnMaActiveX,IObjectSafety

  {

  #region事件,处理程序,实例

  publicdelegatevoidVolumeChangedHandler(int value);

  publicdelegatevoidSimpleHandler();

  publiceventVolumeChangedHandler OnRecorderVolumeChanged;

  publiceventSimpleHandler OnRecorderStarted;

  publiceventSimpleHandler OnRecorderStopped;

  #endregion

  #region IBosnMaActiveX的实现

  /// <摘要>

  ///调用该方法将引发OnRecorderStarted事件,并在3秒后引发OnRecorderVolumeChanged

  /// </ summary>

  publicvoid Start()

  {

  OnRecorderStarted();

  SimpleHandler d =工作;

  d.BeginInvoke(null,null);

  }

  publicvoid Work()

  {

  Thread.Sleep(3000);

  OnRecorderVolumeChanged(53);

  }

  /// <摘要>

  ///调用该方法将引发OnRecorderStopped事件

  /// </ summary>

  publicvoid Stop()

  {

  OnRecorderStopped();

  }

  #endregion

  }

  这里要注意主体类的事件名称要与事件接口(在上例中为BosnMaActiveXEvents)中的方法名相同。在BosnAcX中我们实现了IBosnMaActiveX中的方法,当调用Start()时引发一个OnRecorderStarted事件,并在3秒后引发一个OnRecorderVolumeChanged事件,在调用Stop()时引发一个OnRecorderStopped事件。

  编译并注册ActiveX

  编译整个项目将输出dll。

  图2编译ActiveX项目生成dll文件

  然后我们启动命令行CMD(如果是Vista / Win7使用管理员方式打开),使用以下命令注册控件。

  C:\> D://转到.dll所在目录,笔者为了方便将.dll复制到了D盘根目录

  D:\> regasm activexofbosnma.dll /代码库/ tlb

  * regasm命令在%systemroot%\ Microsoft.NET \ Framework \ v2.x.xxxx \目录下,将目录注册到用户环境变量中即可不使用完全定义名运行该命令。

  *使用regasm activexofbosnma.dll / codebase / tlb / unregister可以反注册,在ActiveX代码变更时重编译后,需要先反注册再注册。

  图3注册商标和反注册ActiveX控件

  测试ActiveX

  最后我们创建一个html页面来测试该ActiveX。

  <html>

  <headrunat =“ server”>

  <title> </ title>

  <objectid =“ myAcX” name =“ myAcX” classid =“ clsid:78E683CE-EC77-40b0-B0C3-4060FFC70A93”>广州代孕[电13802269370]  北京代孕咨询电13802269370   代孕[微13802269370]+

猜你喜欢

转载自www.cnblogs.com/bbc2020/p/12503476.html