Underline Tabs
A keyboard-accessible tab strip with the active tab underlined.
6 फ्रेमवर्कमध्यम
Tabs that pair a leading icon with a visible label.
<!--
Icon + label tabs. The icons are aria-hidden and the label stays visible: the
icon is a scanning aid, never the accessible name. If you ever hide the label
to save space, the tab needs an aria-label carrying the same words - an
icon-only tab with no name is unusable with a screen reader.
-->
<div class="tabs-icons" data-tabs-icons>
<div class="tabs-icons__list" role="tablist" aria-label="Mailbox">
<button class="tabs-icons__tab" type="button" role="tab" id="ico-inbox" aria-controls="ico-panel-inbox" aria-selected="true" tabindex="0">
<svg class="tabs-icons__icon" viewBox="0 0 20 20" fill="none" stroke="currentColor" stroke-width="1.6" aria-hidden="true">
<path d="M2.5 12.5h4l1 2h5l1-2h4M2.5 12.5 4 4.5h12l1.5 8v3a1 1 0 0 1-1 1h-13a1 1 0 0 1-1-1v-3Z" stroke-linecap="round" stroke-linejoin="round" />
</svg>
Inbox
</button>
<button class="tabs-icons__tab" type="button" role="tab" id="ico-starred" aria-controls="ico-panel-starred" aria-selected="false" tabindex="-1">
<svg class="tabs-icons__icon" viewBox="0 0 20 20" fill="none" stroke="currentColor" stroke-width="1.6" aria-hidden="true">
<path d="m10 2.5 2.35 4.76 5.25.76-3.8 3.7.9 5.23L10 14.48l-4.7 2.47.9-5.23-3.8-3.7 5.25-.76L10 2.5Z" stroke-linecap="round" stroke-linejoin="round" />
</svg>
Starred
</button>
<button class="tabs-icons__tab" type="button" role="tab" id="ico-archive" aria-controls="ico-panel-archive" aria-selected="false" tabindex="-1">
<svg class="tabs-icons__icon" viewBox="0 0 20 20" fill="none" stroke="currentColor" stroke-width="1.6" aria-hidden="true">
<path d="M2.5 6.5h15m-13.5 0v9a1 1 0 0 0 1 1h10a1 1 0 0 0 1-1v-9M3.5 3.5h13v3h-13v-3ZM8 10h4" stroke-linecap="round" stroke-linejoin="round" />
</svg>
Archive
</button>
</div>
<div class="tabs-icons__panel" role="tabpanel" id="ico-panel-inbox" aria-labelledby="ico-inbox" tabindex="0">
<p>12 unread messages, 3 of them flagged as urgent.</p>
</div>
<div class="tabs-icons__panel" role="tabpanel" id="ico-panel-starred" aria-labelledby="ico-starred" tabindex="0" hidden>
<p>4 starred threads. Nothing new since Tuesday.</p>
</div>
<div class="tabs-icons__panel" role="tabpanel" id="ico-panel-archive" aria-labelledby="ico-archive" tabindex="0" hidden>
<p>1,204 archived messages, searchable for two years.</p>
</div>
</div>
<script>
(function () {
document.querySelectorAll('[data-tabs-icons]').forEach(function (root) {
var tabs = Array.prototype.slice.call(root.querySelectorAll('[role="tab"]'));
var panels = Array.prototype.slice.call(root.querySelectorAll('[role="tabpanel"]'));
function select(index, setFocus) {
tabs.forEach(function (tab, i) {
var isSelected = i === index;
tab.setAttribute('aria-selected', String(isSelected));
tab.tabIndex = isSelected ? 0 : -1;
if (panels[i]) panels[i].hidden = !isSelected;
});
if (setFocus) tabs[index].focus();
}
tabs.forEach(function (tab, i) {
tab.addEventListener('click', function () {
select(i, false);
});
tab.addEventListener('keydown', function (event) {
var next = -1;
if (event.key === 'ArrowRight') next = (i + 1) % tabs.length;
else if (event.key === 'ArrowLeft') next = (i - 1 + tabs.length) % tabs.length;
else if (event.key === 'Home') next = 0;
else if (event.key === 'End') next = tabs.length - 1;
else return;
event.preventDefault();
select(next, true);
});
});
});
})();
</script>| Prop | टाइप | डिफ़ॉल्ट | विवरण |
|---|---|---|---|
itemsआवश्यक | TabItem[] | - | रेंडर की जाने वाली आइटम की सूची। |
defaultTabId | string | - | माउंट पर खुले रहने वाले आइटम की id। |
onSelect | (id: string) => void | - | यूज़र द्वारा चुने गए मेन्यू आइटम के साथ चलता है। |
className | string | - | रूट एलिमेंट पर मर्ज होने वाली अतिरिक्त क्लासेज़। |
Icons are drawn with `currentColor` and marked `aria-hidden`, so one `aria-selected` rule paints the icon and the label together and the accessible name stays the visible text. If you ever drop the label to save space, the tab needs an `aria-label` carrying the same words - an icon-only tab with no name is unusable with a screen reader, and the icon alone rarely survives a user's first guess anyway. Swap in any 20×20 stroke icon set; the `1.125rem` box keeps the row rhythm.