@spatika/react 1.0.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 (406) hide show
  1. package/README.md +72 -0
  2. package/dist/composites/ActionBar.d.ts +7 -0
  3. package/dist/composites/ActionBar.d.ts.map +1 -0
  4. package/dist/composites/ActionBar.js +5 -0
  5. package/dist/composites/AmountInput.d.ts +10 -0
  6. package/dist/composites/AmountInput.d.ts.map +1 -0
  7. package/dist/composites/AmountInput.js +7 -0
  8. package/dist/composites/AppHeader.d.ts +25 -0
  9. package/dist/composites/AppHeader.d.ts.map +1 -0
  10. package/dist/composites/AppHeader.js +13 -0
  11. package/dist/composites/AppSidebar.d.ts +30 -0
  12. package/dist/composites/AppSidebar.d.ts.map +1 -0
  13. package/dist/composites/AppSidebar.js +15 -0
  14. package/dist/composites/BottomSheet.d.ts +36 -0
  15. package/dist/composites/BottomSheet.d.ts.map +1 -0
  16. package/dist/composites/BottomSheet.js +37 -0
  17. package/dist/composites/Breadcrumb.d.ts +10 -0
  18. package/dist/composites/Breadcrumb.d.ts.map +1 -0
  19. package/dist/composites/Breadcrumb.js +10 -0
  20. package/dist/composites/Callout.d.ts +8 -0
  21. package/dist/composites/Callout.d.ts.map +1 -0
  22. package/dist/composites/Callout.js +5 -0
  23. package/dist/composites/Card.d.ts +31 -0
  24. package/dist/composites/Card.d.ts.map +1 -0
  25. package/dist/composites/Card.js +33 -0
  26. package/dist/composites/Chip.d.ts +13 -0
  27. package/dist/composites/Chip.d.ts.map +1 -0
  28. package/dist/composites/Chip.js +59 -0
  29. package/dist/composites/ChipGroup.d.ts +23 -0
  30. package/dist/composites/ChipGroup.d.ts.map +1 -0
  31. package/dist/composites/ChipGroup.js +27 -0
  32. package/dist/composites/CommandSearchField.d.ts +27 -0
  33. package/dist/composites/CommandSearchField.d.ts.map +1 -0
  34. package/dist/composites/CommandSearchField.js +17 -0
  35. package/dist/composites/CoverHero.d.ts +51 -0
  36. package/dist/composites/CoverHero.d.ts.map +1 -0
  37. package/dist/composites/CoverHero.js +71 -0
  38. package/dist/composites/CoverPattern.d.ts +12 -0
  39. package/dist/composites/CoverPattern.d.ts.map +1 -0
  40. package/dist/composites/CoverPattern.js +14 -0
  41. package/dist/composites/DataTableToolbar.d.ts +13 -0
  42. package/dist/composites/DataTableToolbar.d.ts.map +1 -0
  43. package/dist/composites/DataTableToolbar.js +7 -0
  44. package/dist/composites/DividerLabel.d.ts +5 -0
  45. package/dist/composites/DividerLabel.d.ts.map +1 -0
  46. package/dist/composites/DividerLabel.js +5 -0
  47. package/dist/composites/EmptyState.d.ts +16 -0
  48. package/dist/composites/EmptyState.d.ts.map +1 -0
  49. package/dist/composites/EmptyState.js +10 -0
  50. package/dist/composites/EntityCard.d.ts +31 -0
  51. package/dist/composites/EntityCard.d.ts.map +1 -0
  52. package/dist/composites/EntityCard.js +21 -0
  53. package/dist/composites/EntityMediaCard.d.ts +25 -0
  54. package/dist/composites/EntityMediaCard.d.ts.map +1 -0
  55. package/dist/composites/EntityMediaCard.js +17 -0
  56. package/dist/composites/FilterSheet.d.ts +34 -0
  57. package/dist/composites/FilterSheet.d.ts.map +1 -0
  58. package/dist/composites/FilterSheet.js +36 -0
  59. package/dist/composites/FloatingPageChrome.d.ts +90 -0
  60. package/dist/composites/FloatingPageChrome.d.ts.map +1 -0
  61. package/dist/composites/FloatingPageChrome.js +67 -0
  62. package/dist/composites/FormField.d.ts +15 -0
  63. package/dist/composites/FormField.d.ts.map +1 -0
  64. package/dist/composites/FormField.js +9 -0
  65. package/dist/composites/GlassCard.d.ts +13 -0
  66. package/dist/composites/GlassCard.d.ts.map +1 -0
  67. package/dist/composites/GlassCard.js +32 -0
  68. package/dist/composites/HeaderIconButton.d.ts +13 -0
  69. package/dist/composites/HeaderIconButton.d.ts.map +1 -0
  70. package/dist/composites/HeaderIconButton.js +12 -0
  71. package/dist/composites/ListRow.d.ts +9 -0
  72. package/dist/composites/ListRow.d.ts.map +1 -0
  73. package/dist/composites/ListRow.js +6 -0
  74. package/dist/composites/MediaEntryCard.d.ts +25 -0
  75. package/dist/composites/MediaEntryCard.d.ts.map +1 -0
  76. package/dist/composites/MediaEntryCard.js +10 -0
  77. package/dist/composites/MobileTabBar.d.ts +33 -0
  78. package/dist/composites/MobileTabBar.d.ts.map +1 -0
  79. package/dist/composites/MobileTabBar.js +19 -0
  80. package/dist/composites/NotificationBell.d.ts +28 -0
  81. package/dist/composites/NotificationBell.d.ts.map +1 -0
  82. package/dist/composites/NotificationBell.js +25 -0
  83. package/dist/composites/PageHeader.d.ts +11 -0
  84. package/dist/composites/PageHeader.d.ts.map +1 -0
  85. package/dist/composites/PageHeader.js +6 -0
  86. package/dist/composites/PageShell.d.ts +12 -0
  87. package/dist/composites/PageShell.d.ts.map +1 -0
  88. package/dist/composites/PageShell.js +8 -0
  89. package/dist/composites/PageStickyHeader.d.ts +33 -0
  90. package/dist/composites/PageStickyHeader.d.ts.map +1 -0
  91. package/dist/composites/PageStickyHeader.js +19 -0
  92. package/dist/composites/Pagination.d.ts +7 -0
  93. package/dist/composites/Pagination.d.ts.map +1 -0
  94. package/dist/composites/Pagination.js +6 -0
  95. package/dist/composites/PhotoViewer.d.ts +18 -0
  96. package/dist/composites/PhotoViewer.d.ts.map +1 -0
  97. package/dist/composites/PhotoViewer.js +37 -0
  98. package/dist/composites/PinPad.d.ts +29 -0
  99. package/dist/composites/PinPad.d.ts.map +1 -0
  100. package/dist/composites/PinPad.js +58 -0
  101. package/dist/composites/ProfileHero.d.ts +34 -0
  102. package/dist/composites/ProfileHero.d.ts.map +1 -0
  103. package/dist/composites/ProfileHero.js +21 -0
  104. package/dist/composites/QuickFilterRail.d.ts +25 -0
  105. package/dist/composites/QuickFilterRail.d.ts.map +1 -0
  106. package/dist/composites/QuickFilterRail.js +18 -0
  107. package/dist/composites/QuickSettings.d.ts +27 -0
  108. package/dist/composites/QuickSettings.d.ts.map +1 -0
  109. package/dist/composites/QuickSettings.js +18 -0
  110. package/dist/composites/RichTextEditor.d.ts +13 -0
  111. package/dist/composites/RichTextEditor.d.ts.map +1 -0
  112. package/dist/composites/RichTextEditor.js +23 -0
  113. package/dist/composites/SearchField.d.ts +8 -0
  114. package/dist/composites/SearchField.d.ts.map +1 -0
  115. package/dist/composites/SearchField.js +8 -0
  116. package/dist/composites/SectionPanel.d.ts +16 -0
  117. package/dist/composites/SectionPanel.d.ts.map +1 -0
  118. package/dist/composites/SectionPanel.js +8 -0
  119. package/dist/composites/SegmentedControl.d.ts +17 -0
  120. package/dist/composites/SegmentedControl.d.ts.map +1 -0
  121. package/dist/composites/SegmentedControl.js +11 -0
  122. package/dist/composites/StatCard.d.ts +11 -0
  123. package/dist/composites/StatCard.d.ts.map +1 -0
  124. package/dist/composites/StatCard.js +6 -0
  125. package/dist/composites/StatusDot.d.ts +11 -0
  126. package/dist/composites/StatusDot.d.ts.map +1 -0
  127. package/dist/composites/StatusDot.js +23 -0
  128. package/dist/composites/SurfaceCard.d.ts +12 -0
  129. package/dist/composites/SurfaceCard.d.ts.map +1 -0
  130. package/dist/composites/SurfaceCard.js +24 -0
  131. package/dist/composites/Timeline.d.ts +19 -0
  132. package/dist/composites/Timeline.d.ts.map +1 -0
  133. package/dist/composites/Timeline.js +12 -0
  134. package/dist/composites/Toast.d.ts +26 -0
  135. package/dist/composites/Toast.d.ts.map +1 -0
  136. package/dist/composites/Toast.js +49 -0
  137. package/dist/composites/Toolbar.d.ts +6 -0
  138. package/dist/composites/Toolbar.d.ts.map +1 -0
  139. package/dist/composites/Toolbar.js +5 -0
  140. package/dist/composites/ViewFiltersPanel.d.ts +21 -0
  141. package/dist/composites/ViewFiltersPanel.d.ts.map +1 -0
  142. package/dist/composites/ViewFiltersPanel.js +11 -0
  143. package/dist/index.d.ts +96 -0
  144. package/dist/index.d.ts.map +1 -0
  145. package/dist/index.js +95 -0
  146. package/dist/lib/animations.d.ts +62 -0
  147. package/dist/lib/animations.d.ts.map +1 -0
  148. package/dist/lib/animations.js +37 -0
  149. package/dist/lib/avatar-utils.d.ts +10 -0
  150. package/dist/lib/avatar-utils.d.ts.map +1 -0
  151. package/dist/lib/avatar-utils.js +49 -0
  152. package/dist/lib/chips.d.ts +10 -0
  153. package/dist/lib/chips.d.ts.map +1 -0
  154. package/dist/lib/chips.js +30 -0
  155. package/dist/lib/cn.d.ts +4 -0
  156. package/dist/lib/cn.d.ts.map +1 -0
  157. package/dist/lib/cn.js +6 -0
  158. package/dist/lib/compose-refs.d.ts +6 -0
  159. package/dist/lib/compose-refs.d.ts.map +1 -0
  160. package/dist/lib/compose-refs.js +17 -0
  161. package/dist/lib/cover-chrome.d.ts +9 -0
  162. package/dist/lib/cover-chrome.d.ts.map +1 -0
  163. package/dist/lib/cover-chrome.js +23 -0
  164. package/dist/lib/cover-pattern.d.ts +75 -0
  165. package/dist/lib/cover-pattern.d.ts.map +1 -0
  166. package/dist/lib/cover-pattern.js +135 -0
  167. package/dist/lib/overlay-stack.d.ts +23 -0
  168. package/dist/lib/overlay-stack.d.ts.map +1 -0
  169. package/dist/lib/overlay-stack.js +37 -0
  170. package/dist/lib/portal.d.ts +12 -0
  171. package/dist/lib/portal.d.ts.map +1 -0
  172. package/dist/lib/portal.js +12 -0
  173. package/dist/lib/slot.d.ts +12 -0
  174. package/dist/lib/slot.d.ts.map +1 -0
  175. package/dist/lib/slot.js +55 -0
  176. package/dist/lib/surfaces.d.ts +14 -0
  177. package/dist/lib/surfaces.d.ts.map +1 -0
  178. package/dist/lib/surfaces.js +18 -0
  179. package/dist/lib/themes.d.ts +16 -0
  180. package/dist/lib/themes.d.ts.map +1 -0
  181. package/dist/lib/themes.js +53 -0
  182. package/dist/lib/typography.d.ts +17 -0
  183. package/dist/lib/typography.d.ts.map +1 -0
  184. package/dist/lib/typography.js +16 -0
  185. package/dist/lib/use-controllable-state.d.ts +12 -0
  186. package/dist/lib/use-controllable-state.d.ts.map +1 -0
  187. package/dist/lib/use-controllable-state.js +20 -0
  188. package/dist/lib/use-cover-chrome-bleed.d.ts +9 -0
  189. package/dist/lib/use-cover-chrome-bleed.d.ts.map +1 -0
  190. package/dist/lib/use-cover-chrome-bleed.js +28 -0
  191. package/dist/lib/use-dismissable.d.ts +13 -0
  192. package/dist/lib/use-dismissable.d.ts.map +1 -0
  193. package/dist/lib/use-dismissable.js +33 -0
  194. package/dist/lib/use-floating-position.d.ts +27 -0
  195. package/dist/lib/use-floating-position.d.ts.map +1 -0
  196. package/dist/lib/use-floating-position.js +115 -0
  197. package/dist/lib/use-focus-trap.d.ts +7 -0
  198. package/dist/lib/use-focus-trap.d.ts.map +1 -0
  199. package/dist/lib/use-focus-trap.js +61 -0
  200. package/dist/lib/use-media-query.d.ts +5 -0
  201. package/dist/lib/use-media-query.d.ts.map +1 -0
  202. package/dist/lib/use-media-query.js +19 -0
  203. package/dist/primitives/Accordion.d.ts +24 -0
  204. package/dist/primitives/Accordion.d.ts.map +1 -0
  205. package/dist/primitives/Accordion.js +37 -0
  206. package/dist/primitives/Alert.d.ts +10 -0
  207. package/dist/primitives/Alert.d.ts.map +1 -0
  208. package/dist/primitives/Alert.js +25 -0
  209. package/dist/primitives/AlertDialog.d.ts +33 -0
  210. package/dist/primitives/AlertDialog.d.ts.map +1 -0
  211. package/dist/primitives/AlertDialog.js +96 -0
  212. package/dist/primitives/Avatar.d.ts +15 -0
  213. package/dist/primitives/Avatar.d.ts.map +1 -0
  214. package/dist/primitives/Avatar.js +52 -0
  215. package/dist/primitives/Badge.d.ts +12 -0
  216. package/dist/primitives/Badge.d.ts.map +1 -0
  217. package/dist/primitives/Badge.js +27 -0
  218. package/dist/primitives/Button.d.ts +14 -0
  219. package/dist/primitives/Button.d.ts.map +1 -0
  220. package/dist/primitives/Button.js +37 -0
  221. package/dist/primitives/Checkbox.d.ts +9 -0
  222. package/dist/primitives/Checkbox.d.ts.map +1 -0
  223. package/dist/primitives/Checkbox.js +22 -0
  224. package/dist/primitives/Command.d.ts +17 -0
  225. package/dist/primitives/Command.d.ts.map +1 -0
  226. package/dist/primitives/Command.js +33 -0
  227. package/dist/primitives/Dialog.d.ts +34 -0
  228. package/dist/primitives/Dialog.d.ts.map +1 -0
  229. package/dist/primitives/Dialog.js +96 -0
  230. package/dist/primitives/DropdownMenu.d.ts +65 -0
  231. package/dist/primitives/DropdownMenu.d.ts.map +1 -0
  232. package/dist/primitives/DropdownMenu.js +196 -0
  233. package/dist/primitives/Input.d.ts +4 -0
  234. package/dist/primitives/Input.d.ts.map +1 -0
  235. package/dist/primitives/Input.js +6 -0
  236. package/dist/primitives/Kbd.d.ts +4 -0
  237. package/dist/primitives/Kbd.d.ts.map +1 -0
  238. package/dist/primitives/Kbd.js +6 -0
  239. package/dist/primitives/Label.d.ts +4 -0
  240. package/dist/primitives/Label.d.ts.map +1 -0
  241. package/dist/primitives/Label.js +6 -0
  242. package/dist/primitives/NativeSelect.d.ts +7 -0
  243. package/dist/primitives/NativeSelect.d.ts.map +1 -0
  244. package/dist/primitives/NativeSelect.js +10 -0
  245. package/dist/primitives/Popover.d.ts +29 -0
  246. package/dist/primitives/Popover.d.ts.map +1 -0
  247. package/dist/primitives/Popover.js +95 -0
  248. package/dist/primitives/Progress.d.ts +8 -0
  249. package/dist/primitives/Progress.d.ts.map +1 -0
  250. package/dist/primitives/Progress.js +7 -0
  251. package/dist/primitives/RadioGroup.d.ts +13 -0
  252. package/dist/primitives/RadioGroup.d.ts.map +1 -0
  253. package/dist/primitives/RadioGroup.js +33 -0
  254. package/dist/primitives/Select.d.ts +33 -0
  255. package/dist/primitives/Select.d.ts.map +1 -0
  256. package/dist/primitives/Select.js +178 -0
  257. package/dist/primitives/Separator.d.ts +7 -0
  258. package/dist/primitives/Separator.d.ts.map +1 -0
  259. package/dist/primitives/Separator.js +6 -0
  260. package/dist/primitives/Sheet.d.ts +28 -0
  261. package/dist/primitives/Sheet.d.ts.map +1 -0
  262. package/dist/primitives/Sheet.js +96 -0
  263. package/dist/primitives/Skeleton.d.ts +4 -0
  264. package/dist/primitives/Skeleton.d.ts.map +1 -0
  265. package/dist/primitives/Skeleton.js +6 -0
  266. package/dist/primitives/Slider.d.ts +12 -0
  267. package/dist/primitives/Slider.d.ts.map +1 -0
  268. package/dist/primitives/Slider.js +23 -0
  269. package/dist/primitives/Spinner.d.ts +6 -0
  270. package/dist/primitives/Spinner.d.ts.map +1 -0
  271. package/dist/primitives/Spinner.js +7 -0
  272. package/dist/primitives/StarRating.d.ts +10 -0
  273. package/dist/primitives/StarRating.d.ts.map +1 -0
  274. package/dist/primitives/StarRating.js +11 -0
  275. package/dist/primitives/Switch.d.ts +8 -0
  276. package/dist/primitives/Switch.d.ts.map +1 -0
  277. package/dist/primitives/Switch.js +20 -0
  278. package/dist/primitives/Table.d.ts +13 -0
  279. package/dist/primitives/Table.d.ts.map +1 -0
  280. package/dist/primitives/Table.js +20 -0
  281. package/dist/primitives/Tabs.d.ts +17 -0
  282. package/dist/primitives/Tabs.d.ts.map +1 -0
  283. package/dist/primitives/Tabs.js +30 -0
  284. package/dist/primitives/Textarea.d.ts +4 -0
  285. package/dist/primitives/Textarea.d.ts.map +1 -0
  286. package/dist/primitives/Textarea.js +6 -0
  287. package/dist/primitives/Tooltip.d.ts +31 -0
  288. package/dist/primitives/Tooltip.d.ts.map +1 -0
  289. package/dist/primitives/Tooltip.js +94 -0
  290. package/dist/theme/OriginThemeProvider.d.ts +31 -0
  291. package/dist/theme/OriginThemeProvider.d.ts.map +1 -0
  292. package/dist/theme/OriginThemeProvider.js +37 -0
  293. package/dist/theme/SpatikaThemeProvider.d.ts +36 -0
  294. package/dist/theme/SpatikaThemeProvider.d.ts.map +1 -0
  295. package/dist/theme/SpatikaThemeProvider.js +38 -0
  296. package/package.json +58 -0
  297. package/src/composites/ActionBar.tsx +25 -0
  298. package/src/composites/AmountInput.tsx +40 -0
  299. package/src/composites/AppHeader.tsx +88 -0
  300. package/src/composites/AppSidebar.tsx +120 -0
  301. package/src/composites/BottomSheet.tsx +179 -0
  302. package/src/composites/Breadcrumb.tsx +42 -0
  303. package/src/composites/Callout.tsx +22 -0
  304. package/src/composites/Card.tsx +119 -0
  305. package/src/composites/Chip.tsx +87 -0
  306. package/src/composites/ChipGroup.component.test.tsx +31 -0
  307. package/src/composites/ChipGroup.test.ts +16 -0
  308. package/src/composites/ChipGroup.tsx +86 -0
  309. package/src/composites/CommandSearchField.tsx +124 -0
  310. package/src/composites/CoverHero.tsx +359 -0
  311. package/src/composites/CoverPattern.tsx +90 -0
  312. package/src/composites/DataTableToolbar.tsx +48 -0
  313. package/src/composites/DividerLabel.tsx +22 -0
  314. package/src/composites/EmptyState.tsx +55 -0
  315. package/src/composites/EntityCard.tsx +100 -0
  316. package/src/composites/EntityMediaCard.tsx +118 -0
  317. package/src/composites/FilterSheet.tsx +178 -0
  318. package/src/composites/FloatingPageChrome.tsx +294 -0
  319. package/src/composites/FormField.tsx +44 -0
  320. package/src/composites/GlassCard.tsx +47 -0
  321. package/src/composites/HeaderIconButton.tsx +49 -0
  322. package/src/composites/ListRow.tsx +29 -0
  323. package/src/composites/MediaEntryCard.tsx +95 -0
  324. package/src/composites/MobileTabBar.tsx +130 -0
  325. package/src/composites/NotificationBell.tsx +164 -0
  326. package/src/composites/PageHeader.tsx +27 -0
  327. package/src/composites/PageShell.tsx +20 -0
  328. package/src/composites/PageStickyHeader.tsx +157 -0
  329. package/src/composites/Pagination.tsx +41 -0
  330. package/src/composites/PhotoViewer.tsx +142 -0
  331. package/src/composites/PinPad.tsx +163 -0
  332. package/src/composites/ProfileHero.tsx +163 -0
  333. package/src/composites/QuickFilterRail.tsx +92 -0
  334. package/src/composites/QuickSettings.tsx +120 -0
  335. package/src/composites/RichTextEditor.tsx +103 -0
  336. package/src/composites/SearchField.tsx +38 -0
  337. package/src/composites/SectionPanel.tsx +59 -0
  338. package/src/composites/SegmentedControl.tsx +62 -0
  339. package/src/composites/StatCard.tsx +26 -0
  340. package/src/composites/StatusDot.tsx +40 -0
  341. package/src/composites/SurfaceCard.tsx +44 -0
  342. package/src/composites/Timeline.tsx +70 -0
  343. package/src/composites/Toast.tsx +135 -0
  344. package/src/composites/Toolbar.tsx +19 -0
  345. package/src/composites/ViewFiltersPanel.tsx +82 -0
  346. package/src/composites/chrome.test.tsx +170 -0
  347. package/src/composites/smoke.test.tsx +49 -0
  348. package/src/index.ts +355 -0
  349. package/src/lib/animations.ts +47 -0
  350. package/src/lib/avatar-utils.ts +52 -0
  351. package/src/lib/chips.ts +58 -0
  352. package/src/lib/cn.test.ts +16 -0
  353. package/src/lib/cn.ts +7 -0
  354. package/src/lib/compose-refs.ts +21 -0
  355. package/src/lib/cover-chrome.ts +31 -0
  356. package/src/lib/cover-pattern.ts +242 -0
  357. package/src/lib/overlay-stack.ts +44 -0
  358. package/src/lib/portal.tsx +21 -0
  359. package/src/lib/slot.tsx +69 -0
  360. package/src/lib/surfaces.ts +57 -0
  361. package/src/lib/themes.test.ts +73 -0
  362. package/src/lib/themes.ts +59 -0
  363. package/src/lib/tokens.test.ts +52 -0
  364. package/src/lib/typography.ts +27 -0
  365. package/src/lib/use-controllable-state.ts +38 -0
  366. package/src/lib/use-cover-chrome-bleed.ts +33 -0
  367. package/src/lib/use-dismissable.ts +49 -0
  368. package/src/lib/use-floating-position.ts +168 -0
  369. package/src/lib/use-focus-trap.ts +73 -0
  370. package/src/lib/use-media-query.ts +22 -0
  371. package/src/primitives/Accordion.tsx +114 -0
  372. package/src/primitives/Alert.tsx +57 -0
  373. package/src/primitives/AlertDialog.tsx +270 -0
  374. package/src/primitives/Avatar.tsx +140 -0
  375. package/src/primitives/Badge.test.tsx +15 -0
  376. package/src/primitives/Badge.tsx +43 -0
  377. package/src/primitives/Button.test.tsx +37 -0
  378. package/src/primitives/Button.tsx +58 -0
  379. package/src/primitives/Checkbox.tsx +75 -0
  380. package/src/primitives/Command.tsx +175 -0
  381. package/src/primitives/Dialog.tsx +241 -0
  382. package/src/primitives/DropdownMenu.tsx +552 -0
  383. package/src/primitives/Input.test.tsx +22 -0
  384. package/src/primitives/Input.tsx +22 -0
  385. package/src/primitives/Kbd.tsx +17 -0
  386. package/src/primitives/Label.tsx +20 -0
  387. package/src/primitives/NativeSelect.tsx +22 -0
  388. package/src/primitives/Popover.tsx +209 -0
  389. package/src/primitives/Progress.tsx +31 -0
  390. package/src/primitives/RadioGroup.tsx +116 -0
  391. package/src/primitives/Select.tsx +409 -0
  392. package/src/primitives/Separator.tsx +30 -0
  393. package/src/primitives/Sheet.tsx +265 -0
  394. package/src/primitives/Skeleton.tsx +16 -0
  395. package/src/primitives/Slider.tsx +97 -0
  396. package/src/primitives/Spinner.tsx +21 -0
  397. package/src/primitives/StarRating.tsx +53 -0
  398. package/src/primitives/Switch.tsx +68 -0
  399. package/src/primitives/Table.tsx +134 -0
  400. package/src/primitives/Tabs.tsx +97 -0
  401. package/src/primitives/Textarea.tsx +20 -0
  402. package/src/primitives/Tooltip.tsx +193 -0
  403. package/src/primitives/smoke.test.tsx +34 -0
  404. package/src/test/setup.ts +1 -0
  405. package/src/theme/SpatikaThemeProvider.test.tsx +82 -0
  406. package/src/theme/SpatikaThemeProvider.tsx +112 -0
@@ -0,0 +1,13 @@
1
+ import * as React from "react";
2
+ type UseDismissableOptions = {
3
+ enabled?: boolean;
4
+ onDismiss: () => void;
5
+ /** Refs whose nodes count as "inside" (content + trigger). */
6
+ refs: React.RefObject<HTMLElement | null>[];
7
+ };
8
+ /**
9
+ * Closes on Escape and pointer-down outside the provided refs.
10
+ */
11
+ export declare function useDismissable({ enabled, onDismiss, refs, }: UseDismissableOptions): void;
12
+ export {};
13
+ //# sourceMappingURL=use-dismissable.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-dismissable.d.ts","sourceRoot":"","sources":["../../src/lib/use-dismissable.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,KAAK,qBAAqB,GAAG;IAC3B,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,SAAS,EAAE,MAAM,IAAI,CAAC;IACtB,8DAA8D;IAC9D,IAAI,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,EAAE,CAAC;CAC7C,CAAC;AAEF;;GAEG;AACH,wBAAgB,cAAc,CAAC,EAC7B,OAAc,EACd,SAAS,EACT,IAAI,GACL,EAAE,qBAAqB,QAgCvB"}
@@ -0,0 +1,33 @@
1
+ import * as React from "react";
2
+ /**
3
+ * Closes on Escape and pointer-down outside the provided refs.
4
+ */
5
+ export function useDismissable({ enabled = true, onDismiss, refs, }) {
6
+ const onDismissRef = React.useRef(onDismiss);
7
+ onDismissRef.current = onDismiss;
8
+ React.useEffect(() => {
9
+ if (!enabled)
10
+ return;
11
+ const handleKeyDown = (event) => {
12
+ if (event.key === "Escape") {
13
+ event.stopPropagation();
14
+ onDismissRef.current();
15
+ }
16
+ };
17
+ const handlePointerDown = (event) => {
18
+ const target = event.target;
19
+ if (!target)
20
+ return;
21
+ const isInside = refs.some((ref) => ref.current?.contains(target));
22
+ if (!isInside) {
23
+ onDismissRef.current();
24
+ }
25
+ };
26
+ document.addEventListener("keydown", handleKeyDown);
27
+ document.addEventListener("pointerdown", handlePointerDown, true);
28
+ return () => {
29
+ document.removeEventListener("keydown", handleKeyDown);
30
+ document.removeEventListener("pointerdown", handlePointerDown, true);
31
+ };
32
+ }, [enabled, refs]);
33
+ }
@@ -0,0 +1,27 @@
1
+ import * as React from "react";
2
+ export type FloatingSide = "top" | "right" | "bottom" | "left";
3
+ export type FloatingAlign = "start" | "center" | "end";
4
+ export type FloatingPosition = {
5
+ top: number;
6
+ left: number;
7
+ side: FloatingSide;
8
+ /** Measured trigger size for consumers that match width. */
9
+ triggerWidth: number;
10
+ triggerHeight: number;
11
+ };
12
+ type UseFloatingPositionOptions = {
13
+ open: boolean;
14
+ triggerRef: React.RefObject<HTMLElement | null>;
15
+ contentRef: React.RefObject<HTMLElement | null>;
16
+ side?: FloatingSide;
17
+ align?: FloatingAlign;
18
+ sideOffset?: number;
19
+ collisionPadding?: number;
20
+ };
21
+ /**
22
+ * Positions floating content relative to a trigger using getBoundingClientRect.
23
+ * Returns fixed-position coordinates suitable for `position: fixed` portals.
24
+ */
25
+ export declare function useFloatingPosition({ open, triggerRef, contentRef, side, align, sideOffset, collisionPadding, }: UseFloatingPositionOptions): FloatingPosition | null;
26
+ export {};
27
+ //# sourceMappingURL=use-floating-position.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-floating-position.d.ts","sourceRoot":"","sources":["../../src/lib/use-floating-position.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,MAAM,MAAM,YAAY,GAAG,KAAK,GAAG,OAAO,GAAG,QAAQ,GAAG,MAAM,CAAC;AAC/D,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,QAAQ,GAAG,KAAK,CAAC;AAEvD,MAAM,MAAM,gBAAgB,GAAG;IAC7B,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,YAAY,CAAC;IACnB,4DAA4D;IAC5D,YAAY,EAAE,MAAM,CAAC;IACrB,aAAa,EAAE,MAAM,CAAC;CACvB,CAAC;AAEF,KAAK,0BAA0B,GAAG;IAChC,IAAI,EAAE,OAAO,CAAC;IACd,UAAU,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAChD,UAAU,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,CAAC;IAChD,IAAI,CAAC,EAAE,YAAY,CAAC;IACpB,KAAK,CAAC,EAAE,aAAa,CAAC;IACtB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gBAAgB,CAAC,EAAE,MAAM,CAAC;CAC3B,CAAC;AAEF;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,EAClC,IAAI,EACJ,UAAU,EACV,UAAU,EACV,IAAe,EACf,KAAgB,EAChB,UAAc,EACd,gBAAoB,GACrB,EAAE,0BAA0B,GAAG,gBAAgB,GAAG,IAAI,CAmItD"}
@@ -0,0 +1,115 @@
1
+ import * as React from "react";
2
+ /**
3
+ * Positions floating content relative to a trigger using getBoundingClientRect.
4
+ * Returns fixed-position coordinates suitable for `position: fixed` portals.
5
+ */
6
+ export function useFloatingPosition({ open, triggerRef, contentRef, side = "bottom", align = "center", sideOffset = 4, collisionPadding = 8, }) {
7
+ const [position, setPosition] = React.useState(null);
8
+ const update = React.useCallback(() => {
9
+ const trigger = triggerRef.current;
10
+ const content = contentRef.current;
11
+ if (!trigger || !content)
12
+ return;
13
+ const triggerRect = trigger.getBoundingClientRect();
14
+ // Prefer laid-out size; fall back to trigger size (min 1) so first paint /
15
+ // happy-dom still yields a position — avoids `visibility: hidden` menus that
16
+ // testing-library cannot query by role.
17
+ const contentWidth = content.offsetWidth > 0 ? content.offsetWidth : Math.max(triggerRect.width, 1);
18
+ const contentHeight = content.offsetHeight > 0 ? content.offsetHeight : Math.max(triggerRect.height, 1);
19
+ let resolvedSide = side;
20
+ const viewportW = window.innerWidth;
21
+ const viewportH = window.innerHeight;
22
+ // Prefer requested side; flip if clearly overflowing.
23
+ if (side === "bottom" &&
24
+ triggerRect.bottom + sideOffset + contentHeight > viewportH - collisionPadding) {
25
+ if (triggerRect.top - sideOffset - contentHeight > collisionPadding) {
26
+ resolvedSide = "top";
27
+ }
28
+ }
29
+ else if (side === "top" &&
30
+ triggerRect.top - sideOffset - contentHeight < collisionPadding) {
31
+ if (triggerRect.bottom + sideOffset + contentHeight <
32
+ viewportH - collisionPadding) {
33
+ resolvedSide = "bottom";
34
+ }
35
+ }
36
+ else if (side === "right" &&
37
+ triggerRect.right + sideOffset + contentWidth > viewportW - collisionPadding) {
38
+ if (triggerRect.left - sideOffset - contentWidth > collisionPadding) {
39
+ resolvedSide = "left";
40
+ }
41
+ }
42
+ else if (side === "left" &&
43
+ triggerRect.left - sideOffset - contentWidth < collisionPadding) {
44
+ if (triggerRect.right + sideOffset + contentWidth <
45
+ viewportW - collisionPadding) {
46
+ resolvedSide = "right";
47
+ }
48
+ }
49
+ let top = 0;
50
+ let left = 0;
51
+ if (resolvedSide === "bottom") {
52
+ top = triggerRect.bottom + sideOffset;
53
+ }
54
+ else if (resolvedSide === "top") {
55
+ top = triggerRect.top - contentHeight - sideOffset;
56
+ }
57
+ else if (resolvedSide === "left" || resolvedSide === "right") {
58
+ if (align === "start")
59
+ top = triggerRect.top;
60
+ else if (align === "end")
61
+ top = triggerRect.bottom - contentHeight;
62
+ else
63
+ top = triggerRect.top + (triggerRect.height - contentHeight) / 2;
64
+ }
65
+ if (resolvedSide === "right") {
66
+ left = triggerRect.right + sideOffset;
67
+ }
68
+ else if (resolvedSide === "left") {
69
+ left = triggerRect.left - contentWidth - sideOffset;
70
+ }
71
+ else if (align === "start") {
72
+ left = triggerRect.left;
73
+ }
74
+ else if (align === "end") {
75
+ left = triggerRect.right - contentWidth;
76
+ }
77
+ else {
78
+ left = triggerRect.left + (triggerRect.width - contentWidth) / 2;
79
+ }
80
+ // Keep the panel fully inside the viewport.
81
+ left = Math.min(Math.max(collisionPadding, left), Math.max(collisionPadding, viewportW - contentWidth - collisionPadding));
82
+ top = Math.min(Math.max(collisionPadding, top), Math.max(collisionPadding, viewportH - contentHeight - collisionPadding));
83
+ setPosition({
84
+ top,
85
+ left,
86
+ side: resolvedSide,
87
+ triggerWidth: triggerRect.width,
88
+ triggerHeight: triggerRect.height,
89
+ });
90
+ }, [align, collisionPadding, contentRef, side, sideOffset, triggerRef]);
91
+ React.useLayoutEffect(() => {
92
+ if (!open) {
93
+ setPosition(null);
94
+ return;
95
+ }
96
+ update();
97
+ // Remeasure after paint in case fonts/layout settle one frame later.
98
+ const raf = window.requestAnimationFrame(() => update());
99
+ const handle = () => update();
100
+ window.addEventListener("resize", handle);
101
+ window.addEventListener("scroll", handle, true);
102
+ const ro = typeof ResizeObserver !== "undefined" ? new ResizeObserver(handle) : null;
103
+ if (contentRef.current && ro)
104
+ ro.observe(contentRef.current);
105
+ if (triggerRef.current && ro)
106
+ ro.observe(triggerRef.current);
107
+ return () => {
108
+ window.cancelAnimationFrame(raf);
109
+ window.removeEventListener("resize", handle);
110
+ window.removeEventListener("scroll", handle, true);
111
+ ro?.disconnect();
112
+ };
113
+ }, [open, update, contentRef, triggerRef]);
114
+ return position;
115
+ }
@@ -0,0 +1,7 @@
1
+ import * as React from "react";
2
+ /**
3
+ * Locks body scroll and restores focus to the previously focused element on cleanup.
4
+ * Also traps Tab within the container while enabled.
5
+ */
6
+ export declare function useFocusTrap(containerRef: React.RefObject<HTMLElement | null>, enabled: boolean): void;
7
+ //# sourceMappingURL=use-focus-trap.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-focus-trap.d.ts","sourceRoot":"","sources":["../../src/lib/use-focus-trap.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAK/B;;;GAGG;AACH,wBAAgB,YAAY,CAC1B,YAAY,EAAE,KAAK,CAAC,SAAS,CAAC,WAAW,GAAG,IAAI,CAAC,EACjD,OAAO,EAAE,OAAO,QA6DjB"}
@@ -0,0 +1,61 @@
1
+ import * as React from "react";
2
+ const FOCUSABLE_SELECTOR = 'a[href],button:not([disabled]),textarea:not([disabled]),input:not([disabled]),select:not([disabled]),[tabindex]:not([tabindex="-1"])';
3
+ /**
4
+ * Locks body scroll and restores focus to the previously focused element on cleanup.
5
+ * Also traps Tab within the container while enabled.
6
+ */
7
+ export function useFocusTrap(containerRef, enabled) {
8
+ React.useEffect(() => {
9
+ if (!enabled)
10
+ return;
11
+ const previouslyFocused = document.activeElement;
12
+ const previousOverflow = document.body.style.overflow;
13
+ document.body.style.overflow = "hidden";
14
+ const focusFirst = () => {
15
+ const container = containerRef.current;
16
+ if (!container)
17
+ return;
18
+ const focusable = container.querySelectorAll(FOCUSABLE_SELECTOR);
19
+ if (focusable.length > 0) {
20
+ focusable[0].focus();
21
+ }
22
+ else {
23
+ container.focus();
24
+ }
25
+ };
26
+ // Defer so portal content is mounted.
27
+ const id = window.setTimeout(focusFirst, 0);
28
+ const handleKeyDown = (event) => {
29
+ if (event.key !== "Tab")
30
+ return;
31
+ const container = containerRef.current;
32
+ if (!container)
33
+ return;
34
+ const focusable = Array.from(container.querySelectorAll(FOCUSABLE_SELECTOR)).filter((el) => !el.hasAttribute("disabled") && el.tabIndex !== -1);
35
+ if (focusable.length === 0) {
36
+ event.preventDefault();
37
+ return;
38
+ }
39
+ const first = focusable[0];
40
+ const last = focusable[focusable.length - 1];
41
+ const active = document.activeElement;
42
+ if (event.shiftKey) {
43
+ if (active === first || !container.contains(active)) {
44
+ event.preventDefault();
45
+ last.focus();
46
+ }
47
+ }
48
+ else if (active === last || !container.contains(active)) {
49
+ event.preventDefault();
50
+ first.focus();
51
+ }
52
+ };
53
+ document.addEventListener("keydown", handleKeyDown);
54
+ return () => {
55
+ window.clearTimeout(id);
56
+ document.removeEventListener("keydown", handleKeyDown);
57
+ document.body.style.overflow = previousOverflow;
58
+ previouslyFocused?.focus?.();
59
+ };
60
+ }, [containerRef, enabled]);
61
+ }
@@ -0,0 +1,5 @@
1
+ /** Subscribe to a CSS media query. Defaults to `false` until mounted. */
2
+ export declare function useMediaQuery(query: string): boolean;
3
+ /** True when the viewport is below the `md` breakpoint (768px). */
4
+ export declare function useIsMobile(): boolean;
5
+ //# sourceMappingURL=use-media-query.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-media-query.d.ts","sourceRoot":"","sources":["../../src/lib/use-media-query.ts"],"names":[],"mappings":"AAEA,yEAAyE;AACzE,wBAAgB,aAAa,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAapD;AAED,mEAAmE;AACnE,wBAAgB,WAAW,IAAI,OAAO,CAErC"}
@@ -0,0 +1,19 @@
1
+ import { useEffect, useState } from "react";
2
+ /** Subscribe to a CSS media query. Defaults to `false` until mounted. */
3
+ export function useMediaQuery(query) {
4
+ const [matches, setMatches] = useState(false);
5
+ useEffect(() => {
6
+ if (typeof window.matchMedia !== "function")
7
+ return;
8
+ const media = window.matchMedia(query);
9
+ const update = () => setMatches(media.matches);
10
+ update();
11
+ media.addEventListener("change", update);
12
+ return () => media.removeEventListener("change", update);
13
+ }, [query]);
14
+ return matches;
15
+ }
16
+ /** True when the viewport is below the `md` breakpoint (768px). */
17
+ export function useIsMobile() {
18
+ return useMediaQuery("(max-width: 767px)");
19
+ }
@@ -0,0 +1,24 @@
1
+ import * as React from "react";
2
+ declare function Accordion({ type, defaultValue, className, children, }: {
3
+ type?: "single" | "multiple";
4
+ defaultValue?: string | string[];
5
+ className?: string;
6
+ children: React.ReactNode;
7
+ }): React.JSX.Element;
8
+ declare function AccordionItem({ value, className, children, }: {
9
+ value: string;
10
+ className?: string;
11
+ children: React.ReactNode;
12
+ }): React.JSX.Element;
13
+ declare function AccordionTrigger({ value, className, children, }: {
14
+ value: string;
15
+ className?: string;
16
+ children: React.ReactNode;
17
+ }): React.JSX.Element;
18
+ declare function AccordionContent({ value, className, children, }: {
19
+ value: string;
20
+ className?: string;
21
+ children: React.ReactNode;
22
+ }): React.JSX.Element | null;
23
+ export { Accordion, AccordionItem, AccordionTrigger, AccordionContent };
24
+ //# sourceMappingURL=Accordion.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Accordion.d.ts","sourceRoot":"","sources":["../../src/primitives/Accordion.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAY/B,iBAAS,SAAS,CAAC,EACjB,IAAe,EACf,YAAY,EACZ,SAAS,EACT,QAAQ,GACT,EAAE;IACD,IAAI,CAAC,EAAE,QAAQ,GAAG,UAAU,CAAC;IAC7B,YAAY,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IACjC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B,qBAqBA;AAED,iBAAS,aAAa,CAAC,EACrB,KAAK,EACL,SAAS,EACT,QAAQ,GACT,EAAE;IACD,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B,qBAUA;AAED,iBAAS,gBAAgB,CAAC,EACxB,KAAK,EACL,SAAS,EACT,QAAQ,GACT,EAAE;IACD,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B,qBAoBA;AAED,iBAAS,gBAAgB,CAAC,EACxB,KAAK,EACL,SAAS,EACT,QAAQ,GACT,EAAE;IACD,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B,4BAQA;AAED,OAAO,EAAE,SAAS,EAAE,aAAa,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,CAAC"}
@@ -0,0 +1,37 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import * as React from "react";
3
+ import { ChevronDown } from "lucide-react";
4
+ import { cn } from "../lib/cn";
5
+ const AccordionContext = React.createContext(null);
6
+ function Accordion({ type = "single", defaultValue, className, children, }) {
7
+ const initial = Array.isArray(defaultValue)
8
+ ? defaultValue
9
+ : defaultValue
10
+ ? [defaultValue]
11
+ : [];
12
+ const [open, setOpen] = React.useState(initial);
13
+ const toggle = (id) => {
14
+ setOpen((prev) => {
15
+ const isOpen = prev.includes(id);
16
+ if (type === "single")
17
+ return isOpen ? [] : [id];
18
+ return isOpen ? prev.filter((x) => x !== id) : [...prev, id];
19
+ });
20
+ };
21
+ return (_jsx(AccordionContext.Provider, { value: { open, toggle, type }, children: _jsx("div", { "data-slot": "accordion", className: cn("space-y-2", className), children: children }) }));
22
+ }
23
+ function AccordionItem({ value, className, children, }) {
24
+ return (_jsx("div", { "data-slot": "accordion-item", "data-value": value, className: cn("overflow-hidden rounded-xl border border-border/40 bg-card/40", className), children: children }));
25
+ }
26
+ function AccordionTrigger({ value, className, children, }) {
27
+ const ctx = React.useContext(AccordionContext);
28
+ const isOpen = ctx?.open.includes(value);
29
+ return (_jsxs("button", { type: "button", "data-slot": "accordion-trigger", "aria-expanded": isOpen, className: cn("flex w-full items-center justify-between gap-2 px-4 py-3 text-left text-sm font-bold", className), onClick: () => ctx?.toggle(value), children: [children, _jsx(ChevronDown, { className: cn("size-4 shrink-0 transition-transform", isOpen && "rotate-180") })] }));
30
+ }
31
+ function AccordionContent({ value, className, children, }) {
32
+ const ctx = React.useContext(AccordionContext);
33
+ if (!ctx?.open.includes(value))
34
+ return null;
35
+ return (_jsx("div", { "data-slot": "accordion-content", className: cn("border-t border-border/30 px-4 py-3 text-sm", className), children: children }));
36
+ }
37
+ export { Accordion, AccordionItem, AccordionTrigger, AccordionContent };
@@ -0,0 +1,10 @@
1
+ import * as React from "react";
2
+ import { type VariantProps } from "class-variance-authority";
3
+ declare const alertVariants: (props?: ({
4
+ variant?: "default" | "info" | "warm" | "highlight" | "danger" | null | undefined;
5
+ } & import("class-variance-authority/types").ClassProp) | undefined) => string;
6
+ declare function Alert({ className, variant, ...props }: React.ComponentProps<"div"> & VariantProps<typeof alertVariants>): React.JSX.Element;
7
+ declare function AlertTitle({ className, ...props }: React.ComponentProps<"h5">): React.JSX.Element;
8
+ declare function AlertDescription({ className, ...props }: React.ComponentProps<"div">): React.JSX.Element;
9
+ export { Alert, AlertTitle, AlertDescription, alertVariants };
10
+ //# sourceMappingURL=Alert.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Alert.d.ts","sourceRoot":"","sources":["../../src/primitives/Alert.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAC/B,OAAO,EAAO,KAAK,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAGlE,QAAA,MAAM,aAAa;;8EAelB,CAAC;AAEF,iBAAS,KAAK,CAAC,EACb,SAAS,EACT,OAAO,EACP,GAAG,KAAK,EACT,EAAE,KAAK,CAAC,cAAc,CAAC,KAAK,CAAC,GAAG,YAAY,CAAC,OAAO,aAAa,CAAC,qBASlE;AAED,iBAAS,UAAU,CAAC,EAAE,SAAS,EAAE,GAAG,KAAK,EAAE,EAAE,KAAK,CAAC,cAAc,CAAC,IAAI,CAAC,qBAQtE;AAED,iBAAS,gBAAgB,CAAC,EAAE,SAAS,EAAE,GAAG,KAAK,EAAE,EAAE,KAAK,CAAC,cAAc,CAAC,KAAK,CAAC,qBAQ7E;AAED,OAAO,EAAE,KAAK,EAAE,UAAU,EAAE,gBAAgB,EAAE,aAAa,EAAE,CAAC"}
@@ -0,0 +1,25 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import { cva } from "class-variance-authority";
3
+ import { cn } from "../lib/cn";
4
+ const alertVariants = cva("relative w-full rounded-[var(--radius-card)] border px-4 py-3 text-sm", {
5
+ variants: {
6
+ variant: {
7
+ default: "border-border/50 bg-card/60 text-foreground",
8
+ info: "border-[color-mix(in_srgb,var(--accent-info)_35%,transparent)] bg-[var(--accent-info-bg)] text-[var(--accent-info)]",
9
+ warm: "border-[color-mix(in_srgb,var(--accent-warm)_35%,transparent)] bg-[var(--accent-warm-bg)] text-[var(--accent-warm)]",
10
+ highlight: "border-[color-mix(in_srgb,var(--accent-highlight)_35%,transparent)] bg-[var(--accent-highlight-bg)] text-[var(--accent-highlight)]",
11
+ danger: "border-destructive/40 bg-[var(--accent-danger-bg)] text-destructive",
12
+ },
13
+ },
14
+ defaultVariants: { variant: "default" },
15
+ });
16
+ function Alert({ className, variant, ...props }) {
17
+ return (_jsx("div", { role: "alert", "data-slot": "alert", className: cn(alertVariants({ variant }), className), ...props }));
18
+ }
19
+ function AlertTitle({ className, ...props }) {
20
+ return (_jsx("h5", { "data-slot": "alert-title", className: cn("mb-1 font-black tracking-tight", className), ...props }));
21
+ }
22
+ function AlertDescription({ className, ...props }) {
23
+ return (_jsx("div", { "data-slot": "alert-description", className: cn("text-sm font-medium opacity-90", className), ...props }));
24
+ }
25
+ export { Alert, AlertTitle, AlertDescription, alertVariants };
@@ -0,0 +1,33 @@
1
+ import * as React from "react";
2
+ type AlertDialogProps = {
3
+ open?: boolean;
4
+ defaultOpen?: boolean;
5
+ onOpenChange?: (open: boolean) => void;
6
+ children?: React.ReactNode;
7
+ };
8
+ declare function AlertDialog({ open: openProp, defaultOpen, onOpenChange, children, }: AlertDialogProps): React.JSX.Element;
9
+ declare const AlertDialogTrigger: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.ButtonHTMLAttributes<HTMLButtonElement>, HTMLButtonElement>, "ref"> & {
10
+ asChild?: boolean;
11
+ } & React.RefAttributes<HTMLButtonElement>>;
12
+ declare function AlertDialogPortal({ children }: {
13
+ children?: React.ReactNode;
14
+ }): React.JSX.Element;
15
+ declare const AlertDialogOverlay: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, "ref"> & React.RefAttributes<HTMLDivElement>>;
16
+ declare const AlertDialogContent: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, "ref"> & {
17
+ /** Extra classes for the dimmer (z-index, backdrop tweaks, etc.). */
18
+ overlayClassName?: string;
19
+ } & React.RefAttributes<HTMLDivElement>>;
20
+ declare const AlertDialogHeader: {
21
+ ({ className, ...props }: React.HTMLAttributes<HTMLDivElement>): React.JSX.Element;
22
+ displayName: string;
23
+ };
24
+ declare const AlertDialogFooter: {
25
+ ({ className, ...props }: React.HTMLAttributes<HTMLDivElement>): React.JSX.Element;
26
+ displayName: string;
27
+ };
28
+ declare const AlertDialogTitle: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLHeadingElement>, HTMLHeadingElement>, "ref"> & React.RefAttributes<HTMLHeadingElement>>;
29
+ declare const AlertDialogDescription: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLParagraphElement>, HTMLParagraphElement>, "ref"> & React.RefAttributes<HTMLParagraphElement>>;
30
+ declare const AlertDialogAction: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.ButtonHTMLAttributes<HTMLButtonElement>, HTMLButtonElement>, "ref"> & React.RefAttributes<HTMLButtonElement>>;
31
+ declare const AlertDialogCancel: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.ButtonHTMLAttributes<HTMLButtonElement>, HTMLButtonElement>, "ref"> & React.RefAttributes<HTMLButtonElement>>;
32
+ export { AlertDialog, AlertDialogPortal, AlertDialogOverlay, AlertDialogTrigger, AlertDialogContent, AlertDialogHeader, AlertDialogFooter, AlertDialogTitle, AlertDialogDescription, AlertDialogAction, AlertDialogCancel, };
33
+ //# sourceMappingURL=AlertDialog.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AlertDialog.d.ts","sourceRoot":"","sources":["../../src/primitives/AlertDialog.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AA4B/B,KAAK,gBAAgB,GAAG;IACtB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,YAAY,CAAC,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,CAAC;IACvC,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;CAC5B,CAAC;AAEF,iBAAS,WAAW,CAAC,EACnB,IAAI,EAAE,QAAQ,EACd,WAAW,EACX,YAAY,EACZ,QAAQ,GACT,EAAE,gBAAgB,qBAiBlB;AAED,QAAA,MAAM,kBAAkB;cAEiC,OAAO;2CAiB9D,CAAC;AAGH,iBAAS,iBAAiB,CAAC,EAAE,QAAQ,EAAE,EAAE;IAAE,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;CAAE,qBAEtE;AAED,QAAA,MAAM,kBAAkB,mKAoBtB,CAAC;AAGH,QAAA,MAAM,kBAAkB;IAGpB,qEAAqE;uBAClD,MAAM;wCAuC3B,CAAC;AAGH,QAAA,MAAM,iBAAiB;8BAGpB,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;;CAMtC,CAAC;AAGF,QAAA,MAAM,iBAAiB;8BAGpB,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;;CAStC,CAAC;AAGF,QAAA,MAAM,gBAAgB,+KAapB,CAAC;AAGH,QAAA,MAAM,sBAAsB,qLAa1B,CAAC;AAGH,QAAA,MAAM,iBAAiB,kLAiBrB,CAAC;AAGH,QAAA,MAAM,iBAAiB,kLAqBrB,CAAC;AAGH,OAAO,EACL,WAAW,EACX,iBAAiB,EACjB,kBAAkB,EAClB,kBAAkB,EAClB,kBAAkB,EAClB,iBAAiB,EACjB,iBAAiB,EACjB,gBAAgB,EAChB,sBAAsB,EACtB,iBAAiB,EACjB,iBAAiB,GAClB,CAAC"}
@@ -0,0 +1,96 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import * as React from "react";
3
+ import { composeRefs } from "../lib/compose-refs";
4
+ import { Portal } from "../lib/portal";
5
+ import { Slot } from "../lib/slot";
6
+ import { useControllableState } from "../lib/use-controllable-state";
7
+ import { useFocusTrap } from "../lib/use-focus-trap";
8
+ import { cn } from "../lib/cn";
9
+ import { OVERLAY_Z_INDEX, fixedLayerStyle } from "../lib/overlay-stack";
10
+ import { buttonVariants } from "./Button";
11
+ const AlertDialogContext = React.createContext(null);
12
+ function useAlertDialogContext(component) {
13
+ const ctx = React.useContext(AlertDialogContext);
14
+ if (!ctx) {
15
+ throw new Error(`${component} must be used within <AlertDialog>`);
16
+ }
17
+ return ctx;
18
+ }
19
+ function AlertDialog({ open: openProp, defaultOpen, onOpenChange, children, }) {
20
+ const [open = false, setOpen] = useControllableState({
21
+ prop: openProp,
22
+ defaultProp: defaultOpen ?? false,
23
+ onChange: onOpenChange,
24
+ });
25
+ const contentRef = React.useRef(null);
26
+ // Provider-only root — no DOM wrapper (matches Radix Root / Dialog / Select).
27
+ // A wrapper div becomes an extra CSS grid/flex item when AlertDialog is a Fragment sibling.
28
+ return (_jsx(AlertDialogContext.Provider, { value: { open, setOpen: (next) => setOpen(next), contentRef }, children: children }));
29
+ }
30
+ const AlertDialogTrigger = React.forwardRef(({ asChild = false, onClick, ...props }, ref) => {
31
+ const { setOpen } = useAlertDialogContext("AlertDialogTrigger");
32
+ const Comp = asChild ? Slot : "button";
33
+ return (_jsx(Comp, { ref: ref, type: asChild ? undefined : "button", "data-slot": "alert-dialog-trigger", ...props, onClick: (event) => {
34
+ onClick?.(event);
35
+ if (!event.defaultPrevented)
36
+ setOpen(true);
37
+ } }));
38
+ });
39
+ AlertDialogTrigger.displayName = "AlertDialogTrigger";
40
+ function AlertDialogPortal({ children }) {
41
+ return _jsx(Portal, { children: children });
42
+ }
43
+ const AlertDialogOverlay = React.forwardRef(({ className, style, ...props }, ref) => {
44
+ const { open } = useAlertDialogContext("AlertDialogOverlay");
45
+ if (!open)
46
+ return null;
47
+ return (_jsx("div", { ref: ref, "data-slot": "alert-dialog-overlay", "data-state": "open", className: cn("fixed inset-0 z-[11000] bg-[var(--modal-overlay-bg)] backdrop-blur-[var(--modal-overlay-blur)] data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0", className), ...props, style: fixedLayerStyle(OVERLAY_Z_INDEX.modal, style) }));
48
+ });
49
+ AlertDialogOverlay.displayName = "AlertDialogOverlay";
50
+ const AlertDialogContent = React.forwardRef(({ className, overlayClassName, style, ...props }, ref) => {
51
+ const { open, setOpen, contentRef } = useAlertDialogContext("AlertDialogContent");
52
+ useFocusTrap(contentRef, open);
53
+ React.useEffect(() => {
54
+ if (!open)
55
+ return;
56
+ const handleKeyDown = (event) => {
57
+ if (event.key === "Escape") {
58
+ event.stopPropagation();
59
+ setOpen(false);
60
+ }
61
+ };
62
+ document.addEventListener("keydown", handleKeyDown);
63
+ return () => document.removeEventListener("keydown", handleKeyDown);
64
+ }, [open, setOpen]);
65
+ if (!open)
66
+ return null;
67
+ return (_jsxs(AlertDialogPortal, { children: [_jsx(AlertDialogOverlay, { className: overlayClassName }), _jsx("div", { ref: composeRefs(ref, contentRef), role: "alertdialog", "aria-modal": "true", "data-slot": "alert-dialog-content", "data-state": "open", tabIndex: -1, className: cn("glass data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 fixed top-[50%] left-[50%] z-[11000] grid w-full max-w-[calc(100%-2rem)] translate-x-[-50%] translate-y-[-50%] gap-4 rounded-2xl p-6 shadow-2xl duration-200 sm:max-w-lg overflow-hidden", className), ...props, style: fixedLayerStyle(OVERLAY_Z_INDEX.modal, style) })] }));
68
+ });
69
+ AlertDialogContent.displayName = "AlertDialogContent";
70
+ const AlertDialogHeader = ({ className, ...props }) => (_jsx("div", { "data-slot": "alert-dialog-header", className: cn("flex flex-col gap-2 text-center", className), ...props }));
71
+ AlertDialogHeader.displayName = "AlertDialogHeader";
72
+ const AlertDialogFooter = ({ className, ...props }) => (_jsx("div", { "data-slot": "alert-dialog-footer", className: cn("flex flex-col-reverse gap-2 sm:flex-row sm:justify-between border-t border-border/50 pt-4", className), ...props }));
73
+ AlertDialogFooter.displayName = "AlertDialogFooter";
74
+ const AlertDialogTitle = React.forwardRef(({ className, ...props }, ref) => (_jsx("h2", { ref: ref, "data-slot": "alert-dialog-title", className: cn("text-xl font-bold leading-tight tracking-tight text-center", className), ...props })));
75
+ AlertDialogTitle.displayName = "AlertDialogTitle";
76
+ const AlertDialogDescription = React.forwardRef(({ className, ...props }, ref) => (_jsx("p", { ref: ref, "data-slot": "alert-dialog-description", className: cn("text-sm leading-relaxed text-foreground/70 text-center", className), ...props })));
77
+ AlertDialogDescription.displayName = "AlertDialogDescription";
78
+ const AlertDialogAction = React.forwardRef(({ className, onClick, ...props }, ref) => {
79
+ const { setOpen } = useAlertDialogContext("AlertDialogAction");
80
+ return (_jsx("button", { ref: ref, type: "button", className: cn(buttonVariants({ size: "lg" }), "px-8", className), ...props, onClick: (event) => {
81
+ onClick?.(event);
82
+ if (!event.defaultPrevented)
83
+ setOpen(false);
84
+ } }));
85
+ });
86
+ AlertDialogAction.displayName = "AlertDialogAction";
87
+ const AlertDialogCancel = React.forwardRef(({ className, onClick, ...props }, ref) => {
88
+ const { setOpen } = useAlertDialogContext("AlertDialogCancel");
89
+ return (_jsx("button", { ref: ref, type: "button", className: cn(buttonVariants({ variant: "outline", size: "lg" }), "px-8 border-2", className), ...props, onClick: (event) => {
90
+ onClick?.(event);
91
+ if (!event.defaultPrevented)
92
+ setOpen(false);
93
+ } }));
94
+ });
95
+ AlertDialogCancel.displayName = "AlertDialogCancel";
96
+ export { AlertDialog, AlertDialogPortal, AlertDialogOverlay, AlertDialogTrigger, AlertDialogContent, AlertDialogHeader, AlertDialogFooter, AlertDialogTitle, AlertDialogDescription, AlertDialogAction, AlertDialogCancel, };
@@ -0,0 +1,15 @@
1
+ import * as React from "react";
2
+ declare const Avatar: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLSpanElement>, HTMLSpanElement>, "ref"> & React.RefAttributes<HTMLSpanElement>>;
3
+ declare const AvatarImage: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.ImgHTMLAttributes<HTMLImageElement>, HTMLImageElement>, "ref"> & React.RefAttributes<HTMLImageElement>>;
4
+ declare const AvatarFallback: React.ForwardRefExoticComponent<Omit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLSpanElement>, HTMLSpanElement>, "ref"> & React.RefAttributes<HTMLSpanElement>>;
5
+ /**
6
+ * Plain initials circle — use when {@link AvatarFallback} would stay hidden
7
+ * without an image load cycle (e.g. no {@link AvatarImage} child).
8
+ */
9
+ declare function InitialsAvatar({ name, className, textClassName, }: {
10
+ name?: string | null;
11
+ className?: string;
12
+ textClassName?: string;
13
+ }): React.JSX.Element;
14
+ export { Avatar, AvatarImage, AvatarFallback, InitialsAvatar };
15
+ //# sourceMappingURL=Avatar.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Avatar.d.ts","sourceRoot":"","sources":["../../src/primitives/Avatar.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAc/B,QAAA,MAAM,MAAM,sKA6BV,CAAC;AAGH,QAAA,MAAM,WAAW,4KAsCf,CAAC;AAGH,QAAA,MAAM,cAAc,sKAoBlB,CAAC;AAGH;;;GAGG;AACH,iBAAS,cAAc,CAAC,EACtB,IAAI,EACJ,SAAS,EACT,aAAa,GACd,EAAE;IACD,IAAI,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB,qBAcA;AAED,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,cAAc,EAAE,cAAc,EAAE,CAAC"}
@@ -0,0 +1,52 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import * as React from "react";
3
+ import { getAvatarColor, getInitials } from "../lib/avatar-utils";
4
+ import { cn } from "../lib/cn";
5
+ const AvatarContext = React.createContext(null);
6
+ const Avatar = React.forwardRef(({ className, children, ...props }, ref) => {
7
+ const [imageStatus, setImageStatus] = React.useState("idle");
8
+ const hasImage = React.Children.toArray(children).some((child) => React.isValidElement(child) &&
9
+ child.type?.displayName === "AvatarImage" &&
10
+ !!child.props.src);
11
+ return (_jsx(AvatarContext.Provider, { value: { imageStatus, setImageStatus }, children: _jsx("span", { ref: ref, "data-slot": "avatar", className: cn("relative flex size-10 shrink-0 overflow-hidden rounded-full", className), ...props, children: children }, hasImage ? "has-image" : "no-image") }));
12
+ });
13
+ Avatar.displayName = "Avatar";
14
+ const AvatarImage = React.forwardRef(({ src, className, onLoad, onError, ...props }, ref) => {
15
+ const ctx = React.useContext(AvatarContext);
16
+ const setImageStatus = ctx?.setImageStatus;
17
+ React.useEffect(() => {
18
+ if (!src) {
19
+ setImageStatus?.("error");
20
+ return;
21
+ }
22
+ setImageStatus?.("loading");
23
+ }, [src, setImageStatus]);
24
+ if (!src)
25
+ return null;
26
+ return (_jsx("img", { ref: ref, "data-slot": "avatar-image", className: cn("aspect-square size-full", ctx?.imageStatus !== "loaded" && "hidden", className), src: src, onLoad: (event) => {
27
+ setImageStatus?.("loaded");
28
+ onLoad?.(event);
29
+ }, onError: (event) => {
30
+ setImageStatus?.("error");
31
+ onError?.(event);
32
+ }, ...props }));
33
+ });
34
+ AvatarImage.displayName = "AvatarImage";
35
+ const AvatarFallback = React.forwardRef(({ className, ...props }, ref) => {
36
+ const ctx = React.useContext(AvatarContext);
37
+ const show = !ctx || ctx.imageStatus !== "loaded";
38
+ if (!show)
39
+ return null;
40
+ return (_jsx("span", { ref: ref, "data-slot": "avatar-fallback", className: cn("bg-muted flex size-full items-center justify-center rounded-full", className), ...props }));
41
+ });
42
+ AvatarFallback.displayName = "AvatarFallback";
43
+ /**
44
+ * Plain initials circle — use when {@link AvatarFallback} would stay hidden
45
+ * without an image load cycle (e.g. no {@link AvatarImage} child).
46
+ */
47
+ function InitialsAvatar({ name, className, textClassName, }) {
48
+ const n = name?.trim() || "User";
49
+ const initials = getInitials(n) || "?";
50
+ return (_jsx("div", { className: cn("relative flex shrink-0 select-none items-center justify-center overflow-hidden rounded-full text-white", getAvatarColor(n), className), children: _jsx("span", { className: cn("leading-none", textClassName), children: initials }) }));
51
+ }
52
+ export { Avatar, AvatarImage, AvatarFallback, InitialsAvatar };