如何使用 Package 对象的参数调用 ToolWindowPane 构造函数?
How to call ToolWindowPane constructor with parameters from Package object?
我正在使用需要显示的工具 window 创建 Visual Studio 包扩展。
我有一个 class 代表我的工具 window 扩展 ToolWindowPane
:
[Guid(GuidList.guidToolWindowPersistanceString)]
public class MyToolWindow : ToolWindowPane
{
public MyToolWindow() :
base(null)
{
// Set the window title
this.Caption = "ToolWindowName";
// Set content of ToolWindow
base.Content = new MyControl();
}
}
其中 MyControl
是要托管在工具 window 内的 WPF 对象。当调用方法 Package.CreateToolWindow
:
时,从 Package
class 调用此无参数构造函数
[ProvideToolWindow(typeof(MyToolWindow))]
public sealed class MyPackage : Package
{
//... Package initialization code...
private void ShowMainToolWindow()
{
var window = (ToolWindowPane)CreateToolWindow(typeof(MyToolWindow), 0); //how to pass parameters in tool window constructor??
if ((null == window) || (null == window.Frame))
throw new NotSupportedException(Resources.CanNotCreateWindow);
IVsWindowFrame windowFrame = (IVsWindowFrame)window.Frame;
Microsoft.VisualStudio.ErrorHandler.ThrowOnFailure(windowFrame.Show());
}
那么问题来了,有没有办法从Package
对象调用ToolWindowPane
的非无参数构造函数?
我不这么认为。
此处没有任何内容表明它是:
https://docs.microsoft.com/en-us/visualstudio/extensibility/registering-a-tool-window
https://www.mztools.com/articles/2015/MZ2015004.aspx
So the question is, is there any way to call a non - parameterless constructor of a ToolWindowPane from the Package object?
如果要将参数传递给 WPF 控件,可以在 WPF 控件中创建一个参数构造函数。像这样:
public partial class MyControl: UserControl
{
/// <summary>
/// Initializes a new instance of the <see cref="MyControl"/> class.
/// </summary>
public MyControl()
{
this.InitializeComponent();
}
public MyControl(List<User> users)
{
this.InitializeComponent();
dgUsers.ItemsSource = users;
}
然后你可以像这样通过构造函数传递参数:
public MyToolWindow() : base(null)
{
this.Caption = "TestToolWindow";
List<User> users = new List<User>();
users.Add(new User() { Id = 1, Name = "Test Xu", Birthday = new DateTime(1971, 7, 23) });
users.Add(new User() { Id = 2, Name = "Jane Doe", Birthday = new DateTime(1974, 1, 17) });
users.Add(new User() { Id = 3, Name = "Jack Doe", Birthday = new DateTime(1991, 9, 2) });
this.Content = new MyControl(users);
}
因此似乎无法从 Package
对象调用非无参数构造函数。我采用的解决方法是在 MyToolWindow
对象中创建 public 属性或方法,并从 Package
对象调用它们,如下所示:
var window = (ToolWindowPane)CreateToolWindow(typeof(MyToolWindow),0);
if ((null == window) || (null == window.Frame))
throw new NotSupportedException(Resources.CanNotCreateWindow);
((MyToolWindow)window).Property1 = ...
((MyToolWindow)window).Property2 = ...
((MyToolWindow)window).ExecuteMethod();
对于正在寻找如何做到这一点的任何人,现在有 很多 更好的方法,您可以在这个 AsyncToolWindow sample.
中看到
通过重写 AsyncPackage
class 中的 3 个方法,您可以定义一些 状态 ,当 window它已初始化:
public override IVsAsyncToolWindowFactory GetAsyncToolWindowFactory(Guid toolWindowType)
{
return toolWindowType.Equals(Guid.Parse(SampleToolWindow.WindowGuidString)) ? this : null;
}
protected override string GetToolWindowTitle(Type toolWindowType, int id)
{
return toolWindowType == typeof(SampleToolWindow) ? SampleToolWindow.Title : base.GetToolWindowTitle(toolWindowType, id);
}
protected override async Task<object> InitializeToolWindowAsync(Type toolWindowType, int id, CancellationToken cancellationToken)
{
// Perform as much work as possible in this method which is being run on a background thread.
// The object returned from this method is passed into the constructor of the SampleToolWindow
var dte = await GetServiceAsync(typeof(EnvDTE.DTE)) as EnvDTE80.DTE2;
return new SampleToolWindowState
{
DTE = dte
};
}
通过向您的 ToolWindowPanel
class 添加参数化构造函数,然后您可以接收传递的状态:
// "state" parameter is the object returned from MyPackage.InitializeToolWindowAsync
public SampleToolWindow(SampleToolWindowState state) : base()
{
Caption = Title;
BitmapImageMoniker = KnownMonikers.ImageIcon;
Content = new SampleToolWindowControl(state);
}
我正在使用需要显示的工具 window 创建 Visual Studio 包扩展。
我有一个 class 代表我的工具 window 扩展 ToolWindowPane
:
[Guid(GuidList.guidToolWindowPersistanceString)]
public class MyToolWindow : ToolWindowPane
{
public MyToolWindow() :
base(null)
{
// Set the window title
this.Caption = "ToolWindowName";
// Set content of ToolWindow
base.Content = new MyControl();
}
}
其中 MyControl
是要托管在工具 window 内的 WPF 对象。当调用方法 Package.CreateToolWindow
:
Package
class 调用此无参数构造函数
[ProvideToolWindow(typeof(MyToolWindow))]
public sealed class MyPackage : Package
{
//... Package initialization code...
private void ShowMainToolWindow()
{
var window = (ToolWindowPane)CreateToolWindow(typeof(MyToolWindow), 0); //how to pass parameters in tool window constructor??
if ((null == window) || (null == window.Frame))
throw new NotSupportedException(Resources.CanNotCreateWindow);
IVsWindowFrame windowFrame = (IVsWindowFrame)window.Frame;
Microsoft.VisualStudio.ErrorHandler.ThrowOnFailure(windowFrame.Show());
}
那么问题来了,有没有办法从Package
对象调用ToolWindowPane
的非无参数构造函数?
我不这么认为。
此处没有任何内容表明它是:
https://docs.microsoft.com/en-us/visualstudio/extensibility/registering-a-tool-window https://www.mztools.com/articles/2015/MZ2015004.aspx
So the question is, is there any way to call a non - parameterless constructor of a ToolWindowPane from the Package object?
如果要将参数传递给 WPF 控件,可以在 WPF 控件中创建一个参数构造函数。像这样:
public partial class MyControl: UserControl
{
/// <summary>
/// Initializes a new instance of the <see cref="MyControl"/> class.
/// </summary>
public MyControl()
{
this.InitializeComponent();
}
public MyControl(List<User> users)
{
this.InitializeComponent();
dgUsers.ItemsSource = users;
}
然后你可以像这样通过构造函数传递参数:
public MyToolWindow() : base(null)
{
this.Caption = "TestToolWindow";
List<User> users = new List<User>();
users.Add(new User() { Id = 1, Name = "Test Xu", Birthday = new DateTime(1971, 7, 23) });
users.Add(new User() { Id = 2, Name = "Jane Doe", Birthday = new DateTime(1974, 1, 17) });
users.Add(new User() { Id = 3, Name = "Jack Doe", Birthday = new DateTime(1991, 9, 2) });
this.Content = new MyControl(users);
}
因此似乎无法从 Package
对象调用非无参数构造函数。我采用的解决方法是在 MyToolWindow
对象中创建 public 属性或方法,并从 Package
对象调用它们,如下所示:
var window = (ToolWindowPane)CreateToolWindow(typeof(MyToolWindow),0);
if ((null == window) || (null == window.Frame))
throw new NotSupportedException(Resources.CanNotCreateWindow);
((MyToolWindow)window).Property1 = ...
((MyToolWindow)window).Property2 = ...
((MyToolWindow)window).ExecuteMethod();
对于正在寻找如何做到这一点的任何人,现在有 很多 更好的方法,您可以在这个 AsyncToolWindow sample.
中看到通过重写 AsyncPackage
class 中的 3 个方法,您可以定义一些 状态 ,当 window它已初始化:
public override IVsAsyncToolWindowFactory GetAsyncToolWindowFactory(Guid toolWindowType)
{
return toolWindowType.Equals(Guid.Parse(SampleToolWindow.WindowGuidString)) ? this : null;
}
protected override string GetToolWindowTitle(Type toolWindowType, int id)
{
return toolWindowType == typeof(SampleToolWindow) ? SampleToolWindow.Title : base.GetToolWindowTitle(toolWindowType, id);
}
protected override async Task<object> InitializeToolWindowAsync(Type toolWindowType, int id, CancellationToken cancellationToken)
{
// Perform as much work as possible in this method which is being run on a background thread.
// The object returned from this method is passed into the constructor of the SampleToolWindow
var dte = await GetServiceAsync(typeof(EnvDTE.DTE)) as EnvDTE80.DTE2;
return new SampleToolWindowState
{
DTE = dte
};
}
通过向您的 ToolWindowPanel
class 添加参数化构造函数,然后您可以接收传递的状态:
// "state" parameter is the object returned from MyPackage.InitializeToolWindowAsync
public SampleToolWindow(SampleToolWindowState state) : base()
{
Caption = Title;
BitmapImageMoniker = KnownMonikers.ImageIcon;
Content = new SampleToolWindowControl(state);
}