Skip to content

Async & cascading options

Options do not have to be baked into the schema. OptionsFrom loads them on demand and declares which fields they depend on — pick a country and the city list reloads (dropping any selection that no longer exists). The company field below is conditionally required and clears itself when it is hidden, so an abandoned branch never reaches your model.

Live form
Where should we deliver?

View source
@page "/cascading"
@inject DemoDirectory Directory

<BormView State="_state" OnValidSubmit="HandleSubmit" SubmitText="Save address" />

@code {
    private readonly DeliveryAddress _model = new();
    private BormState _state = default!;

    protected override void OnInitialized()
    {
        var schema = BormBuilder.For<DeliveryAddress>()
            .Title("Where should we deliver?")
            .Field(x => x.Country, f => f
                .Required()
                .Options(DemoDirectory.Countries.ToArray())
                .Autocomplete("country"))
            .Field(x => x.City, f => f
                .Required()
                // Loaded on demand, and reloaded whenever Country changes.
                .OptionsFrom(
                    load: async ctx => await Directory.GetCitiesAsync(ctx.Value("Country") as string, ctx.CancellationToken),
                    value: city => city,
                    label: city => city,
                    dependsOn: nameof(DeliveryAddress.Country))
                .Placeholder("Pick a country first"))
            .Field(x => x.IsBusiness)
            .Field(x => x.CompanyName, f => f
                .VisibleWhen(nameof(DeliveryAddress.IsBusiness), BormConditionOperator.IsTrue)
                .RequiredWhen(nameof(DeliveryAddress.IsBusiness), BormConditionOperator.IsTrue)
                .ClearOnHide())
            .Field(x => x.Notes, f => f.AsTextArea(2))
            .Build();

        _state = new BormState(schema, new BormModelDataAccessor(_model));
        _state.StateChanged += OnStateChanged;
    }
}
An unhandled error has occurred. Reload 🗙