Menu button
canonThe one action menu of the app: a labelled button with a chevron, or the kebab „⋯“ (iconOnly), opening a menu of actions; no action is the default one.
AD + owner 28 Sep 2026 („sjednotit popover do menu-button“): Menu button is THE action menu — the row anatomy moved here from Popover. Row: .ic (icon | iconNode) · label (.tx > .nm when something is on the right) · .tag · .acrm-kbd (aria-hidden) · .chk (checked rows); variants danger (auto separator before the first danger row), strong, disabled + title (tooltip + aria-describedby); empty/loading row {empty} = .acrm-popover-empty. Kebab = iconOnly → canonical IconButton (sm / framed), label = aria-label + phone sheet title, aria-haspopup/expanded + stopPropagation by the component. „Dimmed but clickable“ rows do not exist. Phone = BottomSheet. Mechanical refactor moved 18 hand-built Popover menus onto it (acrm MR, 28 Sep 2026); sub-menu (mail „Přesunout do složky ›“, reservation „Předat…“), menu header (account menu) and insert menus wait for an approved shape (MR-B). History: FA204, 26 Sep 2026 (acrm !3890) 1:1 port of „Přidat aktivitu“ (P144, TL-12); custom trigger({open, menu, onClick}) acrm !3899 (dialog chip row, rail link !4014). forceMenu (menu even with one item) and danger items (2026-09-28, acrm !4088). Touch (AD 28 Sep 2026, acrm !4111): in the phone sheet a disabled item shows its title as a visible second line .acrm-popover-reason (--hint, --ink-600, aligned with the label, outside the button) — MenuItems sheet; desktop keeps the tooltip. 3 Oct 2026: MenuButtonItem count / countTone / muted / actions / actionsLabel (acrm !4527). Registry repaired 17 Oct 2026 (review F6): added exported MenuPanel to react[].
Used in 63 files · 33 areas · 69× — components/AppShell, components/FilterBar, components/NavItemMenu, components/ReservationControl, components/accounting, components/assistant …
@acrm/ui <MenuButton> <MenuItems> <MenuPanel>.acrm-popover-item .acrm-popover-item.danger .acrm-popover-item.strong .acrm-popover-sep +3SourceStoryKeyboard
- Tab reaches the button; Enter / Space opens the menu and focus moves to the first item.
- Arrow Up / Down, Home and End move between items; Enter activates one, closes the menu and returns focus to the button.
- Escape closes the menu and returns focus to the button (shared Popover behaviour).
ARIA
- The button carries
aria-haspopup="menu"andaria-expanded; the menu isrole="menu"named by the button's label. - Items are
role="menuitem"(menuitemradio+aria-checkedforcheckedrows); the glyph and a custom mark are decorative,ariaLabelnames a row whose label alone is ambiguous. - A disabled item with a
titleis described by it: tooltip +aria-describedbypointing to a visually hidden sibling (outside the button, so it does not join the accessible name). The phone sheet uses the same hidden sibling — no visible second line (owner 28 Sep 2026, ACRM-375–377). - Every row carries its full label in
title, so a label cut by the ellipsis stays readable on hover; the accessible name is always the full label. - A submenu row carries
aria-haspopup="menu"; its chevron isaria-hidden. Entering it replaces the rows in the samerole="menu"— the back row is amenuitemnamed by the submenu's label („Zpět" in the phone sheet, whose title names the level). Enter / Space on the submenu row opens the level; Enter on the back row returns. - A switch row is
role="menuitemcheckbox"witharia-checked; the.acrm-switchdrawing isaria-hidden. Activating it keeps the menu open and focus on the row, so the new state is announced. - The header (identity block) is not an item: plain content above the first separator, skipped by arrow keys.
- The keyboard shortcut (
.acrm-kbd) isaria-hidden— the label names the action. - The empty / loading row is plain text, not an item; a menu holding only it is still
role="menu". - Icon-only trigger (kebab): the canonical
IconButtonwitharia-label= the requiredlabel; the component setsaria-haspopup/aria-expanded, the host never does. - With a single item there is no menu: the button carries neither attribute and runs the action directly.
Focus
- The button draws the foundation focus ring of Button; items use the Popover item focus style.
Contrast
- Same tokens as Button and Popover; nothing of its own.
Known limits
- No typeahead (jump to an item by its first letter) — the shared Popover does not provide it.
Source: docs/button/menu-button.a11y.md · GitLab