我正在尝试实现一个简单的WPF应用程序,在主窗口中有两个嵌套的UserControl,每个UserControl都有自己的视图模型。一个视图模型实现一个命令,允许用户选择目录。当在第一个视图模型中选择了一个文件夹时,它应该向所有其他注册的视图模型发送一条消息。所以我们有三个视图,三个视图模型(包括MainViewModel)和依赖容器。虽然我实现了IRECievier,但ReceiverVM不更新它的属性。
以下是我的视图模型,为了方便起见,我将它们放在同一个文件中:
namespace MessagingReproduction;
public partial class MainViewModel : ObservableRecipient
{
}
public partial class SenderViewModel : ObservableRecipient
{
private string selectedDirectory;
public string SelectedDirectory
{
get => selectedDirectory;
set
{
var oldValue = selectedDirectory;
SetProperty(ref selectedDirectory, value);
Messenger.Send<PropertyChangedMessage<string>>(new PropertyChangedMessage<string>(this, nameof(SelectedDirectory), oldValue, selectedDirectory));
}
}
// simulate a FolderDialog
[RelayCommand]
private void SelectDirectory()
=> this.SelectedDirectory = "C:";
}
public partial class ReceiverViewModel : ObservableRecipient, IRecipient<PropertyChangedMessage<string>>
{
[ObservableProperty]
private string selectedDirectory;
public void Receive(PropertyChangedMessage<string> message)
{
selectedDirectory = message.NewValue;
}
}
我的接收器视图.xaml:
<Grid>
<TextBlock Text="{Binding SelectedDirectory, UpdateSourceTrigger=PropertyChanged}"
Width="120" Height="22"/>
</Grid>
我的发件人视图.xaml:
<StackPanel>
<Button Command="{Binding SelectDirectoryCommand}"
Width="120" Height="22"/>
<TextBlock Text="{Binding SelectedDirectory, UpdateSourceTrigger=PropertyChanged}"
Width="120" Height="22"/>
</StackPanel>
主窗口:
<StackPanel>
<local:SenderView DockPanel.Dock="Top"/>
<local:ReceiverView DockPanel.Dock="Bottom"/>
</StackPanel>
依赖项注入的设置见App.xaml.cs:
public partial class App : Application
{
public App()
{
Services = ConfigureServices();
InitializeComponent();
}
public new static App Current => (App)Application.Current;
public IServiceProvider Services { get; }
private static IServiceProvider ConfigureServices()
{
var services = new ServiceCollection();
services.AddTransient<MainViewModel>();
services.AddTransient<SenderViewModel>();
services.AddTransient<ReceiverViewModel>();
return services.BuildServiceProvider();
}
}
在每个视图中设置数据上下文,如下所示:
public ReceiverView()
{
InitializeComponent();
DataContext = App.Current.Services.GetService<ReceiverViewModel>();
}
尽管实现了IRrecipient,但是视图模型并不通信。注意,除了主窗口之外,我的视图都是用户控件。
1条答案
按热度按时间nhhxz33t1#
我只是学习使用MVVM工具包自己,但它似乎你没有实现任何消息,也没有注册您的接收器视图模型作为一个收件人的消息。
首先,创建消息:
然后,在接收类中注册消息:
最后,当所选目录发生更改时,从任何地方发送消息:
文档中有一个很好的示例说明如何使用此信使:
https://learn.microsoft.com/en-us/windows/communitytoolkit/mvvm/messenger