NavigationBar
MD3 Expressive flexible navigation bar: a 64dp bottom bar of 3–5 destinations for compact windows. The active destination shows a pill indicator behind its icon.
Basic usage
Selection is controlled (value + onChange) or uncontrolled
(defaultValue). selectedIcon shows the filled icon for the active
destination (m3: filled when selected, outlined otherwise).
const [value, setValue] = useState('home')
<NavigationBar aria-label="Main" value={value} onChange={(event, next) => setValue(next)}>
<NavigationBarItem value="home" icon={<HomeIcon />} selectedIcon={<HomeFillIcon />} label="Home" />
<NavigationBarItem value="mail" icon={<MailIcon />} selectedIcon={<MailFillIcon />} label="Mail" />
</NavigationBar>
Horizontal items
itemLayout="horizontal" puts the icon beside the label — for medium
windows. Items are centered with extra space at both ends.
<NavigationBar itemLayout="horizontal">…</NavigationBar>
Badges
badge takes content (e.g. "3") for a large badge or true for a small
dot. It is announced after the label — by default "3 new notifications" /
"New notification"; override the text with badgeLabel.
<NavigationBarItem value="mail" icon={<MailIcon />} label="Mail" badge="3" badgeLabel="3 unread" />
<NavigationBarItem value="alerts" icon={<BellIcon />} label="Alerts" badge />
Disabled
Accessibility
- Renders a
<nav>landmark — give it anaria-labelwhen the page has more than one navigation region. - Items are native
<button>s in the Tab order; the active one carriesaria-current="page"(destinations are page navigation, not tabs). - An item without a
labelneeds anaria-label(which also replaces the announced badge text). - Icons are decorative (
aria-hidden).
Props
NavigationBar
| Prop | Type | Default | Description |
|---|---|---|---|
defaultValue | string | — | Uncontrolled initial destination value. |
itemLayout | enum | vertical | Item layout: icon over label (`vertical`) or beside it (`horizontal`). Horizontal items are centered with the extra width at both ends of the bar (20 / 15 / 10 / 5 % per side for 3 / 4 / 5 / 6 items). |
onChange | ((event: MouseEvent<HTMLButtonElement, MouseEvent>, value: string) => void) | — | Fires with the triggering event and the newly selected destination value. |
value | string | — | Controlled selected destination value. |
NavigationBarItem
| Prop | Type | Default | Description |
|---|---|---|---|
badge | ReactNode | — | Badge on the icon: content (e.g. `"3"`) for a large badge, `true` for a small dot. |
badgeLabel | string | — | Accessible text for the badge, announced after the label. Defaults to `"{badge} new notifications"` for a counting badge and `"New notification"` for a dot. |
icon * | ReactNode | — | The item icon (outlined, per m3.material.io, when `selectedIcon` is given). |
label | ReactNode | — | The item label. Without a label, give the item an `aria-label` (which then also replaces the announced badge text). |
selectedIcon | ReactNode | — | Icon shown while this destination is selected — typically the filled version of `icon` (m3: filled for the selected destination, outlined for the rest). Falls back to `icon`. |
value * | string | — | Identifies the destination; matched against the parent value. |