WPF MvvM在单个View中的视图模型之间进行通信

时间:2014-08-18 17:26:54

标签: c# wpf mvvm mvvm-light mui

这个标题可能不适合问题本身,但留在我身边如果你有更好的建议,我会改变它。这是我的第一个wpf应用程序,所以我可能错过了一些关键概念......我做了谷歌,但我找不到正确的方法。

我正在使用MvvM Light和MUI构建wpf应用程序,我遇到了项目绑定的问题,即视图模型之间的通信。现在,我确信如果我在页面中使用单个View模型及其中的所有用户控件,我就不会遇到这个问题,但我想我在第一次尝试时就过度了。

我在应用程序和页面中有一个主窗口作为用户控件。在每个页面中,我有几个其他用户控件,每个用户控件都有自己的视图模型和自己的逻辑,但最终它们都依赖于具有数据网格的相应VM。我们可以将它们视为穷人角度指令。每个用户控件的数据上下文定义如下:

DataContext="{Binding ViewModelName, Source={StaticResource Locator}}

布局如下所示:Wpf Layout 这样看,VM1中的DG1是Master(客户),UC3和UC4是Details(订单)。如果我向客户添加新订单,我希望在DG1中更新它而不刷新整个网格。

在VM1数据网格1中选择已更改我正在触发命令来设置依赖用户控件的属性值。

<i:Interaction.Triggers>
            <i:EventTrigger EventName="SelectionChanged">
                <mvvm:EventToCommand Command="{Binding ErrorWorkflow.GetErrorWorkflowCommand, Mode=OneWay, Source={StaticResource Locator}}" CommandParameter="{Binding SelectedError.WF_REF}" />
                <mvvm:EventToCommand Command="{Binding ErrorDetails.GetErrorCaseDetailsCommand, Mode=OneWay, Source={StaticResource Locator}}" CommandParameter="{Binding SelectedError}" />
             </i:EventTrigger>
        </i:Interaction.Triggers>

该部分工作正常,但是当我更改VM3和VM1的依赖VM3的值时,即使我调用RaisePropertyChanged或手动显式设置属性,如SelectedError.Status =“somethingnew”,VM1属性值也不会更改

另一方面,如果我从数据网格中清除选择,则依赖视图模型保持绑定(它们上的文本框保留值,因为它们在自己的VM3上引用属性)。

所有View Models都来自mvvmLight的ViewModelBase和来自ObservableObjects的所有模型(我知道我应该使用Poco,但显然我也必须在VM上创建每个属性)。例如:

        public const string SelectedErrorPropertyName = "SelectedError";

    private ErrorLog _selectedError;

    public ErrorLog SelectedError
    {
        get
        {
            return _selectedError;
        }
        set
        {
            Set(() => SelectedError, ref _selectedError, value);

        }
    }

考虑到应用程序的大小,我觉得Messenger会有点过分(只有少数这样的页面)。

我应该更改页面以仅使用一个视图模型并为每个用户控件共享它们,还是我错过了一些明显的东西? 如果你认为我在这个例子中遗漏了一些关键信息,请告诉我,我会更新。

提前感谢您的任何建议,欢呼!

1 个答案:

答案 0 :(得分:1)

永远不应该将页面更改为仅一个视图模型,并且Messenger不是一种矫枉过正。 MVVM Light Messenger 旨在解决您目前遇到的问题(虚拟机之间的通信)。你应该使用它。

有关MVVM Light中消息传递的更多信息,Microsoft的Jesse Liberty有a great tutorial如何使用它。