Wpf 如何使用其他视图模型的属性初始化视图模型

Wpf 如何使用其他视图模型的属性初始化视图模型,wpf,mvvm,data-binding,Wpf,Mvvm,Data Binding,我的问题是,用WPF、MVVM方式初始化子窗口的理想方式是什么 我有一个WPF窗口,我们称之为ParentWindow,它的视图模型类为ParentWindowViewModel。点击ParentWindowUI上的一个按钮,我启动了一个新的WPF窗口——如下所示的ChildWindow ChildWindow r = new ChildWindow (); r.ShowDialog(); r.WindowStartupLocation = WindowStartup

我的问题是,用WPF、MVVM方式初始化子窗口的理想方式是什么

我有一个WPF窗口,我们称之为ParentWindow,它的视图模型类为ParentWindowViewModel。点击ParentWindowUI上的一个按钮,我启动了一个新的WPF窗口——如下所示的ChildWindow

ChildWindow  r = new ChildWindow ();
 r.ShowDialog();           
 r.WindowStartupLocation = WindowStartupLocation.CenterScreen;
现在,ChildWindow有了自己的viewModel,如-ChildWindowViewModel。子窗口的xaml中将datacontext设置为

<Window.DataContext>
        <viewModel:ChildWindowViewModel/>
    </Window.DataContext>


在父窗口中单击按钮时,当我启动子窗口时,我需要将某些值传递给子窗口,该值将用于初始化子窗口。如果没有这些值,则无法初始化子窗口。每次单击按钮启动子窗口时,传递给子窗口的值将根据父窗口中的其他选定项而有所不同。

我将执行类似操作(无错误检查):

在ParentWindow.xaml.cs中

private void Some_Event_In_Parent_Window()
{
   ParentWindowViewModel pvm = DataContext as ParentWindowViewModel;
   ChildWindow cw = new ChildWindow(pvm.Element1, pvm.Element2);
}
public ChildWindow(bool elem1, string elem2)
{
   InitializeComponents();
   DataContext = new ChildWindowViewModel(elem1, elem2);
} 
int ChildWindow.xaml.cs

private void Some_Event_In_Parent_Window()
{
   ParentWindowViewModel pvm = DataContext as ParentWindowViewModel;
   ChildWindow cw = new ChildWindow(pvm.Element1, pvm.Element2);
}
public ChildWindow(bool elem1, string elem2)
{
   InitializeComponents();
   DataContext = new ChildWindowViewModel(elem1, elem2);
} 
如果您处理的是需要在windows/VM之间传输的最小元素,并且主要是发送某种形式的“状态”或“值”,那么在代码中初始化Viewmodel不会有太多问题。请记住,
相当于代码隐藏中的
DataContext=new ChildWindowViewModel()
。是的,您可以创建意大利面代码,或者通过不遵循模式来混淆依赖关系;你也可以过度设计一些不需要努力的东西,也可以让人困惑

我发现有人痴迷于保持代码为空(我也有同样的痴迷)。请记住,代码隐藏是有原因的,您可以使用它。有时,如果您有一个一次性的需求,可以通过添加注释在代码隐藏中处理,那么通过实现一些大的模式来使代码库复杂化是不值得的

除了事件处理程序之外,我还将代码隐藏用于以下主要用例:

  • 需要对UI进行调整,这太复杂了,无法单独在XAML中处理。示例:我需要一个奇怪的字符串连接和一些输入文本字段的逻辑
  • 视图之间需要传输一些最小的状态或数据。(如您的要求)
  • 需要实现某种特定于UI的逻辑,而与底层数据或ViewModel无关。(这种情况很少见,而且几乎总是很小) 就MVVM的“这是否理想”而言;这取决于你对理想的定义

    • 这可以由其他设计模式处理吗?可能但这值得吗
    • 实现上述模式是否会增加只解决一个小问题的膨胀或开销?大概那由你决定
    • 您是否要多次重复此实现?如果是这样的话,你可能需要重新考虑一些糟糕的设计
    • 实现这种使用代码隐藏的解决方案是否能快速解决您的问题,即适度的可维护性和可读性?如果是这样的话,我就看不出有什么问题了
    理想并不总是由规则来定义的。它还针对您的需求和要求

    确定您的用例应该处理在哪里并不总是容易的。视图、视图模型,可能是一个服务或一个单例状态类。
    如果您的用例是这一个窗口,那么代码隐藏就可以了(在我看来)。如果您在20个windows上执行此操作,您可能希望某个服务以某种方式维护该状态。仔细想想-如果您的代码是

    ,我会这样做(不检查错误):

    在ParentWindow.xaml.cs中

    private void Some_Event_In_Parent_Window()
    {
       ParentWindowViewModel pvm = DataContext as ParentWindowViewModel;
       ChildWindow cw = new ChildWindow(pvm.Element1, pvm.Element2);
    }
    
    public ChildWindow(bool elem1, string elem2)
    {
       InitializeComponents();
       DataContext = new ChildWindowViewModel(elem1, elem2);
    } 
    
    int ChildWindow.xaml.cs

    private void Some_Event_In_Parent_Window()
    {
       ParentWindowViewModel pvm = DataContext as ParentWindowViewModel;
       ChildWindow cw = new ChildWindow(pvm.Element1, pvm.Element2);
    }
    
    public ChildWindow(bool elem1, string elem2)
    {
       InitializeComponents();
       DataContext = new ChildWindowViewModel(elem1, elem2);
    } 
    
    如果您处理的是需要在windows/VM之间传输的最小元素,并且主要是发送某种形式的“状态”或“值”,那么在代码中初始化Viewmodel不会有太多问题。请记住,
    相当于代码隐藏中的
    DataContext=new ChildWindowViewModel()
    。是的,您可以创建意大利面代码,或者通过不遵循模式来混淆依赖关系;你也可以过度设计一些不需要努力的东西,也可以让人困惑

    我发现有人痴迷于保持代码为空(我也有同样的痴迷)。请记住,代码隐藏是有原因的,您可以使用它。有时,如果您有一个一次性的需求,可以通过添加注释在代码隐藏中处理,那么通过实现一些大的模式来使代码库复杂化是不值得的

    除了事件处理程序之外,我还将代码隐藏用于以下主要用例:

  • 需要对UI进行调整,这太复杂了,无法单独在XAML中处理。示例:我需要一个奇怪的字符串连接和一些输入文本字段的逻辑
  • 视图之间需要传输一些最小的状态或数据。(如您的要求)
  • 需要实现某种特定于UI的逻辑,而与底层数据或ViewModel无关。(这种情况很少见,而且几乎总是很小) 就MVVM的“这是否理想”而言;这取决于你对理想的定义

    • 这可以由其他设计模式处理吗?可能但这值得吗
    • 实现上述模式是否会增加只解决一个小问题的膨胀或开销?大概那由你决定
    • 您是否要多次重复此实现?如果是这样的话,你可能需要重新考虑一些糟糕的设计
    • 实现这种使用代码隐藏的解决方案是否能快速解决您的问题,即适度的可维护性和可读性?如果是这样的话,我就看不出有什么问题了
    理想并不总是由规则来定义的。这也是特定于您的需求和r