首先,我意识到这里有很多帖子都讨论了这个问题。我肯定已经阅读了超过20篇,但它们都没有给出我需要的答案。
我编写了一个微小的C#测试COM DLL,其中只有一个方法,在消息框中打印“我活着了!”。使用管理员身份运行VStudio,我可以构建和注册COM对象。我已成功从VBA调用该对象并运行该方法。而且我可以在VStudio的添加引用/ COM对话框中看到COM接口的名称。这使我认为对象已经正确构建、注册和可用。
现在,我正在尝试从控制台C#应用程序中调用它。与许多其他人一样,我正在尝试找出在C#中获取对象的VBA“CreateObject(”DLLName.ClassName“)”代码的等效方式。
一种方法是仅将DLL添加到我的控制台应用程序项目的引用中。我通过添加引用对话框的项目部分指向程序集,而不是通过对话框的COM部分指向程序集。然后我可以简单地说var o = new MyComImplementationClass();
并像处理任何其他类一样处理它。那样可以工作,但这意味着我的控制台应用程序是作弊的,并没有通过通常的COM GAC接口使用COM对象。
另一种方法(虽然不起作用,但我希望它能够起作用)是通过添加引用对话框上的COM选项卡添加引用。我可以看到它,但VS抗议说“XXX.tlb文件是从.NET程序集导出的。应该添加对程序集的引用。”这使我回到上面的解决方案,我认为这意味着我的应用程序在作弊。(例如,我不必在VBA测试应用程序中添加引用。)
另一种方法是使用下面代码片段所示的Type.GetTypeFromProgId
。但我也无法让它工作。我一定是传入了不正确的ProgID字符串 - 我有一点感觉它与注册表信息有关,而不是我在VBA中向CreateObject()提供的相同的“DLLName.ClassName”字符串。
public static dynamic ComObjectGet () {
const string progID = "ComExampleDLLName.ComImplementationClassName";
Type foo = Type.GetTypeFromProgID (progID);
dynamic COMobject = Activator.CreateInstance (foo);
return COMobject;
}
更糟的是,在这个MSDN示例页面上,它说:“此方法是为COM支持提供的。在Microsoft .NET Framework中不使用程序ID,因为它们已被命名空间的概念取代。”所以可能我根本不应该使用
GetTypeFromProgID
。如果有帮助的话,我可以在C#中使用VSTO调用MSOffice主要互操作程序集。但它们从“添加引用”对话框的COM选项卡加载(这也是我想从中加载我的COM库的地方)。
为了清晰起见,我的COM DLL名称为ComExampleLibrary.dll。默认命名空间是ComExampleNamespace。接口名称为IComInterface,实现类名为ComImplementation。内部方法名称为Run。
是否有人能给我提供指令或代码片段,以便从C#中调用COM对象(不仅仅是我编写的对象)的正确和批准方法?谢谢。
Type.GetTypeFromCLSID
代替Type.GetTypeFromProgID
。 - Klaus Güttergacutil -i COMExampleLibrary.dll
吗? - Clint