(开始前:我正在使用.NET Framework 4.8)
我一直在WPF中闲逛,我厌倦了不断地键入用于绑定的属性。我现在使用代码片段键入锅炉板代码。
过了一段时间,我厌倦了总是在每个“模型”中粘贴通知属性更改代码,我创建了一个BindableBase
,我已经学会了,因为这是一种常见的做法。这个类看起来像这样:
public class BindableBase : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string name)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(name));
}
/// <summary>
/// Sets the value of a field of type T. <br/>
/// If new field value differs from old value, the funtion returns true. <br/>
/// If the value remains unchanged, the function returns false.
/// </summary>
/// <typeparam name="T">The type of the property / field.</typeparam>
/// <param name="field">A reference to the field that should be updated.</param>
/// <param name="value">The new value to be assigned to the property / field.</param>
/// <param name="propertyName">The variable name in code. Leave empty to let the compiler do this for you.</param>
/// <returns>True on field value change, false if field value remains the same.</returns>
protected bool SetField<T>(ref T field, T value, [CallerMemberName] string propertyName = null)
{
if (EqualityComparer<T>.Default.Equals(field, value)) return false;
field = value;
OnPropertyChanged(propertyName);
return true;
}
public delegate void PropertyValueChangedEventHandler<T>(T newValue);
}
我的财产看起来像这样
private object privateProp;
public object PublicProp
{
get => privateProp;
set => SetField(ref privateProp, value);
}
我不喜欢那些必须调用OnPropertyChanged的属性的一点是,它们添加了太多的代码,在我看来,这有点膨胀了源代码。今天,我试图创建一种方法,不必在任何地方编写(用snippet生成)整个属性。
public class BindableProperty<T> : BindableBase
{
private T value;
public T Value
{
get => value;
set => SetField(ref value, value);
}
}
我想使用如下:
<StackPanel Name="PermissionsPanel">
<CheckBox Name="ReadCheckBox" IsChecked="{Binding ReadFlag.Value}" />
<CheckBox Name="WriteCheckBox" IsChecked="{Binding WriteFlag.Value}" />
<StackPanel />
public class Permissions
{
BindableProperty<bool> ReadFlag = new BindableProperty<bool>();
BindableProperty<bool> WriteFlag = new BindableProperty<bool>();
}
// ...
public class SomeWindow : Window
{
privatye readonly Permissions permissions = new Permissions();
public SomeWindow()
{
InitializeComponent();
PermissionsPanel.DataContext = permissions;
}
}
这看起来像是一个非常干净的解决方案,可以避免到处都有相同的样板代码。很遗憾,好像不管用。
有谁能告诉我这不起作用的原因吗?或者,如果有一个调整,这可能工作?
2条答案
按热度按时间vwhgwdsa1#
你的“Generic bindable property”实际上不是一个 property,而是一个 field。要将其变为属性,add getters:
你可以在这篇文章中找到现成的解决方案:Implementing INotifyPropertyChanged - does a better way exist?
tkclm6bt2#
我不喜欢那些必须调用OnPropertyChanged的属性的一点是,它们添加了太多的代码,在我看来,这有点膨胀了源代码。
您可能需要考虑使用源代码生成器,例如Fody。在编译时,它注入引发
PropertyChanged
事件的代码。有谁能告诉我这不起作用的原因吗?
ReadFlag
和WriteFlag
必须是public properties 才能绑定到它们: