【问题标题】:Where should a Visual Studio Add-in store its settings?Visual Studio 加载项应将其设置存储在哪里?
【发布时间】:2011-04-01 21:05:08
【问题描述】:

目前我将自定义插件的设置存储在注册表中,但这似乎是一个杂项。我想知道是否有官方存储插件设置的地方。我的偏好是将它们存储在 Visual Studio 存储设置的位置,以便可以轻松地导出和导入它们。

是否可以使用 Visual Studio 设置存储加载项设置或有更好的方法?

【问题讨论】:

    标签: visual-studio visual-studio-2010 settings add-in


    【解决方案1】:

    编辑

    我对这个主题的原始回答在使用多年后发现了几个问题。为了完整起见,我将其包含在下面,但这是我对此的最新想法。

    在 VSIX 中使用应用程序设置不是版本安全的。存储的设置文件路径的位置部分包括可执行文件的版本字符串和散列。当 Visual Studio 安装官方更新时,这些值会发生变化,因此会更改设置文件路径。 Visual Studio 本身不支持使用应用程序设置,因此它不会尝试将此文件迁移到新位置,并且所有信息都会丢失。 支持的设置方法是 WritableSettingsStore。它与应用程序设置非常相似,并且很容易通过 SVsServiceProvider 访问

    public static WritableSettingsStore GetWritableSettingsStore(this SVsServiceProvider vsServiceProvider)
    {
        var shellSettingsManager = new ShellSettingsManager(vsServiceProvider);
        return shellSettingsManager.GetWritableSettingsStore(SettingsScope.UserSettings);
    }
    

    原答案

    最直接的方法是使用 .Net 的 Application Settings 基础架构来存储任何设置。这是一个成熟的框架,设计人员支持为您的项目添加设置基础设施。

    但是,它不与 Visual Studio 的导入/导出设置基础结构集成。让它工作是一个非常复杂的过程,包括将自己注册为 VSPackage、实现设置架构等......我通常发现运行起来真的不值得麻烦(从未成功)

    【讨论】:

    • 我可能会走得很远,因为这是我第一次尝试这样做,但我似乎能够使用您的新代码的唯一方法是将参数类型从 SVsServiceProvider 更改为 IServiceProvider。
    【解决方案2】:

    这里有一个快速教程,可以让您了解如何简单地实现这一点(一旦您完成了它就非常简单)。

    我从my extensions 中使用的代码派生了以下代码;它在 VB.NET 中,但可以轻松转换为 C#。

    首先,只需将此类添加到您的扩展项目中。它应该包含您需要存储的每个值的属性。您甚至可以按类别排列它们。您可以查看at MSDN here 以了解支持的类型(对于更复杂的情况,您可以参考“自定义选项页面”,这是by MSDN here 涵盖的主题)。

    Imports Microsoft.VisualBasic
    Imports System
    Imports System.Diagnostics
    Imports System.Globalization
    Imports System.Runtime.InteropServices
    Imports System.ComponentModel.Design
    Imports Microsoft.Win32
    Imports Microsoft.VisualStudio
    Imports Microsoft.VisualStudio.Shell.Interop
    Imports Microsoft.VisualStudio.OLE.Interop
    Imports Microsoft.VisualStudio.Shell
    Imports System.Threading
    Imports System.Text.RegularExpressions
    Imports System.ComponentModel
    
    <ClassInterface(ClassInterfaceType.AutoDual)>
    <CLSCompliant(False), ComVisible(True)>
    Public Class OptionPageGrid
        Inherits DialogPage
    
        Private _MyBooleanSetting As Boolean = False
        <Category("The name or an alias of my extension name")>
        <DisplayName("Simple name of this setting displayed for the user")>
        <Description("Longer description of this setting")>
        Public Property MyBooleanSetting() As Boolean
            Get
                Return Me._MyBooleanSetting
            End Get
            Set(ByVal value As Boolean)
                Me._MyBooleanSetting = value
            End Set
        End Property
    
        Private _MyIntegerSetting As Integer = 2
        <Category("The name or an alias of my extension name")>
        <DisplayName("Simple name of this setting displayed for the user")>
        <Description("Longer description of this setting")>
        Public Property MyIntegerSetting() As Integer
            Get
                Return Me._MyIntegerSetting
            End Get
            Set(ByVal value As Integer)
                Me._MyIntegerSetting = value
            End Set
        End Property
    
        Private _MyStringSetting As String = "DefaultStringValue"
        <Category("The name or an alias of my extension name")>
        <DisplayName("Simple name of this setting displayed for the user")>
        <Description("Longer description of this setting")>
        Public Property MyStringSetting() As Integer
            Get
                Return Me._MyStringSetting
            End Get
            Set(ByVal value As Integer)
                Me._MyStringSetting = value
            End Set
        End Property
    End Class
    

    然后,在您的主包类之前添加以下属性。

    <ProvideOptionPage(GetType(OptionPageGrid), "The name or an alias of my extension name", "The name of a category of settings", 0, 0, True)>
    Public NotInheritable Class MyExtensionMainClass
        Inherits Package
    

    现在要轻松访问设置,您可以在主包类中添加以下属性:

    Protected ReadOnly Property Settings() As OptionPageGrid
        Get
            Return CType(GetDialogPage(GetType(OptionPageGrid)), OptionPageGrid)
        End Get
    End Property
    

    这使得使用友好的从类中的任何位置访问值成为可能:

    If (Me.Settings.MyBooleanSetting) Then MsgBox("It works!");
    

    Visual Studio 将负责保存设置,当您使用导入/导出功能(或任何设置同步扩展,如 this one)时,它们应该包含在内。

    【讨论】:

    • 感谢 MSDN 链接。我在 C# 中执行此操作,他们的示例以及您的示例使启动和运行变得非常容易。我会为其他人说明,尽管您展示了如何创建网格选项页面,因为我想创建一个自定义页面,因为我希望用户单击按钮。
    • 我已经在博客中介绍了如何在 C# 中使用用于 UI 的 WPF UserControl 创建自定义选项页面,因为 MSDN 链接仅显示如何使用 Windows 窗体进行操作。 blog.danskingdom.com/…
    猜你喜欢
    • 2014-09-21
    • 1970-01-01
    • 2022-07-08
    • 1970-01-01
    • 2019-01-31
    • 1970-01-01
    • 1970-01-01
    • 2010-09-13
    • 2018-05-10
    相关资源
    最近更新 更多