Bug Report
A FluentMenu cannot be conditionally added to a page and opened in the same render. Rendering it for the first time with Open="true" races its asynchronous JavaScript initialization.
Observed downstream in the Aspire Dashboard with Microsoft.FluentUI.AspNetCore.Components 4.14.4.
Repro
<FluentButton Id="menu-anchor" @onclick="OpenMenu">
Actions
</FluentButton>
@if (_renderMenu)
{
<FluentMenu Anchor="menu-anchor" Open="true">
<FluentMenuItem>Action</FluentMenuItem>
</FluentMenu>
}
@code {
private bool _renderMenu;
private void OpenMenu()
{
_renderMenu = true;
}
}
Current behavior
The menu is displayed while its JavaScript modules are still initializing, resulting in a JS interop error:
AnchoredRegion module is required for keyboard navigation
FluentMenu.razor.js throws this when initialize receives menuOpen=true before the anchored-region module is available.
Expected behavior
A FluentMenu should support being added to the render tree for the first time with Open="true". It should finish initialization before displaying the menu and initializing keyboard navigation.
This pattern is useful when a page contains many menu buttons. Consumers can avoid constructing every menu and paying their JavaScript import/initialization costs during the initial page render, then create only the menu that the user opens.
Aspire workaround
AspireMenuButton currently:
- Starts observing the anchor before rendering
FluentMenu.
- Renders the menu closed.
- Uses FluentMenu's first
aria-expanded write as a readiness signal that its JavaScript modules have initialized.
- Sets
Open=true only after that signal.
Workaround source:
This works, but it relies on observing an implementation detail and requires downstream JavaScript solely to coordinate FluentMenu initialization.
Possible solutions
- Make FluentMenu wait for all required modules to finish loading before processing an initial
Open=true value.
- Defer FluentMenu module imports and calls such as
initialize until the menu is first opened. That would make a closed FluentMenu inexpensive and remove the need for consumers to conditionally render it solely for performance.
Bug Report
A
FluentMenucannot be conditionally added to a page and opened in the same render. Rendering it for the first time withOpen="true"races its asynchronous JavaScript initialization.Observed downstream in the Aspire Dashboard with
Microsoft.FluentUI.AspNetCore.Components4.14.4.Repro
Current behavior
The menu is displayed while its JavaScript modules are still initializing, resulting in a JS interop error:
FluentMenu.razor.jsthrows this wheninitializereceivesmenuOpen=truebefore the anchored-region module is available.Expected behavior
A
FluentMenushould support being added to the render tree for the first time withOpen="true". It should finish initialization before displaying the menu and initializing keyboard navigation.This pattern is useful when a page contains many menu buttons. Consumers can avoid constructing every menu and paying their JavaScript import/initialization costs during the initial page render, then create only the menu that the user opens.
Aspire workaround
AspireMenuButton currently:
FluentMenu.aria-expandedwrite as a readiness signal that its JavaScript modules have initialized.Open=trueonly after that signal.Workaround source:
This works, but it relies on observing an implementation detail and requires downstream JavaScript solely to coordinate FluentMenu initialization.
Possible solutions
Open=truevalue.initializeuntil the menu is first opened. That would make a closed FluentMenu inexpensive and remove the need for consumers to conditionally render it solely for performance.