HyTabNavItem
Usage examples on this page are written for Lit / plain HTML (
<hy-tab-nav-item>). The same component ships asHyTabNavItemin@whitespaceux/harmony-react(native React 19), with typed wrappers for Angular, Solid, Svelte, and Vue. The API reference below applies to all frameworks.
One link inside an hy-tab-nav: looks exactly like an hy-tab but navigates instead of switching a panel.
It renders a real link with its own URL, so the back button works and the current page is announced through aria-current.
Renders as <a> when href is set and not disabled, otherwise <button> (for apps whose router owns the URL). disabled always wins — a disabled item is a <button disabled> regardless of href, because HTML has no native disabled attribute on anchors.
The current item carries aria-current="page" (the persistent "you are here" state — .claude/rules/components.md "Press / current / selected"). There is no role="tab", no aria-selected and no roving tabindex: these are links, and Tab moves between them.
Tabs vs tab nav vs toggle group
| In place (no URL) | Navigates (URL) | |
|---|---|---|
| Tab-shaped | hy-tab-group / hy-tab | hy-tab-nav / hy-tab-nav-item |
| Value picker | hy-toggle-group | — |
Emphasis and size
Both are normally inherited from the parent hy-tab-nav. The chrome is pixel-identical to hy-tab at every rung of both axes: plain (underline indicator), soft (role-tinted rounded rectangle on the current item), outlined (boxed), solid (filled current item); small / medium / large share hy-tab's type + padding ladder.
Examples
Inside a tab nav
<hy-tab-nav label="Settings section" emphasis="soft" size="small">
<hy-tab-nav-item href="/settings/primitives" active>Primitives</hy-tab-nav-item>
<hy-tab-nav-item href="/settings/semantics">Semantics</hy-tab-nav-item>
<hy-tab-nav-item href="/settings/components">Components</hy-tab-nav-item>
</hy-tab-nav>Client-side routing
<hy-tab-nav-item value="inbox" href="/inbox">Inbox</hy-tab-nav-item>
<script>
document.querySelector('hy-tab-nav-item').addEventListener('activate', (e) => {
e.detail.originalEvent.preventDefault(); // intercept, then route client-side
router.push(e.detail.href);
});
</script>With an icon
<hy-tab-nav-item href="/reports">
<hy-icon slot="icon" name="chart" decorative></hy-icon>
Reports
</hy-tab-nav-item>API
Properties
| Property | Attribute | Type | Default | Description |
|---|---|---|---|---|
value | value | string | '' | Identifier emitted in the activate event. |
href | href | string | '' | When set (and not disabled), the item renders as an <a>. |
target | target | string | '' | Anchor target; paired with href. |
active | active | boolean | false | Marks the item as the current page. Sets aria-current="page". |
disabled | disabled | boolean | false | Disables the item. Forces <button disabled> regardless of href. |
label | label | string | '' | Explicit accessible name (aria-label) overriding the visible label. Useful for i18n or when the visible label alone is ambiguous. |
size | size | 'small' | 'medium' | 'large' | 'medium' | Type + padding rung, typically inherited from the parent tab nav. - small — label-md type on row-nav-md padding - medium (default) — body-md type on row-nav-lg padding - large — body-lg type on row-nav-lg padding |
emphasis | emphasis | 'solid' | 'soft' | 'outlined' | 'plain' | 'plain' | Visual chrome weight, typically inherited from the parent tab nav. - plain (default) — transparent rest, role underline indicator - soft — role-tinted rounded rectangle on the current item - outlined — boxed/bordered items - solid — fully filled current item |
orientation | orientation | 'horizontal' | 'vertical' | 'horizontal' | Layout axis, typically inherited from the parent tab nav. - horizontal (default) — indicator on the block-end edge - vertical — indicator on the inline-start edge |
hasIcon | has-icon | boolean | false | SSR optimization hint indicating the icon slot has content. |
Events
| Event | Detail | Description |
|---|---|---|
activate | — | Fired on click, before navigation. Consumers with client-side routing call detail.originalEvent.preventDefault() to intercept. Detail: { value, href, originalEvent } |
Slots
| Slot | Description |
|---|---|
default | The visible label. |
icon | Icon content displayed before the label. |
CSS Parts
| Part | Description |
|---|---|
base | The interactive <a> or <button> element. |
label | The label wrapper. |
CSS Custom Properties
| Property | Description |
|---|---|
--hy-tab-nav-item-background-brand-rest | Underline / outlined-border / solid fill at rest |
--hy-tab-nav-item-background-brand-hover | Solid fill on hover of the current item |
--hy-tab-nav-item-background-brand-pressed | Solid fill while pressed |
--hy-tab-nav-item-background-active-fill | Soft fill of the current item |
--hy-tab-nav-item-background-active-hover | Hover of the current item (plain / soft) |
--hy-tab-nav-item-background-active-pressed | Pressed fill of the current item (plain / soft) |
--hy-tab-nav-item-background-muted-hover | Hover of a non-current item |
--hy-tab-nav-item-background-muted-pressed | Pressed fill of a non-current item |
--hy-tab-nav-item-background-rest | Background at rest |
--hy-tab-nav-item-foreground-brand-rest | Role-coloured ink on a tint (soft / outlined current item) |
--hy-tab-nav-item-foreground-on-brand-rest | Ink on the solid fill |
--hy-tab-nav-item-foreground-default-rest | Ink at rest |
--hy-tab-nav-item-foreground-default-disabled | Ink when disabled |
--hy-tab-nav-item-gap | Gap between icon and label |
--hy-tab-nav-item-padding-block | Block padding |
--hy-tab-nav-item-padding-inline | Inline padding |
--hy-tab-nav-item-radius | Border radius (plain) |
--hy-tab-nav-item-radius-form | Border radius of the soft / outlined / solid item (default: var(--hy-radius-form-md); set var(--hy-radius-pill-md) for a full pill) |
--hy-tab-nav-item-text-transform | Text transform for the label |
--hy-tab-nav-item-font-family | Font family override for the label |
--hy-tab-nav-item-hover-duration | Transition duration for hover and focus state feedback |
--hy-tab-nav-item-hover-easing | Transition easing for hover and focus state feedback |
--hy-tab-nav-item-expand-duration | Transition duration for the indicator slide animation |
--hy-tab-nav-item-expand-easing | Transition easing for the indicator slide animation |
Methods
focus()
Sets focus on the item's interactive element.
blur()
Removes focus from the item's interactive element.