创建 IDispatch .NET COM 类,其中内容仅在运行时可用

Posted

技术标签:

【中文标题】创建 IDispatch .NET COM 类,其中内容仅在运行时可用【英文标题】:Create IDispatch .NET COM class where content is available only at runtime 【发布时间】:2010-11-18 04:45:03 【问题描述】:

我目前正在将一些代码从本机 C++ 迁移到托管 C++(纯)。该代码涉及与 Windows Active Scripting 的交互。目前我们的原生代码提供了一个 名为“ObjectDispatch”的类实现了“IDispatch”(使用 ATL)。此类实现在运行时查询我们自己的本机类“Object”以确定它支持哪些方法和属性,然后将任何“IDispatch::Invoke”调用转发给该“Object”。

我已经看到使用支持“IDispatch”的 .NET COM 互操作的示例,但是这些实现要么源自 IDL,要么基于规范 .NET 类,它们都不会在运行时发生。

.NET COM 互操作似乎可以生成“IDispatch”的实现 如果您在给定类上使用以下属性,则在编译时:

[ClassInterface(ClassInterfaceType::AutoDispatch)]

我假设我可以在运行时动态生成一个支持该属性的类。但是,在我尝试之前,我想知道是否有人有任何想法 如何通过与本机代码一起使用的类似方式来实现这一点。

请注意,此时“Object”类仍保留为原生类。

【问题讨论】:

我已经多次回到这个问题,我真的不明白你在问什么......你有一个通过 IDispatch 公开的本机对象模型,并且想要从托管代码中使用它? 是的,你是对的。我想更好的标题应该是“我可以直接在 .net 中实现 IDispatch 吗?”。 【参考方案1】:

从微软那里得到了一些“可能”有效的官方反馈。没有时间确认,但如果有人感兴趣,最好发帖。

    [Guid("00020400-0000-0000-c000-000000000046"),
    InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
    public interface IDispatch
    
        int GetTypeInfoCount();


    ITypeInfo GetTypeInfo(
        [MarshalAs(UnmanagedType.U4)] int iTInfo,
        [MarshalAs(UnmanagedType.U4)] int lcid);

    [PreserveSig]
    int GetIDsOfNames(
        ref Guid riid,
        [MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.LPWStr)] string[] rgsNames,
        int cNames,
        int lcid,
        [MarshalAs(UnmanagedType.LPArray)] int[] rgDispId);

    [PreserveSig]
    int Invoke(
        int dispIdMember,
        ref Guid riid,
        [MarshalAs(UnmanagedType.U4)] int lcid,
        [MarshalAs(UnmanagedType.U4)] int dwFlags,
        ref System.Runtime.InteropServices.ComTypes.DISPPARAMS pDispParams,
        [Out, MarshalAs(UnmanagedType.LPArray)] object[] pVarResult,
        ref System.Runtime.InteropServices.ComTypes.EXCEPINFO pExcepInfo,
        [Out, MarshalAs(UnmanagedType.LPArray)] IntPtr[] pArgErr);


class IImplimentIDispatch : IDispatch

    public IImplimentIDispatch(object o)
        
             _o = o;
…

【讨论】:

以上是关于创建 IDispatch .NET COM 类,其中内容仅在运行时可用的主要内容,如果未能解决你的问题,请参考以下文章

COM 互操作 (CCW) 中的重载 - IDispatch 名称包括后缀(_2、_3 等)

.NET 6 IDispatch 客户端实现崩溃

LPDISPATCH是啥数据类型,他和IDispatch有啥关系

使用 IDispatch 的 C++ 和 COM 的类似动态的替代方案

COM技术入门

继承接口 & IUnknown , IDispatch 方法定义