@brightspot/ui 1.1.0 → 1.2.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.
Files changed (108) hide show
  1. package/README.md +3 -90
  2. package/dist/LucideDynamicLoader.d.ts +1 -0
  3. package/dist/LucideDynamicLoader.d.ts.map +1 -1
  4. package/dist/LucideDynamicLoader.js +2 -0
  5. package/dist/LucideDynamicLoader.js.map +1 -1
  6. package/dist/LucideDynamicLoader.ts +3 -0
  7. package/dist/components/avatar/Avatar.d.ts +1 -1
  8. package/dist/components/avatar/Avatar.js +2 -2
  9. package/dist/components/avatar/Avatar.js.map +1 -1
  10. package/dist/components/avatar/AvatarGroup.d.ts +1 -1
  11. package/dist/components/avatar/AvatarGroup.js +2 -2
  12. package/dist/components/avatar/AvatarGroup.js.map +1 -1
  13. package/dist/components/badge/Badge.d.ts +1 -1
  14. package/dist/components/badge/Badge.js +2 -2
  15. package/dist/components/badge/Badge.js.map +1 -1
  16. package/dist/components/circular-progress/CircularProgress.d.ts +57 -0
  17. package/dist/components/circular-progress/CircularProgress.d.ts.map +1 -0
  18. package/dist/components/circular-progress/CircularProgress.js +173 -0
  19. package/dist/components/circular-progress/CircularProgress.js.map +1 -0
  20. package/dist/components/icon/Icon.d.ts +90 -0
  21. package/dist/components/icon/Icon.d.ts.map +1 -0
  22. package/dist/components/icon/Icon.js +172 -0
  23. package/dist/components/icon/Icon.js.map +1 -0
  24. package/dist/components/linear-progress/LinearProgress.d.ts +40 -0
  25. package/dist/components/linear-progress/LinearProgress.d.ts.map +1 -0
  26. package/dist/components/linear-progress/LinearProgress.js +95 -0
  27. package/dist/components/linear-progress/LinearProgress.js.map +1 -0
  28. package/dist/custom-elements.json +341 -6
  29. package/dist/global.d.ts +4 -0
  30. package/dist/storybook/assets/{Avatar.stories-BONZm4v8.js → Avatar.stories-BlxrclP0.js} +1 -1
  31. package/dist/storybook/assets/{AvatarGroup.stories-DDKujPh2.js → AvatarGroup.stories-E3VUvBae.js} +1 -1
  32. package/dist/storybook/assets/{Badge.stories-C8Ahfpp6.js → Badge.stories-f4YvPz0W.js} +5 -18
  33. package/dist/storybook/assets/Button.stories-N66xrq4q.js +63 -0
  34. package/dist/storybook/assets/CircularProgress.stories-zWyELtfc.js +451 -0
  35. package/dist/storybook/assets/{Color-64QXVMR3-CqLd5_0n.js → Color-64QXVMR3-B3Y5c9dl.js} +1 -1
  36. package/dist/storybook/assets/{Colors.stories-BajWDIwn.js → Colors.stories-nEoNeHhf.js} +1 -1
  37. package/dist/storybook/assets/{Events.stories-B32yjxgf.js → Events.stories-BP3ensxX.js} +1 -1
  38. package/dist/storybook/assets/Heading.stories-DGqWaBpi.js +3 -0
  39. package/dist/storybook/assets/Icon.stories-BWWjh4NZ.js +245 -0
  40. package/dist/storybook/assets/LinearProgress.stories-DMVolkoE.js +397 -0
  41. package/dist/storybook/assets/ScrollShadow.stories-BmwSRNje.js +17 -0
  42. package/dist/storybook/assets/Throttle.stories-DBj-9rhV.js +303 -0
  43. package/dist/storybook/assets/{WithTooltip-SK46ZJ2J-BO-IGPcG.js → WithTooltip-SK46ZJ2J-DW4NXFWt.js} +5 -5
  44. package/dist/storybook/assets/formatter-OMEEQ6HG-BBn014aZ.js +1 -0
  45. package/dist/storybook/assets/iframe-CxsKJSj-.css +1 -0
  46. package/dist/storybook/assets/{iframe-BIFmrRK7.js → iframe-Z4F0Cgki.js} +95 -135
  47. package/dist/storybook/assets/{index-B4dkQq9N.js → index-BUj5S-B7.js} +1 -1
  48. package/dist/storybook/assets/{syntaxhighlighter-CAVLW7PM-kyZrfiLk.js → syntaxhighlighter-CAVLW7PM-CsQveU1N.js} +1 -1
  49. package/dist/storybook/iframe.html +2 -2
  50. package/dist/storybook/index.json +1 -1
  51. package/dist/storybook/project.json +1 -1
  52. package/dist/tailwind-plugin-button.js +11 -9
  53. package/dist/tailwind-plugin-button.js.map +1 -1
  54. package/dist/tailwind-plugin-button.ts +11 -10
  55. package/dist/tailwind-plugin-contrast.d.ts +2 -0
  56. package/dist/tailwind-plugin-contrast.d.ts.map +1 -0
  57. package/dist/tailwind-plugin-contrast.js +17 -0
  58. package/dist/tailwind-plugin-contrast.js.map +1 -0
  59. package/dist/tailwind-plugin-contrast.ts +18 -0
  60. package/dist/tailwind-plugin-icon.js +17 -10
  61. package/dist/tailwind-plugin-icon.js.map +1 -1
  62. package/dist/tailwind-plugin-icon.ts +17 -10
  63. package/dist/tailwind-plugin-ring-contrast.d.ts +2 -0
  64. package/dist/tailwind-plugin-ring-contrast.d.ts.map +1 -0
  65. package/dist/tailwind-plugin-ring-contrast.js +76 -0
  66. package/dist/tailwind-plugin-ring-contrast.js.map +1 -0
  67. package/dist/tailwind-plugin-ring-contrast.ts +90 -0
  68. package/dist/tailwind.config.d.ts +21 -0
  69. package/dist/tailwind.config.d.ts.map +1 -1
  70. package/dist/tailwind.config.js +25 -0
  71. package/dist/tailwind.config.js.map +1 -1
  72. package/dist/tailwind.config.ts +25 -0
  73. package/dist/{utils → util}/EventEmitterMixin.d.ts +4 -1
  74. package/dist/util/EventEmitterMixin.d.ts.map +1 -0
  75. package/dist/util/EventEmitterMixin.js.map +1 -0
  76. package/dist/util/ProgressMixin.d.ts +52 -0
  77. package/dist/util/ProgressMixin.d.ts.map +1 -0
  78. package/dist/util/ProgressMixin.js +190 -0
  79. package/dist/util/ProgressMixin.js.map +1 -0
  80. package/dist/util/ReadyMixin.d.ts.map +1 -0
  81. package/dist/util/ReadyMixin.js.map +1 -0
  82. package/dist/util/aria.d.ts +3 -0
  83. package/dist/util/aria.d.ts.map +1 -0
  84. package/dist/util/aria.js +44 -0
  85. package/dist/util/aria.js.map +1 -0
  86. package/dist/util/svg.d.ts +9 -0
  87. package/dist/util/svg.d.ts.map +1 -1
  88. package/dist/util/svg.js +22 -0
  89. package/dist/util/svg.js.map +1 -1
  90. package/dist/util/throttle.d.ts +4 -0
  91. package/dist/util/throttle.d.ts.map +1 -0
  92. package/dist/util/throttle.js +30 -0
  93. package/dist/util/throttle.js.map +1 -0
  94. package/package.json +2 -2
  95. package/dist/storybook/assets/Button.stories-Cwdvbnu1.js +0 -63
  96. package/dist/storybook/assets/Heading.stories-C0ji1wRG.js +0 -3
  97. package/dist/storybook/assets/Icon.stories-DeEHMd7f.js +0 -28543
  98. package/dist/storybook/assets/Loader.stories-NxZ0SGA0.js +0 -3
  99. package/dist/storybook/assets/ScrollShadow.stories-1W8nsrPe.js +0 -17
  100. package/dist/storybook/assets/formatter-OMEEQ6HG-wqmAyL2n.js +0 -1
  101. package/dist/storybook/assets/iframe-BEH5EoNR.css +0 -1
  102. package/dist/utils/EventEmitterMixin.d.ts.map +0 -1
  103. package/dist/utils/EventEmitterMixin.js.map +0 -1
  104. package/dist/utils/ReadyMixin.d.ts.map +0 -1
  105. package/dist/utils/ReadyMixin.js.map +0 -1
  106. /package/dist/{utils → util}/EventEmitterMixin.js +0 -0
  107. /package/dist/{utils → util}/ReadyMixin.d.ts +0 -0
  108. /package/dist/{utils → util}/ReadyMixin.js +0 -0
@@ -0,0 +1,63 @@
1
+ import{x as c}from"./iframe-Z4F0Cgki.js";import"./preload-helper-PPVm8Dsz.js";const v=({color:r="primary",pressed:l,fill:d,contained:u,outlined:p,size:a="sm",label:b,icon:i,hideText:m,disabled:h})=>{const g=d?"":"btu-button-fill-none",y=u?"":"btu-button-container-none",f=p?"btu-button-outline":"",x=m?"btu-button-text-hidden":"";return c`
2
+ <button
3
+ type="button"
4
+ class=${["btu-button",`btu-button-${r}`,`btu-button-${a}`,g,y,f,x].join(" ")}
5
+ ?disabled=${h}
6
+ aria-pressed=${l?"true":"false"}
7
+ >
8
+ ${i?c`<btu-icon symbol=${i} size=${a}></btu-icon>`:""} ${b}
9
+ </button>
10
+ `},I=["ai","black","white","primary","teal","gray","purple","rose","error","warning","success"],T={title:"CSS Plugins/Button",component:"btu-button",tags:["autodocs"],parameters:{docs:{subtitle:"This Tailwind CSS plugin provides the `.btu-button` utility class for styling buttons. Use it on `<button>` elements preferably, but it can also be used on `<a>` or other clickable elements. The plugin includes variants for different colors, sizes, and styles such as filled, outlined, and contained buttons."},controls:{expanded:!0}},render:r=>v(r),argTypes:{color:{control:{type:"select"},options:I},contained:{control:{type:"boolean"},description:"Does the button have a container?"},disabled:{control:{type:"boolean"},description:"Is the button disabled?"},fill:{control:{type:"boolean"},description:"Is the button filled?"},hideText:{control:{type:"boolean"},description:"Icon only mode (hides label)"},icon:{control:{type:"text"},description:'Lucide icon name (e.g., "search", "smile", "check")'},label:{control:{type:"text"},description:"Button label text"},outlined:{control:{type:"boolean"},description:"Is the button outlined?"},pressed:{control:{type:"boolean"},description:"Is the button pressed?"},size:{control:{type:"select"},options:["sm","md","lg","xl","2xl"]}},args:{color:"primary",contained:!0,disabled:!1,fill:!0,hideText:!1,icon:"",label:"Button",outlined:!1,pressed:!1,size:"md"}},e={args:{}},t={args:{label:"Search",icon:"search"},parameters:{docs:{description:{story:"Button with an icon alongside text. Uses the `<btu-icon>` component."}}}},o={args:{icon:"smile",hideText:!0},parameters:{docs:{description:{story:"Icon-only button. Uses `btu-button-text-hidden` to hide the label and `<btu-icon>` for the icon."}}}},s={args:{label:"Disabled Button",disabled:!0},parameters:{docs:{description:{story:"Disabled button state. Uses the `[disabled]` attribute to trigger disabled styling with reduced opacity and pointer events disabled."}}}},n={args:{label:"Active Button",pressed:!0,fill:!1,icon:"check",hideText:!0},parameters:{docs:{description:{story:'Active/pressed button state. Uses `[aria-pressed="true"]` attribute to trigger the pressed styling, typically used for toggle buttons or to show an active state.'}}}};e.parameters={...e.parameters,docs:{...e.parameters?.docs,source:{originalSource:`{
11
+ args: {}
12
+ }`,...e.parameters?.docs?.source}}};t.parameters={...t.parameters,docs:{...t.parameters?.docs,source:{originalSource:`{
13
+ args: {
14
+ label: 'Search',
15
+ icon: 'search'
16
+ },
17
+ parameters: {
18
+ docs: {
19
+ description: {
20
+ story: \`Button with an icon alongside text. Uses the \\\`<btu-icon>\\\` component.\`
21
+ }
22
+ }
23
+ }
24
+ }`,...t.parameters?.docs?.source}}};o.parameters={...o.parameters,docs:{...o.parameters?.docs,source:{originalSource:`{
25
+ args: {
26
+ icon: 'smile',
27
+ hideText: true
28
+ },
29
+ parameters: {
30
+ docs: {
31
+ description: {
32
+ story: \`Icon-only button. Uses \\\`btu-button-text-hidden\\\` to hide the label and \\\`<btu-icon>\\\` for the icon.\`
33
+ }
34
+ }
35
+ }
36
+ }`,...o.parameters?.docs?.source}}};s.parameters={...s.parameters,docs:{...s.parameters?.docs,source:{originalSource:`{
37
+ args: {
38
+ label: 'Disabled Button',
39
+ disabled: true
40
+ },
41
+ parameters: {
42
+ docs: {
43
+ description: {
44
+ story: \`Disabled button state. Uses the \\\`[disabled]\\\` attribute to trigger disabled styling with reduced opacity and pointer events disabled.\`
45
+ }
46
+ }
47
+ }
48
+ }`,...s.parameters?.docs?.source}}};n.parameters={...n.parameters,docs:{...n.parameters?.docs,source:{originalSource:`{
49
+ args: {
50
+ label: 'Active Button',
51
+ pressed: true,
52
+ fill: false,
53
+ icon: 'check',
54
+ hideText: true
55
+ },
56
+ parameters: {
57
+ docs: {
58
+ description: {
59
+ story: \`Active/pressed button state. Uses \\\`[aria-pressed="true"]\\\` attribute to trigger the pressed styling, typically used for toggle buttons or to show an active state.\`
60
+ }
61
+ }
62
+ }
63
+ }`,...n.parameters?.docs?.source}}};const w=["Default","WithIcon","IconOnly","Disabled","ActivePressed"];export{n as ActivePressed,e as Default,s as Disabled,o as IconOnly,t as WithIcon,w as __namedExportsOrder,T as default};
@@ -0,0 +1,451 @@
1
+ import{g as D,E as h,x as T}from"./iframe-Z4F0Cgki.js";import"./preload-helper-PPVm8Dsz.js";const{events:A,args:$,argTypes:u}=D("btu-circular-progress"),k={title:"Components/Circular Progress",component:"btu-circular-progress",tags:["autodocs"],parameters:{docs:{subtitle:"A component for showing loading states or progress",description:{component:`
2
+ <h3>When to use:</h3>
3
+ <ul>
4
+ <li>To indicate loading or processing state</li>
5
+ <li>To show progress of a specific task</li>
6
+ <li>For operations with known or unknown duration</li>
7
+ </ul>
8
+
9
+ <h3>Variants:</h3>
10
+ <ul>
11
+ <li><strong>Indeterminate:</strong> Animated spinner for unknown duration (default)</li>
12
+ <li><strong>Determinate:</strong> Shows specific progress value (0-100)</li>
13
+ </ul>
14
+ `}},actions:{handles:A},controls:{expanded:!0}},args:{...$,indeterminate:!0,color:"primary",size:"sm",thickness:2,progress:0,initialAnimation:!0},argTypes:{...u,"--progress-color":{table:{disable:!0}},"--track-color":{table:{disable:!0}},"--progress-size":{table:{disable:!0}},indeterminate:{...u.indeterminate,control:{type:"boolean"},description:"Whether the progress indicator is indeterminate (animated spinner). When false, shows determinate progress based on the progress value.",table:{category:"Attributes",defaultValue:{summary:"true"}}},color:{...u.color,control:{type:"select"},options:["black","white","primary","teal","gray","purple","rose","error","warning","success"],description:"Theme color of the progress indicator.",table:{category:"Attributes",defaultValue:{summary:"primary"}}},size:{...u.size,control:{type:"select"},options:["sm","md","lg"],description:"Size variant: sm (16px), md (32px), lg (48px)",table:{category:"Attributes",defaultValue:{summary:"sm"}}},thickness:{...u.thickness,control:{type:"number",min:1,max:10},description:"Stroke width of the progress circle.",table:{category:"Attributes",defaultValue:{summary:"2"}}},progress:{...u.progress,control:{type:"range",min:0,max:100,step:1},description:"Progress value for determinate mode. Value between 0 and 100.",table:{category:"Attributes",defaultValue:{summary:"0"}}},label:{...u.label,control:{type:"text"},description:"Optional label text to display below the progress indicator.",table:{category:"Attributes",defaultValue:{summary:"undefined"}}},initialAnimation:{...u.initialAnimation,control:{type:"boolean"},description:"Whether to animate progress from 0 to target value when component first becomes visible in viewport. Only applies to determinate mode. Defaults to true.",table:{category:"Attributes",defaultValue:{summary:"true"}}},ariaLabel:{...u.ariaLabel,control:{type:"text"},description:'Optional aria-label attribute for screen readers. Describes what the progress indicator represents (e.g., "File upload progress").',table:{category:"Attributes",defaultValue:{summary:"undefined"}}},ariaLabelledBy:{...u.ariaLabelledBy,control:{type:"text"},description:"Optional aria-labelledby attribute for screen readers. References the ID of an element that labels the progress indicator.",table:{category:"Attributes",defaultValue:{summary:"undefined"}}},ariaValueText:{...u.ariaValueText,control:{type:"text"},description:"Optional aria-valuetext attribute for screen readers. Provides human-readable text alternative for the progress value in determinate mode.",table:{category:"Attributes",defaultValue:{summary:"undefined"}}},completionAnnouncement:{...u.completionAnnouncement,control:{type:"text"},description:"Optional message to announce to screen readers when progress reaches 100%. If not provided, no announcement will be made on completion.",table:{category:"Attributes",defaultValue:{summary:"undefined"}}},customColor:{name:"--progress-color",control:{type:"color"},description:"Custom progress indicator color - overrides the theme color",table:{category:"CSS Properties"}},customTrackColor:{name:"--track-color",control:{type:"color"},description:"Custom track/background color - overrides default gray-100",table:{category:"CSS Properties"}},customSize:{name:"--progress-size",control:{type:"number",min:1,max:100},description:"Custom size in pixels - overrides the size preset",table:{category:"CSS Properties"}}},render:e=>{const t=[];e.customColor&&t.push(`--progress-color: ${e.customColor}`),e.customTrackColor&&t.push(`--track-color: ${e.customTrackColor}`),e.customSize&&t.push(`--progress-size: ${e.customSize}px`);const r=t.length>0?t.join("; "):"";return T`<btu-circular-progress
15
+ ?indeterminate=${e.indeterminate}
16
+ color="${e.color}"
17
+ size="${e.size}"
18
+ thickness="${e.thickness}"
19
+ progress="${e.progress}"
20
+ label="${e.label||h}"
21
+ aria-label="${e.ariaLabel||h}"
22
+ aria-labelledby="${e.ariaLabelledBy||h}"
23
+ aria-valuetext="${e.ariaValueText||h}"
24
+ completion-announcement="${e.completionAnnouncement||h}"
25
+ ?initial-animation="${e.initialAnimation}"
26
+ style="${r}"
27
+ ></btu-circular-progress>`}},f={args:{},parameters:{docs:{description:{story:"Default indeterminate spinner with primary color and small size."}}}},v={render:()=>T`<div class="flex items-center gap-4">
28
+ <btu-circular-progress .indeterminate=${!1} progress="25" size="md" label="25%"></btu-circular-progress>
29
+ <btu-circular-progress
30
+ .indeterminate=${!1}
31
+ progress="50"
32
+ size="md"
33
+ color="success"
34
+ label="50%"
35
+ ></btu-circular-progress>
36
+ <btu-circular-progress
37
+ .indeterminate=${!1}
38
+ progress="75"
39
+ size="md"
40
+ color="warning"
41
+ label="75%"
42
+ ></btu-circular-progress>
43
+ <btu-circular-progress
44
+ .indeterminate=${!1}
45
+ progress="100"
46
+ size="md"
47
+ color="success"
48
+ label="100%"
49
+ ></btu-circular-progress>
50
+ </div>`,parameters:{docs:{description:{story:"Determinate progress indicators at various completion levels with labels."}}}},x={render:()=>{const e=document.createElement("div");e.className="flex items-center gap-8";let t=0;const r=document.createElement("btu-circular-progress");r.indeterminate=!1,r.progress=0,r.size="lg",r.color="primary",r.label="0%";const i=setInterval(()=>{t=(t+1)%101,r.progress=t,r.label=`${t}%`,t===100&&setTimeout(()=>{t=0},1e3)},100);let s=0;const n=document.createElement("btu-circular-progress");n.indeterminate=!1,n.progress=0,n.size="lg",n.color="teal",n.label="0/5",n.ariaValueText="0 of 5 steps completed";const p=setInterval(()=>{s=(s+1)%6,n.progress=s*20,n.label=`${s}/5`,n.ariaValueText=`${s} of 5 steps completed`,s===5&&setTimeout(()=>{s=0},3e3)},3e3),l=new MutationObserver(o=>{o.forEach(d=>{d.removedNodes.forEach(c=>{(c===e||c.contains(e))&&(clearInterval(i),clearInterval(p),l.disconnect())})})});return setTimeout(()=>{e.parentNode&&l.observe(e.parentNode,{childList:!0})},0),e.appendChild(r),e.appendChild(n),e},parameters:{docs:{description:{story:`
51
+ Animated determinate progress indicators.
52
+
53
+ Left: continuous percentage increments.
54
+
55
+ Right: step-based progress with 20% increments every 3 seconds, fractional labels, and \`aria-valuetext\` for accessibility (e.g., "3 of 5 steps completed").`}}}},y={render:()=>{let e;const t=()=>{const r=document.createElement("div"),i=document.createElement("div");i.className="flex flex-col items-center mb-4";const s=document.createElement("h3");s.className="text-lg font-semibold mb-2",s.textContent="Scroll within the container to see progress circles animate in";const n=document.createElement("button");n.textContent="Reset",n.className="px-4 py-2 bg-primary-500 text-white rounded hover:bg-primary-600",n.onclick=()=>{e.innerHTML="",e.appendChild(t())},i.appendChild(s),i.appendChild(n),r.appendChild(i);const p=document.createElement("div");p.style.height="150px",p.style.overflowY="auto",p.style.border="1px solid #e5e7eb",p.style.borderRadius="4px",p.style.padding="1rem";const l=document.createElement("div");l.className="flex flex-col items-center gap-8",l.style.minHeight="150vh";const o=document.createElement("btu-circular-progress");o.indeterminate=!1,o.progress=30,o.size="lg",o.color="primary",o.label="30%",l.appendChild(o);const d=document.createElement("div");d.className="flex flex-col items-center",d.style.marginTop="30vh";const c=document.createElement("btu-circular-progress");c.indeterminate=!1,c.progress=50,c.size="lg",c.color="teal",c.label="50%",d.appendChild(c),l.appendChild(d);const b=document.createElement("div");b.className="flex flex-col items-center",b.style.marginTop="30vh";const m=document.createElement("btu-circular-progress");m.indeterminate=!1,m.progress=75,m.size="lg",m.color="purple",m.label="75%",b.appendChild(m),l.appendChild(b);const g=document.createElement("div");g.className="flex flex-col items-center",g.style.marginTop="30vh";const a=document.createElement("btu-circular-progress");return a.indeterminate=!1,a.progress=100,a.size="lg",a.color="success",a.label="100%",g.appendChild(a),l.appendChild(g),p.appendChild(l),r.appendChild(p),r};return e=t(),e},parameters:{docs:{description:{story:'Demonstrates the viewport animation for determinate mode - progress circles animate from 0 to their target value when they become visible. Scroll within the container to see each circle animate in. Click "Reset" to restart.'}}}},C={render:()=>{const e=document.createElement("div");e.className="flex flex-col items-center gap-4";let t=0;const r=document.createElement("btu-circular-progress");r.indeterminate=!1,r.progress=0,r.size="lg",r.color="primary",r.label="0%";const i=document.createElement("div");i.className="text-sm text-gray-600",i.textContent="Status: In Progress...";const s=document.createElement("div");s.className="text-xs text-gray-500 mt-2",s.textContent="Event Log: (waiting for completion)",r.addEventListener("btu-progress-complete",()=>{i.textContent="Status: Complete! ✓",i.className="text-sm text-green-600 font-semibold",s.textContent=`Event Log: btu-progress-complete fired at ${new Date().toLocaleTimeString()}`,s.className="text-xs text-green-600 mt-2"});let n=!1;const p=setInterval(()=>{n||(t=t+1,r.progress=t,r.label=`${t}%`,t<100&&(i.textContent="Status: In Progress...",i.className="text-sm text-gray-600"),t===100&&(n=!0,setTimeout(()=>{t=0,n=!1},3e3)))},50),l=new MutationObserver(o=>{o.forEach(d=>{d.removedNodes.forEach(c=>{(c===e||c.contains(e))&&(clearInterval(p),l.disconnect())})})});return setTimeout(()=>{e.parentNode&&l.observe(e.parentNode,{childList:!0})},0),e.appendChild(r),e.appendChild(i),e.appendChild(s),e},parameters:{docs:{description:{story:"Demonstrates the btu-progress-complete event that fires when determinate progress reaches 100%. The event fires each time progress completes a cycle."}}}},E={render:()=>{const e=document.createElement("div");e.className="flex flex-col gap-8";const t=document.createElement("div");t.className="flex flex-col gap-2";const r=document.createElement("h4");r.className="text-sm font-semibold text-gray-900",r.textContent="Indeterminate with aria-label";const i=document.createElement("p");i.className="text-xs text-gray-600 mb-2",i.textContent='Screen readers announce: "Loading application data"';const s=document.createElement("btu-circular-progress");s.indeterminate=!0,s.size="md",s.color="primary",s.ariaLabel="Loading application data",t.appendChild(r),t.appendChild(i),t.appendChild(s);const n=document.createElement("div");n.className="flex flex-col gap-2";const p=document.createElement("h4");p.className="text-sm font-semibold text-gray-900",p.textContent="Determinate with custom aria-valuetext";const l=document.createElement("p");l.className="text-xs text-gray-600 mb-2",l.textContent='Screen readers announce: "File upload progress, 3 of 5 files uploaded"';const o=document.createElement("btu-circular-progress");o.indeterminate=!1,o.progress=60,o.size="md",o.color="teal",o.label="3/5",o.ariaLabel="File upload progress",o.ariaValueText="3 of 5 files uploaded",n.appendChild(p),n.appendChild(l),n.appendChild(o);const d=document.createElement("div");d.className="flex flex-col gap-2";const c=document.createElement("h4");c.className="text-sm font-semibold text-gray-900",c.textContent="With completion announcement";const b=document.createElement("p");b.className="text-xs text-gray-600 mb-2",b.textContent='Screen readers auto-announce when complete: "Download complete!"';const m=document.createElement("div");m.className="text-xs text-gray-500 mt-2",m.textContent="Announcement status: (waiting...)";let g=0;const a=document.createElement("btu-circular-progress");a.indeterminate=!1,a.progress=0,a.size="md",a.color="success",a.label="0%",a.ariaLabel="Download progress",a.completionAnnouncement="Download complete!",a.addEventListener("btu-progress-complete",()=>{m.textContent='Announcement status: "Download complete!" announced at '+new Date().toLocaleTimeString(),m.className="text-xs text-green-600 mt-2"});const w=setInterval(()=>{g<100?(g+=2,a.progress=g,a.label=`${g}%`,a.ariaValueText=`${g} percent complete`):clearInterval(w)},100);d.appendChild(c),d.appendChild(b),d.appendChild(a),d.appendChild(m);const N=new MutationObserver(S=>{S.forEach(z=>{z.removedNodes.forEach(L=>{(L===e||L.contains(e))&&(clearInterval(w),N.disconnect())})})});return setTimeout(()=>{e.parentNode&&N.observe(e.parentNode,{childList:!0})},0),e.appendChild(t),e.appendChild(n),e.appendChild(d),e},parameters:{docs:{description:{story:"\nDemonstrates accessibility best practices for screen reader users:\n\n**1. Indeterminate mode:** Set `ariaLabel` to describe what's loading.\n\n**2. Determinate mode:** Combine `ariaLabel` (what's progressing) with `ariaValueText` (human-readable progress like \"3 of 5 files uploaded\"). Set `completionAnnouncement` to automatically notify screen readers when progress reaches 100%.\n "}}}};f.parameters={...f.parameters,docs:{...f.parameters?.docs,source:{originalSource:`{
56
+ args: {},
57
+ parameters: {
58
+ docs: {
59
+ description: {
60
+ story: 'Default indeterminate spinner with primary color and small size.'
61
+ }
62
+ }
63
+ }
64
+ }`,...f.parameters?.docs?.source}}};v.parameters={...v.parameters,docs:{...v.parameters?.docs,source:{originalSource:`{
65
+ render: () => html\`<div class="flex items-center gap-4">
66
+ <btu-circular-progress .indeterminate=\${false} progress="25" size="md" label="25%"></btu-circular-progress>
67
+ <btu-circular-progress
68
+ .indeterminate=\${false}
69
+ progress="50"
70
+ size="md"
71
+ color="success"
72
+ label="50%"
73
+ ></btu-circular-progress>
74
+ <btu-circular-progress
75
+ .indeterminate=\${false}
76
+ progress="75"
77
+ size="md"
78
+ color="warning"
79
+ label="75%"
80
+ ></btu-circular-progress>
81
+ <btu-circular-progress
82
+ .indeterminate=\${false}
83
+ progress="100"
84
+ size="md"
85
+ color="success"
86
+ label="100%"
87
+ ></btu-circular-progress>
88
+ </div>\`,
89
+ parameters: {
90
+ docs: {
91
+ description: {
92
+ story: 'Determinate progress indicators at various completion levels with labels.'
93
+ }
94
+ }
95
+ }
96
+ }`,...v.parameters?.docs?.source}}};x.parameters={...x.parameters,docs:{...x.parameters?.docs,source:{originalSource:`{
97
+ render: () => {
98
+ const container = document.createElement('div');
99
+ container.className = 'flex items-center gap-8';
100
+
101
+ // First progress: continuous 0-100%
102
+ let progress = 0;
103
+ const progressEl = document.createElement('btu-circular-progress') as any;
104
+ progressEl.indeterminate = false;
105
+ progressEl.progress = 0;
106
+ progressEl.size = 'lg';
107
+ progressEl.color = 'primary';
108
+ progressEl.label = '0%';
109
+ const interval1 = setInterval(() => {
110
+ progress = (progress + 1) % 101;
111
+ progressEl.progress = progress;
112
+ progressEl.label = \`\${progress}%\`;
113
+ if (progress === 100) {
114
+ setTimeout(() => {
115
+ progress = 0;
116
+ }, 1000);
117
+ }
118
+ }, 100);
119
+
120
+ // Second progress: 20% increments every 3 seconds
121
+ let step = 0;
122
+ const progressEl2 = document.createElement('btu-circular-progress') as any;
123
+ progressEl2.indeterminate = false;
124
+ progressEl2.progress = 0;
125
+ progressEl2.size = 'lg';
126
+ progressEl2.color = 'teal';
127
+ progressEl2.label = '0/5';
128
+ progressEl2.ariaValueText = '0 of 5 steps completed';
129
+ const interval2 = setInterval(() => {
130
+ step = (step + 1) % 6;
131
+ progressEl2.progress = step * 20;
132
+ progressEl2.label = \`\${step}/5\`;
133
+ progressEl2.ariaValueText = \`\${step} of 5 steps completed\`;
134
+ if (step === 5) {
135
+ setTimeout(() => {
136
+ step = 0;
137
+ }, 3000);
138
+ }
139
+ }, 3000);
140
+
141
+ // Cleanup intervals when story unmounts
142
+ const observer = new MutationObserver(mutations => {
143
+ mutations.forEach(mutation => {
144
+ mutation.removedNodes.forEach(node => {
145
+ if (node === container || node.contains(container)) {
146
+ clearInterval(interval1);
147
+ clearInterval(interval2);
148
+ observer.disconnect();
149
+ }
150
+ });
151
+ });
152
+ });
153
+ setTimeout(() => {
154
+ if (container.parentNode) {
155
+ observer.observe(container.parentNode, {
156
+ childList: true
157
+ });
158
+ }
159
+ }, 0);
160
+ container.appendChild(progressEl);
161
+ container.appendChild(progressEl2);
162
+ return container;
163
+ },
164
+ parameters: {
165
+ docs: {
166
+ description: {
167
+ story: \`
168
+ Animated determinate progress indicators.
169
+
170
+ Left: continuous percentage increments.
171
+
172
+ Right: step-based progress with 20% increments every 3 seconds, fractional labels, and \\\`aria-valuetext\\\` for accessibility (e.g., "3 of 5 steps completed").\`
173
+ }
174
+ }
175
+ }
176
+ }`,...x.parameters?.docs?.source}}};y.parameters={...y.parameters,docs:{...y.parameters?.docs,source:{originalSource:`{
177
+ render: () => {
178
+ let rootContainer: HTMLElement;
179
+ const createProgressCircles = () => {
180
+ const container = document.createElement('div');
181
+ const header = document.createElement('div');
182
+ header.className = 'flex flex-col items-center mb-4';
183
+ const h3 = document.createElement('h3');
184
+ h3.className = 'text-lg font-semibold mb-2';
185
+ h3.textContent = 'Scroll within the container to see progress circles animate in';
186
+ const resetBtn = document.createElement('button');
187
+ resetBtn.textContent = 'Reset';
188
+ resetBtn.className = 'px-4 py-2 bg-primary-500 text-white rounded hover:bg-primary-600';
189
+ resetBtn.onclick = () => {
190
+ rootContainer.innerHTML = '';
191
+ rootContainer.appendChild(createProgressCircles());
192
+ };
193
+ header.appendChild(h3);
194
+ header.appendChild(resetBtn);
195
+ container.appendChild(header);
196
+ const scrollContainer = document.createElement('div');
197
+ scrollContainer.style.height = '150px';
198
+ scrollContainer.style.overflowY = 'auto';
199
+ scrollContainer.style.border = '1px solid #e5e7eb';
200
+ scrollContainer.style.borderRadius = '4px';
201
+ scrollContainer.style.padding = '1rem';
202
+ const wrapper = document.createElement('div');
203
+ wrapper.className = 'flex flex-col items-center gap-8';
204
+ wrapper.style.minHeight = '150vh';
205
+ const progress1 = document.createElement('btu-circular-progress') as any;
206
+ progress1.indeterminate = false;
207
+ progress1.progress = 30;
208
+ progress1.size = 'lg';
209
+ progress1.color = 'primary';
210
+ progress1.label = '30%';
211
+ wrapper.appendChild(progress1);
212
+ const div2 = document.createElement('div');
213
+ div2.className = 'flex flex-col items-center';
214
+ div2.style.marginTop = '30vh';
215
+ const progress2 = document.createElement('btu-circular-progress') as any;
216
+ progress2.indeterminate = false;
217
+ progress2.progress = 50;
218
+ progress2.size = 'lg';
219
+ progress2.color = 'teal';
220
+ progress2.label = '50%';
221
+ div2.appendChild(progress2);
222
+ wrapper.appendChild(div2);
223
+ const div3 = document.createElement('div');
224
+ div3.className = 'flex flex-col items-center';
225
+ div3.style.marginTop = '30vh';
226
+ const progress3 = document.createElement('btu-circular-progress') as any;
227
+ progress3.indeterminate = false;
228
+ progress3.progress = 75;
229
+ progress3.size = 'lg';
230
+ progress3.color = 'purple';
231
+ progress3.label = '75%';
232
+ div3.appendChild(progress3);
233
+ wrapper.appendChild(div3);
234
+ const div4 = document.createElement('div');
235
+ div4.className = 'flex flex-col items-center';
236
+ div4.style.marginTop = '30vh';
237
+ const progress4 = document.createElement('btu-circular-progress') as any;
238
+ progress4.indeterminate = false;
239
+ progress4.progress = 100;
240
+ progress4.size = 'lg';
241
+ progress4.color = 'success';
242
+ progress4.label = '100%';
243
+ div4.appendChild(progress4);
244
+ wrapper.appendChild(div4);
245
+ scrollContainer.appendChild(wrapper);
246
+ container.appendChild(scrollContainer);
247
+ return container;
248
+ };
249
+ rootContainer = createProgressCircles();
250
+ return rootContainer;
251
+ },
252
+ parameters: {
253
+ docs: {
254
+ description: {
255
+ story: 'Demonstrates the viewport animation for determinate mode - progress circles animate from 0 to their target value when they become visible. Scroll within the container to see each circle animate in. Click "Reset" to restart.'
256
+ }
257
+ }
258
+ }
259
+ }`,...y.parameters?.docs?.source}}};C.parameters={...C.parameters,docs:{...C.parameters?.docs,source:{originalSource:`{
260
+ render: () => {
261
+ const container = document.createElement('div');
262
+ container.className = 'flex flex-col items-center gap-4';
263
+ let progress = 0;
264
+ const progressEl = document.createElement('btu-circular-progress') as any;
265
+ progressEl.indeterminate = false;
266
+ progressEl.progress = 0;
267
+ progressEl.size = 'lg';
268
+ progressEl.color = 'primary';
269
+ progressEl.label = '0%';
270
+ const statusDiv = document.createElement('div');
271
+ statusDiv.className = 'text-sm text-gray-600';
272
+ statusDiv.textContent = 'Status: In Progress...';
273
+ const eventLog = document.createElement('div');
274
+ eventLog.className = 'text-xs text-gray-500 mt-2';
275
+ eventLog.textContent = 'Event Log: (waiting for completion)';
276
+ progressEl.addEventListener('btu-progress-complete', () => {
277
+ statusDiv.textContent = 'Status: Complete! ✓';
278
+ statusDiv.className = 'text-sm text-green-600 font-semibold';
279
+ eventLog.textContent = \`Event Log: btu-progress-complete fired at \${new Date().toLocaleTimeString()}\`;
280
+ eventLog.className = 'text-xs text-green-600 mt-2';
281
+ });
282
+ let isWaiting = false;
283
+ const interval = setInterval(() => {
284
+ if (isWaiting) return;
285
+ progress = progress + 1;
286
+ progressEl.progress = progress;
287
+ progressEl.label = \`\${progress}%\`;
288
+ if (progress < 100) {
289
+ statusDiv.textContent = 'Status: In Progress...';
290
+ statusDiv.className = 'text-sm text-gray-600';
291
+ }
292
+ if (progress === 100) {
293
+ isWaiting = true;
294
+ setTimeout(() => {
295
+ progress = 0;
296
+ isWaiting = false;
297
+ }, 3000);
298
+ }
299
+ }, 50);
300
+
301
+ // Cleanup interval when story unmounts
302
+ const observer = new MutationObserver(mutations => {
303
+ mutations.forEach(mutation => {
304
+ mutation.removedNodes.forEach(node => {
305
+ if (node === container || node.contains(container)) {
306
+ clearInterval(interval);
307
+ observer.disconnect();
308
+ }
309
+ });
310
+ });
311
+ });
312
+ setTimeout(() => {
313
+ if (container.parentNode) {
314
+ observer.observe(container.parentNode, {
315
+ childList: true
316
+ });
317
+ }
318
+ }, 0);
319
+ container.appendChild(progressEl);
320
+ container.appendChild(statusDiv);
321
+ container.appendChild(eventLog);
322
+ return container;
323
+ },
324
+ parameters: {
325
+ docs: {
326
+ description: {
327
+ story: 'Demonstrates the btu-progress-complete event that fires when determinate progress reaches 100%. The event fires each time progress completes a cycle.'
328
+ }
329
+ }
330
+ }
331
+ }`,...C.parameters?.docs?.source}}};E.parameters={...E.parameters,docs:{...E.parameters?.docs,source:{originalSource:`{
332
+ render: () => {
333
+ const container = document.createElement('div');
334
+ container.className = 'flex flex-col gap-8';
335
+
336
+ // Example 1: Indeterminate with aria-label
337
+ const section1 = document.createElement('div');
338
+ section1.className = 'flex flex-col gap-2';
339
+ const heading1 = document.createElement('h4');
340
+ heading1.className = 'text-sm font-semibold text-gray-900';
341
+ heading1.textContent = 'Indeterminate with aria-label';
342
+ const desc1 = document.createElement('p');
343
+ desc1.className = 'text-xs text-gray-600 mb-2';
344
+ desc1.textContent = 'Screen readers announce: "Loading application data"';
345
+ const progress1 = document.createElement('btu-circular-progress') as any;
346
+ progress1.indeterminate = true;
347
+ progress1.size = 'md';
348
+ progress1.color = 'primary';
349
+ progress1.ariaLabel = 'Loading application data';
350
+ section1.appendChild(heading1);
351
+ section1.appendChild(desc1);
352
+ section1.appendChild(progress1);
353
+
354
+ // Example 2: Determinate with aria-valuetext
355
+ const section2 = document.createElement('div');
356
+ section2.className = 'flex flex-col gap-2';
357
+ const heading2 = document.createElement('h4');
358
+ heading2.className = 'text-sm font-semibold text-gray-900';
359
+ heading2.textContent = 'Determinate with custom aria-valuetext';
360
+ const desc2 = document.createElement('p');
361
+ desc2.className = 'text-xs text-gray-600 mb-2';
362
+ desc2.textContent = 'Screen readers announce: "File upload progress, 3 of 5 files uploaded"';
363
+ const progress2 = document.createElement('btu-circular-progress') as any;
364
+ progress2.indeterminate = false;
365
+ progress2.progress = 60;
366
+ progress2.size = 'md';
367
+ progress2.color = 'teal';
368
+ progress2.label = '3/5';
369
+ progress2.ariaLabel = 'File upload progress';
370
+ progress2.ariaValueText = '3 of 5 files uploaded';
371
+ section2.appendChild(heading2);
372
+ section2.appendChild(desc2);
373
+ section2.appendChild(progress2);
374
+
375
+ // Example 3: With completion announcement
376
+ const section3 = document.createElement('div');
377
+ section3.className = 'flex flex-col gap-2';
378
+ const heading3 = document.createElement('h4');
379
+ heading3.className = 'text-sm font-semibold text-gray-900';
380
+ heading3.textContent = 'With completion announcement';
381
+ const desc3 = document.createElement('p');
382
+ desc3.className = 'text-xs text-gray-600 mb-2';
383
+ desc3.textContent = 'Screen readers auto-announce when complete: "Download complete!"';
384
+ const announceLog = document.createElement('div');
385
+ announceLog.className = 'text-xs text-gray-500 mt-2';
386
+ announceLog.textContent = 'Announcement status: (waiting...)';
387
+ let progress3Value = 0;
388
+ const progress3 = document.createElement('btu-circular-progress') as any;
389
+ progress3.indeterminate = false;
390
+ progress3.progress = 0;
391
+ progress3.size = 'md';
392
+ progress3.color = 'success';
393
+ progress3.label = '0%';
394
+ progress3.ariaLabel = 'Download progress';
395
+ progress3.completionAnnouncement = 'Download complete!';
396
+ progress3.addEventListener('btu-progress-complete', () => {
397
+ announceLog.textContent = 'Announcement status: "Download complete!" announced at ' + new Date().toLocaleTimeString();
398
+ announceLog.className = 'text-xs text-green-600 mt-2';
399
+ });
400
+ const interval3 = setInterval(() => {
401
+ if (progress3Value < 100) {
402
+ progress3Value += 2;
403
+ progress3.progress = progress3Value;
404
+ progress3.label = \`\${progress3Value}%\`;
405
+ progress3.ariaValueText = \`\${progress3Value} percent complete\`;
406
+ } else {
407
+ clearInterval(interval3);
408
+ }
409
+ }, 100);
410
+ section3.appendChild(heading3);
411
+ section3.appendChild(desc3);
412
+ section3.appendChild(progress3);
413
+ section3.appendChild(announceLog);
414
+
415
+ // Cleanup interval when story unmounts
416
+ const observer = new MutationObserver(mutations => {
417
+ mutations.forEach(mutation => {
418
+ mutation.removedNodes.forEach(node => {
419
+ if (node === container || node.contains(container)) {
420
+ clearInterval(interval3);
421
+ observer.disconnect();
422
+ }
423
+ });
424
+ });
425
+ });
426
+ setTimeout(() => {
427
+ if (container.parentNode) {
428
+ observer.observe(container.parentNode, {
429
+ childList: true
430
+ });
431
+ }
432
+ }, 0);
433
+ container.appendChild(section1);
434
+ container.appendChild(section2);
435
+ container.appendChild(section3);
436
+ return container;
437
+ },
438
+ parameters: {
439
+ docs: {
440
+ description: {
441
+ story: \`
442
+ Demonstrates accessibility best practices for screen reader users:
443
+
444
+ **1. Indeterminate mode:** Set \\\`ariaLabel\\\` to describe what's loading.
445
+
446
+ **2. Determinate mode:** Combine \\\`ariaLabel\\\` (what's progressing) with \\\`ariaValueText\\\` (human-readable progress like "3 of 5 files uploaded"). Set \\\`completionAnnouncement\\\` to automatically notify screen readers when progress reaches 100%.
447
+ \`
448
+ }
449
+ }
450
+ }
451
+ }`,...E.parameters?.docs?.source}}};const P=["Default","DeterminateProgress","AnimatedProgress","InitialAnimation","CompletionEvent","Accessibility"];export{E as Accessibility,x as AnimatedProgress,C as CompletionEvent,f as Default,v as DeterminateProgress,y as InitialAnimation,P as __namedExportsOrder,k as default};