创建一个C#COM可见的类很容易,并且(如您在评论中所说)很有趣。这是一个小样本。
在一个新的C#库项目,添加:
using System;
using System.Runtime.InteropServices;
using System.Windows.Forms;
namespace CSharpCom
{
[ComVisible(true)]
[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
//The 3 GUIDs in this file need to be unique for your COM object.
//Generate new ones using Tools->Create GUID in VS2010
[Guid("18C66A75-5CA4-4555-991D-7115DB857F7A")]
public interface ICSharpCom
{
string Format(string FormatString, [Optional]object arg0, [Optional]object arg1, [Optional]object arg2, [Optional]object arg3);
void ShowMessageBox(string SomeText);
}
//TODO: Change me!
[Guid("5D338F6F-A028-41CA-9054-18752D14B1BB")] //Change this
[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
interface ICSharpComEvents
{
//Add event definitions here. Add [DispId(1..n)] attributes
//before each event declaration.
}
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ComSourceInterfaces(typeof(ICSharpComEvents))]
//TODO: Change me!
[Guid("C17C5EAD-AA14-464E-AD32-E9521AC17134")]
public sealed class CSharpCom : ICSharpCom
{
public string Format(string FormatString, [Optional]object arg0, [Optional]object arg1, [Optional]object arg2, [Optional]object arg3)
{
return string.Format(FormatString, arg0, arg1, arg2, arg3);
}
public void ShowMessageBox(string SomeText)
{
MessageBox.Show(SomeText);
}
}
}
您将要进入你的项目属性,在“签名”选项卡,选中签署您的集会,并创建一个新的“强名密钥文件“。这将有助于防止注册DLL的版本问题。
编译它,并在Visual Studio命令提示符下使用regasm
注册该DLL。您将使用32位或64位regasm取决于你使用的是什么版本的Office的......你会发现RegAsm在C:\windows\Microsoft.NET\Framework
或C:\windows\Microsoft.NET\Framework64
(32位和64位,分别为):
C:\windows\Microsoft.NET\Framework\v4.0.30319\RegAsm.exe /codebase /tlb CSharpCom.dll
这将在Windows上注册你的DLL,所以现在在VBA编辑器中,你应该可以进入Tools-> References并找到你的COM的命名空间“CSharpCom”。检查框,现在你应该可以在VBA来创建你的COM对象:
Sub TestCom()
Dim c As CSharpCom.CSharpCom
Set c = New CSharpCom.CSharpCom
c.ShowMessageBox c.Format("{0} {1}!", "Hello", "World")
End Sub
您可以添加表格到您的COM对象,并打开它们时,VBA调用特定的方法;你应该可以使用它来创建一个带有进度条的表单。但有一点需要考虑的是,VBA是单线程的。这意味着当你的代码运行时,其他的东西都会被冻结,所以事情可能会变得棘手。你可以在你的COM可见类中创建3个方法:一个打开表单,一个更新进度(在VBA调用update()方法后立即调用VBA的DoEvents()方法在您的COM对象上,以允许Office处理屏幕更新),以及一个关闭它。你应该在窗体上调用Dispose()。这可以在“close”方法中完成,但我认为如果你的VBA崩溃,并且你的close方法从未被调用,那么它可能会导致内存泄漏/问题 - 只是别的可以考虑的事情。
我建议你花点时间让VBA应用程序更好。另外,没有理由不能使用进度条并登录VBA。为什么介绍额外的复杂性,如果你不需要? –
嗯,首先,我认为我不会创建一个更快或更高效的应用程序,因为我几乎全部使用了VBA的所有知识。正如我所说,我是一个绝对的业余爱好者。第二:在工作簿实际完全生成之前,我希望“Excel层”不可见。第三:我在VBA中创建表单的经验绝对没有,但我在C#中有一些经验。第四:正如我所说,这似乎是一件非常有趣的事情。 –
我不明白你是如何抵达你已经学习了用C#编程的形式,而是用VBA编程'其他'的情况?将所有这些运行在一个平台或另一个平台上是不是更有意义?我建议让它在C#中运行,因为它是更新的技术。但是,如果它只是形成,你需要构建一个完整的VBA项目,在VBA中,表单确实非常简单。当你遇到困难时,只需尝试一下并提出问题。这将比试图在VBA之间引发事件并将它们吸收在.NET中简单得多.Net –