绑定在没有 INotifyPropertyChanged 的情况下工作,为什么?
Binding works without INotifyPropertyChanged, why?
这是我们通常的做法:
public class ViewModel : INotifyPropertyChanged
{
string _test;
public string Test
{
get { return _test; }
set
{
_test = value;
OnPropertyChanged();
}
}
public event PropertyChangedEventHandler PropertyChanged;
public void OnPropertyChanged([CallerMemberName] string property = "") =>
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(property));
}
现在我们的 属性 可以被视图中的多个元素使用,例如:
<TextBox Text="{Binding Test, UpdateSourceTrigger=PropertyChanged}" />
<TextBlock Text="{Binding Test}" />
更改 TextBox
中的值将更新 TextBlock
的内容。我们还可以在视图模型中设置值,视图会自动更新它。
如果我们这样写视图模型
public class ViewModel
{
public string Test { get; set; }
}
然后 视图仍然有效(例如,更改 TextBox
中的值将更新 TextBlock
)。当然,不可能再从视图模型中轻松更新 Test
值(不再有事件上升)。但我的问题是关于视图:为什么视图能够工作?它是在后台构造更多东西还是检查某些东西的逻辑?
[...] you are encountering a
another hidden aspect of WPF, that's it WPF's data binding engine will
data bind to PropertyDescriptor instance which wraps the source
property if the source object is a plain CLR object and doesn't
implement INotifyPropertyChanged interface. And the data binding
engine will try to subscribe to the property changed event through
PropertyDescriptor.AddValueChanged() method. And when the target data
bound element change the property values, data binding engine will
call PropertyDescriptor.SetValue() method to transfer the changed
value back to the source property, and it will simultaneously raise
ValueChanged event to notify other subscribers (in this instance, the
other subscribers will be the TextBlocks within the ListBox.
And if you are implementing INotifyPropertyChanged, you are fully
responsible to implement the change notification in every setter of
the properties which needs to be data bound to the UI. Otherwise, the
change will be not synchronized as you'd expect.
这是我们通常的做法:
public class ViewModel : INotifyPropertyChanged
{
string _test;
public string Test
{
get { return _test; }
set
{
_test = value;
OnPropertyChanged();
}
}
public event PropertyChangedEventHandler PropertyChanged;
public void OnPropertyChanged([CallerMemberName] string property = "") =>
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(property));
}
现在我们的 属性 可以被视图中的多个元素使用,例如:
<TextBox Text="{Binding Test, UpdateSourceTrigger=PropertyChanged}" />
<TextBlock Text="{Binding Test}" />
更改 TextBox
中的值将更新 TextBlock
的内容。我们还可以在视图模型中设置值,视图会自动更新它。
如果我们这样写视图模型
public class ViewModel
{
public string Test { get; set; }
}
然后 视图仍然有效(例如,更改 TextBox
中的值将更新 TextBlock
)。当然,不可能再从视图模型中轻松更新 Test
值(不再有事件上升)。但我的问题是关于视图:为什么视图能够工作?它是在后台构造更多东西还是检查某些东西的逻辑?
[...] you are encountering a another hidden aspect of WPF, that's it WPF's data binding engine will data bind to PropertyDescriptor instance which wraps the source property if the source object is a plain CLR object and doesn't implement INotifyPropertyChanged interface. And the data binding engine will try to subscribe to the property changed event through PropertyDescriptor.AddValueChanged() method. And when the target data bound element change the property values, data binding engine will call PropertyDescriptor.SetValue() method to transfer the changed value back to the source property, and it will simultaneously raise ValueChanged event to notify other subscribers (in this instance, the other subscribers will be the TextBlocks within the ListBox.
And if you are implementing INotifyPropertyChanged, you are fully responsible to implement the change notification in every setter of the properties which needs to be data bound to the UI. Otherwise, the change will be not synchronized as you'd expect.