@brightspot/ui 1.10.0 → 1.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/action-bar/ActionBar.d.ts +163 -0
- package/dist/components/action-bar/ActionBar.d.ts.map +1 -0
- package/dist/components/action-bar/ActionBar.js +479 -0
- package/dist/components/action-bar/ActionBar.js.map +1 -0
- package/dist/components/action-bar/ActionItem.d.ts +103 -0
- package/dist/components/action-bar/ActionItem.d.ts.map +1 -0
- package/dist/components/action-bar/ActionItem.js +237 -0
- package/dist/components/action-bar/ActionItem.js.map +1 -0
- package/dist/components/dropdown/Dropdown.d.ts +3 -1
- package/dist/components/dropdown/Dropdown.d.ts.map +1 -1
- package/dist/components/dropdown/Dropdown.js +22 -6
- package/dist/components/dropdown/Dropdown.js.map +1 -1
- package/dist/components/dropdown/DropdownItem.d.ts +14 -1
- package/dist/components/dropdown/DropdownItem.d.ts.map +1 -1
- package/dist/components/dropdown/DropdownItem.js +20 -1
- package/dist/components/dropdown/DropdownItem.js.map +1 -1
- package/dist/components/dropdown/DropdownMenu.d.ts +3 -5
- package/dist/components/dropdown/DropdownMenu.d.ts.map +1 -1
- package/dist/components/dropdown/DropdownMenu.js +17 -32
- package/dist/components/dropdown/DropdownMenu.js.map +1 -1
- package/dist/components/pagination/Pagination.d.ts +33 -4
- package/dist/components/pagination/Pagination.d.ts.map +1 -1
- package/dist/components/pagination/Pagination.js +80 -16
- package/dist/components/pagination/Pagination.js.map +1 -1
- package/dist/components/tabs/Tab.d.ts +108 -0
- package/dist/components/tabs/Tab.d.ts.map +1 -0
- package/dist/components/tabs/Tab.js +152 -0
- package/dist/components/tabs/Tab.js.map +1 -0
- package/dist/components/tabs/Tabs.d.ts +126 -0
- package/dist/components/tabs/Tabs.d.ts.map +1 -0
- package/dist/components/tabs/Tabs.js +390 -0
- package/dist/components/tabs/Tabs.js.map +1 -0
- package/dist/custom-elements.json +2635 -1591
- package/dist/storybook/assets/ActionBar.stories--nAeDC-G.js +408 -0
- package/dist/storybook/assets/ActionItem.stories-BHrGjk-P.js +203 -0
- package/dist/storybook/assets/{Avatar.stories-B26mRkkZ.js → Avatar.stories-Da-mRj6_.js} +1 -1
- package/dist/storybook/assets/{AvatarGroup.stories-J7lVGsMY.js → AvatarGroup.stories-BQlaC_yl.js} +1 -1
- package/dist/storybook/assets/{Badge.stories-BpTIV61M.js → Badge.stories-DnVnOrnF.js} +1 -1
- package/dist/storybook/assets/{Button-Dg-fIrzT.js → Button-CFLAI1H9.js} +1 -1
- package/dist/storybook/assets/{Button.stories-gPKRVbxk.js → Button.stories-DxaBOjwv.js} +1 -1
- package/dist/storybook/assets/{Celebrate.stories-DbY-sKEe.js → Celebrate.stories-CuMm15Nr.js} +1 -1
- package/dist/storybook/assets/{CircularProgress.stories-DeH5JYX_.js → CircularProgress.stories-DRN8Mtvj.js} +1 -1
- package/dist/storybook/assets/{ClipboardMixin.stories-C-lZ4uuw.js → ClipboardMixin.stories-DR7Ou2Av.js} +1 -1
- package/dist/storybook/assets/{Color-6BZIO3FS-Cu6zVIuG.js → Color-6BZIO3FS-Die62Y0Z.js} +1 -1
- package/dist/storybook/assets/{Colors.stories-D6XYMrTD.js → Colors.stories-bIq_ssbI.js} +1 -1
- package/dist/storybook/assets/{CombinedEffects.stories-jFekKTYg.js → CombinedEffects.stories-CtKzOUZn.js} +1 -1
- package/dist/storybook/assets/{ComponentStatesMixin-g50hRCPT.js → ComponentStatesMixin-DMLCk9fE.js} +1 -1
- package/dist/storybook/assets/{ComponentStatesMixin.stories-D3Q5pR38.js → ComponentStatesMixin.stories-D8UI9o-d.js} +1 -1
- package/dist/storybook/assets/{CopyToClipboard.stories-COZZ1VC2.js → CopyToClipboard.stories-ti6CpJNp.js} +1 -1
- package/dist/storybook/assets/{Debounce.stories-Dl10LAnx.js → Debounce.stories-DzZUSvbk.js} +1 -1
- package/dist/storybook/assets/{DocsRenderer-LL677BLK-CFLtMbUx.js → DocsRenderer-LL677BLK-CIRGv5IX.js} +3 -3
- package/dist/storybook/assets/{Dropdown.stories-Drwq-0Z2.js → Dropdown.stories-Lt4cY0Re.js} +41 -14
- package/dist/storybook/assets/{Events.stories-dODeR-g-.js → Events.stories-B1ddcgpT.js} +1 -1
- package/dist/storybook/assets/{Heading.stories-CH7_-_q3.js → Heading.stories-DI4w61cf.js} +1 -1
- package/dist/storybook/assets/{HueRipple.stories-CH1Y739k.js → HueRipple.stories-DjhoxxEw.js} +1 -1
- package/dist/storybook/assets/{Icon.stories-CPjM-jTU.js → Icon.stories-CpziAhae.js} +1 -1
- package/dist/storybook/assets/{IconButton.stories-DuzqvcnN.js → IconButton.stories-KjN28hfc.js} +1 -1
- package/dist/storybook/assets/{LinearProgress.stories-C7IdnJd3.js → LinearProgress.stories-DcIpdz6R.js} +1 -1
- package/dist/storybook/assets/Pagination.stories-BBkLEwoP.js +252 -0
- package/dist/storybook/assets/{Popover.stories-Ca1F-wrI.js → Popover.stories-DLv48c2h.js} +1 -1
- package/dist/storybook/assets/{ReadyMixin-DNZ5dCsZ.js → ReadyMixin-Cw2Dfbu2.js} +1 -1
- package/dist/storybook/assets/RovingTabindexMixin.stories-BWaFx9mu.js +192 -0
- package/dist/storybook/assets/{Rtc.stories-BVJc1vCA.js → Rtc.stories-Ve7Bwo_l.js} +1 -1
- package/dist/storybook/assets/ScrollShadow.stories-C6XmrRLm.js +17 -0
- package/dist/storybook/assets/{Switch.stories-BEEHP8mD.js → Switch.stories-Cf8WM1LG.js} +1 -1
- package/dist/storybook/assets/Tab.stories-CEtdEtOx.js +218 -0
- package/dist/storybook/assets/Tabs.stories-CIAO1bPO.js +211 -0
- package/dist/storybook/assets/{Throttle.stories-C4xsYeAb.js → Throttle.stories-BqxVIb-r.js} +1 -1
- package/dist/storybook/assets/{Tooltip.stories-Ccm4AnSv.js → Tooltip.stories-B6fw6875.js} +1 -1
- package/dist/storybook/assets/{Welcome.stories-Degjk-M0.js → Welcome.stories-CfJtSM19.js} +1 -1
- package/dist/storybook/assets/{Widget.stories-OKnZ9sDs.js → Widget.stories-CiOho7lO.js} +1 -1
- package/dist/storybook/assets/{WithTooltip-65CFNBJE-CXL3TyJ2.js → WithTooltip-65CFNBJE-PGcopp73.js} +2 -2
- package/dist/storybook/assets/{blocks-DLdUKG_W.js → blocks-dP2DwISI.js} +5 -5
- package/dist/storybook/assets/{formatter-EIJCOSYU-29NCxjfM.js → formatter-EIJCOSYU-CZSAC3tg.js} +1 -1
- package/dist/storybook/assets/if-defined-B1RdczOE.js +1 -0
- package/dist/storybook/assets/{iframe-BqvwP3or.js → iframe-DloIUNZz.js} +161 -161
- package/dist/storybook/assets/iframe-bJgLXZKK.css +1 -0
- package/dist/storybook/assets/{index-BIyTv1BF.js → index-DKF0ypu5.js} +1 -1
- package/dist/storybook/assets/onFind-C0l4Gew0.js +1 -0
- package/dist/storybook/assets/{onFind.stories-D64-QZqf.js → onFind.stories-DOTt9puO.js} +1 -1
- package/dist/storybook/assets/{onRemove.stories-BICsnIJL.js → onRemove.stories-CQ9ZC5dm.js} +1 -1
- package/dist/storybook/assets/{onVisible.stories-DpDZP9_5.js → onVisible.stories-Cbj5_Vz0.js} +1 -1
- package/dist/storybook/assets/style-map-DLXysq3r.js +1 -0
- package/dist/storybook/assets/{syntaxhighlighter-ED5Y7EFY-Bz_DuQj8.js → syntaxhighlighter-ED5Y7EFY-Bjjbl9ca.js} +1 -1
- package/dist/storybook/iframe.html +2 -2
- package/dist/storybook/index.json +1 -1
- package/dist/storybook/project.json +1 -1
- package/dist/tailwind-plugin-action-bar.d.ts +2 -0
- package/dist/tailwind-plugin-action-bar.d.ts.map +1 -0
- package/dist/tailwind-plugin-action-bar.js +120 -0
- package/dist/tailwind-plugin-action-bar.js.map +1 -0
- package/dist/tailwind-plugin-action-bar.ts +134 -0
- package/dist/tailwind-plugin-badge.js +4 -5
- package/dist/tailwind-plugin-badge.js.map +1 -1
- package/dist/tailwind-plugin-badge.ts +4 -5
- package/dist/tailwind-plugin-button.js +1 -0
- package/dist/tailwind-plugin-button.js.map +1 -1
- package/dist/tailwind-plugin-button.ts +1 -0
- package/dist/tailwind-plugin-pagination.js +13 -23
- package/dist/tailwind-plugin-pagination.js.map +1 -1
- package/dist/tailwind-plugin-pagination.ts +15 -25
- package/dist/tailwind-plugin-tabs.d.ts +2 -0
- package/dist/tailwind-plugin-tabs.d.ts.map +1 -0
- package/dist/tailwind-plugin-tabs.js +151 -0
- package/dist/tailwind-plugin-tabs.js.map +1 -0
- package/dist/tailwind-plugin-tabs.ts +162 -0
- package/dist/util/EventEmitterMixin.d.ts +16 -0
- package/dist/util/EventEmitterMixin.d.ts.map +1 -1
- package/dist/util/EventEmitterMixin.js.map +1 -1
- package/dist/util/RovingTabindexMixin.d.ts +38 -0
- package/dist/util/RovingTabindexMixin.d.ts.map +1 -0
- package/dist/util/RovingTabindexMixin.js +83 -0
- package/dist/util/RovingTabindexMixin.js.map +1 -0
- package/docs/components/ActionBar.md +71 -0
- package/docs/components/ActionItem.md +76 -0
- package/docs/components/Dropdown.md +7 -7
- package/docs/components/DropdownItem.md +9 -5
- package/docs/components/DropdownMenu.md +12 -12
- package/docs/components/Pagination.md +37 -34
- package/docs/components/README.md +4 -0
- package/docs/components/Tab.md +73 -0
- package/docs/components/Tabs.md +77 -0
- package/package.json +1 -1
- package/dist/storybook/assets/Pagination.stories-C4cLjS_9.js +0 -272
- package/dist/storybook/assets/ScrollShadow.stories-C3W5o9ZW.js +0 -17
- package/dist/storybook/assets/if-defined-BZFPaJjl.js +0 -1
- package/dist/storybook/assets/iframe-C5bIZMJ5.css +0 -1
- package/dist/storybook/assets/onFind-1l3EPW-I.js +0 -1
- package/dist/storybook/assets/style-map-CBrSnxRe.js +0 -1
|
@@ -0,0 +1,192 @@
|
|
|
1
|
+
import{x as l,i as v}from"./iframe-DloIUNZz.js";import{t as m}from"./custom-element-UsVr97OX.js";import"./preload-helper-PPVm8Dsz.js";const h=n=>{class i extends n{constructor(){super(...arguments),this._rovingIndex=0}_getRovingTargets(){return[]}_rovingFocus(t,e=!0){const o=this._getRovingTargets();if(o.length===0)return;const r=Math.max(0,Math.min(t,o.length-1));o.forEach((u,b)=>u.setAttribute("tabindex",b===r?"0":"-1")),e&&o[r]?.focus(),this._rovingIndex=r}_rovingNext(){const t=this._getRovingTargets();if(t.length===0)return;const e=this._rovingCurrentIndex(),o=e<t.length-1?e+1:0;this._rovingFocus(o)}_rovingPrev(){const t=this._getRovingTargets();if(t.length===0)return;const e=this._rovingCurrentIndex(),o=e>0?e-1:t.length-1;this._rovingFocus(o)}_rovingFirst(){this._rovingFocus(0)}_rovingLast(){const t=this._getRovingTargets();t.length>0&&this._rovingFocus(t.length-1)}_rovingCurrentIndex(){const t=document.activeElement;return this._getRovingTargets().findIndex(e=>e===t||e.contains(t))}}return i};var a=Object.freeze,x=Object.defineProperty,p=Object.getOwnPropertyDescriptor,f=(n,i,d,t)=>{for(var e=t>1?void 0:t?p(i,d):i,o=n.length-1,r;o>=0;o--)(r=n[o])&&(e=r(e)||e);return e},y=(n,i)=>a(x(n,"raw",{value:a(n.slice())})),c;const T={title:"Mixins/Roving Tabindex",tags:["autodocs"],parameters:{docs:{description:{component:`
|
|
2
|
+
\`RovingTabindexMixin\` provides **roving tabindex** navigation primitives for toolbar and menu components following the <a href="https://www.w3.org/WAI/ARIA/apd/practices/keyboard-interface/#kbd_roving_tabindex" target="_blank">WAI-ARIA Keyboard Interface Pattern</a>.
|
|
3
|
+
|
|
4
|
+
In a roving tabindex, only one element in the group has \`tabindex="0"\` (reachable via Tab), while all others have \`tabindex="-1"\`. Arrow keys move focus between items, wrapping at both ends.
|
|
5
|
+
|
|
6
|
+
<h3>What RovingTabindexMixin Provides</h3>
|
|
7
|
+
|
|
8
|
+
<table>
|
|
9
|
+
<thead>
|
|
10
|
+
<tr>
|
|
11
|
+
<th>Member</th>
|
|
12
|
+
<th>Type</th>
|
|
13
|
+
<th>Description</th>
|
|
14
|
+
</tr>
|
|
15
|
+
</thead>
|
|
16
|
+
<tbody>
|
|
17
|
+
<tr>
|
|
18
|
+
<td><code>_getRovingTargets()</code></td>
|
|
19
|
+
<td>Method (override)</td>
|
|
20
|
+
<td>Return focusable <code>HTMLElement[]</code> in navigation order. <strong>Subclass must override.</strong></td>
|
|
21
|
+
</tr>
|
|
22
|
+
<tr>
|
|
23
|
+
<td><code>_rovingFocus(index, shouldFocus?)</code></td>
|
|
24
|
+
<td>Method</td>
|
|
25
|
+
<td>Set <code>tabindex="0"</code> on target at index, <code>"-1"</code> on all others. Focuses the element unless <code>shouldFocus=false</code>.</td>
|
|
26
|
+
</tr>
|
|
27
|
+
<tr>
|
|
28
|
+
<td><code>_rovingNext()</code></td>
|
|
29
|
+
<td>Method</td>
|
|
30
|
+
<td>Move focus to next target (wraps to first)</td>
|
|
31
|
+
</tr>
|
|
32
|
+
<tr>
|
|
33
|
+
<td><code>_rovingPrev()</code></td>
|
|
34
|
+
<td>Method</td>
|
|
35
|
+
<td>Move focus to previous target (wraps to last)</td>
|
|
36
|
+
</tr>
|
|
37
|
+
<tr>
|
|
38
|
+
<td><code>_rovingFirst()</code></td>
|
|
39
|
+
<td>Method</td>
|
|
40
|
+
<td>Focus the first target</td>
|
|
41
|
+
</tr>
|
|
42
|
+
<tr>
|
|
43
|
+
<td><code>_rovingLast()</code></td>
|
|
44
|
+
<td>Method</td>
|
|
45
|
+
<td>Focus the last target</td>
|
|
46
|
+
</tr>
|
|
47
|
+
<tr>
|
|
48
|
+
<td><code>_rovingCurrentIndex()</code></td>
|
|
49
|
+
<td>Method</td>
|
|
50
|
+
<td>Find index of the currently focused target</td>
|
|
51
|
+
</tr>
|
|
52
|
+
<tr>
|
|
53
|
+
<td><code>_rovingIndex</code></td>
|
|
54
|
+
<td>Property</td>
|
|
55
|
+
<td>Index of the last focused target</td>
|
|
56
|
+
</tr>
|
|
57
|
+
</tbody>
|
|
58
|
+
</table>
|
|
59
|
+
|
|
60
|
+
<h3>Keydown Handler is NOT Included</h3>
|
|
61
|
+
|
|
62
|
+
<p>The mixin intentionally does <strong>not</strong> install a keyboard event handler. Each component defines its own because:</p>
|
|
63
|
+
<ul>
|
|
64
|
+
<li><strong>Toolbars</strong> use <code>ArrowRight</code>/<code>ArrowLeft</code> (horizontal) with RTL awareness</li>
|
|
65
|
+
<li><strong>Menus</strong> use <code>ArrowDown</code>/<code>ArrowUp</code> (vertical) plus Enter/Space/Escape/Tab</li>
|
|
66
|
+
</ul>
|
|
67
|
+
|
|
68
|
+
<h3>Where It's Used</h3>
|
|
69
|
+
<ul>
|
|
70
|
+
<li><strong>ActionBar</strong> — horizontal toolbar with ArrowRight/Left, RTL support</li>
|
|
71
|
+
<li><strong>DropdownMenu</strong> — vertical menu with ArrowDown/Up, typeahead</li>
|
|
72
|
+
</ul>
|
|
73
|
+
|
|
74
|
+
<h3>TypeScript Usage</h3>
|
|
75
|
+
|
|
76
|
+
\`\`\`typescript
|
|
77
|
+
import { RovingTabindexMixin } from './RovingTabindexMixin'
|
|
78
|
+
import { EventEmitterMixin } from './EventEmitterMixin'
|
|
79
|
+
import { ReadyMixin } from './ReadyMixin'
|
|
80
|
+
import { LitElement } from 'lit'
|
|
81
|
+
|
|
82
|
+
class MyToolbar extends RovingTabindexMixin(EventEmitterMixin(ReadyMixin(LitElement))) {
|
|
83
|
+
// 1. Override to return your focusable elements
|
|
84
|
+
_getRovingTargets(): HTMLElement[] {
|
|
85
|
+
return Array.from(this.querySelectorAll('button'))
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
// 2. Install your own keydown handler
|
|
89
|
+
connectedCallback() {
|
|
90
|
+
super.connectedCallback()
|
|
91
|
+
this.addEventListener('keydown', this._handleKeydown)
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
private _handleKeydown = (e: KeyboardEvent) => {
|
|
95
|
+
switch (e.key) {
|
|
96
|
+
case 'ArrowRight': e.preventDefault(); this._rovingNext(); break
|
|
97
|
+
case 'ArrowLeft': e.preventDefault(); this._rovingPrev(); break
|
|
98
|
+
case 'Home': e.preventDefault(); this._rovingFirst(); break
|
|
99
|
+
case 'End': e.preventDefault(); this._rovingLast(); break
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
\`\`\`
|
|
104
|
+
|
|
105
|
+
<h3>Mixin Composition Order</h3>
|
|
106
|
+
|
|
107
|
+
\`\`\`typescript
|
|
108
|
+
class MyComponent extends RovingTabindexMixin(EventEmitterMixin(ReadyMixin(LitElement))) {}
|
|
109
|
+
\`\`\`
|
|
110
|
+
`}}}};let g=class extends h(v){constructor(){super(...arguments),this._handleKeydown=n=>{switch(n.key){case"ArrowRight":n.preventDefault(),this._rovingNext();break;case"ArrowLeft":n.preventDefault(),this._rovingPrev();break;case"Home":n.preventDefault(),this._rovingFirst();break;case"End":n.preventDefault(),this._rovingLast();break}}}createRenderRoot(){return this}_getRovingTargets(){return Array.from(this.querySelectorAll(".roving-demo-btn"))}connectedCallback(){super.connectedCallback(),this.addEventListener("keydown",this._handleKeydown)}disconnectedCallback(){super.disconnectedCallback(),this.removeEventListener("keydown",this._handleKeydown)}render(){return l`
|
|
111
|
+
<div role="toolbar" aria-label="Demo toolbar" style="display: flex; gap: 0.5rem;">
|
|
112
|
+
<button class="roving-demo-btn btu-button btu-button-gray btu-button-md" tabindex="0">Item 1</button>
|
|
113
|
+
<button class="roving-demo-btn btu-button btu-button-gray btu-button-md" tabindex="-1">Item 2</button>
|
|
114
|
+
<button class="roving-demo-btn btu-button btu-button-gray btu-button-md" tabindex="-1">Item 3</button>
|
|
115
|
+
<button class="roving-demo-btn btu-button btu-button-gray btu-button-md" tabindex="-1">Item 4</button>
|
|
116
|
+
<button class="roving-demo-btn btu-button btu-button-gray btu-button-md" tabindex="-1">Item 5</button>
|
|
117
|
+
</div>
|
|
118
|
+
`}};g=f([m("roving-demo")],g);const s={render:()=>l(c||(c=y([`<div class="flex flex-col gap-4">
|
|
119
|
+
<div>
|
|
120
|
+
<h4 class="mb-2 font-bold">Interactive Roving Tabindex Demo</h4>
|
|
121
|
+
<p class="mb-2 text-sm text-gray-600">
|
|
122
|
+
Click any button below, then use <strong>Arrow Right/Left</strong> to move focus between items.
|
|
123
|
+
<strong>Home</strong> and <strong>End</strong> jump to first/last. Focus wraps at both ends.
|
|
124
|
+
</p>
|
|
125
|
+
<p class="mb-4 text-sm text-gray-600">
|
|
126
|
+
Notice only the focused button has <code>tabindex="0"</code> — pressing <strong>Tab</strong> leaves the
|
|
127
|
+
toolbar entirely, and <strong>Shift+Tab</strong> returns to the last focused item.
|
|
128
|
+
</p>
|
|
129
|
+
</div>
|
|
130
|
+
|
|
131
|
+
<roving-demo id="roving-demo"></roving-demo>
|
|
132
|
+
|
|
133
|
+
<div id="roving-status" class="text-sm text-gray-500" style="font-family: monospace;"></div>
|
|
134
|
+
|
|
135
|
+
<script>
|
|
136
|
+
;(() => {
|
|
137
|
+
const demo = document.getElementById('roving-demo')
|
|
138
|
+
const status = document.getElementById('roving-status')
|
|
139
|
+
if (!demo || !status) return
|
|
140
|
+
|
|
141
|
+
demo.addEventListener('focusin', () => {
|
|
142
|
+
const buttons = demo.querySelectorAll('.roving-demo-btn')
|
|
143
|
+
const indices = Array.from(buttons).map(b => b.getAttribute('tabindex'))
|
|
144
|
+
status.textContent = 'tabindex: [' + indices.join(', ') + '] | _rovingIndex: ' + demo._rovingIndex
|
|
145
|
+
})
|
|
146
|
+
|
|
147
|
+
demo.addEventListener('keyup', () => {
|
|
148
|
+
const buttons = demo.querySelectorAll('.roving-demo-btn')
|
|
149
|
+
const indices = Array.from(buttons).map(b => b.getAttribute('tabindex'))
|
|
150
|
+
status.textContent = 'tabindex: [' + indices.join(', ') + '] | _rovingIndex: ' + demo._rovingIndex
|
|
151
|
+
})
|
|
152
|
+
})()
|
|
153
|
+
<\/script>
|
|
154
|
+
</div>`])))};s.parameters={...s.parameters,docs:{...s.parameters?.docs,source:{originalSource:`{
|
|
155
|
+
render: () => html\`<div class="flex flex-col gap-4">
|
|
156
|
+
<div>
|
|
157
|
+
<h4 class="mb-2 font-bold">Interactive Roving Tabindex Demo</h4>
|
|
158
|
+
<p class="mb-2 text-sm text-gray-600">
|
|
159
|
+
Click any button below, then use <strong>Arrow Right/Left</strong> to move focus between items.
|
|
160
|
+
<strong>Home</strong> and <strong>End</strong> jump to first/last. Focus wraps at both ends.
|
|
161
|
+
</p>
|
|
162
|
+
<p class="mb-4 text-sm text-gray-600">
|
|
163
|
+
Notice only the focused button has <code>tabindex="0"</code> — pressing <strong>Tab</strong> leaves the
|
|
164
|
+
toolbar entirely, and <strong>Shift+Tab</strong> returns to the last focused item.
|
|
165
|
+
</p>
|
|
166
|
+
</div>
|
|
167
|
+
|
|
168
|
+
<roving-demo id="roving-demo"></roving-demo>
|
|
169
|
+
|
|
170
|
+
<div id="roving-status" class="text-sm text-gray-500" style="font-family: monospace;"></div>
|
|
171
|
+
|
|
172
|
+
<script>
|
|
173
|
+
;(() => {
|
|
174
|
+
const demo = document.getElementById('roving-demo')
|
|
175
|
+
const status = document.getElementById('roving-status')
|
|
176
|
+
if (!demo || !status) return
|
|
177
|
+
|
|
178
|
+
demo.addEventListener('focusin', () => {
|
|
179
|
+
const buttons = demo.querySelectorAll('.roving-demo-btn')
|
|
180
|
+
const indices = Array.from(buttons).map(b => b.getAttribute('tabindex'))
|
|
181
|
+
status.textContent = 'tabindex: [' + indices.join(', ') + '] | _rovingIndex: ' + demo._rovingIndex
|
|
182
|
+
})
|
|
183
|
+
|
|
184
|
+
demo.addEventListener('keyup', () => {
|
|
185
|
+
const buttons = demo.querySelectorAll('.roving-demo-btn')
|
|
186
|
+
const indices = Array.from(buttons).map(b => b.getAttribute('tabindex'))
|
|
187
|
+
status.textContent = 'tabindex: [' + indices.join(', ') + '] | _rovingIndex: ' + demo._rovingIndex
|
|
188
|
+
})
|
|
189
|
+
})()
|
|
190
|
+
<\/script>
|
|
191
|
+
</div>\`
|
|
192
|
+
}`,...s.parameters?.docs?.source}}};const A=["RovingTabindex"];export{s as RovingTabindex,A as __namedExportsOrder,T as default};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{x as o}from"./iframe-
|
|
1
|
+
import{x as o}from"./iframe-DloIUNZz.js";import"./preload-helper-PPVm8Dsz.js";const r={title:"Utilities/RTC",tags:["autodocs"],parameters:{docs:{subtitle:"The `rtc` module provides real-time communication between browser tabs and the Brightspot CMS server. Uses BroadcastChannel for cross-tab coordination with leader election, and Server-Sent Events for server communication."},controls:{expanded:!0}}},e={render:()=>o`
|
|
2
2
|
<div class="space-y-6 text-sm">
|
|
3
3
|
<div>
|
|
4
4
|
<h3 class="mb-2 font-bold">Overview</h3>
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import{x as a}from"./iframe-DloIUNZz.js";import"./preload-helper-PPVm8Dsz.js";const l=({theme:e="btu-scrollshadow-25"})=>{const r=new Array(100).fill(0).map((s,t)=>`Item ${t+1}`);return a`
|
|
2
|
+
<style>
|
|
3
|
+
:root {
|
|
4
|
+
--can-scroll: ;
|
|
5
|
+
}
|
|
6
|
+
</style>
|
|
7
|
+
<div class=${["flex","gap-2","bg-gray-500",e].join(" ")}>
|
|
8
|
+
${r.map((s,t)=>a`<div
|
|
9
|
+
class="text-md flex aspect-square h-[100px] items-center justify-center"
|
|
10
|
+
style="background:oklch(80% 50% ${Math.floor(Math.random()*710)+10});"
|
|
11
|
+
>
|
|
12
|
+
${s}
|
|
13
|
+
</div>`)}
|
|
14
|
+
</div>
|
|
15
|
+
`},n={title:"CSS Plugins/Scroll Shadow",component:"btu-scrollshadow",tags:["autodocs"],parameters:{docs:{subtitle:"This Tailwind CSS plugin provides the `.btu-scrollshadow` utility class for adding shadows to the edges of a scrollable container once the content overflows. The shadows use our gray color palette. You can choose which shade of gray you want. The scroll container must not already use before & after pseudo elements. But, if you need to use before/after modifiers on the container, make sure you also manually set the content property to the `--whitespace` variable. This is a workaround for TWCSS automatically adding a content property to the before/after pseudo-elements, which overrides the `--whitespace` variable by default. Note: this currently only supports x-axis scrolling."},controls:{expanded:!0}},render:e=>l(e),argTypes:{theme:{control:{type:"select"},description:"Choose a shade of gray for the scroll shadow. 25 is almost white, and 900 is almost black.",options:["btu-scrollshadow-25","btu-scrollshadow-50","btu-scrollshadow-100","btu-scrollshadow-200","btu-scrollshadow-300","btu-scrollshadow-400","btu-scrollshadow-500","btu-scrollshadow-600","btu-scrollshadow-700","btu-scrollshadow-800","btu-scrollshadow-900"]}},args:{}},o={args:{}};o.parameters={...o.parameters,docs:{...o.parameters?.docs,source:{originalSource:`{
|
|
16
|
+
args: {}
|
|
17
|
+
}`,...o.parameters?.docs?.source}}};const i=["Default"];export{o as Default,i as __namedExportsOrder,n as default};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{g as k,x as c}from"./iframe-
|
|
1
|
+
import{g as k,x as c}from"./iframe-DloIUNZz.js";import{o as s}from"./if-defined-B1RdczOE.js";import{o as f}from"./style-map-DLXysq3r.js";import{L as w}from"./LucideDynamicLoader-jmdq8YDM.js";import"./preload-helper-PPVm8Dsz.js";const{events:v,args:y,argTypes:g}=k("btu-switch"),x={customColorOn:"--switch-color-track-on",customColorOff:"--switch-color-track-off",customKnobColor:"--switch-color-knob",customLabelSpacing:"--switch-label-spacing",customIconSize:"--switch-track-icon-size"},S=e=>Object.entries(x).reduce((o,[t,n])=>(e[t]&&(o[n]=e[t]),o),{}),L={title:"Components/Switch",component:"btu-switch",tags:["autodocs"],parameters:{docs:{subtitle:"A toggle switch for binary on/off states",description:{component:`
|
|
2
2
|
<h3>When to use:</h3>
|
|
3
3
|
<ul>
|
|
4
4
|
<li>For toggling a setting or preference on/off</li>
|
|
@@ -0,0 +1,218 @@
|
|
|
1
|
+
import{g as c,x as t}from"./iframe-DloIUNZz.js";import{o as d}from"./style-map-DLXysq3r.js";import"./preload-helper-PPVm8Dsz.js";const{events:u,args:m,argTypes:e}=c("btu-tab"),y={title:"Components/Tabs/Tab",component:"btu-tab",tags:["autodocs"],parameters:{docs:{subtitle:"btu-tab",description:{component:`
|
|
2
|
+
An individual tab within a \`btu-tabs\` group.
|
|
3
|
+
|
|
4
|
+
Renders a button with \`role="tab"\` that participates in keyboard navigation and selection state managed by the parent \`btu-tabs\` container.
|
|
5
|
+
|
|
6
|
+
<h3>Props managed by btu-tabs:</h3>
|
|
7
|
+
<p><code>size</code> and active state are propagated from the parent — do not set them directly.</p>
|
|
8
|
+
`}},actions:{handles:u},controls:{expanded:!0}},args:{...m,label:"Main",name:"main","icon-name":"",badge:void 0},argTypes:{...e,size:{table:{disable:!0}},"--badge-color-background":{table:{disable:!0}},"--badge-color-foreground":{table:{disable:!0}},label:{...e.label,control:{type:"text"},description:"Text displayed in the tab."},description:{...e.description,control:{type:"text"},description:"Accessibility description for screen readers (`aria-description`)."},disabled:{...e.disabled,control:{type:"boolean"},description:"Whether the tab is disabled and non-interactive."},"icon-name":{...e["icon-name"],control:{type:"text"},description:"Lucide icon name to display."},"icon-position":{...e["icon-position"],control:{type:"select"},options:["leading","trailing"],description:"Placement of the icon relative to the label."},"icon-only":{...e["icon-only"],control:{type:"boolean"},description:'When true, hides the label visually while maintaining accessibility. Intended for use with `variant="full"` only.'},error:{...e.error,control:{type:"boolean"},description:"When true, displays an error badge on the tab."},badge:{...e.badge,control:{type:"text"},description:'Displays a badge with the given value alongside the label. Intended for use with `variant="full"` only.'},customBadgeBackground:{name:"--badge-color-background",control:{type:"color"},description:"Background color of the count badge (default: gray-50)",table:{category:"CSS Properties"}},customBadgeForeground:{name:"--badge-color-foreground",control:{type:"color"},description:"Text color of the count badge (default: gray-700)",table:{category:"CSS Properties"}}},render:a=>{const l={};return a.customBadgeBackground&&(l["--badge-color-background"]=a.customBadgeBackground),a.customBadgeForeground&&(l["--badge-color-foreground"]=a.customBadgeForeground),t`
|
|
9
|
+
<btu-tabs size="md" active-tab="main" style=${d(l)}>
|
|
10
|
+
<btu-tab
|
|
11
|
+
name="main"
|
|
12
|
+
label="${a.label}"
|
|
13
|
+
?disabled="${a.disabled}"
|
|
14
|
+
.iconName="${a["icon-name"]||""}"
|
|
15
|
+
.iconPosition="${a["icon-position"]||"leading"}"
|
|
16
|
+
.iconOnly="${a["icon-only"]??!1}"
|
|
17
|
+
?error="${a.error}"
|
|
18
|
+
.badge="${a.badge}"
|
|
19
|
+
description="${a.description||""}"
|
|
20
|
+
></btu-tab>
|
|
21
|
+
<btu-tab name="other" label="Other"></btu-tab>
|
|
22
|
+
</btu-tabs>
|
|
23
|
+
`}},b={args:{}},n={render:()=>t`
|
|
24
|
+
<div class="flex flex-col gap-8">
|
|
25
|
+
<btu-tabs size="md" active-tab="dashboard">
|
|
26
|
+
<btu-tab name="dashboard" label="Dashboard" icon-name="layout-dashboard"></btu-tab>
|
|
27
|
+
<btu-tab name="search" label="Search" icon-name="search"></btu-tab>
|
|
28
|
+
<btu-tab name="settings" label="Settings" icon-name="settings" icon-position="trailing"></btu-tab>
|
|
29
|
+
</btu-tabs>
|
|
30
|
+
<btu-tabs size="md" variant="menu" active-tab="dashboard">
|
|
31
|
+
<btu-tab name="dashboard" label="Dashboard" icon-name="layout-dashboard"></btu-tab>
|
|
32
|
+
<btu-tab name="search" label="Search" icon-name="search"></btu-tab>
|
|
33
|
+
<btu-tab name="settings" label="Settings" icon-name="settings" icon-position="trailing"></btu-tab>
|
|
34
|
+
</btu-tabs>
|
|
35
|
+
</div>
|
|
36
|
+
`,parameters:{docs:{description:{story:"Set `icon-name` to any Lucide icon name. Use `icon-position` to place the icon before (default) or after the label."}}}},o={render:()=>t`
|
|
37
|
+
<btu-tabs size="md" active-tab="dashboard">
|
|
38
|
+
<btu-tab name="dashboard" label="Dashboard" icon-name="layout-dashboard" icon-only></btu-tab>
|
|
39
|
+
<btu-tab name="search" label="Search" icon-name="search" icon-only></btu-tab>
|
|
40
|
+
<btu-tab name="settings" label="Settings" icon-name="settings" icon-only></btu-tab>
|
|
41
|
+
<btu-tab name="help" label="Help" icon-name="circle-help" icon-only></btu-tab>
|
|
42
|
+
</btu-tabs>
|
|
43
|
+
`,parameters:{docs:{description:{story:'Set `icon-only` to visually hide the label while keeping it accessible via `aria-label`. Intended for use with `variant="full"` only — the `menu` variant always shows the label text.'}}}},r={render:()=>t`
|
|
44
|
+
<btu-tabs size="md" active-tab="inbox">
|
|
45
|
+
<btu-tab name="inbox" label="Inbox" badge="12"></btu-tab>
|
|
46
|
+
<btu-tab name="drafts" label="Drafts" badge="3"></btu-tab>
|
|
47
|
+
<btu-tab name="sent" label="Sent"></btu-tab>
|
|
48
|
+
<btu-tab name="spam" label="Spam" badge="99+"></btu-tab>
|
|
49
|
+
<btu-tab
|
|
50
|
+
name="primary"
|
|
51
|
+
label="Primary"
|
|
52
|
+
badge="5"
|
|
53
|
+
style=${d({"--badge-color-background":"oklch(var(--btu-theme-primary-50))","--badge-color-foreground":"oklch(var(--btu-theme-primary-700))"})}
|
|
54
|
+
></btu-tab>
|
|
55
|
+
<btu-tab
|
|
56
|
+
name="error"
|
|
57
|
+
label="Error"
|
|
58
|
+
badge="2"
|
|
59
|
+
style=${d({"--badge-color-background":"oklch(var(--btu-theme-error-50))","--badge-color-foreground":"oklch(var(--btu-theme-error-700))"})}
|
|
60
|
+
></btu-tab>
|
|
61
|
+
</btu-tabs>
|
|
62
|
+
`,parameters:{docs:{description:{story:'Set `badge` to display a numeric or text badge alongside the label. Defaults to a gray badge (gray-50 background, gray-700 text). Use `--badge-color-background` and `--badge-color-foreground` to customize — inline on a specific `btu-tab` to scope it, or on `btu-tabs` to apply to all. Intended for use with `variant="full"` only.'}}}},i={render:()=>t`
|
|
63
|
+
<div class="flex flex-col gap-8">
|
|
64
|
+
<btu-tabs size="md" active-tab="main">
|
|
65
|
+
<btu-tab name="main" label="Main" error></btu-tab>
|
|
66
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
67
|
+
<btu-tab name="overrides" label="Overrides"></btu-tab>
|
|
68
|
+
<btu-tab name="styles" label="Styles" error></btu-tab>
|
|
69
|
+
</btu-tabs>
|
|
70
|
+
<btu-tabs size="md" variant="menu" active-tab="main">
|
|
71
|
+
<btu-tab name="main" label="Main" error></btu-tab>
|
|
72
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
73
|
+
<btu-tab name="overrides" label="Overrides"></btu-tab>
|
|
74
|
+
<btu-tab name="styles" label="Styles" error></btu-tab>
|
|
75
|
+
</btu-tabs>
|
|
76
|
+
</div>
|
|
77
|
+
`,parameters:{docs:{description:{story:"Set `error` to show a badge indicating the tab content has validation errors. When the tab is active, the indicator underline also turns red. In `menu` variant, the error badge appears next to the active tab label and on items in the dropdown."}}}},s={render:()=>t`
|
|
78
|
+
<div class="flex flex-col gap-8">
|
|
79
|
+
<btu-tabs size="md" active-tab="main">
|
|
80
|
+
<btu-tab name="main" label="Main"></btu-tab>
|
|
81
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
82
|
+
<btu-tab name="overrides" label="Overrides" disabled></btu-tab>
|
|
83
|
+
<btu-tab name="styles" label="Styles"></btu-tab>
|
|
84
|
+
<btu-tab name="api" label="API" disabled></btu-tab>
|
|
85
|
+
</btu-tabs>
|
|
86
|
+
<btu-tabs size="md" variant="menu" active-tab="main">
|
|
87
|
+
<btu-tab name="main" label="Main"></btu-tab>
|
|
88
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
89
|
+
<btu-tab name="overrides" label="Overrides" disabled></btu-tab>
|
|
90
|
+
<btu-tab name="styles" label="Styles"></btu-tab>
|
|
91
|
+
<btu-tab name="api" label="API" disabled></btu-tab>
|
|
92
|
+
</btu-tabs>
|
|
93
|
+
</div>
|
|
94
|
+
`,parameters:{docs:{description:{story:"Set `disabled` to make a tab non-interactive. Disabled tabs remain focusable for keyboard navigation but cannot be activated."}}}};b.parameters={...b.parameters,docs:{...b.parameters?.docs,source:{originalSource:`{
|
|
95
|
+
args: {}
|
|
96
|
+
}`,...b.parameters?.docs?.source}}};n.parameters={...n.parameters,docs:{...n.parameters?.docs,source:{originalSource:`{
|
|
97
|
+
render: () => html\`
|
|
98
|
+
<div class="flex flex-col gap-8">
|
|
99
|
+
<btu-tabs size="md" active-tab="dashboard">
|
|
100
|
+
<btu-tab name="dashboard" label="Dashboard" icon-name="layout-dashboard"></btu-tab>
|
|
101
|
+
<btu-tab name="search" label="Search" icon-name="search"></btu-tab>
|
|
102
|
+
<btu-tab name="settings" label="Settings" icon-name="settings" icon-position="trailing"></btu-tab>
|
|
103
|
+
</btu-tabs>
|
|
104
|
+
<btu-tabs size="md" variant="menu" active-tab="dashboard">
|
|
105
|
+
<btu-tab name="dashboard" label="Dashboard" icon-name="layout-dashboard"></btu-tab>
|
|
106
|
+
<btu-tab name="search" label="Search" icon-name="search"></btu-tab>
|
|
107
|
+
<btu-tab name="settings" label="Settings" icon-name="settings" icon-position="trailing"></btu-tab>
|
|
108
|
+
</btu-tabs>
|
|
109
|
+
</div>
|
|
110
|
+
\`,
|
|
111
|
+
parameters: {
|
|
112
|
+
docs: {
|
|
113
|
+
description: {
|
|
114
|
+
story: 'Set \`icon-name\` to any Lucide icon name. Use \`icon-position\` to place the icon before (default) or after the label.'
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
}`,...n.parameters?.docs?.source}}};o.parameters={...o.parameters,docs:{...o.parameters?.docs,source:{originalSource:`{
|
|
119
|
+
render: () => html\`
|
|
120
|
+
<btu-tabs size="md" active-tab="dashboard">
|
|
121
|
+
<btu-tab name="dashboard" label="Dashboard" icon-name="layout-dashboard" icon-only></btu-tab>
|
|
122
|
+
<btu-tab name="search" label="Search" icon-name="search" icon-only></btu-tab>
|
|
123
|
+
<btu-tab name="settings" label="Settings" icon-name="settings" icon-only></btu-tab>
|
|
124
|
+
<btu-tab name="help" label="Help" icon-name="circle-help" icon-only></btu-tab>
|
|
125
|
+
</btu-tabs>
|
|
126
|
+
\`,
|
|
127
|
+
parameters: {
|
|
128
|
+
docs: {
|
|
129
|
+
description: {
|
|
130
|
+
story: 'Set \`icon-only\` to visually hide the label while keeping it accessible via \`aria-label\`. Intended for use with \`variant="full"\` only — the \`menu\` variant always shows the label text.'
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
}`,...o.parameters?.docs?.source}}};r.parameters={...r.parameters,docs:{...r.parameters?.docs,source:{originalSource:`{
|
|
135
|
+
render: () => html\`
|
|
136
|
+
<btu-tabs size="md" active-tab="inbox">
|
|
137
|
+
<btu-tab name="inbox" label="Inbox" badge="12"></btu-tab>
|
|
138
|
+
<btu-tab name="drafts" label="Drafts" badge="3"></btu-tab>
|
|
139
|
+
<btu-tab name="sent" label="Sent"></btu-tab>
|
|
140
|
+
<btu-tab name="spam" label="Spam" badge="99+"></btu-tab>
|
|
141
|
+
<btu-tab
|
|
142
|
+
name="primary"
|
|
143
|
+
label="Primary"
|
|
144
|
+
badge="5"
|
|
145
|
+
style=\${styleMap({
|
|
146
|
+
'--badge-color-background': 'oklch(var(--btu-theme-primary-50))',
|
|
147
|
+
'--badge-color-foreground': 'oklch(var(--btu-theme-primary-700))'
|
|
148
|
+
})}
|
|
149
|
+
></btu-tab>
|
|
150
|
+
<btu-tab
|
|
151
|
+
name="error"
|
|
152
|
+
label="Error"
|
|
153
|
+
badge="2"
|
|
154
|
+
style=\${styleMap({
|
|
155
|
+
'--badge-color-background': 'oklch(var(--btu-theme-error-50))',
|
|
156
|
+
'--badge-color-foreground': 'oklch(var(--btu-theme-error-700))'
|
|
157
|
+
})}
|
|
158
|
+
></btu-tab>
|
|
159
|
+
</btu-tabs>
|
|
160
|
+
\`,
|
|
161
|
+
parameters: {
|
|
162
|
+
docs: {
|
|
163
|
+
description: {
|
|
164
|
+
story: 'Set \`badge\` to display a numeric or text badge alongside the label. Defaults to a gray badge (gray-50 background, gray-700 text). Use \`--badge-color-background\` and \`--badge-color-foreground\` to customize — inline on a specific \`btu-tab\` to scope it, or on \`btu-tabs\` to apply to all. Intended for use with \`variant="full"\` only.'
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
}`,...r.parameters?.docs?.source}}};i.parameters={...i.parameters,docs:{...i.parameters?.docs,source:{originalSource:`{
|
|
169
|
+
render: () => html\`
|
|
170
|
+
<div class="flex flex-col gap-8">
|
|
171
|
+
<btu-tabs size="md" active-tab="main">
|
|
172
|
+
<btu-tab name="main" label="Main" error></btu-tab>
|
|
173
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
174
|
+
<btu-tab name="overrides" label="Overrides"></btu-tab>
|
|
175
|
+
<btu-tab name="styles" label="Styles" error></btu-tab>
|
|
176
|
+
</btu-tabs>
|
|
177
|
+
<btu-tabs size="md" variant="menu" active-tab="main">
|
|
178
|
+
<btu-tab name="main" label="Main" error></btu-tab>
|
|
179
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
180
|
+
<btu-tab name="overrides" label="Overrides"></btu-tab>
|
|
181
|
+
<btu-tab name="styles" label="Styles" error></btu-tab>
|
|
182
|
+
</btu-tabs>
|
|
183
|
+
</div>
|
|
184
|
+
\`,
|
|
185
|
+
parameters: {
|
|
186
|
+
docs: {
|
|
187
|
+
description: {
|
|
188
|
+
story: 'Set \`error\` to show a badge indicating the tab content has validation errors. When the tab is active, the indicator underline also turns red. In \`menu\` variant, the error badge appears next to the active tab label and on items in the dropdown.'
|
|
189
|
+
}
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
}`,...i.parameters?.docs?.source}}};s.parameters={...s.parameters,docs:{...s.parameters?.docs,source:{originalSource:`{
|
|
193
|
+
render: () => html\`
|
|
194
|
+
<div class="flex flex-col gap-8">
|
|
195
|
+
<btu-tabs size="md" active-tab="main">
|
|
196
|
+
<btu-tab name="main" label="Main"></btu-tab>
|
|
197
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
198
|
+
<btu-tab name="overrides" label="Overrides" disabled></btu-tab>
|
|
199
|
+
<btu-tab name="styles" label="Styles"></btu-tab>
|
|
200
|
+
<btu-tab name="api" label="API" disabled></btu-tab>
|
|
201
|
+
</btu-tabs>
|
|
202
|
+
<btu-tabs size="md" variant="menu" active-tab="main">
|
|
203
|
+
<btu-tab name="main" label="Main"></btu-tab>
|
|
204
|
+
<btu-tab name="seo" label="SEO"></btu-tab>
|
|
205
|
+
<btu-tab name="overrides" label="Overrides" disabled></btu-tab>
|
|
206
|
+
<btu-tab name="styles" label="Styles"></btu-tab>
|
|
207
|
+
<btu-tab name="api" label="API" disabled></btu-tab>
|
|
208
|
+
</btu-tabs>
|
|
209
|
+
</div>
|
|
210
|
+
\`,
|
|
211
|
+
parameters: {
|
|
212
|
+
docs: {
|
|
213
|
+
description: {
|
|
214
|
+
story: 'Set \`disabled\` to make a tab non-interactive. Disabled tabs remain focusable for keyboard navigation but cannot be activated.'
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
}`,...s.parameters?.docs?.source}}};const v=["Default","WithIcon","IconOnly","WithBadge","WithError","Disabled"];export{b as Default,s as Disabled,o as IconOnly,r as WithBadge,i as WithError,n as WithIcon,v as __namedExportsOrder,y as default};
|