在 C# 中动态加载非托管 OCX

2024-05-03

我在 VC++ 中创建了 ocx 如果静态加载它工作正常,但是当我从程序集中动态加载它时它会出现异常。

    public Assembly assembly;

    public Form1()
    {
        InitializeComponent();            
       assembly = Assembly.LoadFile(Application.StartupPath + "\\abc.ocx");

    }

它给出以下异常该模块应包含程序集清单。

(HRESULT 异常:0x80131018)


您必须执行许多在使用工具箱时通常会自动执行的步骤。首先,您必须运行 Aximp.exe 实用程序来生成 .NET 互操作程序集。使用 Visual Studio 命令提示符运行该工具。您将获得两个程序集,axinterop.foo.dll 包含一个从 AxHost 派生的包装类,并允许您将控件放在窗体上。 interop.foo.dll 是互操作程序集,它使控件实现的 COM 接口可从 .NET 程序调用。

接下来,您必须确保这些 DLL 存在于构建目录中。最好的办法是将它们添加到您的项目中并将其“复制到输出目录”设置为“如果较新则复制”。

现在,您可以在代码中使用 Assembly.Load("axinterop.foo.dll") 动态加载互操作程序集。

接下来,您必须创建控件的实例,使用 Assembly.CreateInstance() 并传递 AxHost 包装类的类型名称。如果您不知道它的名称是什么(这并不明显),那么可以使用 ildasm.exe 查看 axinterop.foo.dll 程序集。将返回的对象投射到 AxHost。

接下来,您必须将控件添加到表单的 Controls 集合中,以便它可见且可用。在创建控件实例之前,您无法调用任何接口方法;在添加控件并且触发窗体的 Load 事件之前,不会发生这种情况。

接下来你必须使用反射或dynamic关键字来获取对控件实现的接口的引用,以防您需要设置属性或调用方法。这很难做到正确,您需要首先使用从工具箱添加的控件来编写代码,这样您就不必对正确的名称猜测太多。


这显然是非常痛苦且难以纠正的。通过向项目中添加直接使用 OCX 并通过接口公开其重要属性的类库,可以提高获得良好结果的可能性。并使用 Assembly.Load()that one.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在 C# 中动态加载非托管 OCX 的相关文章

随机推荐