绑定到ViewModel中的依赖项属性

时间:2017-09-07 22:59:14

标签: wpf mvvm dependency-properties

我在SliderViewModel中有依赖项属性,此视图模型实现了DependencyObject,并被设置为BRSliderUserControl的数据上下文。如何从AmplitudeOptionsUserControl绑定到视图模型中的依赖项属性。是否可以这样做。我的猜测是我需要在BRSliderUserControl中创建另一个依赖项属性,然后将更新值发送到视图模型。这是正确的方法吗?

SliderViewModel.cs

public Class SliderViewModel:DependencyObject
{
    public AnalysisViewType AnalysisTypeValue
            {
                get { return (AnalysisViewType)GetValue(AnalysisTypeDependencyProperty); }
                set { SetValue(AnalysisTypeDependencyProperty, value); }
            }


            public static readonly DependencyProperty AnalysisTypeDependencyProperty =
                DependencyProperty.Register("AnalysisTypeValue", typeof(AnalysisViewType), typeof(SliderViewModel),
                    new PropertyMetadata(AnalysisViewType.Unassigned, OnAnalysisTypeChanged));

            private static void OnAnalysisTypeChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
            {
                //Do something here
            }
}

BRSliderUserControl.xaml.cs

  public BRSliderUserControl()
            {
                InitializeComponent();
                SliderViewModel sliderViewModel = new SliderViewModel();
                this.DataContext = sliderViewModel;
            }

现在我如何从另一个用户控件绑定到该依赖项属性?

AmplitudeOptionsControl.xaml

//This does not work..

    <lib:BRSliderUserControl
                    Grid.Row="5"
                    Grid.Column="0"
                    Grid.ColumnSpan="3"
                    AnalysisTypeValue="{Binding AmplitudeOptionsVM.AnalysisType,RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type UserControl}}}"
                 />

2 个答案:

答案 0 :(得分:1)

您在View Models中不需要依赖项属性。您的ViewModel应该实现INotifyPropertyChanged接口,并且您的属性应该在值更改时引发NotifyPropertyChanged事件。周围有许多助手使这更容易。

如果需要,可以使用Dependency属性,但它会使您的视图模型依赖于WPF,尽管绑定到Dependency属性似乎要快得多(参见此处:https://docs.microsoft.com/en-us/dotnet/framework/wpf/advanced/optimizing-performance-data-binding

您可以在此处查看讨论:INotifyPropertyChanged vs. DependencyProperty in ViewModel

此外,由于您的DataContext属于SliderViewModel类型,它具有名为AnalysisTypeValue的公共属性,因此您应该在XAML中绑定

... AnalysisTypeValue = {Binding AnalysisTypeValue}

答案 1 :(得分:0)

将依赖项属性移动到UserControl类的代码隐藏:

public class BRSliderUserControl
{
    public AnalysisViewType AnalysisTypeValue
    {
        get { return (AnalysisViewType)GetValue(AnalysisTypeDependencyProperty); }
        set { SetValue(AnalysisTypeDependencyProperty, value); }
    }

    public static readonly DependencyProperty AnalysisTypeDependencyProperty =
        DependencyProperty.Register("AnalysisTypeValue", typeof(AnalysisViewType), typeof(BRSliderUserControl),
            new PropertyMetadata(AnalysisViewType.Unassigned, OnAnalysisTypeChanged));

    private static void OnAnalysisTypeChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        //Do something here
    }

    public BRSliderUserControl()
    {
        InitializeComponent();
        SliderViewModel sliderViewModel = new SliderViewModel();
        this.DataContext = sliderViewModel;
    }
}

将纯CLR属性添加到视图模型中:

public class SliderViewModel : INotifyPropertyChanged
{
    private AnalysisViewType _analysisTypeValue;
    public AnalysisViewType AnalysisTypeValue
    {
        get { return _analysisTypeValue; }
        set { _analysisTypeValue = value; NotifyPropertyChanged(); }
    }

    public event PropertyChangedEventHandler PropertyChanged;
    private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
    {
        if (PropertyChanged != null)
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
}

将视图中的依赖项属性绑定到视图模型的source属性:

<lib:BRSliderUserControl
                Grid.Row="5"
                Grid.Column="0"
                Grid.ColumnSpan="3"
                AnalysisTypeValue="{Binding AnalysisTypeValue}" />