aural-ui 4.0.1 → 4.1.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 (174) hide show
  1. package/dist/components/aspect-ratio/AspectRatio.stories.tsx +290 -1228
  2. package/dist/components/avatar/Avatar.stories.tsx +219 -235
  3. package/dist/components/badge/Badge.stories.tsx +379 -116
  4. package/dist/components/banner/Banner.stories.tsx +445 -391
  5. package/dist/components/breadcrumb/Breadcrumb.stories.tsx +453 -199
  6. package/dist/components/button/Button.stories.tsx +585 -230
  7. package/dist/components/card/Card.stories.tsx +619 -301
  8. package/dist/components/char-count/CharCount.stories.tsx +350 -248
  9. package/dist/components/checkbox/Checkbox.stories.tsx +309 -167
  10. package/dist/components/chip/Chip.stories.tsx +362 -168
  11. package/dist/components/circular-loader/CircularLoader.stories.tsx +221 -636
  12. package/dist/components/clamp-lines/ClampLines.stories.tsx +246 -117
  13. package/dist/components/collapsible/Collapsible.stories.tsx +391 -252
  14. package/dist/components/command/Command.stories.tsx +530 -867
  15. package/dist/components/dialog/Dialog.stories.tsx +501 -950
  16. package/dist/components/divider/Divider.stories.tsx +264 -527
  17. package/dist/components/dot-loader/DotLoader.stories.tsx +256 -257
  18. package/dist/components/drawer/Drawer.stories.tsx +659 -1023
  19. package/dist/components/dropdown/Dropdown.stories.tsx +643 -1028
  20. package/dist/components/form/Form.stories.tsx +560 -274
  21. package/dist/components/helper-text/HelperText.stories.tsx +199 -200
  22. package/dist/components/hover-card/HoverCard.stories.tsx +318 -1254
  23. package/dist/components/icon-button/IconButton.stories.tsx +837 -194
  24. package/dist/components/if-else/if-else.stories.tsx +370 -83
  25. package/dist/components/input/Input.stories.tsx +436 -368
  26. package/dist/components/label/Label.stories.tsx +156 -154
  27. package/dist/components/list/List.stories.tsx +484 -835
  28. package/dist/components/marquee/Marquee.stories.tsx +356 -712
  29. package/dist/components/otp-inputs/OtpInputs.stories.tsx +352 -422
  30. package/dist/components/overlay/Overlay.stories.tsx +452 -824
  31. package/dist/components/pagination/Pagination.stories.tsx +721 -210
  32. package/dist/components/popover/Popover.stories.tsx +481 -896
  33. package/dist/components/radio/Radio.stories.tsx +432 -124
  34. package/dist/components/resizable/Resizable.stories.tsx +495 -799
  35. package/dist/components/scroll-area/ScrollArea.stories.tsx +383 -1059
  36. package/dist/components/search/Search.stories.tsx +312 -595
  37. package/dist/components/select/Select.stories.tsx +684 -789
  38. package/dist/components/sheet/Sheet.stories.tsx +671 -950
  39. package/dist/components/skelton/Skelton.stories.tsx +230 -764
  40. package/dist/components/slider/Slider.stories.tsx +383 -760
  41. package/dist/components/stepper/Stepper.stories.tsx +371 -514
  42. package/dist/components/switch/Switch.stories.tsx +461 -208
  43. package/dist/components/switch-case/SwitchCase.stories.tsx +367 -188
  44. package/dist/components/table/Table.stories.tsx +770 -916
  45. package/dist/components/tabs/Tabs.stories.tsx +458 -1455
  46. package/dist/components/tag/Tag.stories.tsx +714 -542
  47. package/dist/components/textarea/TextArea.stories.tsx +621 -562
  48. package/dist/components/thumbnail-tags/ThumbnailTags.stories.tsx +228 -154
  49. package/dist/components/toast/Toast.stories.tsx +452 -1339
  50. package/dist/components/toggle/Toggle.stories.tsx +488 -931
  51. package/dist/components/tooltip/Tooltip.stories.tsx +344 -1388
  52. package/dist/components/typography/Typography.stories.tsx +406 -89
  53. package/dist/hooks/use-change-state/UseChangeState.stories.tsx +309 -606
  54. package/dist/hooks/use-previous/UsePrevious.stories.tsx +367 -917
  55. package/dist/hooks/use-standalone-pagination/UseStandalonePagination.stories.tsx +639 -867
  56. package/dist/icons/Icons.stories.tsx +0 -12
  57. package/dist/icons/ai-avatar-icon/AiAvatarIcon.stories.tsx +223 -1060
  58. package/dist/icons/alert-icon/AlertIcon.stories.tsx +106 -968
  59. package/dist/icons/all-icons.tsx +37 -16
  60. package/dist/icons/angle-down-icon/AngleDownIcon.stories.tsx +137 -1010
  61. package/dist/icons/apple-logo-icon/AppleLogoIcon.stories.tsx +145 -935
  62. package/dist/icons/arrow-box-left-icon/ArrowBoxLeftIcon.stories.tsx +132 -1046
  63. package/dist/icons/arrow-corner-up-left-icon/ArrowCornerUpLeftIcon.stories.tsx +134 -986
  64. package/dist/icons/arrow-corner-up-right-icon/ArrowCornerUpRightIcon.stories.tsx +135 -1028
  65. package/dist/icons/arrow-left-icon/ArrowLeftIcon.stories.tsx +133 -971
  66. package/dist/icons/arrow-right-icon/ArrowRightIcon.stories.tsx +145 -1123
  67. package/dist/icons/arrow-right-up-icon/ArrowRightUpIcon.stories.tsx +143 -1252
  68. package/dist/icons/art-board-icon/ArtBoardIcon.stories.tsx +123 -632
  69. package/dist/icons/audio-bar-icon/AudioBarIcon.stories.tsx +141 -1223
  70. package/dist/icons/backward-ten-seconds-icon/BackwardTenSecondsIcon.stories.tsx +164 -1018
  71. package/dist/icons/bubble-check-icon/BubbleCheckIcon.stories.tsx +121 -1236
  72. package/dist/icons/bubble-crossed-icon/BubbleCrossedIcon.stories.tsx +121 -1213
  73. package/dist/icons/bubble-sparkle-icon/BubbleSparkleIcon.stories.tsx +116 -893
  74. package/dist/icons/camera-icon/CameraIcon.stories.tsx +109 -1254
  75. package/dist/icons/capital-a-letter-icon/CapitalALetterIcon.stories.tsx +114 -975
  76. package/dist/icons/chevron-double-left-icon/ChevronDoubleLeftIcon.stories.tsx +157 -994
  77. package/dist/icons/chevron-double-right-icon/ChevronDoubleRightIcon.stories.tsx +160 -992
  78. package/dist/icons/chevron-down-icon/ChevronDownIcon.stories.tsx +140 -970
  79. package/dist/icons/chevron-left-icon/ChevronLeftIcon.stories.tsx +126 -993
  80. package/dist/icons/chevron-right-icon/ChevronRightIcon.stories.tsx +144 -987
  81. package/dist/icons/chevron-up-icon/ChevronUpIcon.stories.tsx +141 -1007
  82. package/dist/icons/circle-tick-icon/CircleTickIcon.stories.tsx +147 -1187
  83. package/dist/icons/circular-play-icon/CircularPlayIcon.stories.tsx +110 -476
  84. package/dist/icons/coin-icon/CoinIcon.stories.tsx +120 -1364
  85. package/dist/icons/coin-toons-icon/CoinToonsIcon.stories.tsx +113 -1360
  86. package/dist/icons/column-wide-add-icon/ColumnWideAddIcon.stories.tsx +111 -942
  87. package/dist/icons/command-icon/CommandIcon.stories.tsx +124 -1087
  88. package/dist/icons/copy-icon/CopyIcon.stories.tsx +119 -996
  89. package/dist/icons/cross-circle-icon/CrossCircleIcon.stories.tsx +144 -1046
  90. package/dist/icons/cross-icon/CrossIcon.stories.tsx +136 -999
  91. package/dist/icons/download-icon/DownloadIcon.stories.tsx +123 -857
  92. package/dist/icons/edit-big-icon/EditBigIcon.stories.tsx +121 -1080
  93. package/dist/icons/email-icon/EmailIcon.stories.tsx +112 -979
  94. package/dist/icons/expand-icon/ExpandIcon.stories.tsx +109 -1146
  95. package/dist/icons/eye-close-icon/EyeCloseIcon.stories.tsx +141 -1068
  96. package/dist/icons/eye-open-icon/EyeOpenIcon.stories.tsx +140 -1081
  97. package/dist/icons/feature-shine-icon/FeatureShineIcon.stories.tsx +124 -1050
  98. package/dist/icons/file-chart-icon/FileChartIcon.stories.tsx +123 -1091
  99. package/dist/icons/file-text-icon/FileTextIcon.stories.tsx +122 -633
  100. package/dist/icons/filter-bar-row-icon/FilterBarRowIcon.stories.tsx +116 -1087
  101. package/dist/icons/forward-ten-seconds-icon/ForwardTenSecondsIcon.stories.tsx +166 -1020
  102. package/dist/icons/git-branch-icon/GitBranchIcon.stories.tsx +112 -1182
  103. package/dist/icons/git-fork-icon/GitForkIcon.stories.tsx +112 -1155
  104. package/dist/icons/globe-icon/GlobeIcon.stories.tsx +127 -325
  105. package/dist/icons/google-logo-icon/GoogleLogoIcon.stories.tsx +142 -985
  106. package/dist/icons/grip-vertical-icon/GripVerticalIcon.stories.tsx +116 -1217
  107. package/dist/icons/head-icon/HeadIcon.stories.tsx +108 -953
  108. package/dist/icons/heart-icon/HeartIcon.stories.tsx +117 -1060
  109. package/dist/icons/image-avatar-sparkle-icon/ImageAvatarSparkleIcon.stories.tsx +116 -716
  110. package/dist/icons/image-icon/ImageIcon.stories.tsx +102 -1164
  111. package/dist/icons/import-folder-icon/ImportFolderIcon.stories.tsx +108 -1233
  112. package/dist/icons/import-left-arrow-folder-icon/ImportLeftArrowFolderIcon.stories.tsx +133 -1289
  113. package/dist/icons/indian-flag-icon/IndianFlagIcon.stories.tsx +155 -1012
  114. package/dist/icons/instagram-icon/InstagramIcon.stories.tsx +158 -1438
  115. package/dist/icons/layout-column-icon/LayoutColumnIcon.stories.tsx +121 -1011
  116. package/dist/icons/layout-left-icon/LayoutLeftIcon.stories.tsx +116 -981
  117. package/dist/icons/layout-right-icon/LayoutRightIcon.stories.tsx +116 -979
  118. package/dist/icons/light-bulb-simple-icon/LightBulbSimpleIcon.stories.tsx +105 -1252
  119. package/dist/icons/linked-in-icon/LinkedInIcon.stories.tsx +151 -1554
  120. package/dist/icons/magic-book-icon/MagicBookIcon.stories.tsx +107 -1227
  121. package/dist/icons/magic-edit-icon/MagicEditIcon.stories.tsx +116 -707
  122. package/dist/icons/maintenance-icon/MaintenanceIcon.stories.tsx +119 -1226
  123. package/dist/icons/message-icon/MessageIcon.stories.tsx +111 -557
  124. package/dist/icons/minimize-icon/MinimizeIcon.stories.tsx +112 -1198
  125. package/dist/icons/moon-icon/MoonIcon.stories.tsx +117 -557
  126. package/dist/icons/move-horizontal-icon/MoveHorizontalIcon.stories.tsx +106 -1235
  127. package/dist/icons/move-vertical-icon/MoveVerticalIcon.stories.tsx +112 -1185
  128. package/dist/icons/musical-note-icon/MusicalNoteIcon.stories.tsx +116 -1012
  129. package/dist/icons/notepad-icon/NotepadIcon.stories.tsx +108 -1137
  130. package/dist/icons/notes-icon/NotesIcon.stories.tsx +116 -1138
  131. package/dist/icons/page-search-icon/PageSearchIcon.stories.tsx +106 -1146
  132. package/dist/icons/page-text-icon/PageTextIcon.stories.tsx +119 -719
  133. package/dist/icons/paint-roll-icon/PaintRollIcon.stories.tsx +110 -999
  134. package/dist/icons/paper-plane-icon/PaperPlaneIcon.stories.tsx +109 -912
  135. package/dist/icons/pause-icon/PauseIcon.stories.tsx +110 -1041
  136. package/dist/icons/pencil-icon/PencilIcon.stories.tsx +112 -1109
  137. package/dist/icons/phone-icon/PhoneIcon.stories.tsx +112 -1023
  138. package/dist/icons/plus-icon/PlusIcon.stories.tsx +103 -1132
  139. package/dist/icons/pocket-studio-icon/PocketStudioIcon.stories.tsx +104 -870
  140. package/dist/icons/scroll-down-icon/ScrollDownIcon.stories.tsx +99 -476
  141. package/dist/icons/search-icon/SearchIcon.stories.tsx +108 -1161
  142. package/dist/icons/setting-icon/SettingIcon.stories.tsx +104 -1009
  143. package/dist/icons/share-icon/ShareIcon.stories.tsx +117 -1064
  144. package/dist/icons/shield-icon/ShieldIcon.stories.tsx +114 -974
  145. package/dist/icons/site-logo-icon/SiteLogoIcon.stories.tsx +134 -1160
  146. package/dist/icons/skip-backward-icon/SkipBackwardIcon.stories.tsx +169 -1017
  147. package/dist/icons/skip-forward-icon/SkipForwardIcon.stories.tsx +161 -1016
  148. package/dist/icons/sparkles-soft-icon/SparklesSoftIcon.stories.tsx +102 -1001
  149. package/dist/icons/spinner-gradient-icon/SpinnerGradientIcon.stories.tsx +155 -593
  150. package/dist/icons/spinner-solid-icon/SpinnerSolidIcon.stories.tsx +155 -608
  151. package/dist/icons/spinner-solid-neutral-icon/SpinnerSolidINeutralcon.stories.tsx +142 -712
  152. package/dist/icons/star-icon/StarIcon.stories.tsx +120 -946
  153. package/dist/icons/store-coin-icon/StoreCoinIcon.stories.tsx +109 -1013
  154. package/dist/icons/suggestion-icon/SuggestionIcon.stories.tsx +113 -891
  155. package/dist/icons/sun-icon/SunIcon.stories.tsx +117 -864
  156. package/dist/icons/text-color-icon/TextColorIcon.stories.tsx +113 -989
  157. package/dist/icons/text-indicator-icon/TextIndicatorIcon.stories.tsx +120 -1027
  158. package/dist/icons/threads-icon/ThreadsIcon.stories.tsx +153 -1476
  159. package/dist/icons/tick-circle-icon/TickCircleIcon.stories.tsx +143 -1187
  160. package/dist/icons/tick-icon/TickIcon.stories.tsx +142 -1322
  161. package/dist/icons/trash-icon/TrashIcon.stories.tsx +105 -970
  162. package/dist/icons/twitter-x-icon/TwitterXIcon.stories.tsx +154 -1457
  163. package/dist/icons/upload-icon/UploadIcon.stories.tsx +112 -930
  164. package/dist/icons/vertical-menu-icon/VerticalMenuIcon.stories.tsx +115 -1019
  165. package/dist/icons/video-play-list-icon/VideoPlaylistIcon.stories.tsx +122 -1092
  166. package/dist/icons/voice-playing-icon/VoicePlayingIcon.stories.tsx +120 -1401
  167. package/dist/icons/volume-full-icon/VolumeFullIcon.stories.tsx +107 -1212
  168. package/dist/icons/volume-half-icon/VolumeHalfIcon.stories.tsx +109 -1122
  169. package/dist/icons/volume-off-icon/VolumeOffIcon.stories.tsx +112 -1124
  170. package/dist/icons/warning-icon/WarningIcon.stories.tsx +119 -1083
  171. package/dist/icons/youtube-icon/YoutubeIcon.stories.tsx +158 -983
  172. package/dist/index.cjs +1 -1
  173. package/dist/index.js +1 -1
  174. package/package.json +1 -1
@@ -1,7 +1,9 @@
1
- import React, { useState } from "react"
1
+ import React from "react"
2
2
  import { Button } from "@components/button"
3
3
  import type { Meta, StoryObj } from "@storybook/react-vite"
4
4
 
5
+ import { AuralComponentDocsPage } from "src/ui/story-spec/components/component-story-docs-page"
6
+
5
7
  import CircularLoader from "."
6
8
 
7
9
  const meta: Meta<typeof CircularLoader> = {
@@ -9,107 +11,32 @@ const meta: Meta<typeof CircularLoader> = {
9
11
  component: CircularLoader,
10
12
  parameters: {
11
13
  layout: "centered",
12
- backgrounds: {
13
- default: "dark",
14
- values: [
15
- { name: "dark", value: "#0a0a0a" },
16
- { name: "darker", value: "#000000" },
17
- { name: "light", value: "#ffffff" },
18
- ],
19
- },
20
14
  docs: {
21
15
  description: {
22
- component: `
23
- # CircularLoader Component
24
-
25
- An accessible circular loading spinner component with multiple variants, customizable sizing, and comprehensive screen reader support. Built with proper ARIA attributes and semantic HTML.
26
-
27
- ## Features
28
-
29
- - **Multiple Variants**: Three distinct spinner designs (gradient, solid, neutral)
30
- - **Size Options**: Four predefined sizes (sm, md, lg, xl) for different contexts
31
- - **Accessibility First**: Full ARIA support with screen reader compatibility
32
- - **Customizable Text**: Optional visual text with separate screen reader messages
33
- - **Live Regions**: Configurable aria-live announcements for dynamic updates
34
- - **Flexible Styling**: Custom classes for root, loader, and text elements
35
- - **Semantic HTML**: Proper role and status indicators
36
-
37
- ## Accessibility Features
38
-
39
- - **ARIA Labels**: Automatic labeling for screen readers
40
- - **Live Regions**: Announces loading state changes
41
- - **Screen Reader Text**: Hidden text for assistive technologies
42
- - **Keyboard Safe**: Non-focusable decorative elements
43
- - **Status Role**: Proper semantic meaning for loading states
44
-
45
- ## Usage Examples
46
-
47
- ### Basic Loading
48
- \`\`\`tsx
49
- import CircularLoader from '@/components/circular-loader'
50
-
51
- // Simple loading with visual text
52
- <CircularLoader text="Loading..." />
53
-
54
- // Screen reader only (no visual text)
55
- <CircularLoader aria-label="Loading user data" />
56
- \`\`\`
57
-
58
- ### Different Variants
59
- \`\`\`tsx
60
- // Gradient spinner (default)
61
- <CircularLoader variant="v1" text="Loading..." />
62
-
63
- // Solid spinner
64
- <CircularLoader variant="v2" text="Processing..." />
65
-
66
- // Neutral spinner
67
- <CircularLoader variant="v3" text="Please wait..." />
68
- \`\`\`
69
-
70
- ### Size Variations
71
- \`\`\`tsx
72
- // Small loader for buttons
73
- <CircularLoader size="sm" text="Save" />
74
-
75
- // Large loader for page loading
76
- <CircularLoader size="xl" text="Loading application..." />
77
- \`\`\`
78
-
79
- ### Advanced Accessibility
80
- \`\`\`tsx
81
- // Custom loading message for screen readers
82
- <CircularLoader
83
- text="Submitting form..."
84
- loadingMessage="Your form is being processed, please wait"
85
- aria-live="assertive"
86
- />
87
-
88
- // Programmatic control
89
- <CircularLoader
90
- id="form-loader"
91
- aria-label="Saving changes"
92
- aria-live="polite"
93
- />
94
- \`\`\`
95
-
96
- ### Custom Styling
97
- \`\`\`tsx
98
- <CircularLoader
99
- variant="v2"
100
- size="lg"
101
- text="Loading..."
102
- classes={{
103
- root: "my-8",
104
- loader: "text-blue-500",
105
- text: "text-gray-600 font-medium"
106
- }}
107
- />
108
- \`\`\`
109
- `,
16
+ component:
17
+ "An accessible circular loading spinner with three visual variants (gradient, solid, neutral), four sizes (sm/md/lg/xl), optional visible text, and full ARIA support including aria-live regions and screen-reader-only messages.",
110
18
  },
19
+ page: () => (
20
+ <AuralComponentDocsPage
21
+ features={[
22
+ {
23
+ title: "3 Visual Variants",
24
+ description: "Gradient, solid, neutral",
25
+ },
26
+ {
27
+ title: "Size Scale",
28
+ description: "sm to xl scale",
29
+ },
30
+ {
31
+ title: "ARIA Support",
32
+ description: "Live regions built in",
33
+ },
34
+ ]}
35
+ />
36
+ ),
111
37
  },
112
38
  },
39
+ tags: ["autodocs"],
113
40
  argTypes: {
114
41
  variant: {
115
42
  control: { type: "select" },
@@ -148,610 +75,268 @@ import CircularLoader from '@/components/circular-loader'
148
75
  description: "Custom classes for different parts of the component",
149
76
  },
150
77
  },
151
- tags: ["autodocs"],
152
78
  }
153
79
 
154
80
  export default meta
155
81
  type Story = StoryObj<typeof CircularLoader>
156
82
 
157
- // Story parameters for consistent dark theme
158
- const storyParameters = {
159
- backgrounds: {
160
- default: "dark",
161
- values: [
162
- { name: "dark", value: "#0a0a0a" },
163
- { name: "darker", value: "#000000" },
164
- ],
165
- },
83
+ const loaderTextClass = "text-fm-primary"
84
+
85
+ function StoryCircularLoader(
86
+ props: React.ComponentProps<typeof CircularLoader>
87
+ ) {
88
+ return (
89
+ <CircularLoader
90
+ {...props}
91
+ classes={{
92
+ ...props.classes,
93
+ text: [loaderTextClass, props.classes?.text].filter(Boolean).join(" "),
94
+ }}
95
+ />
96
+ )
166
97
  }
167
98
 
168
- // 1. Basic Examples
169
- export const Default: Story = {
99
+ // ─── 1. Playground ────────────────────────────────────────────────────────────
100
+
101
+ export const Playground: Story = {
170
102
  args: {
171
- text: "Loading...",
172
103
  variant: "v1",
173
104
  size: "md",
105
+ text: "Loading...",
106
+ "aria-label": "Loading",
107
+ "aria-live": "polite",
108
+ loadingMessage: "",
174
109
  },
175
- parameters: storyParameters,
176
110
  render: (args) => (
177
- <div className="bg-fm-surface-primary flex h-32 items-center justify-center rounded-lg p-8">
178
- <CircularLoader {...args} />
179
- </div>
180
- ),
181
- }
182
-
183
- // 2. Variant Showcase
184
- export const Variants: Story = {
185
- parameters: {
186
- ...storyParameters,
187
- docs: {
188
- description: {
189
- story:
190
- "Different visual variants of the CircularLoader component with consistent accessibility features.",
191
- },
192
- },
193
- },
194
- render: () => (
195
- <div className="bg-fm-surface-primary space-y-8 rounded-lg p-8">
196
- <div className="text-center">
197
- <h3 className="text-fm-primary mb-4 text-xl font-bold">
198
- Spinner Variants
199
- </h3>
200
- <p className="text-fm-secondary text-sm">
201
- Three distinct visual styles with full accessibility support
202
- </p>
111
+ <div className="w-full max-w-sm space-y-4">
112
+ <div className="flex justify-center py-6">
113
+ <StoryCircularLoader {...args} />
203
114
  </div>
204
-
205
- <div className="grid grid-cols-1 gap-8 md:grid-cols-3">
206
- <div className="text-center">
207
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-32 items-center justify-center rounded-lg border">
208
- <CircularLoader variant="v1" text="Gradient" size="lg" />
209
- </div>
210
- <div className="space-y-1">
211
- <div className="text-fm-primary font-medium">Variant V1</div>
212
- <div className="text-fm-secondary text-xs">
213
- Gradient spinner with smooth transitions
214
- </div>
215
- </div>
216
- </div>
217
-
218
- <div className="text-center">
219
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-32 items-center justify-center rounded-lg border">
220
- <CircularLoader variant="v2" text="Solid" size="lg" />
221
- </div>
222
- <div className="space-y-1">
223
- <div className="text-fm-primary font-medium">Variant V2</div>
224
- <div className="text-fm-secondary text-xs">
225
- Solid spinner with consistent theming
226
- </div>
227
- </div>
228
- </div>
229
-
230
- <div className="text-center">
231
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-32 items-center justify-center rounded-lg border">
232
- <CircularLoader variant="v3" text="Neutral" size="lg" />
233
- </div>
234
- <div className="space-y-1">
235
- <div className="text-fm-primary font-medium">Variant V3</div>
236
- <div className="text-fm-secondary text-xs">
237
- Neutral spinner for any theme
238
- </div>
239
- </div>
240
- </div>
115
+ <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border px-4 py-3">
116
+ <code className="text-fm-secondary text-fm-md leading-fm-md font-(--font-fm-mono)">
117
+ {`<CircularLoader variant="${args.variant}" size="${args.size}"${args.text ? ` text="${args.text}"` : ""} />`}
118
+ </code>
241
119
  </div>
242
120
  </div>
243
121
  ),
244
- }
245
-
246
- // 3. Size Variations
247
- export const Sizes: Story = {
248
122
  parameters: {
249
- ...storyParameters,
250
123
  docs: {
251
124
  description: {
252
125
  story:
253
- "Different sizes of the CircularLoader for various use cases from small inline loaders to large page loaders.",
126
+ "Adjust variant, size, text, and accessibility props using the controls panel in the sidebar.",
254
127
  },
255
128
  },
256
129
  },
257
- render: () => (
258
- <div className="bg-fm-surface-primary space-y-8 rounded-lg p-8">
259
- <div className="text-center">
260
- <h3 className="text-fm-primary mb-4 text-xl font-bold">
261
- Size Variations
262
- </h3>
263
- <p className="text-fm-secondary text-sm">
264
- Four predefined sizes for different contexts and use cases
265
- </p>
266
- </div>
267
-
268
- <div className="grid grid-cols-2 gap-6 md:grid-cols-4">
269
- <div className="text-center">
270
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-24 items-center justify-center rounded-lg border">
271
- <CircularLoader size="sm" text="Small" />
272
- </div>
273
- <div className="space-y-1">
274
- <div className="text-fm-primary font-medium">Small</div>
275
- <div className="text-fm-secondary text-xs">
276
- 16×16px - Inline elements
277
- </div>
278
- </div>
279
- </div>
280
-
281
- <div className="text-center">
282
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-24 items-center justify-center rounded-lg border">
283
- <CircularLoader size="md" text="Medium" />
284
- </div>
285
- <div className="space-y-1">
286
- <div className="text-fm-primary font-medium">Medium</div>
287
- <div className="text-fm-secondary text-xs">
288
- 24×24px - Default size
289
- </div>
290
- </div>
291
- </div>
130
+ }
292
131
 
293
- <div className="text-center">
294
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-24 items-center justify-center rounded-lg border">
295
- <CircularLoader size="lg" text="Large" />
296
- </div>
297
- <div className="space-y-1">
298
- <div className="text-fm-primary font-medium">Large</div>
299
- <div className="text-fm-secondary text-xs">
300
- 32×32px - Prominent loading
301
- </div>
302
- </div>
303
- </div>
132
+ // ─── 2. AllVariants ───────────────────────────────────────────────────────────
304
133
 
305
- <div className="text-center">
306
- <div className="border-fm-divider-secondary bg-fm-surface-secondary mb-4 flex h-24 items-center justify-center rounded-lg border">
307
- <CircularLoader size="xl" text="Extra Large" />
308
- </div>
309
- <div className="space-y-1">
310
- <div className="text-fm-primary font-medium">Extra Large</div>
311
- <div className="text-fm-secondary text-xs">
312
- 48×48px - Page loading
313
- </div>
134
+ export const AllVariants: Story = {
135
+ render: () => (
136
+ <div className="space-y-8">
137
+ <div className="space-y-4">
138
+ <h4 className="text-fm-secondary font-fm-text text-fm-md leading-fm-md font-medium">
139
+ Spinner Variants
140
+ </h4>
141
+ <div className="flex flex-wrap items-end gap-8">
142
+ <div className="space-y-2 text-center">
143
+ <StoryCircularLoader variant="v1" size="lg" text="Gradient" />
144
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
145
+ V1 — Gradient
146
+ </p>
147
+ </div>
148
+ <div className="space-y-2 text-center">
149
+ <StoryCircularLoader variant="v2" size="lg" text="Solid" />
150
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
151
+ V2 — Solid
152
+ </p>
153
+ </div>
154
+ <div className="space-y-2 text-center">
155
+ <StoryCircularLoader variant="v3" size="lg" text="Neutral" />
156
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
157
+ V3 — Neutral
158
+ </p>
314
159
  </div>
315
160
  </div>
316
161
  </div>
317
162
  </div>
318
163
  ),
319
- }
320
-
321
- // 4. Accessibility Features
322
- export const AccessibilityFeatures: Story = {
323
164
  parameters: {
324
- ...storyParameters,
325
165
  docs: {
326
166
  description: {
327
167
  story:
328
- "Comprehensive accessibility features including ARIA labels, live regions, and screen reader support.",
168
+ "Three distinct spinner designs gradient (v1), solid branded (v2), and neutral (v3) — shown at large size for easy comparison.",
329
169
  },
330
170
  },
331
171
  },
332
- render: () => (
333
- <div className="bg-fm-surface-primary space-y-8 rounded-lg p-8">
334
- <div className="text-center">
335
- <h3 className="text-fm-primary mb-4 text-xl font-bold">
336
- Accessibility Features
337
- </h3>
338
- <p className="text-fm-secondary text-sm">
339
- Built with comprehensive screen reader support and ARIA attributes
340
- </p>
341
- </div>
342
-
343
- <div className="grid grid-cols-1 gap-6 md:grid-cols-2">
344
- <div className="space-y-6">
345
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-6">
346
- <h4 className="text-fm-primary mb-4 text-lg font-semibold">
347
- Visual + Screen Reader
348
- </h4>
349
- <div className="mb-4 flex items-center justify-center">
350
- <CircularLoader text="Loading data..." size="lg" />
351
- </div>
352
- <div className="text-fm-secondary text-sm">
353
- Shows visible text and provides the same message to screen readers
354
- </div>
355
- </div>
356
-
357
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-6">
358
- <h4 className="text-fm-primary mb-4 text-lg font-semibold">
359
- Screen Reader Only
360
- </h4>
361
- <div className="mb-4 flex items-center justify-center">
362
- <CircularLoader
363
- aria-label="Processing user authentication"
364
- size="lg"
365
- />
366
- </div>
367
- <div className="text-fm-secondary text-sm">
368
- No visible text but provides descriptive label for screen readers
369
- </div>
370
- </div>
371
- </div>
372
-
373
- <div className="space-y-6">
374
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-6">
375
- <h4 className="text-fm-primary mb-4 text-lg font-semibold">
376
- Custom Loading Message
377
- </h4>
378
- <div className="mb-4 flex items-center justify-center">
379
- <CircularLoader
380
- text="Saving..."
381
- loadingMessage="Your changes are being saved to the server"
382
- size="lg"
383
- />
384
- </div>
385
- <div className="text-fm-secondary text-sm">
386
- Visual text differs from detailed screen reader message
387
- </div>
388
- </div>
172
+ }
389
173
 
390
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-6">
391
- <h4 className="text-fm-primary mb-4 text-lg font-semibold">
392
- Assertive Announcements
393
- </h4>
394
- <div className="mb-4 flex items-center justify-center">
395
- <CircularLoader
396
- text="Critical process..."
397
- aria-live="assertive"
398
- size="lg"
399
- />
400
- </div>
401
- <div className="text-fm-secondary text-sm">
402
- Immediately announces changes to screen readers
403
- </div>
404
- </div>
405
- </div>
406
- </div>
174
+ // ─── 3. Sizes ─────────────────────────────────────────────────────────────────
407
175
 
408
- <div className="border-fm-divider-secondary bg-fm-surface-info-sec rounded-lg border p-6">
409
- <h4 className="text-fm-info mb-4 text-lg font-semibold">
410
- Accessibility Best Practices
176
+ export const Sizes: Story = {
177
+ render: () => (
178
+ <div className="space-y-8">
179
+ <div className="space-y-4">
180
+ <h4 className="text-fm-secondary font-fm-text text-fm-md leading-fm-md font-medium">
181
+ Size Scale
411
182
  </h4>
412
- <div className="grid grid-cols-1 gap-4 md:grid-cols-2">
413
- <div>
414
- <h5 className="text-fm-info mb-2 font-medium">Built-in Features</h5>
415
- <ul className="text-fm-info-sec space-y-1 text-sm">
416
- <li>• Role="status" for loading states</li>
417
- <li>• ARIA-live regions for dynamic updates</li>
418
- <li>• ARIA-hidden on decorative elements</li>
419
- <li>• Screen reader optimized text</li>
420
- <li>• Keyboard navigation safe</li>
421
- </ul>
422
- </div>
423
- <div>
424
- <h5 className="text-fm-info mb-2 font-medium">Usage Guidelines</h5>
425
- <ul className="text-fm-info-sec space-y-1 text-sm">
426
- <li>• Always provide context about what's loading</li>
427
- <li>• Use "polite" for non-critical updates</li>
428
- <li>• Use "assertive" for important changes</li>
429
- <li>• Test with screen readers</li>
430
- <li>• Consider reduced motion preferences</li>
431
- </ul>
183
+ <div className="flex flex-wrap items-end justify-center gap-8">
184
+ <div className="space-y-2 text-center">
185
+ <CircularLoader size="sm" aria-label="Loading small" />
186
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
187
+ Small (16px)
188
+ </p>
189
+ </div>
190
+ <div className="space-y-2 text-center">
191
+ <CircularLoader size="md" aria-label="Loading medium" />
192
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
193
+ Medium (24px)
194
+ </p>
195
+ </div>
196
+ <div className="space-y-2 text-center">
197
+ <CircularLoader size="lg" aria-label="Loading large" />
198
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
199
+ Large (32px)
200
+ </p>
201
+ </div>
202
+ <div className="space-y-2 text-center">
203
+ <CircularLoader size="xl" aria-label="Loading extra large" />
204
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
205
+ Extra Large (48px)
206
+ </p>
432
207
  </div>
433
208
  </div>
434
209
  </div>
435
210
  </div>
436
211
  ),
437
- }
438
-
439
- // 5. Real-world Usage Examples
440
- export const UsageExamples: Story = {
441
212
  parameters: {
442
- ...storyParameters,
443
213
  docs: {
444
214
  description: {
445
215
  story:
446
- "Real-world usage examples showing CircularLoader in different UI contexts and scenarios.",
216
+ "Four predefined sizes side by side sm for inline/button use, md as the default, lg for prominent loading areas, xl for full-page loading states.",
447
217
  },
448
218
  },
449
219
  },
450
- render: () => {
451
- const [buttonLoading, setButtonLoading] = useState(false)
452
- const [cardLoading, setCardLoading] = useState(false)
453
- const [pageLoading, setPageLoading] = useState(false)
454
-
455
- const handleButtonClick = () => {
456
- setButtonLoading(true)
457
- setTimeout(() => setButtonLoading(false), 3000)
458
- }
459
-
460
- const handleCardRefresh = () => {
461
- setCardLoading(true)
462
- setTimeout(() => setCardLoading(false), 2000)
463
- }
464
-
465
- const handlePageRefresh = () => {
466
- setPageLoading(true)
467
- setTimeout(() => setPageLoading(false), 4000)
468
- }
469
-
470
- return (
471
- <div className="bg-fm-surface-primary space-y-8 rounded-lg p-8">
472
- <div className="text-center">
473
- <h3 className="text-fm-primary mb-4 text-xl font-bold">
474
- Real-world Usage
475
- </h3>
476
- <p className="text-fm-secondary text-sm">
477
- Common UI patterns and contexts where CircularLoader is used
478
- </p>
479
- </div>
480
-
481
- <div className="grid grid-cols-1 gap-8 lg:grid-cols-3">
482
- {/* Button Loading */}
483
- <div className="space-y-4">
484
- <h4 className="text-fm-primary text-lg font-semibold">
485
- Button Loading
486
- </h4>
487
- <div className="space-y-3">
488
- <Button
489
- onClick={handleButtonClick}
490
- disabled={buttonLoading}
491
- className="w-full"
492
- >
493
- {buttonLoading ? (
494
- <div className="flex items-center gap-2">
495
- <CircularLoader size="sm" aria-label="Saving changes" />
496
- <span>Saving...</span>
497
- </div>
498
- ) : (
499
- "Save Changes"
500
- )}
501
- </Button>
502
- <div className="text-fm-secondary text-xs">
503
- Inline loader in button with accessible label
504
- </div>
505
- </div>
506
- </div>
220
+ }
507
221
 
508
- {/* Card Loading */}
509
- <div className="space-y-4">
510
- <h4 className="text-fm-primary text-lg font-semibold">
511
- Card Loading
512
- </h4>
513
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-4">
514
- {cardLoading ? (
515
- <div className="flex h-32 items-center justify-center">
516
- <CircularLoader
517
- text="Refreshing data..."
518
- loadingMessage="Refreshing chart data from server"
519
- size="lg"
520
- />
521
- </div>
522
- ) : (
523
- <div className="space-y-3">
524
- <div className="bg-fm-surface-tertiary h-4 rounded"></div>
525
- <div className="bg-fm-surface-tertiary h-4 rounded"></div>
526
- <div className="bg-fm-surface-tertiary h-4 w-3/4 rounded"></div>
527
- <Button
528
- onClick={handleCardRefresh}
529
- size="sm"
530
- className="mt-2"
531
- >
532
- Refresh Data
533
- </Button>
534
- </div>
535
- )}
536
- </div>
537
- <div className="text-fm-secondary text-xs">
538
- Content area with detailed loading message
539
- </div>
540
- </div>
222
+ // ─── 4. Accessibility ─────────────────────────────────────────────────────────
541
223
 
542
- {/* Page Loading */}
543
- <div className="space-y-4">
544
- <h4 className="text-fm-primary text-lg font-semibold">
545
- Page Loading
546
- </h4>
547
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-4">
548
- {pageLoading ? (
549
- <div className="flex h-32 items-center justify-center">
550
- <CircularLoader
551
- text="Loading application..."
552
- aria-live="assertive"
553
- size="xl"
554
- variant="v2"
555
- />
556
- </div>
557
- ) : (
558
- <div className="space-y-3">
559
- <div className="text-center">
560
- <div className="text-fm-primary mb-2 text-sm font-medium">
561
- Application Ready
562
- </div>
563
- <Button
564
- onClick={handlePageRefresh}
565
- variant="outline"
566
- size="sm"
567
- >
568
- Simulate Loading
569
- </Button>
570
- </div>
571
- </div>
572
- )}
573
- </div>
574
- <div className="text-fm-secondary text-xs">
575
- Full page loading with assertive announcements
576
- </div>
224
+ export const Accessibility: Story = {
225
+ render: () => (
226
+ <div className="space-y-8">
227
+ <div className="space-y-4">
228
+ <h4 className="text-fm-secondary font-fm-text text-fm-md leading-fm-md font-medium">
229
+ ARIA Patterns
230
+ </h4>
231
+ <div className="flex flex-wrap items-start gap-8">
232
+ <div className="space-y-2 text-center">
233
+ <StoryCircularLoader
234
+ size="lg"
235
+ text="Loading data..."
236
+ aria-live="polite"
237
+ />
238
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
239
+ Visual text (polite)
240
+ </p>
241
+ </div>
242
+ <div className="space-y-2 text-center">
243
+ <CircularLoader
244
+ size="lg"
245
+ aria-label="Processing your authentication"
246
+ aria-live="polite"
247
+ />
248
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
249
+ SR label only
250
+ </p>
251
+ </div>
252
+ <div className="space-y-2 text-center">
253
+ <StoryCircularLoader
254
+ size="lg"
255
+ text="Saving..."
256
+ loadingMessage="Your changes are being saved to the server"
257
+ aria-live="polite"
258
+ />
259
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
260
+ Custom SR message
261
+ </p>
262
+ </div>
263
+ <div className="space-y-2 text-center">
264
+ <StoryCircularLoader
265
+ size="lg"
266
+ text="Critical update..."
267
+ aria-live="assertive"
268
+ />
269
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
270
+ Assertive announce
271
+ </p>
577
272
  </div>
578
273
  </div>
274
+ </div>
579
275
 
580
- {/* Form Submission Example */}
581
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-6">
582
- <h4 className="text-fm-primary mb-4 text-lg font-semibold">
583
- Form Submission
584
- </h4>
585
- <div className="space-y-4">
586
- <div className="grid grid-cols-1 gap-4 md:grid-cols-2">
587
- <input
588
- type="text"
589
- placeholder="Name"
590
- className="border-fm-divider-secondary bg-fm-surface-tertiary text-fm-primary placeholder:text-fm-tertiary rounded-lg border p-3"
591
- />
592
- <input
593
- type="email"
594
- placeholder="Email"
595
- className="border-fm-divider-secondary bg-fm-surface-tertiary text-fm-primary placeholder:text-fm-tertiary rounded-lg border p-3"
596
- />
597
- </div>
598
- <textarea
599
- placeholder="Message"
600
- rows={3}
601
- className="border-fm-divider-secondary bg-fm-surface-tertiary text-fm-primary placeholder:text-fm-tertiary w-full rounded-lg border p-3"
602
- />
603
- <div className="flex items-center justify-between">
604
- <div className="flex items-center gap-2">
605
- <CircularLoader size="sm" aria-label="Submitting form" />
606
- <span className="text-fm-secondary text-sm">
607
- Submitting your message...
608
- </span>
609
- </div>
610
- <Button disabled>Submit</Button>
611
- </div>
612
- </div>
276
+ <div className="space-y-4">
277
+ <h4 className="text-fm-secondary font-fm-text text-fm-md leading-fm-md font-medium">
278
+ In-context Usage
279
+ </h4>
280
+ <div className="flex flex-wrap gap-6">
281
+ <div className="border-fm-divider-secondary bg-fm-surface-secondary flex items-center gap-3 rounded-lg border px-4 py-3">
282
+ <CircularLoader size="sm" aria-label="Saving changes" />
283
+ <span className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
284
+ Saving changes...
285
+ </span>
286
+ </div>
287
+ <Button disabled>
288
+ <CircularLoader size="sm" aria-label="Submitting form" />
289
+ Submitting
290
+ </Button>
613
291
  </div>
614
292
  </div>
615
- )
616
- },
617
- }
618
293
 
619
- // 6. Interactive Playground
620
- export const Playground: Story = {
294
+ <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-4">
295
+ <p className="text-fm-secondary font-fm-text text-fm-md leading-fm-xl">
296
+ <strong className="text-fm-primary">Best practices:</strong>
297
+ </p>
298
+ <ul className="mt-2 space-y-1">
299
+ <li>
300
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
301
+ • Always supply <code>text</code> or <code>aria-label</code> so
302
+ screen readers know what is loading.
303
+ </p>
304
+ </li>
305
+ <li>
306
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
307
+ • Use <code>loadingMessage</code> when the visible text is too
308
+ brief — the message is read instead by screen readers.
309
+ </p>
310
+ </li>
311
+ <li>
312
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
313
+ • Prefer <code>aria-live="polite"</code> for background tasks;
314
+ reserve <code>"assertive"</code> for critical, time-sensitive
315
+ updates.
316
+ </p>
317
+ </li>
318
+ <li>
319
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
320
+ • The spinner icon carries <code>aria-hidden="true"</code> — it is
321
+ purely decorative and excluded from the accessibility tree.
322
+ </p>
323
+ </li>
324
+ <li>
325
+ <p className="text-fm-secondary font-fm-text text-fm-sm leading-fm-sm">
326
+ • <code>role="status"</code> is set automatically on the root
327
+ element, meeting WCAG 4.1.3 (Status Messages).
328
+ </p>
329
+ </li>
330
+ </ul>
331
+ </div>
332
+ </div>
333
+ ),
621
334
  parameters: {
622
- ...storyParameters,
623
335
  docs: {
624
336
  description: {
625
337
  story:
626
- "Interactive playground to experiment with all CircularLoader configurations and accessibility features.",
338
+ "Accessibility-focused examples covering polite and assertive aria-live regions, screen-reader-only labels, custom loading messages, and inline button integration — with a best-practices reference.",
627
339
  },
628
340
  },
629
341
  },
630
- args: {
631
- variant: "v1",
632
- size: "md",
633
- text: "Loading...",
634
- "aria-label": "",
635
- "aria-live": "polite",
636
- loadingMessage: "",
637
- className: "",
638
- classes: {},
639
- },
640
- argTypes: {
641
- variant: {
642
- control: { type: "select" },
643
- options: ["v1", "v2", "v3"],
644
- description: "Visual variant of the spinner",
645
- },
646
- size: {
647
- control: { type: "select" },
648
- options: ["sm", "md", "lg", "xl"],
649
- description: "Size of the spinner",
650
- },
651
- text: {
652
- control: "text",
653
- description: "Visible text displayed below the spinner",
654
- },
655
- "aria-label": {
656
- control: "text",
657
- description:
658
- "Accessible label for screen readers when no text is provided",
659
- },
660
- "aria-live": {
661
- control: { type: "select" },
662
- options: ["polite", "assertive", "off"],
663
- description: "How screen readers announce loading state changes",
664
- },
665
- loadingMessage: {
666
- control: "text",
667
- description: "Custom loading message for screen readers",
668
- },
669
- className: {
670
- control: "text",
671
- description: "Additional CSS classes for the spinner icon",
672
- },
673
- classes: {
674
- control: "object",
675
- description: "Custom classes for different parts of the component",
676
- },
677
- },
678
- render: (args) => (
679
- <div className="bg-fm-surface-primary space-y-8 rounded-lg p-8">
680
- <div className="text-center">
681
- <h3 className="text-fm-primary mb-4 text-xl font-bold">
682
- Interactive Playground
683
- </h3>
684
- <p className="text-fm-secondary text-sm">
685
- Experiment with all CircularLoader configurations and accessibility
686
- features
687
- </p>
688
- </div>
689
-
690
- <div className="flex items-center justify-center">
691
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-8">
692
- <CircularLoader {...args} />
693
- </div>
694
- </div>
695
-
696
- <div className="border-fm-divider-secondary bg-fm-surface-secondary rounded-lg border p-6">
697
- <h4 className="text-fm-primary mb-4 text-lg font-semibold">
698
- Current Configuration
699
- </h4>
700
- <div className="grid grid-cols-2 gap-4 text-sm">
701
- <div>
702
- <div className="text-fm-primary font-medium">Variant:</div>
703
- <div className="text-fm-secondary">{args.variant}</div>
704
- </div>
705
- <div>
706
- <div className="text-fm-primary font-medium">Size:</div>
707
- <div className="text-fm-secondary">{args.size}</div>
708
- </div>
709
- <div>
710
- <div className="text-fm-primary font-medium">Visual Text:</div>
711
- <div className="text-fm-secondary">{args.text || "None"}</div>
712
- </div>
713
- <div>
714
- <div className="text-fm-primary font-medium">ARIA Label:</div>
715
- <div className="text-fm-secondary">
716
- {args["aria-label"] || "None"}
717
- </div>
718
- </div>
719
- <div>
720
- <div className="text-fm-primary font-medium">ARIA Live:</div>
721
- <div className="text-fm-secondary">{args["aria-live"]}</div>
722
- </div>
723
- <div>
724
- <div className="text-fm-primary font-medium">Loading Message:</div>
725
- <div className="text-fm-secondary">
726
- {args.loadingMessage || "None"}
727
- </div>
728
- </div>
729
- </div>
730
- </div>
731
-
732
- <div className="border-fm-divider-positive bg-fm-surface-positive-sec rounded-lg border p-6">
733
- <h4 className="text-fm-positive mb-4 text-lg font-semibold">
734
- Accessibility Info
735
- </h4>
736
- <div className="text-fm-positive-sec space-y-2 text-sm">
737
- <div>
738
- <strong>Screen Reader Message:</strong>{" "}
739
- {args.text ||
740
- args.loadingMessage ||
741
- args["aria-label"] ||
742
- "Loading"}
743
- </div>
744
- <div>
745
- <strong>Announcement Type:</strong> {args["aria-live"]}
746
- </div>
747
- <div>
748
- <strong>Role:</strong> status
749
- </div>
750
- <div>
751
- <strong>Focusable:</strong> No (decorative spinner)
752
- </div>
753
- </div>
754
- </div>
755
- </div>
756
- ),
757
342
  }