属性更改不会传播到绑定目​​标(UWP)

时间:2018-09-13 08:20:15

标签: xaml binding uwp inotifypropertychanged

我有一个ViewModel和一个类。他们看起来像这样:

//viewmodel
public class MyViewModel : ViewModelBase {

    private MyClass myClass;
    public MyClass MyClass{
        get{
            return myClass;
        }
        set{
            this.myClass = value;
            base.OnPropertyChanged();
        }
    }

    private string testString;
    public string TestString{
                get{
            return testString;
        }
        set{
            this.testString = value;
            base.OnPropertyChanged();
        }
    }

    public MyViewModel(){
        this.MyClass = new MyClass();
        this.TestString = "blah, blah, blah"
    }}



//class
    public class MyClass : ViewModelBase{
    private string  myString;
    public string MyString{
        get {
        return myString
        }
        set{
            this.myString = value;
            base.OnPropertyChanged();
        }
    }

    public MyClass (){
        this.MyString = "25";   }}

基类-ViewModelBase实现INotifyChange并包含OnPropertyChanged处理程序逻辑。 我有一个UserControl,它希望像这样绑定MyClass的值:

  <TextBlock Text="{x:Bind  Path=MyViewModel.MyClass.MyString, Mode=TwoWay}"></TextBlock>

但是,这不起作用。值已正确绑定到初始化中,但MyViewModel.MyClass.MyString中的任何更改均未反映在texblock中,文本保持不变。引发OnPropertyChange,使用更改的MyString值命中ViewModelBase中的断点,但是它不以某种方式传播到texblock。 绑定MyClass上的简单值就像魅力一样,当属性更改时,此文本块也会更新:

  <TextBlock Text="{x:Bind  Path=MyViewModel.TestString, Mode=TwoWay}"></TextBlock>

我想念什么?为什么绑定到“ MyViewModel.MyClass.MyString”的文本块没有更新?

1 个答案:

答案 0 :(得分:0)

我已经测试了您提供的代码,但认为它没有任何问题。但是,问题可能出在您的Page的代码后面。碰巧,您不是使用它作为属性声明吗?

public MyViewModel MyViewModel => new MyViewModel();

因为在这种情况下,对MyViewModel属性的每次访问都将被视为MyViewModel类的新实例。在此配置中,您将适当地更改属性,但是UI不会注意到,因为您将在新实例上更新属性。如果您改为使用

public MyViewModel MyViewModel { get; } = new MyViewModel();

在创建页面时,您将获得仅创建一个实例的正确行为。

我有以下代码:

public sealed partial class MainPage : Page
{
    public MainPage()
    {
        this.InitializeComponent();            
    }

    public MyViewModel MyViewModel { get; } = new MyViewModel();

    private void Button_Click(object sender, RoutedEventArgs e)
    {
        MyViewModel.MyClass.MyString = "test";
    }
}

还有我简单的ViewModelBase

public class ViewModelBase : INotifyPropertyChanged
{
    public event PropertyChangedEventHandler PropertyChanged;

    protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}