在JavaScript中调用对象时,可动态添加删除成员如:

  1. var obj=new Object;
  2. obj.member1='aaaaa';
  3. obj.fun1=function()
  4. {
  5. alert('fun1');
  6. }
查了好些资料,原来Object这个COM对象,是实现了IDispatchEx接口

JS在调用对象成员之前,先利用IDispatchEx::GetDispID(成员名) 判断成员是否存在

那么在VC++中编写COM对象时即可以这样 在GetDispID中 添加对应的成员即可

  1. //类头文件
  2. class CSRObject :public IDispatchEx
  3. {
  4. CSRObject(void);
  5. ~CSRObject(void);
  6. virtual HRESULT STDMETHODCALLTYPE GetDispID( __RPC__in BSTR bstrName, DWORD grfdex, __RPC__out DISPID *pid );
  7.  
  8. virtual HRESULT STDMETHODCALLTYPE InvokeEx( DISPID id, LCID lcid, WORD wFlags, DISPPARAMS *pdp, VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller );
  9.  
  10. virtual HRESULT STDMETHODCALLTYPE DeleteMemberByName( __RPC__in BSTR bstrName, DWORD grfdex );
  11. virtual HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, void **ppvObject );
  12. //省略若干虚函数实现...
  13. }
  1. HRESULT STDMETHODCALLTYPE CSRObject::QueryInterface( REFIID riid, void **ppvObject )
  2. {
  3. if (riid==IID_IUnknown)
  4. {
  5. *ppvObject = (CSRObject *)this;
  6. }else if (riid==IID_IDispatch)
  7. {
  8. *ppvObject = (CSRObject *)this;
  9. }else if (riid==IID_IDispatchEx)
  10. {
  11. *ppvObject = (CSRObject *)this;
  12. //IDispatchEx接口
  13. }else{
  14. *ppvObject = NULL;
  15. return(E_NOINTERFACE);
  16. }
  17. return S_OK;
  18. }
  19.  
  20. //这里是JS按照成员名字查成员DISPID
  21. //JS在调用成员前会先调用该函数
  22. HRESULT STDMETHODCALLTYPE CSRObject::GetDispID( __RPC__in BSTR bstrName, DWORD grfdex, __RPC__out DISPID *pid )
  23. {
  24. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  25.  
  26. if(grfdex & fdexNameCaseInsensitive)
  1. //如果有fdexNameCaseInsensitive标志,查找成员名时忽略大小写
  2.  
  3. if (成员不存在 && grfdex & fdexNameEnsure)
  1. //如果成员不存在且有fdexNameEnsure标志,你需要动态的创建这个成员名
  2.  
  3. //存在成员返回S_OK,并且 *pid=该成员ID
  4.  
  5. //没有该成员返回 DISP_E_UNKNOWNNAME
  6. }
  7.  
  8. //这里才是真正的调用函数
  9. HRESULT STDMETHODCALLTYPE CSRObject::InvokeEx( DISPID id, LCID lcid, WORD wFlags, DISPPARAMS *pdp, VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller )
  10. {
  11. AFX_MANAGE_STATE(AfxGetStaticModuleState());
  12.  
  13. //参数:id 就是JS通过GetDispID得到的DISPID,你需要按照该ID判断此次调用的是什么函数
  14.  
  15. if (wFlags & DISPATCH_PROPERTYGET && wFlags & DISPATCH_METHOD)
  16. {
  17. //比如在JS中的代码:
  18. //var n=xxx.getvalue([param]);
  19. //那么将会到这里来
  20. }else if (wFlags & DISPATCH_PROPERTYGET) //获取属性值
  21. {
  22. //比如在JS中的代码:
  23. //var n=xxx.value;
  24. //那么将会到这里来
  25. }else if (wFlags & DISPATCH_PROPERTYPUT) //设置属性值
  26. {
  27. //比如在JS中的代码:
  28. //xxx.value=n;
  29. //那么将会到这里来
  30. }else if (wFlags & DISPATCH_METHOD) //调用成员
  31. {
  32. //比如在JS中的代码:
  33. //xxx.getvalue();
  34. //那么将会到这里来
  35. }else{
  36. //其它情况暂时没遇到过
  37. return DISP_E_MEMBERNOTFOUND;
  38. }
  39.  
  40. return hr;
  41. }

备份:http://www.silenceret.com/view.asp?id=12

COM动态添加删除成员,类似JavaScript中调用的对象的更多相关文章

  1. JAVAFX 2.0 javascript中调用java代码

    现在你已经知道如何在JavaFX中调用JavaScript.在本章中,你将了解到相反的功能——在web页面中调用JavaFX. 大体上的理念是在JavaFX程序中创建一个接口对象,并通过调用JSObj ...

  2. 使用Ajax在javascript中调用后台C#函数

    使用Ajax在javascript中调用后台C#函数 最近一段时间在紧跟一个网站的项目,数据库中用户表的UserName要求是唯一的,所以当用户选定一个用户名进行注册时要首先检查该用户名是否已被占用, ...

  3. 将HTML字符转换为DOM节点并动态添加到文档中

    将HTML字符转换为DOM节点并动态添加到文档中 将字符串动态转换为DOM节点,在开发中经常遇到,尤其在模板引擎中更是不可或缺的技术. 字符串转换为DOM节点本身并不难,本篇文章主要涉及两个主题: 1 ...

  4. JavaScript中的事件对象

    JavaScript中的事件对象 JavaScript中的事件对象是非常重要的,恐怕是我们在项目中使用的最多的了.在触发DOM上的某个事件时,会产生一个事件对象event,这个对象中包含这所有与事件有 ...

  5. 详解javascript中的this对象

    详解javascript中的this对象 前言 Javascript是一门基于对象的动态语言,也就是说,所有东西都是对象,一个很典型的例子就是函数也被视为普通的对象.Javascript可以通过一定的 ...

  6. JavaScript中创建字典对象(dictionary)实例

    这篇文章主要介绍了JavaScript中创建字典对象(dictionary)实例,本文直接给出了实现的源码,并给出了使用示例,需要的朋友可以参考下 对于JavaScript来说,其自身的Array对象 ...

  7. Javascript学习1 - Javascript中的类型对象

    原文:Javascript学习1 - Javascript中的类型对象 1.1关于Numbers对象. 常用的方法:number.toString() 不用具体介绍,把数字转换为字符串,相应的还有一个 ...

  8. 简单使用JSON,JavaScript中创建 JSON 对象(一)

    JSON:JavaScript 对象表示法(JavaScript Object Notation). JSON 是存储和交换文本信息的语法.类似 XML. JSON 比 XML 更小.更快,更易解析. ...

  9. javascript中如何获取对象名

    javascript中如何获取对象名 一.总结 一句话总结:将对象传入参数,看参数是否为函数(js中的对象和函数是一个意思么(函数肯定是对象)),对象参数.name属性即可获得 //版本4 funct ...

随机推荐

  1. [转]使用C#调用cmd来执行sql脚本

    本文转自:https://blog.csdn.net/tvmerp/article/details/1822669 下面是使用C#调用cmd来执行osql实现脚本的执行. using System; ...

  2. Winsock API TCP/IP网络通信

    通信流程如下: 1.Winsock库的装入.初始化 #pragma comment(lib,"WS2_32.lib").WSAStartup() 2.套接字的创建(服务器端是监听套 ...

  3. java 实现多重继承

    java提高篇(九)-----实现多重继承 接口 多重继承指的是一个类可以同时从多于一个的父类那里继承行为和特征,然而我们知道Java为了保证数据安全,它只允许单继承.有些时候我们会认为如果系统中需要 ...

  4. 使用git将本地仓库同步到github远程仓库

    一.下载安装git客户端windows版本 二.建立本地仓库文件夹 三.在本地仓库里右键点击Git Bash Here 四.初始化本地仓库 [git init] 执行之后仓库中会创建隐藏的文件夹.gi ...

  5. Windows平台如何部署scrapy

    0.安装Anaconda 这个不教了,自己去Anaconda官网上下个安装包,装上就好. https://www.anaconda.com/distribution/ 1.使用Anaconda创建一个 ...

  6. js-ES6学习笔记-字符串的扩展

    1.codePointAt方法是测试一个字符由两个字节还是由四个字节组成的最简单方法.codePointAt方法会正确返回32位的UTF-16字符的码点. function is32Bit(c) { ...

  7. json 平面转树状 child [zhuan]

    <script> /** * json格式转树状结构 * @param {json} json数据 * @param {String} id的字符串 * @param {String} 父 ...

  8. 如何解决Your project contains C++ files but it is not using a supported native build system

    最近因为项目需要下载Android终端模拟器(Android-Terminal-Emulator)源码进行调试编译,编译过程中出现报错 Error:Execution failed for task ...

  9. Android网络编程系列之Volley总结

    前言 Volley的中文翻译为“齐射.并发”,是在2013年的Google大会上发布的一款Android平台网络通信库,具有网络请求的处理.小图片的异步加载和缓存等功能,能够帮助 Android AP ...

  10. 容器监控—阿里云&容器内部服务监控

    目前Docker的使用越来越离不开对容器的监控,阿里云最近上线了容器服务,不但提供了核心的容器和宿主机监控能力,而且支持集成 Cloud Insight 监控,下面会介绍如何集成. 首先介绍一下阿里云 ...