I need some help with a Blazor implementation of input controls. I am using CSLA with Telerik Blazor controls.
I have taken the standard Telerik Blazor TelerikTextBox and TelerikNumericTextBox controls and created my own custom component wrappers to those controls called CslaTextInput and CslaNumericInput.
The wrapper components have a Property [Parameter] that takes in a Csla.Blazor.IPropertyInfo from a BusinessBase model. e.g.
Property="@(vm.GetPropertyInfo(() => vm.Model.CustomTelerikTextBox))"
Then in the wrapper the the Telerik component binds the value based on the Csla.Blazor.IPropertyInfo Value e.g.
@bind-Value="Value"
[Parameter]
public IPropertyInfo Property { get; set; }
protected string Value
{
get => (string)Property.Value;
set => Property.Value = value;
}
Where as the standard Telerik component deals directly with the property e.g.
@bind-Value="vm.Model.StandardTelerikTextBox"
I believe the issue I am facing (not 100% sure) is that when the Value property of the Csla.Blazor.IPropertyInfo changes the Blazor UI doesn't get notified that a change has been made and doesn't update the bound model value on screen.
The below video shows the issue on the custom control where the bound model value to the right of the control doesn't stay in sync with the input control value until a different control is changed and forces an update on screen.
If I update the model behind the scenes it works
https://drive.google.com/file/d/1Exfl0U39GU_61vCjieTp5w-TN6yx6rbp/view?usp=sharing
In this code snippet:
@bind-Value="Value"
[Parameter]
public IPropertyInfo Property { get; set; }
protected string Value
{
get => (string)Property.Value;
set => Property.Value = value;
}
you should add another parameter, of type event call back, that should be invoked when the bound value of the Value
property is changed:
[Parameter] public EventCallback PropertyChanged { get; set; }
And your Value
property should look like this:
protected string Value
{
get => (string)Property.Value;
set
{
if( Property.Value != value}
{
Property.Value = value;
// Notify the parents component that the parameter Property
// property has changed, and that she should consider re-
// rendering
_ = PropertyChanged.InvokeAsync(Property.Value);
}
}
}
Warning: Component parameter properties should not be mutated or modified from the child component