Skip to content

MudSelectExtended: ItemCollection changes are ignored while the dropdown is open #645

Description

@MartinSoka

Summary

When items are added to a MudSelectExtended's ItemCollection while the dropdown is open, the
list does not redraw. The new items appear only after some unrelated interaction — clicking inside
or outside the popover, or typing in the search box.

This makes an incremental "load more" pattern inside the dropdown impossible: a paged picker that
appends the next batch of results updates its model but shows nothing.

Reproduction

<MudSelectExtended T="string" MultiSelection="true" ItemCollection="_items"
                   SearchBox="true" ShowStaticContentAtEnd="true">
    <StaticContent>
        <MudButton OnClick="AddMore">Show more</MudButton>
    </StaticContent>
</MudSelectExtended>

@code {
    private readonly List<string> _items = Enumerable.Range(1, 5).Select(i => $"Item {i}").ToList();
    private int _next = 6;

    private void AddMore()
    {
        for (var i = 0; i < 5; i++)
        {
            _items.Add($"Item {_next++}");
        }

        StateHasChanged();
    }
}
  1. Open the dropdown.
  2. Click Show more.

Expected: the list shows 10 items.
Actual: the list still shows 5. Click anywhere inside the popover, or type a character into the
search box, and all 10 appear at once.

Root cause

MudListExtended.SetParametersAsync
returns before calling base whenever the list is hosted by a select or an autocomplete:

public override Task SetParametersAsync(ParameterView parameters)
{
    if (_centralCommanderIsProcessing)
    {
        return Task.CompletedTask;
    }

    if (MudSelectExtended != null || MudAutocomplete != null)
    {
        return Task.CompletedTask;   // <-- base is never called
    }

    base.SetParametersAsync(parameters).CatchAndLog();

    _setParametersDone = true;
    return Task.CompletedTask;
}

MudSelectExtended is a cascading parameter, so it is null only during the very first
SetParametersAsync. From the second call onward the early return discards every parameter update,
the component never re-renders, and GetSearchedItems() — which reads ItemCollection live and
would return the new items — is never re-evaluated.

Workaround

We are currently using two workarounds either the user types in the search box or selects some item which calls StateHasChanged() on the list directly or using CloseMenu() then OpenMenu() which destroys and recreates the subtree.

CloseMenu()/OpenMenu() is a usable workaround but tears the popover down: the search box loses
its text and the list scrolls back to the top on every append.

Ruled out: MudBlazor's popover

A plain MudPopover (no MudExtensions) whose child content renders a mutable list redraws correctly
as items are appended — rendered rows went 3 → 4 → 5 → 6 across three appends. The popover fragment
push (PopoverService.UpdatePopoverAsyncMudPopoverProvider) is working as intended.

Suggested fix

The early return reads as a re-entrancy guard for central-commander processing rather than an
intentional block on all parameter updates. Applying the parameters and skipping only the
select-specific side effects would restore normal Blazor parameter flow:

if (_centralCommanderIsProcessing)
{
    return Task.CompletedTask;
}

base.SetParametersAsync(parameters).CatchAndLog();
_setParametersDone = true;
return Task.CompletedTask;

If the guard exists to prevent the select and the list fighting over selection state, narrowing it
to the selection parameters — rather than dropping ItemCollection and everything else with them —
would keep that protection without freezing the rendered list.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions