2023年12月30日发(作者:)

前段时间装了个visual studio 2010,试着用里面的VSTO4.0,但是对如何生成一个自定义函数始终搞不明白(之前也看了《VSTO开发指南》,但觉得里面所讲的东西太泛了,而且版本不一样,形式也改变了不少),终于在网上看到有人写出一个完整的过程(原文请看/brooks-dotnet/archive/2011/01/16/),但在实操中还是有不少问题,但经过多次尝试,终于解决了所遇到的问题,现在我就根据原文的内容以及建立过程中所遇到的问题,重新整理后讲述建立一个自定义函数的过程。

一、 启动VS2010,(这里尝试着用C#来编写)新建一个类库,填好名称之后按确定,开始编码。

二、 进入编程界面后,先引用必须的类库

using

System;

using

c;

using

;

using

;

using

pServices;

using 32;

using

设置GUID及COM的一些特性

[Guid("A4AAE79B-9587-4014-BABB-966C5DF76C83")]

[ClassInterface(al),ComVisible(true)]

如图示:

Guid这个标识码可用LINQPad程序来获取(可从/下载)

在类中,除了有函数主体外,还必须有注册及注销时的行为语句,所以必须添加以下语句:

#region COM Related

[ComRegisterFunction]

public static void RegisterFunction(Type type)

{

SubKey(GetSubKeyName(type, "Programmable"));

var key = bKey(GetSubKeyName(type, "InprocServer32"), true);

ue("", Directory + @"", );

}

[ComUnregisterFunction]

public static void UnregisterFunction(Type type)

{

SubKey(GetSubKeyName(type, "Programmable"), false);

}

private static string GetSubKeyName(Type type, string subKeyName)

{

var s = new Builder();

(@"CLSID{");

(ng().ToUpper());

(@"}");

(subKeyName);

return ng();

}

#endregion

如图示:

三、 这些准备工作完毕后就可以写自己的函数主体了,这里以一个自定义的字符串联结为例:

public string MyConcate(params Object[] values)

{

string iStr = "";

Range iRng;

for (int iStep = 0; iStep < ; iStep++)

{

if (values[iStep].ToString() == "System.__ComObject")

{

iRng = (Range)values[iStep];

if ( > 1)

{

foreach(Range cRng in iRng)

{

iStr += ng();

}

}

else

{

iStr += ng();

}

}

else

{

iStr += values[iStep].ToString();

}

}

return iStr;

}

注:由于这里是用了params来传递不定数量的参数,所以需要把Object强制转换为Range类型,否则直接写

iStr += values[iStep].ToString();

只能获取到一个“ect”字符串,由于需要强制转换,所以要加入另外一个引用

using ;(此引用需事先在解决方案资源管理器那里添加,否则无法引用)

四、 编写函数完毕,即可进行编译生成,在编译之前,有必要设置一些选项。

进入菜单栏-》项目-》(项目名称)属性

打开属性设置窗体,进入“生成”项

其中的“为COM互操作注册”,如果你的系统是WIN7,那就不要选择此项,你选择了的话,由于权限问题,在编译的时候就会出现错误,导致无法编译成功,但即使是在XP的情况下,编译成功了,但在加载的时候仍不能自动注册,导致加载不成功,不知道是不是VSTO4.0的缘故,所以这项如果选了的话就把它取消。

如果你想调试程序,那么就可以进入“调试”项,选择“启动外部程序”然后选择EXCEL程序作为函数调试的实体

设置好后就可以生成项目了。

五、 注册加载DLL

注册与注销DLL需要一个regasm程序来完成,如果你装的是.NetFrameWork4.0,那么这个程序就在%windir%meworkv4.0.30319文件夹下,我们打开CMD,进入此文件夹,如图示:

这里要注意的一点是,如果你的系统是Win7或Vista,那么你运行CMD时必须是以管理员的身份运行,否则的话会因为权限问题,在注册时无法向注册表写入数据导致注册不成功。

进入文件夹后,输入注册语句为DLL进行注册,如图示:

Regasm有多个运行参数,详细可通过帮助查看 /help

回车运行后,显示如下信息:

因为是未签名程序集,所以会有警告,你在项目属性那里设置好签名就不会有这样的警告了。

现在这个DLL已经注册成功,可以在EXCEL中引用这个DLL并使用其中所写的自定义函数了。以EXCEL2003为例来使用刚注册的这个DLL(2007、2010只是在引用的操作上有所不同),打开EXCEL,(菜单栏)工具-》加载宏-》自动化

在弹出的窗口中找到并选择刚才自己写的那个类文件,按两次确定后,即加载成功

加载完毕就可以在工作页面中使用所编写的自定义函数了。

至此,一个由C#编写的自定义函数就可以正常使用了。

六、 注销DLL

当这个自定义的DLL不再需要时,该如何注销呢,其过程跟注册差不多,只是在应用regasm时的参数有所不同而已:regasm /unregister "D:My DocumentsVisual Studio "