首先,我是WPF和MVVM的新手,正在努力编写结构良好/分离的代码,请保持友善。
我创建了一个用户控件及其独立的视图模型。在视图模型中,我有一个ICommand,它中继到同一视图模型中的方法。我在类似这样的事件上使用System.Windows.Interactivity绑定到XAML中的此命令:-
<UserControl x:Class="MyNamespace.MyControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity"
xmlns:local="clr-namespace:MyNamespace"
mc:Ignorable="d"
Height="300"
d:DesignHeight="300" d:DesignWidth="1500"
IsManipulationEnabled="True"
Background="{StaticResource BackgroundWhiteBrush}">
<Grid
d:DataContext="{x:Static local:MyControlDesignModel.Instance}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="PreviewMouseUp">
<i:InvokeCommandAction Command="{Binding MyViewModelCommand}"/>
</i:EventTrigger>
</i:Interaction.Triggers>
</Grid>
我后面的代码(试图将其保留为空)如下所示:
namespace MyNamespace
{
/// <summary>
/// Interaction logic for MyControl.xaml
/// </summary>
public partial class MyControl : UserControl
{
public MyControl()
{
DataContext = ViewModelMyControl;
InitializeComponent();
}
}
}
我希望能够在多个页面中使用此控件。我还希望能够从其他视图模型中调用此视图模型中的方法(传递参数),以允许其从数据存储中进行更新。
我使用了一个DI容器来提供对视图模型的引用,以便我可以a)从另一个地方引用其数据加载方法,并b)在其后的代码中(上方)将其设置为DataContext。
DI容器的实现如下:
/// <summary>
/// A shortcut to access the <see cref="MyControlViewModel"/>
/// </summary>
public static MyControlViewModel ViewModelMyControl => Framework.Service<MyControlViewModel>();
在DataContext上使用此DI引用的视图模型时,事件/命令不会触发。
如果我将后面的代码更改为以下内容,则事件/命令会触发,但随后我丢失了静态引用,而该静态引用是我试图“保存”页面之间的数据的。我似乎能够具有事件或静态引用,但不能同时具有两者。
namespace MyNamespace
{
/// <summary>
/// Interaction logic for MyControl.xaml
/// </summary>
public partial class MyControl : UserControl
{
public MyControl()
{
DataContext = new MyControlViewModel();
InitializeComponent();
}
}
}
我认为这与ViewModel的生命周期或一般而言的绑定有关。我一直在遵循很多指南,但现在发现自己陷入困境。
如何触发事件/命令,并在使用它的页面之间维护对用户控件数据的引用?