dotnet
dotnet copied to clipboard
Add support for custom callback method in ObservableProperty
Overview
Assume that you are developing an observable model of a setting that contains a set of fields, decorated by the ObservableProperty
attribute:
[ObservableObject]
public sealed partial class MyModel
{
[ObservableProperty] private string _myField = string.Empty;
}
Assuming that this is a setting, other parts of the application might need to know when this setting is modified, i.e., it becomes dirty.
This is easily achieved using Messaging; however, it would require the developer to manually convert this field to a property with a backing field, defeating the purpose of the ObservableProperty
attribute:
[ObservableObject]
public sealed partial class MyModel
{
private string _myField = string.Empty;
public string MyField
{
get => _myField;
set
{
if (SetProperty(ref _myField, value))
WeakReferenceMessenger.Default.Send(new SettingsChangedMessage(value, nameof(MyModel)));
}
}
}
I believe an additional attribute that allows the developer to specify a callback method to be executed once the property is changed or even retrieved would be beneficial.
API breakdown
I'm not familiar enough with IIncrementalGenerator
and the current CommunityToolkit.MVVM implementation to provide a useful API breakdown.
However, I believe the generated code could utilize the SetPropertyAndNotifyOnCompletion
method.
Usage example
public sealed partial class MyObservableClass : ObservableObject
{
[ObservableProperty(CallbackSet = nameof(CustomSetCallback))] private string m_userEmail;
private void CustomSetCallback(object oldValue, object newValue)
{
// TODO
}
}
Breaking change?
I'm not sure
Alternatives
Currently, I've reserved to implement a custom generator using ISourceGenerator
that finds an ObservablePropertyEx
attribute to generate the necessary code with callback support.
Additional context
No response
Help us help you
No, just wanted to propose this
I would like to have this feature too! Sometimes I have to reload some properties when another property has changed. A callback method within the setter would be great for this.
+1 on this
I thinks this could be helpful also for those cases where we want to trigger the same callback for multiple properties OnChanged
events.
Right now we have to do something like this:
[ObservableProperty]
private bool _propertyA;
partial void OnPropertyAChanged(bool value) => DoStuff();
[ObservableProperty]
private bool _propertyB;
partial void OnPropertyBChanged(bool value) => DoStuff();
[ObservableProperty]
private bool _propertyC;
partial void OnPropertyCChanged(bool value) => DoStuff();
private void DoStuff()
{
// do stuff here
}
With the proposed feature we could simplify, like this:
[ObservableProperty(CallbackSet = nameof(DoStuff))]
private bool _propertyA;
[ObservableProperty(CallbackSet = nameof(DoStuff))]
private bool _propertyB;
[ObservableProperty(CallbackSet = nameof(DoStuff))]
private bool _propertyC;
private void DoStuff()
{
// do stuff here
}