我正在尝试学习MVVM模式(C#),它来自Windows窗体背景。我正在使用MVVM Light工具包,到目前为止我认为它很棒。 我已经制作了几个小应用程序,但是我正在努力的一件事是引入第二个视图。
我想(例如),在我的MainViewModel上有一个按钮,它通过RelayCommand打开一个新窗口 - 让我们说一个“关于”窗口。我已经在网上做了几个小时的研究,但似乎我无法让我的AboutViewModel与/显示我的AboutView进行交流。
我在AboutView.xaml的代码隐藏构造函数中放置了一个接收信使 - 但是我无法接收来自AboutViewModel的任何消息,因此无法使它成为'Show()'。< / p>
如果有人拥有使用多个视图的Mvvm Light WPF应用程序的示例,那将非常棒:)
答案 0 :(得分:3)
我可以通过两种方式轻松地做到这一点
第一种方法是使用Popup
而不是新的Window
。例如,我经常在ViewModel
PopupContent
和IsPopupVisible
的{{1}}中添加属性,并在我想要显示Popup
控件的任何时候设置这些值。例如,ShowAboutPopup
relay命令可能会运行如下:
void ShowAboutPopup()
{
PopupContent = new AboutViewModel();
IsPopupVisible = true;
}
您可以使用Popup
对象或自定义UserControl
来显示它。我更喜欢使用我自己的custom Popup UserControl,这通常看起来像这样:
<Window>
<Canvas x:Name="RootPanel">
<SomePanel>
<!-- Regular content goes here -->
</SomePanel>
<local:PopupPanel Content="{Binding PopupContent}"
local:PopupPanel.IsPopupVisible="{Binding IsPopupVisible}"
local:PopupPanel.PopupParent="{Binding ElementName=RootPanel}" />
</Canvas>
</Window>
PopupContent
属性为ViewModel
(例如AboutViewModel
),DataTemplates
用于告诉WPF绘制具体ViewModels
{ {1}}
Views
另一种方法是在启动时运行某种<Window.Resources>
<DataTemplate DataType="{x:Type local:AboutViewModel}">
<local:AboutView />
</DataTemplate>
</Window.Resources>
,并负责整个应用程序状态,包括哪些窗口是打开的。
通常情况下,我更喜欢使用包含ApplicationViewModel
的{{1}}来显示当前页面
ApplicationView
但它也可用于管理多个窗口。如果您确实使用它来管理多个ContentControl
对象,请注意这不是纯<Window>
<ContentControl Content="{Binding CurrentViewModel}" />
</Window>
因为它需要访问某些特定于View的对象,并且引用UI对象它不是Window
{1}}应该这样做。例如,它可以订阅接收ViewModel
消息,并且在接收到这些消息后,它将创建指定的视图并显示它,并且可能也隐藏当前窗口。
就个人而言,我尽量避免使用多个窗口。我通常的方法是让一个View包含任何页面的一致应用程序对象,以及包含更改的动态内容的ViewModel
。如果你有兴趣,我有一个example using this navigation style on my blog
答案 1 :(得分:0)