因为最近的项目可能会用到调用外部设备,读取信息。为了和现有的BS系统兼容,并以较小的代价满足需求,于是想到了使用ActiveX技术(也有人建议使用Silverlight),这技术虽然比较早了,但还是能够满足目前的需求的

所以在网上找了找资料看看,折腾了两天,总算有点效果了

现在记录一下大致的过程

1、创建一个类库,用于生成ActiveX组件

  A、实现IObjectSafety接口

    [ComImport, GuidAttribute("CB5BDC81-93C1-11CF-8F20-00805F2CD064")][InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]public interface IObjectSafety{[PreserveSig]int GetInterfaceSafetyOptions(ref Guid riid, [MarshalAs(UnmanagedType.U4)] ref int pdwSupportedOptions, [MarshalAs(UnmanagedType.U4)] ref int pdwEnabledOptions);[PreserveSig()]int SetInterfaceSafetyOptions(ref Guid riid, [MarshalAs(UnmanagedType.U4)] int dwOptionSetMask, [MarshalAs(UnmanagedType.U4)] int dwEnabledOptions);}

  B、实现IOleClientSite接口

    [ComImport, Guid("00000118-0000-0000-C000-000000000046"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]public interface IOleClientSite{void SaveObject();void GetMoniker(uint dwAssign, uint dwWhichMoniker, object ppmk);void GetContainer(out IOleContainer ppContainer);void ShowObject();void OnShowWindow(bool fShow);void RequestNewObjectLayout();}

  C、实现IOleContainer接口

    [ComImport, Guid("0000011B-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]public interface IOleContainer{void EnumObjects([In, MarshalAs(UnmanagedType.U4)] int grfFlags,[Out, MarshalAs(UnmanagedType.LPArray)] object[] ppenum);void ParseDisplayName([In, MarshalAs(UnmanagedType.Interface)] object pbc,[In, MarshalAs(UnmanagedType.BStr)] string pszDisplayName,[Out, MarshalAs(UnmanagedType.LPArray)] int[] pchEaten,[Out, MarshalAs(UnmanagedType.LPArray)] object[] ppmkOut);void LockContainer([In, MarshalAs(UnmanagedType.I4)] int fLock);}

其中A为ActiveX组件必需,

B和C是为了与页面中的JS进行交互

以下为A在组件中的实现

#region IObjectSafety 成员private const string _IID_IDispatch = "{00020400-0000-0000-C000-000000000046}";private const string _IID_IDispatchEx = "{a6ef9860-c720-11d0-9337-00a0c90dcaa9}";private const string _IID_IPersistStorage = "{0000010A-0000-0000-C000-000000000046}";private const string _IID_IPersistStream = "{00000109-0000-0000-C000-000000000046}";private const string _IID_IPersistPropertyBag = "{37D84F60-42CB-11CE-8135-00AA004BB851}";private const int INTERFACESAFE_FOR_UNTRUSTED_CALLER = 0x00000001;private const int INTERFACESAFE_FOR_UNTRUSTED_DATA = 0x00000002;private const int S_OK = 0;private const int E_FAIL = unchecked((int)0x80004005);private const int E_NOINTERFACE = unchecked((int)0x80004002);private bool _fSafeForScripting = true;private bool _fSafeForInitializing = true;public int GetInterfaceSafetyOptions(ref Guid riid, ref int pdwSupportedOptions, ref int pdwEnabledOptions){int Rslt = E_FAIL;string strGUID = riid.ToString("B");pdwSupportedOptions = INTERFACESAFE_FOR_UNTRUSTED_CALLER | INTERFACESAFE_FOR_UNTRUSTED_DATA;switch (strGUID){case _IID_IDispatch:case _IID_IDispatchEx:Rslt = S_OK;pdwEnabledOptions = 0;if (_fSafeForScripting == true)pdwEnabledOptions = INTERFACESAFE_FOR_UNTRUSTED_CALLER;break;case _IID_IPersistStorage:case _IID_IPersistStream:case _IID_IPersistPropertyBag:Rslt = S_OK;pdwEnabledOptions = 0;if (_fSafeForInitializing == true)pdwEnabledOptions = INTERFACESAFE_FOR_UNTRUSTED_DATA;break;default:Rslt = E_NOINTERFACE;break;}return Rslt;}public int SetInterfaceSafetyOptions(ref Guid riid, int dwOptionSetMask, int dwEnabledOptions){int Rslt = E_FAIL;string strGUID = riid.ToString("B");switch (strGUID){case _IID_IDispatch:case _IID_IDispatchEx:if (((dwEnabledOptions & dwOptionSetMask) == INTERFACESAFE_FOR_UNTRUSTED_CALLER) && (_fSafeForScripting == true))Rslt = S_OK;break;case _IID_IPersistStorage:case _IID_IPersistStream:case _IID_IPersistPropertyBag:if (((dwEnabledOptions & dwOptionSetMask) == INTERFACESAFE_FOR_UNTRUSTED_DATA) && (_fSafeForInitializing == true))Rslt = S_OK;break;default:Rslt = E_NOINTERFACE;break;}return Rslt;}#endregion

以下为B和C的使用(这是使用的一个示例,可以根据需要自行处理)

#region CallJavaScriptprivate void CallJavaScript(string Filenames){Type typeIOleObject = this.GetType().GetInterface("IOleObject", true);object oleClientSite = typeIOleObject.InvokeMember("GetClientSite",BindingFlags.Instance | BindingFlags.InvokeMethod | BindingFlags.Public,null,this,null);IOleClientSite oleClientSite2 = oleClientSite as IOleClientSite;IOleContainer pObj;oleClientSite2.GetContainer(out pObj);//参数数组object[] args = new object[1];args[0] = Filenames;//获取页面的Script集合
IHTMLDocument pDoc2 = (IHTMLDocument)pObj;object script = pDoc2.Script;try{//调用JavaScript方法OnScaned并传递参数,因为此方法可能并没有在页面中实现,所以要进行异常处理
                script.GetType().InvokeMember("OnScaned",BindingFlags.Instance | BindingFlags.InvokeMethod | BindingFlags.Public,null,script,args);}catch { }}#endregion CallJavaScript

上面的代码基本上就是ActiveX实现的内容了,再实现自己一些Public方法就可以了,下面说说如何打包

(一些设置之类的,网上都有说)

        /// <summary>/// 获取客户端主机的MAC地址/// </summary>/// <returns></returns>public string GetMacAddress(){var mc = new ManagementClass("Win32_NetworkAdapterConfiguration");var mos = mc.GetInstances();var sb = new StringBuilder();foreach (ManagementObject mo in mos){var macAddress = mo["MacAddress"];if (macAddress != null)sb.AppendLine(macAddress.ToString());}return sb.ToString();}

  另见:注意事项

  附件:

    CAB打包工具

    自签名证书工具

转载于:https://www.cnblogs.com/dreamcat/p/7483053.html

C#创建ActiveX相关推荐

  1. .NET环境下创建Activex (转)

    虽然不倡导在Web环境下使用Activex控件,但有时会遇到与底层通信的问题,这时利用Activex可以比较好的解决,工商银行的U盾就是如此.Activex还有一个好处就是可以把winform下封装的 ...

  2. 【VS开发】动态创建ActiveX控件

    bool CCollectDataDlgDlg::CreateMyCtrl(LPRECT lpRect, UINT nID, CWnd *pParent) {  CLSID clsid;  wstri ...

  3. 用javascript 创建ActiveX对象时出现:Automation server can't create object(Automation 服务器不能创建对). 错误的解决办法。

    今天,想实现在客户端读取一个EXCEL文件到一个Table中 ,所以写了如下代码: function  readExcel() ... {    var fileName = document.get ...

  4. C++ 使用VS2010创建MFC ActiveX工程项目

    1.ActiveX的基本概念 ActiveX控件可以看作是一个极小的服务器应用程序,它不能独立运行,必须嵌入到某个容器程序中,与该容器一起运行.这个容器包括WEB网页,应用程序窗体等... Activ ...

  5. MFC ActiveX控件的创建

    参考资料:MFC ActiveX (ocx)控件的开发_hk的博客-CSDN博客MFC ActiveX (ocx)开发https://blog.csdn.net/hkcsdn/article/deta ...

  6. 创建带界面UI的Activex

    1.ActiveX的基本概念 ActiveX控件可以看作是一个极小的服务器应用程序,它不能独立运行,必须嵌入到某个容器程序中,与该容器一起运行.这个容器包括WEB网页,应用程序窗体等... Activ ...

  7. 在 .NET Compact Framework 2.0 中宿主 ActiveX 控件

    适用于: ActiveX Microsoft .NET Compact Framework 版本 2.0 摘要:了解如何在使用 .NET Compact 的应用程序中宿主 ActiveX 控件.本文提 ...

  8. ActiveX (.ocx)的写法,及在IE里调用

    ActiveX组件编制与ASP接口应用 ActiveX ActiveX是Microsoft为了使开发人员能够把计算机桌面环境与构成Internet及其大量资源的环境集成起来,同时保护在Windows中 ...

  9. ActiveX技术在WEB页上的应用[转载]

       ActiveX技术在WEB页上的应用 汪涛 Internet 的发展可以说是日新月异,这种快速的发展给人们带来了大量的机会.全世界的电信服务商都在寻找增强Internet在线服务的方法.在Int ...

最新文章

  1. VS Code 安装插件、自定义模板、自定义配置参数、自定义主题、配置参数说明、常用的扩展插件
  2. AI求解薛定谔方程,兼具准确度和计算效率,登上《自然-化学》
  3. 深度学习笔记 第五门课 序列模型 第二周 自然语言处理与词嵌入
  4. 使用Spring框架能带来那些好处?
  5. centos下升级jdk版本
  6. 【kafka】Kafka 集群配置SASL+ACL
  7. source insight 导入JDK源码
  8. html中图片为什么反了,HTML5 canvas如何实现图片反色
  9. Tslib的触摸屏5点校准算法原理和实现
  10. python:算术平方根的实现
  11. b站首页banner景深移动特效 bilibili秋
  12. 在我附近的网吧的代理服务器iptables脚本
  13. Java开心农场源码Java欢乐农场源码
  14. 制作stlink(烧录部分)
  15. 乌班图服务器账号密码忘了,如何在Ubuntu 20.04 LTS服务器中重置Sudo密码
  16. 千年古都西安 一座城市的辉煌与梦想
  17. (八)Java算法:堆排序(详细图解)
  18. html点击图标出现日历,日历图标的纯CSS实现
  19. 单光子发射CsPbX3 单颗粒钛矿胶体量子点/配体C8/C18-CsPbI3钙钛矿量子点
  20. 武汉理工计算机学院吧,告诫那些想到武汉理工大学计算机学院读书的同学们!...

热门文章

  1. layui 自动渲染_Layui表格自动渲染
  2. SQL Server高级查询之数据库设计(E-R模型图)
  3. JavaScript数据类型之typeof检测变量数据类型(5)
  4. 计算几何-判断两条线段是否相交
  5. 如何才能在jsp文件中使用el表达式
  6. 计算机组成原理—地址码
  7. 输入挂(bzoj 2901: 矩阵求和)
  8. 关于YOLOv3的文章
  9. string类型的数字字符串直接转换成int型方法
  10. [GCN+FocalLoss] 从数据角度分析实验 of Semi-supervised classification with graph convolutional networks