当前位置:数据分析 > vs2010安装自定义扩展_实现Visual Studio 2010一个很简单的很酷的扩展

vs2010安装自定义扩展_实现Visual Studio 2010一个很简单的很酷的扩展

  • 发布:2023-09-23 12:28

这里简单介绍如何在VS2010开发环境下制作安装项目,其中包括如何设置开机启动、删除注册表及安装后自动运行,加上卸载功能。

1、? 创建安装项目

??? 打开VS2010,点击菜单上的“文件”>>“新建”>>“项目”,弹出如下对话框。

?

??? 如上图所示,在“其他项目类型”中选择“安装项目”,根据自己的需求命名,这里命名为“MySetup”,选择保存路径。这样就创建了一个安装项目。

2、?在安装项目中添加其他应用程序项目 点击菜单上的“文件”>>“添加”>>“现有项目”,弹出如下对话框。

??? 这里选择之前已经做好的一个WPF应用程序项目

3、?将WPF的可执行文件(.exe)、类库(.dll文件)及所需图片加入安装项目中 右击“MySetup”>>“视图”>>“文件系统”,主窗口显示文件系统界面,如下图

??? 右击“应用程序文件夹”>>“添加”>>“项目输出”,弹出如下对话框。

??? 在“项目”选项中选择“DataServiceHost”,按住“Ctrl”键,选中“主输出”和“内容文件”,单击“确定”。 再右击“应用程序文件夹”>>“添加”>>“文件夹”,命名为“Images”,在“Images”中放入应用程序需要的图片,右击“Images”>>“添加”>>“文件”,在弹出的对话框中添加所需的图片。

4、?创建快捷方式 在“应用程序文件夹”中右击“主输出来自DataServiceHost(活动)”,如下图。

?? 点击“创建主输出来自DataServiceHost(活动)的快捷方式”,将快捷方式重命名为“我的WPF应用程序”,这里可以根据需要命名。 在“文件系统”中的“用户的“程序”菜单”添加文件夹“我的WPF应用程序”,这里可以根据需求命名,将之前“我的WPF应用程序快捷方式”剪切到该文件夹中。 同理可以在“文件系统”中的“用户桌面”中创建快捷方式。(在用户桌面中不要添加文件夹)

5、?实现安装程序卸载 这里直接引用了Windows系统中自带的一个卸载程序,该卸载程序在“C:/Windows/System32”文件夹中,名称为“msiexec.exe”,右击“应用程序文件夹”>>“添加”>>“文件”,将“msiexec.exe”加入“应用程序文件夹”中

??? 同步骤4,创建卸载程序的快捷方式,这里建议不要在“用户桌面”中创建卸载程序,难看!!! 重点,“卸载快捷方式”的属性“Argument”值设为“/x{710AD120-3D4C-430D-A9FA-A1D504465CC8}”,其中“{710AD120-3D4C-430D-A9FA-A1D504465CC8}”可在“MySetup”属性框口中找到。左击“MySetup”(不是右击),再点击属性窗口,如下图。 “ProductName”属性值就是上述的“{710AD120-3D4C-430D-A9FA-A1D504465CC8}”。

6、?改变各快捷方式的图标 这里只拿“我的WPF应用程序快捷方式”为例,其他同理。 在“应用程序文件夹”中的“Images”中添加需要的“.ico图标”,这里添加一个“mywpf.ico”图标。如下图。 右击“我的WPF应用程序快捷方式”>>“属性窗口”,属性窗口如下图。 设置“Icon”属性,选择“Images”中的“mywpf.ico”图标。

7、?实现开机启动 右击“MySetup”>>“视图”>>“注册表”,主窗口显示如下图。

?? 在“HKEY_LOCAL-MACHINE”文件夹下新建键“Software”>>“Microsoft”>>“Windows”>>“CurrentVersion”>>“Run”,在“Run”文件夹新建字符串值,命名为“DataServiceHost.exe”,可根据需求命名,右击“DataServiceHost”>>“属性窗口”,其中“Value”属性设为“[TARGETDIR] DataServiceHost.exe”。如此,便实现了开机启动。

8、?实现安装后自动运行及删除注册表 实现这两个功能就需要一些技巧,点击菜单上的“文件”>>“添加”>>“新项目”,如下图。 在“HKEY_LOCAL-MACHINE”文件夹下新建键“Software”>>“Microsoft”>>“Windows”>>“CurrentVersion”>>“Run”,在“Run”文件夹新建字符串值,命名为“DataServiceHost.exe”,可根据需求命名,右击“DataServiceHost”>>“属性窗口”,其中“Value”属性设为“[TARGETDIR] DataServiceHost.exe”。如此,便实现了开机启动。

8、?实现安装后自动运行及删除注册表 实现这两个功能就需要一些技巧,点击菜单上的“文件”>>“添加”>>“新项目”,如下图。

选择“安装程序类”,命名为“Installer”。 在“Installer.cs”代码中重写如下方法:

///

/// 函数入口——主函数

///

public static void Main()

{

}

public Installer1()

{

InitializeComponent();

}

///

/// 重写安装完成后函数

/// 实现安装完成后自动启动已安装的程序

///

///

protected override void OnAfterInstall(IDictionary savedState)

{

base.OnAfterInstall(savedState);

}

///

/// 重写安装过程方法

///

///

///

public override void Install(IDictionary stateSaver)

{

base.Install(stateSaver);

}

protected override void OnBeforeInstall(IDictionary savedState)

{

base.OnBeforeInstall(savedState);

}

///

/// 重写卸载方法

///

///

public override void Uninstall(IDictionary savedState)

{

base.Uninstall(savedState);

}

///

/// 重写卸载完成后函数

/// 实现安装完成后自动删除注册表

///

///

protected override void OnAfterUninstall(IDictionary savedState)

{

base.OnAfterUninstall(savedState);

}

///

/// 重写回滚方法

///

///

public override void Rollback(IDictionary savedState)

{

base.Rollback(savedState);

}

这里对protected override void OnAfterInstall(IDictionary savedState){}和protected override void OnAfterUninstall(IDictionary savedState){}进行如下自定义操作(当然也可以对其它方法进行自定义以实现其它功能)。

protected override void OnAfterInstall(IDictionary savedState)

{

base.OnAfterInstall(savedState);

Assembly asm = Assembly.GetExecutingAssembly();

string path = asm.Location.Remove(asm.Location.LastIndexOf("\\")) + "\\";

try

{

System.Diagnostics.Process.Start(path + "\\DataServiceHost.exe");

}

catch (Exception my)

{

throw new Exception(my.Message);

}

}

protected override void OnAfterUninstall(IDictionary savedState)

{

base.OnAfterUninstall(savedState);

RegistryKey hklm = Registry.LocalMachine;

RegistryKey run = hklm.CreateSubKey(@"Software\Microsoft\Windows\CurrentVersion\Run");

try

{

run.DeleteValue("DataServiceHost.exe");

run.Close();

hklm.Close();

}

catch (Exception my)

{

throw new Exception(my.Message);

}

}

自定义操作完成后,一定要将应用程序生成,这样就可以得到“.dll”文件。

生成成功后,就可以将该“.dll”程序集添加到安装项目中。右击“MySetup”>>“视图”>>“自定义操作”,主窗口如下图。

右击“安装”>>“添加自定义操作”,弹出如下对话框。

在“应用程序文件夹”中添加程序集,在之前“InstallService应用程序”中debug文件夹中找到“.dll”文件,添加进去。这样便实现了安装后自动运行和卸载后删除注册表的功能。9、?现在可以点击生成

右击“MySetup”>>“生成”,成啦!!!在安装项目中Debug文件夹中找到“Setup.msi”,双击就可以安装了….

10 Context.Parameters["targetdir"]为获取安装路径,需要在部署项目中设置?其次,在部署项目的自定义操作中,把安装,提交,回滚,卸载都添加上面项目的主输出设置主输出的属性CustomActionData值为/targetdir="[TARGETDIR]\",这样Context.Parameters["targetdir"]才能获取到安装路径。

?

当原始控件无法满足你的开发要求的时候,自定义控件无疑使最好的选择。

关于自定义控件的使用:

一般情况下,在VS2010等版本的IDE中会将你的自定义控件自动加载到你的工具箱,但是也有些时候,VS不会自动加载,但是再程序中控件是可用的。这就会对使用自定义控件造成一定的麻烦,原因是自定义控件没有自动加载,需要手动载入。

手动载入方法: 在工具箱新建一个选项卡,右键-选择项(I)(英文:choose items)选择浏览,找到自定义控件的dll 文件,加载,即可!

在设计自定义控件时,系统默认生成的图标比较单一难看,如何为控件设计自己的图标呢,这里给出了一种基于ToolBoxBitmap?属性设置自定义控件工具箱图标的方法。

1)首先将图标文件名改为自定义控件名,如自定义控件类为

??public?partial?class?UserDefindControl:?UserControl ????????{ ????????}

那么就要将图标图片文件更名为UserDefindControl,如UserDefindControl.bmp

2)然后将图标图片复制到程序根目录下,在解决方案管理器中在项目名称右键选择“添加”—>“添加现有项”,将图标图片加入到项目中,对图片资源的属性进行修改,将“生成操作”一栏该为“嵌入的资源”。

3)添加代码。在类头部添加如下代码

??[ToolboxBitmap(typeof(UserDefindControl),"UserDefindControl.bmp")]//新添加的代码

??public?partial?class?UserDefindControl:?UserControl ????????{ ????????}

需要注意的是,使用ToolboxBitmap时需要添加using?System.Drawing引用。

如果图标图片不是放在程序根目录下,就要调整以上代码。比如图片放在程序根目录的下一级目录文件夹Icons下时,代码就要修改为:

[ToolboxBitmap(typeof(UserDefindControl),"Icons.UserDefindControl.bmp")]

至此,控件的自定义工具箱图标设置就完成了,编译程序,然后把控件拖到工具箱中试试吧!

基本介绍篇

??? 在实现这个扩展之前,让我们先弄清楚这个扩展实现什么功能。这个扩展实际上是在你的VS窗口的右上角创建了一个信息框代码。该信息框显示您的源代码的统计信息。这些信息包括:

??? 1、文件的代码行数??? 2、文件的字符数??? 3、命名空间的个数??? 4、字段个数??? 5、接口个数??? 6、类的个数??? 7、函数个数??? 8、属性个数??? 9、注释的数量???10、统计文件的大小(Bytes, KB, MB等)。

??? 当您键入您的代码,你会看到信息窗口中的数据会即时更新。

??? 这个信息窗口,是利用可扩展面板。你可以把它看成两个部分,每一个部分都可以根据您的需要展开和折叠。这样,当你不需要它时,你将它可以折叠起来,需要的时候,将它展开。下面演示如何展开/折叠这个控件。

?

??? 这个控件有三个特殊的状态。第一个状态是一个很小的扩展按钮。如上图的第一部分。只需点击它,就会打开控件右侧的面板,这个面板显示文件的基本数据,如上图的第二部分。这个控件还有一个可扩展面板,如果点击扩展,就会看到下面的面板,其中显示其他的统计数据,如上图的第三部分。

实现篇:

??? 需要软件:

??? 1、 Microsoft Visual Studio 2010??? 2、 Visual Studio 2010 SDK

??? 你安装 Visual Studio SDK之后,你的Visual Studio 2010中会多出下面这些模板:

??? 这篇文章中,我们使用模板Editor ViewPort Adornment实现这个扩展,此模板将为你的代码编辑器的带来一个装饰品。?

??? 其实这个扩展包一个WPF用户控件,我把它放进VS的视窗中就成了信息框。它还含有两个类,一个类用来解析代码,获取代码的相关信息;另一个类用来处理自定义编辑器的事件和当页以及加载的时候将WPF控件添加到页面中。

第一步:创建一个Viewport Adornment项目

??? 我们从Extensibility中选择Viewport Adornment模板创建一个项目。这将生成一个SourceManifest文件和两个类文件。一个是Adornment类本身,另外一个是AdornmentFactory类。

第二步:添加一个WPF用户控件

??? 右键单击项目,选择添加一个新的WPF用户控件。为了简单起见,我使用了一个用户控件。这个用户控件实际上包含一个Expander控件,设置它的ExpandDirection = Left,它里面又包含了一些TextBlock控件和另外一个Expander ,设置里面的这个Expander的ExpandDirection = Down。看下面的代码(我删除不必要的元素,使其更简单):

?1?

??

<

Expander?

ExpandDirection

="Left"

?Style

="

{DynamicResource?ExpanderStyle1}

"

?

?2?

???????????x:Name

="expMain"

?

>

?3?

??

<

StackPanel

>

?4?

????????????????

<

TextBlock?

x:Name

="txtNoLines"

?

?5?

???????????????????????????Text

="No?of?Lines?:?{0}"

?

?6?

???????????????????????????Margin

="25?25?25?0"

?

?7?

???????????????????????????FontSize

="12"

?

?8?

???????????????????????????FontFamily

="Verdana"

?

?9?

???????????????????????????FontWeight

="Bold"

?

10?

???????????????????????????Foreground

="Yellow"

>

TextBlock

>

11?

????????????????

<

TextBlock?

x:Name

="txtNoCharacters"

?

12?

???????????????????????????Text

="No?of?Characters?:?{0}"

?

13?

???????????????????????????Margin

="25?5?25?15"

?

14?

???????????????????????????FontSize

="12"

?

15?

???????????????????????????FontFamily

="Verdana"

?

16?

???????????????????????????FontWeight

="Bold"

?

17?

???????????????????????????Foreground

="Yellow"

>

TextBlock

>

18?

????????????????

<

Expander?

x:Name

="expCodeInfo"

?ExpandDirection

="Down"

?

19?

?????????????????????????????????????Header

="Code?Information"

>

20?

????????????????????

<

StackPanel

>

21?

????????????????????????

<

TextBlock?

x:Name

="txtClassInfo"

?

22?

???????????????????????????????????Margin

="25?25?25?0"

?

23?

???????????????????????????????????FontSize

="12"

?

24?

???????????????????????????????????FontFamily

="Verdana"

?

25?

???????????????????????????????????FontWeight

="Bold"

?

26?

???????????????????????????????????Foreground

="LightYellow"

/>

27?

????????????????????????

<

Line

28?

??????????????????????????????

Margin

="0,4"

29?

??????????????????????????????SnapsToDevicePixels

="True"

30?

??????????????????????????????Stroke

="Gold"

31?

??????????????????????????????Stretch

="Fill"

32?

??????????????????????????????X1

="0"

?X2

="1"

?

33?

??????????????????????????????

/>

34?

????????????????????????

<

TextBlock?

x:Name

="txtFileSize"

35?

???????????????????????????????????Margin

="25?5?25?15"

?

36?

???????????????????????????????????FontSize

="12"

?

37?

???????????????????????????????????FontFamily

="Verdana"

?

38?

???????????????????????????????????FontWeight

="Bold"

?

39?

???????????????????????????????????Foreground

="AliceBlue"

/>

40?

????????????????????

StackPanel

>

41?

????????????????

Expander

>

42?

????????????

StackPanel

>

43?

?????????

Expander

>

??? 你可以看到,代码很简单,两个Expanders,一个用来显示基本的统计信息和另外一个显示扩展的统计信息。我还使用StackPanel来固定TextBlocks布局。

??? 现在,如果你看一下后台代码,发现它也一样简单。其实我已经创建了一个CodeInfoTracker类,用它来为我们分析源代码文件。我只是为我们的用户控件添加了一个构造函数,使用户控件更具扩展性而已。

?1?

private

?CodeInfoTracker?_cinfo;

?2?

private

?CodeInfoTracker.Calculators?_calculator;

?3?

public

?ucInfoBox(CodeInfoTracker?cinfo)

?4?

????????????:?

this

()

?5?

{

?6?

????????

this

._cinfo?

=

?cinfo;

?7?

}

?8?

?

public

?

void

?UpdateInfo(CodeInfoTracker?info)

?9?

?{

10?

????????????_calculator?

=

?info.PerFormCalculate();

11?

????????????

this

.txtNoLines.Text?

=

?

string

.Format(

"

No?of?Lines?:?{0}

"

,?

12?

????????????????????????????????????_www.sychzs.cn_of_lines);

13?

????????????

this

.txtNoCharacters.Text?

=

?

string

.Format(

"

No?of?Characters?:?{0}

"

,?

14?

???????????????????????????????????????????????????????_www.sychzs.cn_of_characters);

15?

????????????

this

.txtFileSize.Text?

=

?

string

.Format(

"

Total?File?Size?:?{0}

"

,?

16?

???????????????????????????????????????????????????????_calculator.totalfilesize);

17?

18?

????????????StringBuilder?builder?

=

?

new

?StringBuilder();

19?

????????????

if

?(

this

._calculator.interfaces?

!=

?

0

)

20?

????????????????builder.AppendFormat(

"

Interfaces?:?{0}\n\r

"

,?

21?

??????????????????????????????????????????

this

._calculator.interfaces);

22?

????????????

if

?(

this

._calculator.namespaces?

!=

?

0

)

23?

????????????????builder.AppendFormat(

"

NameSpaces?:?{0}\n\r

"

,?

24?

????????????????????????????????????????????

this

._calculator.namespaces);

25?

????????????

if

?(

this

._calculator.classes?

!=

?

0

)

26?

????????????????builder.AppendFormat(

"

Classes?:?{0}\n\r

"

,?

27?

????????????????????????????????????????????

this

._calculator.classes);

28?

????????????

if

?(

this

._calculator.methods?

!=

?

0

)

29?

????????????????builder.AppendFormat(

"

Methods?:?{0}\n\r

"

,?

this

._calculator.methods);

30?

????????????

if

?(

this

._calculator.properties?

!=

?

0

)

31?

????????????????builder.AppendFormat(

"

Properties?:?{0}\n\r

"

,?

32?

???????????????????????????????????????????????

this

._calculator.properties);

33?

????????????

if

?(

this

._calculator.fields?

!=

?

0

)

34?

????????????????builder.AppendFormat(

"

Fields?:?{0}\n\r

"

,?

this

._calculator.fields);

35?

????????????

if

?(

this

._calculator.comments?

!=

?

0

)

36?

????????????????builder.AppendFormat(

"

Comments?:?{0}\n\r

"

,?

this

._calculator.comments);

37?

38?

????????????

if

?(builder.Length?

>

?

0

)

39?

????????????{

40?

????????????????

this

.txtClassInfo.Visibility?

=

?System.Windows.Visibility.Visible;

41?

????????????????

this

.txtClassInfo.Text?

=

?builder.ToString();

42?

????????????}

43?

????????????

else

44?

????????????{

45?

????????????????

this

.txtClassInfo.Text?

=

?

""

;

46?

????????????????

this

.txtClassInfo.Visibility?

=

?System.Windows.Visibility.Hidden;

47?

???????}

48?

??}

??? 使用了一个结构体Calculators ,这个结构体放置在我们的自定义类中,它有几个int属性用来保存分析源文件获取的所有信息。?info.PerFormCalculate(); 给出分析的结果。这里使用的所有获取的信息来更新了UIElements。

第三步:创建获取源文件信息的类

??? 虽然代码存在一些复杂性,但是这个类其实很简单。我很感谢CS Parser [^],它帮助我自动地解析源代码。???

??? 这个类需要一个IWpfTextView对象,它代表着Visual Studio文本编辑器。实际上WpfTextView实现了IWpfTextView。在执行期间这个类接受这个对象。我可以从WPFTextView.TextSnapshot.GetText()获得到了源代码。??? 在我调用的这个分析的时候,我只需要检测的代码是什么语言写的。开始我想自己来实现,但是感谢上帝,我在WPFTextView中发现已经存在这个对象了。

?1?

public

?

enum

?Language

?2?

{

?3?

????????CSharp,?VisualBasic,?Indeterminate

?4?

}

?5?

internal

?Language?DetectLanguage

?6?

{

?7?

????????????

get

?8?

????????????{

?9?

????????????????

string

?langtype?

=

?

10?

????????

this

._view.FormattedLineSource.TextAndAdornmentSequencer.

11?

????????SourceBuffer.ContentType.DisplayName;

12?

????????????????

if

(langtype.Equals(

"

CSHARP

"

,?

13?

????????????StringComparison.InvariantCultureIgnoreCase))

14?

????????????????????

return

?Language.CSharp;

15?

????????????????

else

?

if

(langtype.Equals(

"

BASIC

"

,?

16?

??????????????????????????????StringComparison.InvariantCultureIgnoreCase))

17?

????????????????????

return

?Language.VisualBasic;

18?

????????????????

else

19?

????????????????????

return

?Language.Indeterminate;

20?

????????????}

21?

}

???? DetectLanguage妥善地利用WPFTextView对象的FormattedLineSource.TextAndAdornmentSequencer.SourceBuffer.ContentType.DisplayName,这个属性告诉我是使用了哪种语言。之后我创建了一个新的方法PerFormCalculate,用它来解析源代码,它返回一个Calculation结构对象。

第四步:创建 Adornment Factory 类

??? 回到这个扩展,我创建一个Adornment(InfoBoxAdornmentFactory)的Factory类。这个类继承IWpfTextViewCreationListener,用来监听WPF的编辑和创建事件。

?1?

[Export(

typeof

(IWpfTextViewCreationListener))]

?2?

[ContentType(

"

text

"

)]

?3?

[TextViewRole(PredefinedTextViewRoles.Document)]?

?4?

internal

?

sealed

?

class

?InfoBoxAdornmentFactory?:?IWpfTextViewCreationListener

?5?

{

?6?

????????[Export(

typeof

(AdornmentLayerDefinition))]

?7?

????????[Name(

"

AlwaysVisibleInfoBox

"

)]

?8?

????????[Order(After?

=

?www.sychzs.cnion)]

?9?

????????[TextViewRole(PredefinedTextViewRoles.Interactive)]

10?

????????

public

?AdornmentLayerDefinition?editorAdornmentLayer?

=

?

null

;

11?

????????

public

?

void

?TextViewCreated(IWpfTextView?textView)

12?

????????{

13?

????????????

new

?AlwaysVisibleInfoBox(textView);

14?

????????}

15?

?}?

??? 这里,你可以看到我在这个类上使用了很多Attributes,像ContentType,它定义了我们只处理文本格式的编辑器;还有TextViewRole,它定义了将被这个类处理的textview的类型。

??? 在这个类中,我创建了一个AdornmentLayerDefination对象。可能你想知道我们没有使用它,无什么还需要定义它呢,它只是用来配置属性的。Order属性指定,当,InfoBox在层被选之后监听,Name是编辑扩展的名字。

第五步:创建Adornment 类

????Adornment类实际创建了一个WPF用户控件对象,并设置它的视图画布。在内部构造函数中,我处理IWpfTextView.LayoutChanged事件,当代码修改或者布局改变的时候,就触发这个事件。因此,通过这一事件,当我们编辑的文档时,我们可以很容易地得到回调。当浏览器编辑器的大小改变时,我还通过处理WPFTextView.ViewportHeightChanged,WPFTextView.ViewportWidthChanged得到回调,使我们可以重新定位相应的UserControl。

?1?

public

?AlwaysVisibleInfoBox(IWpfTextView?view)

?2?

{

?3?

??????????_view.LayoutChanged?

+=

?

this

.OnLayoutChanged;

?4?

??????????

this

.GetLayer();

?5?

}

?6?

private

?

void

?GetLayer()

?7?

?{

?8?

????????????_adornmentLayer?

=

?

this

._view.GetAdornmentLayer(

"

AlwaysVisibleInfoBox

"

);

?9?

????????????_view.ViewportHeightChanged?

+=

?

delegate

?{?

this

.onSizeChange();?};

10?

????????????_view.ViewportWidthChanged?

+=

?

delegate

?{?

this

.onSizeChange();?};

11?

}

12?

?

private

?

void

?OnLayoutChanged(

object

?sender,?TextViewLayoutChangedEventArgs?e)

13?

{

14?

????????????

this

._info?

=

?

new

?CodeInfoTracker(_view);

15?

????????????

this

.infobox.UpdateInfo(

this

._info);

16?

?}

17?

?

public

?

void

?onSizeChange()

18?

?{

19?

?????

20?

????????????_adornmentLayer.RemoveAllAdornments();

21?

????????????Canvas.SetLeft(infobox,?_view.ViewportRight?

-

?

255

);

22?

????????????Canvas.SetTop(infobox,?_view.ViewportTop?

+

?

10

);

23?

????????????

24?

??????????_adornmentLayer.AddAdornment(AdornmentPositioningBehavior.ViewportRelative,?

25?

??????????

null

,?

null

,?

26?

??????????infobox,?

null

);

27?

}

?? 因此,构造函数只是调用GetLayer来获取的Layer对象,发生在ViewportHeightChanged和ViewportWidthChanged ViewPortSizeChage事件。当一个布局改变时,我就能更新这个用户的控件。

??? 至此,我们成功地建立我们的扩展。你可以使用F5运行它,它会打开一个Visual Studio的Experimental实例。

安装和卸载这个扩展:??? 安装和卸载这个扩展是非常容易的。当您编译项目后,它会产生一个VSIX文件。您可以只需双击这个文件,它会自动安装到Visual Studio。???

??? 要卸载的文件,您打开Visual Studio,转到 Tools - > Extension Manager,然后选择卸载该扩展。

发布您的扩展:

??? 发布你的扩展到Visual Studio库的方式也非常的酷。只要你需要上传VSIX文件到http://www.sychzs.cn/。我已经上载我的这个扩展。

总结:这篇文章,从头到尾一步一步教你实现一个很简单很酷的VS2010的扩展

原文:Code InfoBox Visual Studio Extension (VSX) 2010

参考:

Building and publishing an extension for Visual Studio 2010 [^]

Official Extension Site [^]

代码:Zip

(全文完)

以下为广告部分

您部署的HTTPS网站安全吗?

如果您想看下您的网站HTTPS部署的是否安全,花1分钟时间来 www.sychzs.cn 检测以下吧。让您的HTTPS网站变得更安全!

SSL检测评估

快速了解HTTPS网站安全情况。

安全评级(A+、A、A-...)、行业合规检测、证书信息查看、证书链信息以及补完、服务器套件信息、证书兼容性检测等。

SSL证书工具

安装部署SSL证书变得更方便。

SSL证书内容查看、SSL证书格式转换、CSR在线生成、SSL私钥加解密、CAA检测等。

SSL漏洞检测

让服务器远离SSL证书漏洞侵扰

TLS ROBOT漏洞检测、心血漏洞检测、FREAK Attack漏洞检测、SSL Poodle漏洞检测、CCS注入漏洞检测。

相关文章

热门推荐