@mortenbrudvik/waveui 0.4.0 → 0.7.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 (574) hide show
  1. package/README.md +1221 -173
  2. package/dist/_virtual/_rolldown/runtime.cjs +1 -0
  3. package/dist/components/button/Button.cjs +2 -0
  4. package/dist/components/button/Button.cjs.map +1 -0
  5. package/dist/components/button/Button.mjs +50 -0
  6. package/dist/components/button/Button.mjs.map +1 -0
  7. package/dist/components/button/Button.semantics.cjs +2 -0
  8. package/dist/components/button/Button.semantics.cjs.map +1 -0
  9. package/dist/components/button/Button.semantics.mjs +61 -0
  10. package/dist/components/button/Button.semantics.mjs.map +1 -0
  11. package/dist/components/button/Button.slots.cjs +2 -0
  12. package/dist/components/button/Button.slots.cjs.map +1 -0
  13. package/dist/components/button/Button.slots.mjs +47 -0
  14. package/dist/components/button/Button.slots.mjs.map +1 -0
  15. package/dist/components/button/CompoundButton.cjs +2 -0
  16. package/dist/components/button/CompoundButton.cjs.map +1 -0
  17. package/dist/components/button/CompoundButton.mjs +53 -0
  18. package/dist/components/button/CompoundButton.mjs.map +1 -0
  19. package/dist/components/button/Link.cjs +2 -0
  20. package/dist/components/button/Link.cjs.map +1 -0
  21. package/dist/components/button/Link.mjs +37 -0
  22. package/dist/components/button/Link.mjs.map +1 -0
  23. package/dist/components/button/MenuButton.cjs +2 -0
  24. package/dist/components/button/MenuButton.cjs.map +1 -0
  25. package/dist/components/button/MenuButton.mjs +45 -0
  26. package/dist/components/button/MenuButton.mjs.map +1 -0
  27. package/dist/components/button/SplitButton.cjs +2 -0
  28. package/dist/components/button/SplitButton.cjs.map +1 -0
  29. package/dist/components/button/SplitButton.mjs +66 -0
  30. package/dist/components/button/SplitButton.mjs.map +1 -0
  31. package/dist/components/button/ToggleButton.cjs +2 -0
  32. package/dist/components/button/ToggleButton.cjs.map +1 -0
  33. package/dist/components/button/ToggleButton.mjs +65 -0
  34. package/dist/components/button/ToggleButton.mjs.map +1 -0
  35. package/dist/components/button/Toolbar.cjs +2 -0
  36. package/dist/components/button/Toolbar.cjs.map +1 -0
  37. package/dist/components/button/Toolbar.context.cjs +2 -0
  38. package/dist/components/button/Toolbar.context.cjs.map +1 -0
  39. package/dist/components/button/Toolbar.context.mjs +31 -0
  40. package/dist/components/button/Toolbar.context.mjs.map +1 -0
  41. package/dist/components/button/Toolbar.mjs +63 -0
  42. package/dist/components/button/Toolbar.mjs.map +1 -0
  43. package/dist/components/button/Toolbar.parts.cjs +2 -0
  44. package/dist/components/button/Toolbar.parts.cjs.map +1 -0
  45. package/dist/components/button/Toolbar.parts.mjs +131 -0
  46. package/dist/components/button/Toolbar.parts.mjs.map +1 -0
  47. package/dist/components/button/buttonStyles.cjs +2 -0
  48. package/dist/components/button/buttonStyles.cjs.map +1 -0
  49. package/dist/components/button/buttonStyles.mjs +39 -0
  50. package/dist/components/button/buttonStyles.mjs.map +1 -0
  51. package/dist/components/data-display/Avatar.cjs +2 -0
  52. package/dist/components/data-display/Avatar.cjs.map +1 -0
  53. package/dist/components/data-display/Avatar.mjs +157 -0
  54. package/dist/components/data-display/Avatar.mjs.map +1 -0
  55. package/dist/components/data-display/AvatarGroup.cjs +2 -0
  56. package/dist/components/data-display/AvatarGroup.cjs.map +1 -0
  57. package/dist/components/data-display/AvatarGroup.mjs +134 -0
  58. package/dist/components/data-display/AvatarGroup.mjs.map +1 -0
  59. package/dist/components/data-display/Badge.cjs +2 -0
  60. package/dist/components/data-display/Badge.cjs.map +1 -0
  61. package/dist/components/data-display/Badge.colors.cjs +2 -0
  62. package/dist/components/data-display/Badge.colors.cjs.map +1 -0
  63. package/dist/components/data-display/Badge.colors.mjs +58 -0
  64. package/dist/components/data-display/Badge.colors.mjs.map +1 -0
  65. package/dist/components/data-display/Badge.mjs +32 -0
  66. package/dist/components/data-display/Badge.mjs.map +1 -0
  67. package/dist/components/data-display/CounterBadge.cjs +2 -0
  68. package/dist/components/data-display/CounterBadge.cjs.map +1 -0
  69. package/dist/components/data-display/CounterBadge.mjs +28 -0
  70. package/dist/components/data-display/CounterBadge.mjs.map +1 -0
  71. package/dist/components/data-display/Divider.cjs +2 -0
  72. package/dist/components/data-display/Divider.cjs.map +1 -0
  73. package/dist/components/data-display/Divider.mjs +52 -0
  74. package/dist/components/data-display/Divider.mjs.map +1 -0
  75. package/dist/components/data-display/Image.cjs +2 -0
  76. package/dist/components/data-display/Image.cjs.map +1 -0
  77. package/dist/components/data-display/Image.mjs +32 -0
  78. package/dist/components/data-display/Image.mjs.map +1 -0
  79. package/dist/components/data-display/InfoLabel.cjs +2 -0
  80. package/dist/components/data-display/InfoLabel.cjs.map +1 -0
  81. package/dist/components/data-display/InfoLabel.mjs +104 -0
  82. package/dist/components/data-display/InfoLabel.mjs.map +1 -0
  83. package/dist/components/data-display/List.cjs +2 -0
  84. package/dist/components/data-display/List.cjs.map +1 -0
  85. package/dist/components/data-display/List.mjs +381 -0
  86. package/dist/components/data-display/List.mjs.map +1 -0
  87. package/dist/components/data-display/List.registry.cjs +2 -0
  88. package/dist/components/data-display/List.registry.cjs.map +1 -0
  89. package/dist/components/data-display/List.registry.mjs +101 -0
  90. package/dist/components/data-display/List.registry.mjs.map +1 -0
  91. package/dist/components/data-display/Persona.cjs +2 -0
  92. package/dist/components/data-display/Persona.cjs.map +1 -0
  93. package/dist/components/data-display/Persona.mjs +48 -0
  94. package/dist/components/data-display/Persona.mjs.map +1 -0
  95. package/dist/components/data-display/PresenceBadge.cjs +2 -0
  96. package/dist/components/data-display/PresenceBadge.cjs.map +1 -0
  97. package/dist/components/data-display/PresenceBadge.mjs +71 -0
  98. package/dist/components/data-display/PresenceBadge.mjs.map +1 -0
  99. package/dist/components/data-display/Tag.cjs +2 -0
  100. package/dist/components/data-display/Tag.cjs.map +1 -0
  101. package/dist/components/data-display/Tag.mjs +147 -0
  102. package/dist/components/data-display/Tag.mjs.map +1 -0
  103. package/dist/components/feedback/MessageBar.cjs +2 -0
  104. package/dist/components/feedback/MessageBar.cjs.map +1 -0
  105. package/dist/components/feedback/MessageBar.mjs +144 -0
  106. package/dist/components/feedback/MessageBar.mjs.map +1 -0
  107. package/dist/components/feedback/MessageBar.status.cjs +2 -0
  108. package/dist/components/feedback/MessageBar.status.cjs.map +1 -0
  109. package/dist/components/feedback/MessageBar.status.mjs +45 -0
  110. package/dist/components/feedback/MessageBar.status.mjs.map +1 -0
  111. package/dist/components/feedback/ProgressBar.cjs +2 -0
  112. package/dist/components/feedback/ProgressBar.cjs.map +1 -0
  113. package/dist/components/feedback/ProgressBar.mjs +72 -0
  114. package/dist/components/feedback/ProgressBar.mjs.map +1 -0
  115. package/dist/components/feedback/Skeleton.cjs +2 -0
  116. package/dist/components/feedback/Skeleton.cjs.map +1 -0
  117. package/dist/components/feedback/Skeleton.mjs +47 -0
  118. package/dist/components/feedback/Skeleton.mjs.map +1 -0
  119. package/dist/components/feedback/Spinner.cjs +2 -0
  120. package/dist/components/feedback/Spinner.cjs.map +1 -0
  121. package/dist/components/feedback/Spinner.mjs +60 -0
  122. package/dist/components/feedback/Spinner.mjs.map +1 -0
  123. package/dist/components/feedback/Toast.cjs +2 -0
  124. package/dist/components/feedback/Toast.cjs.map +1 -0
  125. package/dist/components/feedback/Toast.mjs +347 -0
  126. package/dist/components/feedback/Toast.mjs.map +1 -0
  127. package/dist/components/input/Checkbox.cjs +2 -0
  128. package/dist/components/input/Checkbox.cjs.map +1 -0
  129. package/dist/components/input/Checkbox.mjs +96 -0
  130. package/dist/components/input/Checkbox.mjs.map +1 -0
  131. package/dist/components/input/ColorPicker.cjs +6 -0
  132. package/dist/components/input/ColorPicker.cjs.map +1 -0
  133. package/dist/components/input/ColorPicker.mjs +236 -0
  134. package/dist/components/input/ColorPicker.mjs.map +1 -0
  135. package/dist/components/input/Combobox.cjs +2 -0
  136. package/dist/components/input/Combobox.cjs.map +1 -0
  137. package/dist/components/input/Combobox.expand.cjs +2 -0
  138. package/dist/components/input/Combobox.expand.cjs.map +1 -0
  139. package/dist/components/input/Combobox.expand.mjs +38 -0
  140. package/dist/components/input/Combobox.expand.mjs.map +1 -0
  141. package/dist/components/input/Combobox.mjs +187 -0
  142. package/dist/components/input/Combobox.mjs.map +1 -0
  143. package/dist/components/input/DatePicker.cjs +2 -0
  144. package/dist/components/input/DatePicker.cjs.map +1 -0
  145. package/dist/components/input/DatePicker.mjs +340 -0
  146. package/dist/components/input/DatePicker.mjs.map +1 -0
  147. package/dist/components/input/Dropdown.cjs +2 -0
  148. package/dist/components/input/Dropdown.cjs.map +1 -0
  149. package/dist/components/input/Dropdown.mjs +128 -0
  150. package/dist/components/input/Dropdown.mjs.map +1 -0
  151. package/dist/components/input/Field.cjs +2 -0
  152. package/dist/components/input/Field.cjs.map +1 -0
  153. package/dist/components/input/Field.mjs +200 -0
  154. package/dist/components/input/Field.mjs.map +1 -0
  155. package/dist/components/input/Input.cjs +2 -0
  156. package/dist/components/input/Input.cjs.map +1 -0
  157. package/dist/components/input/Input.mjs +81 -0
  158. package/dist/components/input/Input.mjs.map +1 -0
  159. package/dist/components/input/Label.cjs +2 -0
  160. package/dist/components/input/Label.cjs.map +1 -0
  161. package/dist/components/input/Label.mjs +28 -0
  162. package/dist/components/input/Label.mjs.map +1 -0
  163. package/dist/components/input/Option.cjs +2 -0
  164. package/dist/components/input/Option.cjs.map +1 -0
  165. package/dist/components/input/Option.mjs +169 -0
  166. package/dist/components/input/Option.mjs.map +1 -0
  167. package/dist/components/input/RadioGroup.cjs +2 -0
  168. package/dist/components/input/RadioGroup.cjs.map +1 -0
  169. package/dist/components/input/RadioGroup.mjs +139 -0
  170. package/dist/components/input/RadioGroup.mjs.map +1 -0
  171. package/dist/components/input/Rating.cjs +2 -0
  172. package/dist/components/input/Rating.cjs.map +1 -0
  173. package/dist/components/input/Rating.mjs +196 -0
  174. package/dist/components/input/Rating.mjs.map +1 -0
  175. package/dist/components/input/SearchBox.cjs +2 -0
  176. package/dist/components/input/SearchBox.cjs.map +1 -0
  177. package/dist/components/input/SearchBox.mjs +205 -0
  178. package/dist/components/input/SearchBox.mjs.map +1 -0
  179. package/dist/components/input/Select.cjs +2 -0
  180. package/dist/components/input/Select.cjs.map +1 -0
  181. package/dist/components/input/Select.mjs +33 -0
  182. package/dist/components/input/Select.mjs.map +1 -0
  183. package/dist/components/input/Slider.cjs +2 -0
  184. package/dist/components/input/Slider.cjs.map +1 -0
  185. package/dist/components/input/Slider.mjs +79 -0
  186. package/dist/components/input/Slider.mjs.map +1 -0
  187. package/dist/components/input/SpinButton.cjs +2 -0
  188. package/dist/components/input/SpinButton.cjs.map +1 -0
  189. package/dist/components/input/SpinButton.mjs +157 -0
  190. package/dist/components/input/SpinButton.mjs.map +1 -0
  191. package/dist/components/input/SwatchPicker.cjs +2 -0
  192. package/dist/components/input/SwatchPicker.cjs.map +1 -0
  193. package/dist/components/input/SwatchPicker.mjs +113 -0
  194. package/dist/components/input/SwatchPicker.mjs.map +1 -0
  195. package/dist/components/input/Switch.cjs +2 -0
  196. package/dist/components/input/Switch.cjs.map +1 -0
  197. package/dist/components/input/Switch.mjs +92 -0
  198. package/dist/components/input/Switch.mjs.map +1 -0
  199. package/dist/components/input/TagPicker.cjs +2 -0
  200. package/dist/components/input/TagPicker.cjs.map +1 -0
  201. package/dist/components/input/TagPicker.mjs +249 -0
  202. package/dist/components/input/TagPicker.mjs.map +1 -0
  203. package/dist/components/input/Textarea.cjs +2 -0
  204. package/dist/components/input/Textarea.cjs.map +1 -0
  205. package/dist/components/input/Textarea.mjs +32 -0
  206. package/dist/components/input/Textarea.mjs.map +1 -0
  207. package/dist/components/input/TimePicker.cjs +2 -0
  208. package/dist/components/input/TimePicker.cjs.map +1 -0
  209. package/dist/components/input/TimePicker.mjs +292 -0
  210. package/dist/components/input/TimePicker.mjs.map +1 -0
  211. package/dist/components/input/colorUtils.cjs +2 -0
  212. package/dist/components/input/colorUtils.cjs.map +1 -0
  213. package/dist/components/input/colorUtils.mjs +96 -0
  214. package/dist/components/input/colorUtils.mjs.map +1 -0
  215. package/dist/components/input/dateUtils.cjs +2 -0
  216. package/dist/components/input/dateUtils.cjs.map +1 -0
  217. package/dist/components/input/dateUtils.mjs +250 -0
  218. package/dist/components/input/dateUtils.mjs.map +1 -0
  219. package/dist/components/input/pickerStyles.cjs +2 -0
  220. package/dist/components/input/pickerStyles.cjs.map +1 -0
  221. package/dist/components/input/pickerStyles.mjs +10 -0
  222. package/dist/components/input/pickerStyles.mjs.map +1 -0
  223. package/dist/components/internal/HiddenInput.cjs +2 -0
  224. package/dist/components/internal/HiddenInput.cjs.map +1 -0
  225. package/dist/components/internal/HiddenInput.mjs +88 -0
  226. package/dist/components/internal/HiddenInput.mjs.map +1 -0
  227. package/dist/components/layout/Accordion.cjs +2 -0
  228. package/dist/components/layout/Accordion.cjs.map +1 -0
  229. package/dist/components/layout/Accordion.mjs +236 -0
  230. package/dist/components/layout/Accordion.mjs.map +1 -0
  231. package/dist/components/layout/Card.cjs +2 -0
  232. package/dist/components/layout/Card.cjs.map +1 -0
  233. package/dist/components/layout/Card.mjs +121 -0
  234. package/dist/components/layout/Card.mjs.map +1 -0
  235. package/dist/components/layout/Carousel.cjs +2 -0
  236. package/dist/components/layout/Carousel.cjs.map +1 -0
  237. package/dist/components/layout/Carousel.mjs +205 -0
  238. package/dist/components/layout/Carousel.mjs.map +1 -0
  239. package/dist/components/layout/Flex.cjs +2 -0
  240. package/dist/components/layout/Flex.cjs.map +1 -0
  241. package/dist/components/layout/Flex.mjs +54 -0
  242. package/dist/components/layout/Flex.mjs.map +1 -0
  243. package/dist/components/layout/Grid.cjs +2 -0
  244. package/dist/components/layout/Grid.cjs.map +1 -0
  245. package/dist/components/layout/Grid.mjs +62 -0
  246. package/dist/components/layout/Grid.mjs.map +1 -0
  247. package/dist/components/layout/Overflow.cjs +2 -0
  248. package/dist/components/layout/Overflow.cjs.map +1 -0
  249. package/dist/components/layout/Overflow.mjs +269 -0
  250. package/dist/components/layout/Overflow.mjs.map +1 -0
  251. package/dist/components/layout/Stack.cjs +2 -0
  252. package/dist/components/layout/Stack.cjs.map +1 -0
  253. package/dist/components/layout/Stack.mjs +39 -0
  254. package/dist/components/layout/Stack.mjs.map +1 -0
  255. package/dist/components/layout/TabList.cjs +2 -0
  256. package/dist/components/layout/TabList.cjs.map +1 -0
  257. package/dist/components/layout/TabList.mjs +238 -0
  258. package/dist/components/layout/TabList.mjs.map +1 -0
  259. package/dist/components/layout/Tree.cjs +2 -0
  260. package/dist/components/layout/Tree.cjs.map +1 -0
  261. package/dist/components/layout/Tree.mjs +220 -0
  262. package/dist/components/layout/Tree.mjs.map +1 -0
  263. package/dist/components/layout/disclosureIds.cjs +2 -0
  264. package/dist/components/layout/disclosureIds.cjs.map +1 -0
  265. package/dist/components/layout/disclosureIds.mjs +12 -0
  266. package/dist/components/layout/disclosureIds.mjs.map +1 -0
  267. package/dist/components/motion/Presence.cjs +2 -0
  268. package/dist/components/motion/Presence.cjs.map +1 -0
  269. package/dist/components/motion/Presence.mjs +35 -0
  270. package/dist/components/motion/Presence.mjs.map +1 -0
  271. package/dist/components/navigation/Breadcrumb.cjs +2 -0
  272. package/dist/components/navigation/Breadcrumb.cjs.map +1 -0
  273. package/dist/components/navigation/Breadcrumb.mjs +144 -0
  274. package/dist/components/navigation/Breadcrumb.mjs.map +1 -0
  275. package/dist/components/navigation/Menu.cjs +2 -0
  276. package/dist/components/navigation/Menu.cjs.map +1 -0
  277. package/dist/components/navigation/Menu.context.cjs +2 -0
  278. package/dist/components/navigation/Menu.context.cjs.map +1 -0
  279. package/dist/components/navigation/Menu.context.mjs +82 -0
  280. package/dist/components/navigation/Menu.context.mjs.map +1 -0
  281. package/dist/components/navigation/Menu.group.cjs +2 -0
  282. package/dist/components/navigation/Menu.group.cjs.map +1 -0
  283. package/dist/components/navigation/Menu.group.mjs +58 -0
  284. package/dist/components/navigation/Menu.group.mjs.map +1 -0
  285. package/dist/components/navigation/Menu.items.cjs +2 -0
  286. package/dist/components/navigation/Menu.items.cjs.map +1 -0
  287. package/dist/components/navigation/Menu.items.mjs +127 -0
  288. package/dist/components/navigation/Menu.items.mjs.map +1 -0
  289. package/dist/components/navigation/Menu.link.cjs +2 -0
  290. package/dist/components/navigation/Menu.link.cjs.map +1 -0
  291. package/dist/components/navigation/Menu.link.mjs +41 -0
  292. package/dist/components/navigation/Menu.link.mjs.map +1 -0
  293. package/dist/components/navigation/Menu.mjs +27 -0
  294. package/dist/components/navigation/Menu.mjs.map +1 -0
  295. package/dist/components/navigation/Menu.popover.cjs +2 -0
  296. package/dist/components/navigation/Menu.popover.cjs.map +1 -0
  297. package/dist/components/navigation/Menu.popover.mjs +231 -0
  298. package/dist/components/navigation/Menu.popover.mjs.map +1 -0
  299. package/dist/components/navigation/Menu.root.cjs +2 -0
  300. package/dist/components/navigation/Menu.root.cjs.map +1 -0
  301. package/dist/components/navigation/Menu.root.mjs +308 -0
  302. package/dist/components/navigation/Menu.root.mjs.map +1 -0
  303. package/dist/components/navigation/Menu.selectable.cjs +2 -0
  304. package/dist/components/navigation/Menu.selectable.cjs.map +1 -0
  305. package/dist/components/navigation/Menu.selectable.mjs +89 -0
  306. package/dist/components/navigation/Menu.selectable.mjs.map +1 -0
  307. package/dist/components/navigation/Menu.shared.cjs +2 -0
  308. package/dist/components/navigation/Menu.shared.cjs.map +1 -0
  309. package/dist/components/navigation/Menu.shared.mjs +23 -0
  310. package/dist/components/navigation/Menu.shared.mjs.map +1 -0
  311. package/dist/components/navigation/Menu.splitGroup.cjs +2 -0
  312. package/dist/components/navigation/Menu.splitGroup.cjs.map +1 -0
  313. package/dist/components/navigation/Menu.splitGroup.mjs +51 -0
  314. package/dist/components/navigation/Menu.splitGroup.mjs.map +1 -0
  315. package/dist/components/navigation/Menu.trigger.cjs +2 -0
  316. package/dist/components/navigation/Menu.trigger.cjs.map +1 -0
  317. package/dist/components/navigation/Menu.trigger.mjs +79 -0
  318. package/dist/components/navigation/Menu.trigger.mjs.map +1 -0
  319. package/dist/components/navigation/Nav.cjs +2 -0
  320. package/dist/components/navigation/Nav.cjs.map +1 -0
  321. package/dist/components/navigation/Nav.mjs +276 -0
  322. package/dist/components/navigation/Nav.mjs.map +1 -0
  323. package/dist/components/navigation/Pagination.cjs +2 -0
  324. package/dist/components/navigation/Pagination.cjs.map +1 -0
  325. package/dist/components/navigation/Pagination.mjs +110 -0
  326. package/dist/components/navigation/Pagination.mjs.map +1 -0
  327. package/dist/components/navigation/Stepper.cjs +2 -0
  328. package/dist/components/navigation/Stepper.cjs.map +1 -0
  329. package/dist/components/navigation/Stepper.mjs +204 -0
  330. package/dist/components/navigation/Stepper.mjs.map +1 -0
  331. package/dist/components/overlays/Dialog.cjs +2 -0
  332. package/dist/components/overlays/Dialog.cjs.map +1 -0
  333. package/dist/components/overlays/Dialog.mjs +180 -0
  334. package/dist/components/overlays/Dialog.mjs.map +1 -0
  335. package/dist/components/overlays/Dialog.shared.cjs +2 -0
  336. package/dist/components/overlays/Dialog.shared.cjs.map +1 -0
  337. package/dist/components/overlays/Dialog.shared.mjs +227 -0
  338. package/dist/components/overlays/Dialog.shared.mjs.map +1 -0
  339. package/dist/components/overlays/Drawer.cjs +2 -0
  340. package/dist/components/overlays/Drawer.cjs.map +1 -0
  341. package/dist/components/overlays/Drawer.mjs +192 -0
  342. package/dist/components/overlays/Drawer.mjs.map +1 -0
  343. package/dist/components/overlays/Popover.cjs +2 -0
  344. package/dist/components/overlays/Popover.cjs.map +1 -0
  345. package/dist/components/overlays/Popover.mjs +365 -0
  346. package/dist/components/overlays/Popover.mjs.map +1 -0
  347. package/dist/components/overlays/Popover.shared.cjs +2 -0
  348. package/dist/components/overlays/Popover.shared.cjs.map +1 -0
  349. package/dist/components/overlays/Popover.shared.mjs +182 -0
  350. package/dist/components/overlays/Popover.shared.mjs.map +1 -0
  351. package/dist/components/overlays/TeachingPopover.cjs +2 -0
  352. package/dist/components/overlays/TeachingPopover.cjs.map +1 -0
  353. package/dist/components/overlays/TeachingPopover.mjs +181 -0
  354. package/dist/components/overlays/TeachingPopover.mjs.map +1 -0
  355. package/dist/components/overlays/Tooltip.cjs +2 -0
  356. package/dist/components/overlays/Tooltip.cjs.map +1 -0
  357. package/dist/components/overlays/Tooltip.mjs +160 -0
  358. package/dist/components/overlays/Tooltip.mjs.map +1 -0
  359. package/dist/components/portal/Portal.cjs +2 -0
  360. package/dist/components/portal/Portal.cjs.map +1 -0
  361. package/dist/components/portal/Portal.mjs +45 -0
  362. package/dist/components/portal/Portal.mjs.map +1 -0
  363. package/dist/components/provider/WaveProvider.cjs +2 -0
  364. package/dist/components/provider/WaveProvider.cjs.map +1 -0
  365. package/dist/components/provider/WaveProvider.mjs +51 -0
  366. package/dist/components/provider/WaveProvider.mjs.map +1 -0
  367. package/dist/components/table/DataGrid.cjs +2 -0
  368. package/dist/components/table/DataGrid.cjs.map +1 -0
  369. package/dist/components/table/DataGrid.mjs +489 -0
  370. package/dist/components/table/DataGrid.mjs.map +1 -0
  371. package/dist/components/table/Table.cjs +2 -0
  372. package/dist/components/table/Table.cjs.map +1 -0
  373. package/dist/components/table/Table.mjs +99 -0
  374. package/dist/components/table/Table.mjs.map +1 -0
  375. package/dist/components/table/useGridNavigation.cjs +2 -0
  376. package/dist/components/table/useGridNavigation.cjs.map +1 -0
  377. package/dist/components/table/useGridNavigation.mjs +336 -0
  378. package/dist/components/table/useGridNavigation.mjs.map +1 -0
  379. package/dist/components/typography/Text.cjs +2 -0
  380. package/dist/components/typography/Text.cjs.map +1 -0
  381. package/dist/components/typography/Text.mjs +38 -0
  382. package/dist/components/typography/Text.mjs.map +1 -0
  383. package/dist/hooks/useAnnounce.cjs +2 -0
  384. package/dist/hooks/useAnnounce.cjs.map +1 -0
  385. package/dist/hooks/useAnnounce.mjs +88 -0
  386. package/dist/hooks/useAnnounce.mjs.map +1 -0
  387. package/dist/hooks/useCheckedValues.cjs +2 -0
  388. package/dist/hooks/useCheckedValues.cjs.map +1 -0
  389. package/dist/hooks/useCheckedValues.mjs +102 -0
  390. package/dist/hooks/useCheckedValues.mjs.map +1 -0
  391. package/dist/hooks/useContextMenuAnchor.cjs +2 -0
  392. package/dist/hooks/useContextMenuAnchor.cjs.map +1 -0
  393. package/dist/hooks/useContextMenuAnchor.mjs +132 -0
  394. package/dist/hooks/useContextMenuAnchor.mjs.map +1 -0
  395. package/dist/hooks/useControllable.cjs +2 -0
  396. package/dist/hooks/useControllable.cjs.map +1 -0
  397. package/dist/hooks/useControllable.mjs +37 -0
  398. package/dist/hooks/useControllable.mjs.map +1 -0
  399. package/dist/hooks/useDirection.cjs +2 -0
  400. package/dist/hooks/useDirection.cjs.map +1 -0
  401. package/dist/hooks/useDirection.mjs +57 -0
  402. package/dist/hooks/useDirection.mjs.map +1 -0
  403. package/dist/hooks/useDismiss.cjs +2 -0
  404. package/dist/hooks/useDismiss.cjs.map +1 -0
  405. package/dist/hooks/useDismiss.mjs +57 -0
  406. package/dist/hooks/useDismiss.mjs.map +1 -0
  407. package/dist/hooks/useEventCallback.cjs +2 -0
  408. package/dist/hooks/useEventCallback.cjs.map +1 -0
  409. package/dist/hooks/useEventCallback.mjs +16 -0
  410. package/dist/hooks/useEventCallback.mjs.map +1 -0
  411. package/dist/hooks/useFieldControl.cjs +2 -0
  412. package/dist/hooks/useFieldControl.cjs.map +1 -0
  413. package/dist/hooks/useFieldControl.mjs +62 -0
  414. package/dist/hooks/useFieldControl.mjs.map +1 -0
  415. package/dist/hooks/useFocusTrap.cjs +2 -0
  416. package/dist/hooks/useFocusTrap.cjs.map +1 -0
  417. package/dist/hooks/useFocusTrap.mjs +266 -0
  418. package/dist/hooks/useFocusTrap.mjs.map +1 -0
  419. package/dist/hooks/useFormReset.cjs +2 -0
  420. package/dist/hooks/useFormReset.cjs.map +1 -0
  421. package/dist/hooks/useFormReset.mjs +33 -0
  422. package/dist/hooks/useFormReset.mjs.map +1 -0
  423. package/dist/hooks/useHoverIntent.cjs +2 -0
  424. package/dist/hooks/useHoverIntent.cjs.map +1 -0
  425. package/dist/hooks/useHoverIntent.mjs +201 -0
  426. package/dist/hooks/useHoverIntent.mjs.map +1 -0
  427. package/dist/hooks/useId.cjs +2 -0
  428. package/dist/hooks/useId.cjs.map +1 -0
  429. package/dist/hooks/useId.mjs +11 -0
  430. package/dist/hooks/useId.mjs.map +1 -0
  431. package/dist/hooks/useIsClient.cjs +2 -0
  432. package/dist/hooks/useIsClient.cjs.map +1 -0
  433. package/dist/hooks/useIsClient.mjs +19 -0
  434. package/dist/hooks/useIsClient.mjs.map +1 -0
  435. package/dist/hooks/useListbox.cjs +2 -0
  436. package/dist/hooks/useListbox.cjs.map +1 -0
  437. package/dist/hooks/useListbox.mjs +492 -0
  438. package/dist/hooks/useListbox.mjs.map +1 -0
  439. package/dist/hooks/useMergedRefs.cjs +2 -0
  440. package/dist/hooks/useMergedRefs.cjs.map +1 -0
  441. package/dist/hooks/useMergedRefs.mjs +57 -0
  442. package/dist/hooks/useMergedRefs.mjs.map +1 -0
  443. package/dist/hooks/useModalIsolation.cjs +2 -0
  444. package/dist/hooks/useModalIsolation.cjs.map +1 -0
  445. package/dist/hooks/useModalIsolation.mjs +87 -0
  446. package/dist/hooks/useModalIsolation.mjs.map +1 -0
  447. package/dist/hooks/useModalLayer.cjs +2 -0
  448. package/dist/hooks/useModalLayer.cjs.map +1 -0
  449. package/dist/hooks/useModalLayer.mjs +30 -0
  450. package/dist/hooks/useModalLayer.mjs.map +1 -0
  451. package/dist/hooks/usePopupPosition.cjs +2 -0
  452. package/dist/hooks/usePopupPosition.cjs.map +1 -0
  453. package/dist/hooks/usePopupPosition.mjs +117 -0
  454. package/dist/hooks/usePopupPosition.mjs.map +1 -0
  455. package/dist/hooks/usePrefersReducedMotion.cjs +2 -0
  456. package/dist/hooks/usePrefersReducedMotion.cjs.map +1 -0
  457. package/dist/hooks/usePrefersReducedMotion.mjs +24 -0
  458. package/dist/hooks/usePrefersReducedMotion.mjs.map +1 -0
  459. package/dist/hooks/usePresence.cjs +2 -0
  460. package/dist/hooks/usePresence.cjs.map +1 -0
  461. package/dist/hooks/usePresence.mjs +136 -0
  462. package/dist/hooks/usePresence.mjs.map +1 -0
  463. package/dist/hooks/usePreserveFocus.cjs +2 -0
  464. package/dist/hooks/usePreserveFocus.cjs.map +1 -0
  465. package/dist/hooks/usePreserveFocus.mjs +50 -0
  466. package/dist/hooks/usePreserveFocus.mjs.map +1 -0
  467. package/dist/hooks/useRestoreFocus.cjs +2 -0
  468. package/dist/hooks/useRestoreFocus.cjs.map +1 -0
  469. package/dist/hooks/useRestoreFocus.mjs +271 -0
  470. package/dist/hooks/useRestoreFocus.mjs.map +1 -0
  471. package/dist/hooks/useRovingTabIndex.cjs +2 -0
  472. package/dist/hooks/useRovingTabIndex.cjs.map +1 -0
  473. package/dist/hooks/useRovingTabIndex.mjs +389 -0
  474. package/dist/hooks/useRovingTabIndex.mjs.map +1 -0
  475. package/dist/hooks/useScrollLock.cjs +2 -0
  476. package/dist/hooks/useScrollLock.cjs.map +1 -0
  477. package/dist/hooks/useScrollLock.mjs +71 -0
  478. package/dist/hooks/useScrollLock.mjs.map +1 -0
  479. package/dist/hooks/useTriggerElement.cjs +2 -0
  480. package/dist/hooks/useTriggerElement.cjs.map +1 -0
  481. package/dist/hooks/useTriggerElement.mjs +126 -0
  482. package/dist/hooks/useTriggerElement.mjs.map +1 -0
  483. package/dist/hooks/useTypeahead.cjs +2 -0
  484. package/dist/hooks/useTypeahead.cjs.map +1 -0
  485. package/dist/hooks/useTypeahead.mjs +38 -0
  486. package/dist/hooks/useTypeahead.mjs.map +1 -0
  487. package/dist/index.cjs +1 -1
  488. package/dist/index.d.cts +9099 -0
  489. package/dist/index.d.ts +7688 -1027
  490. package/dist/index.mjs +91 -5695
  491. package/dist/lib/aria.cjs +2 -0
  492. package/dist/lib/aria.cjs.map +1 -0
  493. package/dist/lib/aria.mjs +29 -0
  494. package/dist/lib/aria.mjs.map +1 -0
  495. package/dist/lib/children.cjs +2 -0
  496. package/dist/lib/children.cjs.map +1 -0
  497. package/dist/lib/children.mjs +37 -0
  498. package/dist/lib/children.mjs.map +1 -0
  499. package/dist/lib/cn.cjs +2 -0
  500. package/dist/lib/cn.cjs.map +1 -0
  501. package/dist/lib/cn.mjs +64 -0
  502. package/dist/lib/cn.mjs.map +1 -0
  503. package/dist/lib/composeEventHandlers.cjs +2 -0
  504. package/dist/lib/composeEventHandlers.cjs.map +1 -0
  505. package/dist/lib/composeEventHandlers.mjs +11 -0
  506. package/dist/lib/composeEventHandlers.mjs.map +1 -0
  507. package/dist/lib/dev.cjs +2 -0
  508. package/dist/lib/dev.cjs.map +1 -0
  509. package/dist/lib/dev.mjs +42 -0
  510. package/dist/lib/dev.mjs.map +1 -0
  511. package/dist/lib/direction.cjs +2 -0
  512. package/dist/lib/direction.cjs.map +1 -0
  513. package/dist/lib/direction.mjs +35 -0
  514. package/dist/lib/direction.mjs.map +1 -0
  515. package/dist/lib/events.cjs +2 -0
  516. package/dist/lib/events.cjs.map +1 -0
  517. package/dist/lib/events.mjs +31 -0
  518. package/dist/lib/events.mjs.map +1 -0
  519. package/dist/lib/focus.cjs +2 -0
  520. package/dist/lib/focus.cjs.map +1 -0
  521. package/dist/lib/focus.mjs +119 -0
  522. package/dist/lib/focus.mjs.map +1 -0
  523. package/dist/lib/globalRegistry.cjs +2 -0
  524. package/dist/lib/globalRegistry.cjs.map +1 -0
  525. package/dist/lib/globalRegistry.mjs +13 -0
  526. package/dist/lib/globalRegistry.mjs.map +1 -0
  527. package/dist/lib/icons.cjs +2 -0
  528. package/dist/lib/icons.cjs.map +1 -0
  529. package/dist/lib/icons.mjs +254 -0
  530. package/dist/lib/icons.mjs.map +1 -0
  531. package/dist/lib/labelInName.cjs +2 -0
  532. package/dist/lib/labelInName.cjs.map +1 -0
  533. package/dist/lib/labelInName.mjs +54 -0
  534. package/dist/lib/labelInName.mjs.map +1 -0
  535. package/dist/lib/layers.cjs +2 -0
  536. package/dist/lib/layers.cjs.map +1 -0
  537. package/dist/lib/layers.mjs +224 -0
  538. package/dist/lib/layers.mjs.map +1 -0
  539. package/dist/lib/mergeProps.cjs +2 -0
  540. package/dist/lib/mergeProps.cjs.map +1 -0
  541. package/dist/lib/mergeProps.mjs +21 -0
  542. package/dist/lib/mergeProps.mjs.map +1 -0
  543. package/dist/lib/mergeRefs.cjs +2 -0
  544. package/dist/lib/mergeRefs.cjs.map +1 -0
  545. package/dist/lib/mergeRefs.mjs +29 -0
  546. package/dist/lib/mergeRefs.mjs.map +1 -0
  547. package/dist/lib/renderTrigger.cjs +2 -0
  548. package/dist/lib/renderTrigger.cjs.map +1 -0
  549. package/dist/lib/renderTrigger.mjs +29 -0
  550. package/dist/lib/renderTrigger.mjs.map +1 -0
  551. package/dist/lib/slot.cjs +2 -0
  552. package/dist/lib/slot.cjs.map +1 -0
  553. package/dist/lib/slot.mjs +122 -0
  554. package/dist/lib/slot.mjs.map +1 -0
  555. package/dist/lib/styles.cjs +2 -0
  556. package/dist/lib/styles.cjs.map +1 -0
  557. package/dist/lib/styles.mjs +16 -0
  558. package/dist/lib/styles.mjs.map +1 -0
  559. package/dist/lib/theme.cjs +2 -0
  560. package/dist/lib/theme.cjs.map +1 -0
  561. package/dist/lib/theme.mjs +16 -0
  562. package/dist/lib/theme.mjs.map +1 -0
  563. package/dist/preflight.css +2 -0
  564. package/dist/styles.css +2 -0
  565. package/package.json +149 -100
  566. package/src/styles/animations.css +7 -39
  567. package/src/styles/base.css +103 -0
  568. package/src/styles/globals.css +10 -22
  569. package/src/styles/legacy-tokens.css +184 -0
  570. package/src/styles/preflight.css +7 -0
  571. package/src/styles/styles.css +32 -0
  572. package/src/styles/tailwind.css +17 -0
  573. package/src/styles/tokens.css +561 -221
  574. package/src/styles/variants.css +29 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Toast.mjs","names":["useId","useId$1","React","promoteQueued","shownCount","toast","toasts","limit","resolveLimit","ToasterContext","ToasterRegionContext","INERT_CONTROLLER","options","MISSING_TOASTER_MESSAGE","useToastController","reportMissingContext","Toast","rest","inToasterRegion","body","materialiseSlotContent","children","hasBody","slotRendersContent","status","cn","STATUS_BORDER","className","STATUS_ICON_COLOR","StatusIcon","StatusText","getStatusLabel","statusLabel","title","onDismiss","focusRing","dismissLabel","DismissIcon","DEFAULT_TIMEOUT","createToastTimers","timers","pauses","started","inBackground","suspended","sync","timer","id","canRun","onExpire","syncAll","stop","seq","timeout","reasons","reason","value","positionClasses","EDGE_GAP","isOnRightSide","inline","position","rtl","getDirection","viewport","getSidePanelOffset","modals","getOpenLayers","layer","doc","view","width","height","right","top","offset","el","box","onSide","onEdge","getAnnouncement","ANNOUNCEMENT_DURATION","LiveMessage","present","setPresent","handle","text","ToasterItem","ref","getFocusFallback","index","entry","next","event","Toaster","limitProp","setToasts","settled","shownToasts","warnOnce","prefix","counterRef","viewportRef","viewportRefs","useMergedRefs","previousFocusRef","dir","useDirection","sideOffset","setSideOffset","update","unsubscribe","subscribeLayers","prev","blurred","handleBlur","handleFocus","dispatchToast","t","dismissToast","dismissAllToasts","controller","remaining","target","getFirstTabbable","previous","rememberFocusOrigin","from","forgetFocusOrigin","to","active","polite","assertive","message","viewportStyle","style","Portal","onFocus","onBlur"],"sources":["../../../src/components/feedback/Toast.tsx"],"sourcesContent":["import * as React from 'react';\nimport { cn } from '../../lib/cn';\nimport { reportMissingContext, warnOnce } from '../../lib/dev';\nimport { getDirection } from '../../lib/direction';\nimport { getFirstTabbable } from '../../lib/focus';\nimport { DismissIcon } from '../../lib/icons';\nimport { getOpenLayers, subscribeLayers } from '../../lib/layers';\nimport { materialiseSlotContent, slotRendersContent } from '../../lib/slot';\nimport { focusRing } from '../../lib/styles';\nimport type { Status } from '../../lib/types';\nimport { useDirection } from '../../hooks/useDirection';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { usePreserveFocus } from '../../hooks/usePreserveFocus';\nimport { Portal } from '../portal/Portal';\nimport {\n STATUS_BORDER,\n STATUS_ICON_COLOR,\n StatusIcon,\n StatusText,\n getStatusLabel,\n} from './MessageBar.status';\n\n/* ------------------------------------------------------------------ */\n/* Types */\n/* ------------------------------------------------------------------ */\n\n/** Options for dispatching a toast notification. */\nexport interface ToastOptions {\n /** Status level controlling the toast color, icon, status text and announcement politeness\n * (`error` is announced assertively, every other status politely).\n * @default 'info'\n */\n status?: Status;\n /** Title text of the toast. */\n title: string;\n /** Optional body text displayed below the title. */\n body?: string;\n /**\n * Auto-dismiss timeout in milliseconds. The countdown starts when the toast is shown (a toast\n * waiting beyond the Toaster's `limit` does not count down) and pauses while the pointer is over\n * the toast, while focus is inside it and while the browser window is in the background (it has\n * lost focus, or the page is not shown, as in a background tab, also when the Toaster mounts\n * there). `0` (or any value that is not a positive finite number) keeps the toast until it is\n * dismissed.\n * @default 5000\n */\n timeout?: number;\n /**\n * Identifier of the toast. `dispatchToast` returns it (a generated one when omitted). Dispatching\n * again with the id of a toast that is still shown replaces that toast (content and timer); with\n * the id of a toast that waits beyond the Toaster's `limit`, it replaces its options and the toast\n * keeps its place in the queue.\n */\n toastId?: string;\n /**\n * Visually hidden status text read before the toast (`'Info:'`, `'Success:'`, `'Warning:'`,\n * `'Error:'` by default). Pass a translation for other languages, or `''` to omit it.\n */\n statusLabel?: string;\n /**\n * Accessible name of the toast's dismiss button. Pass a translation for other languages.\n * @default 'Dismiss'\n */\n dismissLabel?: string;\n}\n\n/** The toast API returned by {@link useToastController}. */\nexport interface ToastController {\n /**\n * Shows a toast and returns its id (`options.toastId`, or a generated one). A toast with the same\n * id is replaced. Beyond the Toaster's `limit`, the toast waits in a queue until it can be shown.\n */\n dispatchToast: (options: ToastOptions) => string;\n /**\n * Removes the toast with this id (shown or waiting) and cancels its timer. Unknown ids are\n * ignored.\n */\n dismissToast: (id: string) => void;\n /** Removes every toast, shown and queued, and cancels their timers. */\n dismissAllToasts: () => void;\n}\n\ninterface ToastEntry {\n id: string;\n options: ToastOptions;\n /** Increases with every dispatch, so a replaced toast is announced again. */\n seq: number;\n /**\n * Whether the toast is shown (rendered, announced, its timer running) or still waits beyond the\n * Toaster's `limit`. Only {@link promoteQueued} sets it; it never goes back to `false`.\n */\n shown: boolean;\n}\n\n/**\n * Flags the oldest waiting toasts as shown while fewer than `limit` are shown. Returns `toasts`\n * itself when nothing changes, so the Toaster's render-time update settles.\n */\nfunction promoteQueued(toasts: ToastEntry[], limit: number): ToastEntry[] {\n let shownCount = 0;\n for (const toast of toasts) if (toast.shown) shownCount += 1;\n if (shownCount >= limit || shownCount === toasts.length) return toasts;\n return toasts.map((toast) => {\n if (toast.shown || shownCount >= limit) return toast;\n shownCount += 1;\n return { ...toast, shown: true };\n });\n}\n\n/** `limit` as the Toaster applies it: whole toasts, at least 1; `undefined` means no limit. */\nfunction resolveLimit(limit: number | undefined): number {\n if (limit === undefined) return Infinity;\n return limit >= 1 ? Math.floor(limit) : 1;\n}\n\n/* ------------------------------------------------------------------ */\n/* Context */\n/* ------------------------------------------------------------------ */\n\nconst ToasterContext = React.createContext<ToastController | null>(null);\nToasterContext.displayName = 'ToasterContext';\n\n/**\n * `true` for the toasts the Toaster renders in its region, which its live regions announce. A\n * Toast rendered anywhere else (also as app content inside `<Toaster>`) is a live region itself.\n */\nconst ToasterRegionContext = React.createContext(false);\nToasterRegionContext.displayName = 'ToasterRegionContext';\n\nconst INERT_CONTROLLER: ToastController = {\n dispatchToast: (options) => options.toastId ?? '',\n dismissToast: () => {},\n dismissAllToasts: () => {},\n};\n\n/** The C-CONTEXT message without the `[WaveUI] ` prefix, which `reportMissingContext` adds. */\nconst MISSING_TOASTER_MESSAGE =\n 'useToastController must be used within <Toaster>. Wrap your app (or the part of it that shows toasts) in <Toaster>: it provides the controller to its children.';\n\n/**\n * Returns the {@link ToastController} of the enclosing `<Toaster>`: `dispatchToast(options)` shows\n * a toast and returns its id, `dismissToast(id)` removes it, `dismissAllToasts()` removes every\n * toast.\n *\n * Must be called inside `<Toaster>`, which provides the controller to its children — wrap the app\n * (or the part of it that shows toasts) in `<Toaster>`; a sibling `<Toaster />` does not work.\n * Outside a Toaster it throws in development; in production it logs an error (once) and returns a\n * controller that does nothing.\n *\n * @example\n * function SaveButton() {\n * const { dispatchToast } = useToastController();\n * return <Button onClick={() => dispatchToast({ status: 'success', title: 'Saved' })}>Save</Button>;\n * }\n * // <Toaster><App /></Toaster>\n */\nexport function useToastController(): ToastController {\n const controller = React.useContext(ToasterContext);\n if (controller) return controller;\n reportMissingContext('useToastController', '<Toaster>', MISSING_TOASTER_MESSAGE);\n return INERT_CONTROLLER;\n}\n\n/* ------------------------------------------------------------------ */\n/* Toast (individual notification) */\n/* ------------------------------------------------------------------ */\n\n/** Properties for the Toast component. */\nexport interface ToastProps extends React.HTMLAttributes<HTMLDivElement> {\n /** Status level controlling the toast color, icon and status text.\n * @default 'info'\n */\n status?: Status;\n /** Title text displayed in the toast. */\n title?: string;\n /**\n * Visually hidden status text read before the toast (`'Info:'`, `'Success:'`, `'Warning:'`,\n * `'Error:'` by default). Pass a translation for other languages, or `''` to omit it.\n */\n statusLabel?: string;\n /** Called when the dismiss button is activated. Passing it renders the dismiss button. */\n onDismiss?: () => void;\n /**\n * Accessible name of the dismiss button. Pass a translation for other languages.\n * @default 'Dismiss'\n */\n dismissLabel?: string;\n /** Ref to the root `<div>`. */\n ref?: React.Ref<HTMLDivElement>;\n}\n\n/**\n * The visual of a single notification: status icon, visually hidden status text, title, body and an\n * optional dismiss button. Usually rendered by `<Toaster>` through `useToastController()`.\n *\n * - **In a Toaster** (dispatched with `useToastController()`): not a live region itself; the\n * Toaster announces it through its permanent live regions.\n * - **On its own** (your own container, an inline notice): a live region, as in 0.4 —\n * `role=\"status\"` with `aria-live=\"polite\"`, or `role=\"alert\"` with `aria-live=\"assertive\"` for\n * `error` (override with `role`/`aria-live`). A live region that is added together with its\n * text is not announced by every screen reader, so render the Toast in advance and change its\n * content, or dispatch it through a Toaster.\n */\nexport const Toast = ({\n status = 'info',\n title,\n statusLabel,\n onDismiss,\n dismissLabel = 'Dismiss',\n className,\n children,\n ref,\n ...rest\n}: ToastProps) => {\n const inToasterRegion = React.useContext(ToasterRegionContext);\n // Content that renders nothing (`''`, `[]`, `<></>`) gets no body element; a generator is read\n // once by the check and its items render.\n const body = materialiseSlotContent(children);\n const hasBody = slotRendersContent(body);\n const liveRegion: React.HTMLAttributes<HTMLDivElement> = inToasterRegion\n ? {}\n : status === 'error'\n ? { role: 'alert', 'aria-live': 'assertive' }\n : { role: 'status', 'aria-live': 'polite' };\n return (\n <div\n ref={ref}\n {...liveRegion}\n {...rest}\n className={cn(\n 'flex items-start gap-3 rounded border border-s-4 border-border bg-background p-3 text-foreground shadow-4',\n STATUS_BORDER[status],\n className,\n )}\n >\n <span\n aria-hidden=\"true\"\n className={cn('mt-0.5 inline-flex shrink-0', STATUS_ICON_COLOR[status])}\n >\n <StatusIcon status={status} />\n </span>\n <div className=\"min-w-0 flex-1\">\n <StatusText label={getStatusLabel(status, statusLabel)} />\n {title ? <div className=\"text-body-2 font-semibold text-foreground\">{title}</div> : null}\n {hasBody ? <div className=\"mt-0.5 text-body-1 text-muted-foreground\">{body}</div> : null}\n </div>\n {onDismiss ? (\n <button\n type=\"button\"\n onClick={() => onDismiss()}\n className={cn(\n 'inline-flex shrink-0 cursor-pointer items-center justify-center rounded border-none bg-transparent p-1 text-muted-foreground',\n 'not-disabled:not-aria-disabled:hover:bg-subtle-hover not-disabled:not-aria-disabled:hover:text-foreground',\n 'not-disabled:not-aria-disabled:active:bg-subtle-pressed',\n focusRing,\n )}\n aria-label={dismissLabel}\n >\n <DismissIcon />\n </button>\n ) : null}\n </div>\n );\n};\nToast.displayName = 'Toast';\n\n/* ------------------------------------------------------------------ */\n/* Timers */\n/* ------------------------------------------------------------------ */\n\nconst DEFAULT_TIMEOUT = 5000;\n\ntype PauseReason = 'hover' | 'focus';\n\ninterface RunningTimer {\n handle: ReturnType<typeof setTimeout> | null;\n remaining: number;\n startedAt: number;\n}\n\n/**\n * Auto-dismiss timers of one Toaster. A timer runs only while its toast is neither hovered nor\n * focused, the window is in the foreground and the Toaster is mounted; otherwise it is suspended\n * and keeps its remaining time. Every method is called from event handlers or effects, never\n * during render.\n */\ninterface ToastTimers {\n /**\n * Starts the timer of the shown toast `id` for its dispatch `seq`, once: a call with the `seq`\n * already started does nothing, a new `seq` (the toast was replaced) restarts it. A timeout that\n * is not a positive finite number means none. The pause state of `id` is kept: a replaced toast\n * that is hovered or focused stays paused.\n */\n start(id: string, seq: number, timeout: number): void;\n /** Cancels the timer of `id` and forgets its pause state. */\n remove(id: string): void;\n /** Cancels every timer and forgets every pause state. */\n clear(): void;\n pause(id: string, reason: PauseReason): void;\n resume(id: string, reason: PauseReason): void;\n /** `true` while the window has lost focus or the page is not shown (a background tab). */\n setInBackground(inBackground: boolean): void;\n /** `true` while the Toaster is unmounted (including StrictMode's simulated unmount). */\n setSuspended(suspended: boolean): void;\n}\n\nfunction createToastTimers(onExpire: (id: string) => void): ToastTimers {\n const timers = new Map<string, RunningTimer>();\n const pauses = new Map<string, Set<PauseReason>>();\n /** The dispatch (`seq`) whose timer was started last, per toast. */\n const started = new Map<string, number>();\n let inBackground = false;\n let suspended = false;\n\n const sync = (id: string) => {\n const timer = timers.get(id);\n if (!timer) return;\n const canRun = !suspended && !inBackground && !(pauses.get(id)?.size ?? 0);\n if (canRun && timer.handle === null) {\n timer.startedAt = Date.now();\n timer.handle = setTimeout(() => {\n timers.delete(id);\n pauses.delete(id);\n started.delete(id);\n onExpire(id);\n }, timer.remaining);\n } else if (!canRun && timer.handle !== null) {\n clearTimeout(timer.handle);\n timer.handle = null;\n timer.remaining = Math.max(0, timer.remaining - (Date.now() - timer.startedAt));\n }\n };\n const syncAll = () => {\n for (const id of Array.from(timers.keys())) sync(id);\n };\n const stop = (id: string) => {\n const timer = timers.get(id);\n if (timer?.handle != null) clearTimeout(timer.handle);\n timers.delete(id);\n };\n\n return {\n start(id, seq, timeout) {\n if (started.get(id) === seq) return;\n started.set(id, seq);\n stop(id);\n if (!(timeout > 0) || !Number.isFinite(timeout)) return;\n timers.set(id, { handle: null, remaining: timeout, startedAt: 0 });\n sync(id);\n },\n remove(id) {\n stop(id);\n pauses.delete(id);\n started.delete(id);\n },\n clear() {\n for (const id of Array.from(timers.keys())) stop(id);\n pauses.clear();\n started.clear();\n },\n pause(id, reason) {\n let reasons = pauses.get(id);\n if (!reasons) {\n reasons = new Set();\n pauses.set(id, reasons);\n }\n reasons.add(reason);\n sync(id);\n },\n resume(id, reason) {\n pauses.get(id)?.delete(reason);\n sync(id);\n },\n setInBackground(value) {\n inBackground = value;\n syncAll();\n },\n setSuspended(value) {\n suspended = value;\n syncAll();\n },\n };\n}\n\n/* ------------------------------------------------------------------ */\n/* Toaster (container) */\n/* ------------------------------------------------------------------ */\n\n/**\n * Corner of the viewport a {@link Toaster} shows its toasts in (`ToasterProps.position`).\n * `start`/`end` follow the writing direction; `left`/`right` are physical.\n */\nexport type ToastPosition =\n | 'top-start'\n | 'top-end'\n | 'bottom-start'\n | 'bottom-end'\n | 'top-right'\n | 'top-left'\n | 'bottom-right'\n | 'bottom-left';\n\n/** Properties for the Toaster container component. */\nexport interface ToasterProps extends React.HTMLAttributes<HTMLDivElement> {\n /**\n * Corner of the viewport the toasts appear in. `start`/`end` follow the writing direction (the\n * `end` side is the right in LTR and the left in RTL); `left`/`right` are physical.\n * @default 'bottom-end'\n */\n position?: ToastPosition;\n /**\n * Most toasts shown at once. Further toasts wait in a queue (in dispatch order) and appear when\n * a shown toast goes; a queued toast is not announced and its timer does not run until then.\n * Lowering it never hides a toast that is already shown. A value below 1 counts as 1\n * (development warning); `Infinity` means no limit.\n * @default Infinity\n */\n limit?: number;\n /** Ref to the toast region (the portaled `<div role=\"region\">`). */\n ref?: React.Ref<HTMLDivElement>;\n}\n\n/**\n * Corner placement. The margin on the toasts' side is `--wave-toaster-offset`, which the Toaster\n * sets while a modal panel covers that side (see {@link getSidePanelOffset}); unset, it is `0`.\n */\nconst positionClasses: Record<ToastPosition, string> = {\n 'top-start': 'top-4 start-4 ms-(--wave-toaster-offset)',\n 'top-end': 'top-4 end-4 me-(--wave-toaster-offset)',\n 'bottom-start': 'bottom-4 start-4 ms-(--wave-toaster-offset)',\n 'bottom-end': 'bottom-4 end-4 me-(--wave-toaster-offset)',\n 'top-right': 'top-4 right-4 mr-(--wave-toaster-offset)', // wave-allow-physical: explicit physical position value\n 'top-left': 'top-4 left-4 ml-(--wave-toaster-offset)', // wave-allow-physical: explicit physical position value\n 'bottom-right': 'bottom-4 right-4 mr-(--wave-toaster-offset)', // wave-allow-physical: explicit physical position value\n 'bottom-left': 'bottom-4 left-4 ml-(--wave-toaster-offset)', // wave-allow-physical: explicit physical position value\n};\n\n/** The toasts' distance from the window edges (`*-4`), also the tolerance for \"at the edge\". */\nconst EDGE_GAP = 16;\n\n/** Whether the toasts sit at the right edge of the window (`end` is the right in LTR). */\nfunction isOnRightSide(position: ToastPosition, viewport: HTMLElement): boolean {\n const inline = position.slice(position.indexOf('-') + 1);\n if (inline === 'right' || inline === 'left') return inline === 'right';\n const rtl = getDirection(viewport) === 'rtl';\n return inline === 'end' ? !rtl : rtl;\n}\n\n/**\n * How far the toasts move away from their side while an open modal surface (a Drawer panel) covers\n * their corner, so they never hide the panel's controls (WCAG 2.4.11 Focus Not Obscured): the\n * surface's width from that side of the window, which leaves the usual gap between toasts and\n * panel. A surface counts when it reaches the toasts' side and their top or bottom edge (a centered\n * Dialog does not). `0` when no such surface is open, or when the toasts would not fit beside it\n * (a full-width panel on a phone): then they keep their corner.\n */\nfunction getSidePanelOffset(viewport: HTMLElement, position: ToastPosition): number {\n const modals = getOpenLayers().filter((layer) => layer.kind === 'modal');\n if (modals.length === 0) return 0;\n const doc = viewport.ownerDocument;\n const view = doc.defaultView;\n if (!view) return 0;\n // The box fixed elements are placed in: the window without its scrollbars.\n const width = doc.documentElement.clientWidth || view.innerWidth;\n const height = doc.documentElement.clientHeight || view.innerHeight;\n const right = isOnRightSide(position, viewport);\n const top = position.startsWith('top');\n\n let offset = 0;\n for (const layer of modals) {\n for (const el of layer.getElements()) {\n if (!el?.isConnected) continue;\n const box = el.getBoundingClientRect();\n if (box.width <= 0 || box.height <= 0) continue;\n const onSide = right ? box.right >= width - EDGE_GAP : box.left <= EDGE_GAP;\n const onEdge = top ? box.top <= EDGE_GAP : box.bottom >= height - EDGE_GAP;\n if (onSide && onEdge) offset = Math.max(offset, right ? width - box.left : box.right);\n }\n }\n if (offset <= 0 || width - offset < viewport.offsetWidth + 2 * EDGE_GAP) return 0;\n return Math.ceil(offset);\n}\n\n/** The text written into the live region for a toast (\"Error: Upload failed Try again.\"). */\nfunction getAnnouncement({ status = 'info', statusLabel, title, body }: ToastOptions): string {\n return [getStatusLabel(status, statusLabel), title, body].filter(Boolean).join(' ');\n}\n\n/**\n * How long a toast's text stays in the live region: long enough for screen readers to pick it up\n * (also a polite message queued behind other speech), short enough that someone browsing the\n * Notifications region later meets the text once, in the toast, not a second time in the region.\n */\nconst ANNOUNCEMENT_DURATION = 2000;\n\n/**\n * One toast's message in a live region. It is added when the toast is shown (at dispatch, or when\n * a waiting toast appears; a replacement remounts it, so it is read again) and removed after\n * {@link ANNOUNCEMENT_DURATION} or with the toast. Removal is not announced (`aria-relevant` stays\n * at its default, additions and text).\n */\nfunction LiveMessage({ text }: { text: string }) {\n const [present, setPresent] = React.useState(true);\n React.useEffect(() => {\n const handle = setTimeout(() => setPresent(false), ANNOUNCEMENT_DURATION);\n return () => clearTimeout(handle);\n }, []);\n return present ? <div>{text}</div> : null;\n}\nLiveMessage.displayName = 'LiveMessage';\n\ninterface ToasterItemProps {\n entry: ToastEntry;\n index: number;\n timers: ToastTimers;\n onDismiss: (id: string) => void;\n getFocusFallback: (index: number) => HTMLElement | null;\n}\n\n/** One toast of the Toaster: pause handlers and focus preservation on removal. */\nfunction ToasterItem({ entry, index, timers, onDismiss, getFocusFallback }: ToasterItemProps) {\n const ref = React.useRef<HTMLDivElement>(null);\n usePreserveFocus(ref, () => getFocusFallback(index));\n const { id, options } = entry;\n return (\n <Toast\n ref={ref}\n data-wave-toast=\"\"\n status={options.status}\n statusLabel={options.statusLabel}\n title={options.title}\n dismissLabel={options.dismissLabel}\n onDismiss={() => onDismiss(id)}\n onPointerEnter={() => timers.pause(id, 'hover')}\n onPointerLeave={() => timers.resume(id, 'hover')}\n onFocus={() => timers.pause(id, 'focus')}\n onBlur={(event) => {\n const next = event.relatedTarget;\n if (next instanceof Node && event.currentTarget.contains(next)) return;\n timers.resume(id, 'focus');\n }}\n >\n {options.body}\n </Toast>\n );\n}\nToasterItem.displayName = 'ToasterItem';\n\n/**\n * Provides {@link useToastController} to its children and shows the dispatched toasts.\n *\n * - **Wrap the app** in `<Toaster>`; components below it call `useToastController()`.\n * - The toasts render in a portal (the `toast` layer, above dialogs) inside a region labelled\n * \"Notifications\" (override with `aria-label`). The region is allow-listed for modals\n * (`data-wave-focus-trap-allow`): it stays reachable by Tab and exposed to assistive technology\n * while a Dialog or Drawer is open, and clicking a toast never dismisses the overlay below.\n * - Two permanent, visually hidden live regions (polite, and assertive for `error`) announce every\n * toast; the toasts themselves are not live regions. Each message stays in its live region for\n * 2 seconds (or until its toast goes), so browsing the region later meets the text only once.\n * - While an open modal panel covers the toasts' corner (a Drawer on the same side), the toasts\n * move beside it, so they never hide its focused controls (WCAG 2.4.11). Without room beside it\n * (a full-width panel on a narrow screen) they keep their corner.\n * - Timers pause while a toast is hovered or focused and while the window is in the background\n * (it has lost focus, or the page is not shown, as in a background tab).\n * When a toast that contains focus goes away, focus moves to the next toast (or the previous one\n * when the last toast goes), or back to the element that was focused before focus entered the\n * toasts once no toast is left (kept across the moves between toasts and while another window\n * is active; forgotten once focus has returned to it, and when focus leaves the toasts for\n * another element or for the page body).\n * - Each toast's dismiss button is named \"Dismiss\"; pass `dismissLabel` to `dispatchToast` for\n * other languages.\n * - `limit` caps how many toasts show at once: the others wait in a queue, in dispatch order,\n * unannounced and without a running timer, and appear as shown toasts go.\n * `dismissAllToasts()` removes every toast, shown and queued.\n *\n * @example\n * <Toaster position=\"bottom-end\" limit={3}>\n * <App />\n * </Toaster>\n */\nexport const Toaster = ({\n position = 'bottom-end',\n limit: limitProp,\n className,\n style,\n children,\n onFocus,\n onBlur,\n ref,\n ...rest\n}: ToasterProps) => {\n const [toasts, setToasts] = React.useState<ToastEntry[]>([]);\n const limit = resolveLimit(limitProp);\n // Waiting toasts are shown here, during render, with the current limit (adjust state while\n // rendering, C-HOOKS): every path that frees a place or raises the limit promotes them, and a\n // lowered limit never hides a shown toast. `promoteQueued` returns the same array once settled.\n const settled = promoteQueued(toasts, limit);\n if (settled !== toasts) setToasts(settled);\n const shownToasts = settled.filter((toast) => toast.shown);\n\n // Development diagnostics (C-DEV): emitted from an effect, once per page.\n React.useEffect(() => {\n if (limitProp !== undefined && !(limitProp >= 1)) {\n warnOnce(\n 'Toaster:limit',\n `Toaster: \\`limit\\` must be 1 or more (got ${String(limitProp)}); it counts as 1.`,\n );\n }\n }, [limitProp]);\n const prefix = useId('toast');\n const counterRef = React.useRef(0);\n const viewportRef = React.useRef<HTMLDivElement | null>(null);\n const viewportRefs = useMergedRefs(ref, viewportRef);\n const previousFocusRef = React.useRef<HTMLElement | null>(null);\n const dir = useDirection();\n\n // Beside an open modal panel on the toasts' side (a Drawer), not over its controls. Measured when\n // a layer opens or closes (synchronously in its layout effect, before paint), on resize, and\n // after a transition or animation (a panel that slides in reaches its place only then).\n const [sideOffset, setSideOffset] = React.useState(0);\n React.useLayoutEffect(() => {\n const update = () => {\n const viewport = viewportRef.current;\n setSideOffset(viewport ? getSidePanelOffset(viewport, position) : 0);\n };\n update();\n const unsubscribe = subscribeLayers(update);\n window.addEventListener('resize', update);\n document.addEventListener('transitionend', update, true);\n document.addEventListener('animationend', update, true);\n return () => {\n unsubscribe();\n window.removeEventListener('resize', update);\n document.removeEventListener('transitionend', update, true);\n document.removeEventListener('animationend', update, true);\n };\n }, [position, dir]);\n\n const [timers] = React.useState(() =>\n createToastTimers((id) =>\n setToasts((prev) => (prev.some((t) => t.id === id) ? prev.filter((t) => t.id !== id) : prev)),\n ),\n );\n\n // Timers run only while mounted (StrictMode's simulated unmount suspends and resumes them) and\n // pause while the window is in the background: after the window loses focus, and while the page\n // is not shown. The page visibility is read at mount too, so a Toaster that mounts in a\n // background tab waits until the tab is shown. (Focus is not read at mount: `hasFocus()` is also\n // false in an embedded frame nobody clicked yet and in test DOMs.)\n React.useEffect(() => {\n const doc = document;\n let blurred = false;\n const update = () => timers.setInBackground(blurred || doc.visibilityState === 'hidden');\n // Only the window's own blur/focus (element focus events do not bubble to a bubble-phase\n // window listener; anything targeted at a node is ignored).\n const handleBlur = (event: FocusEvent) => {\n if (event.target instanceof Node) return;\n blurred = true;\n update();\n };\n const handleFocus = (event: FocusEvent) => {\n if (event.target instanceof Node) return;\n blurred = false;\n update();\n };\n update();\n timers.setSuspended(false);\n window.addEventListener('blur', handleBlur);\n window.addEventListener('focus', handleFocus);\n doc.addEventListener('visibilitychange', update);\n return () => {\n window.removeEventListener('blur', handleBlur);\n window.removeEventListener('focus', handleFocus);\n doc.removeEventListener('visibilitychange', update);\n timers.setSuspended(true);\n };\n }, [timers]);\n\n // Starts the timer of every newly shown toast, and restarts it for a shown toast dispatched again\n // (a new `seq`); `timers.start` ignores a dispatch it has already started.\n React.useEffect(() => {\n for (const toast of toasts) {\n if (toast.shown) timers.start(toast.id, toast.seq, toast.options.timeout ?? DEFAULT_TIMEOUT);\n }\n }, [toasts, timers]);\n\n // A new toast waits until the render promotes it; a replaced one keeps its place and whether it\n // is shown (a waiting toast keeps waiting with the new options).\n const dispatchToast = React.useCallback(\n (options: ToastOptions): string => {\n counterRef.current += 1;\n const seq = counterRef.current;\n const id = options.toastId ?? `${prefix}-${seq}`;\n setToasts((prev) => {\n const index = prev.findIndex((t) => t.id === id);\n if (index === -1) return [...prev, { id, options, seq, shown: false }];\n const next = prev.slice();\n next[index] = { id, options, seq, shown: prev[index].shown };\n return next;\n });\n return id;\n },\n [prefix],\n );\n\n const dismissToast = React.useCallback(\n (id: string) => {\n timers.remove(id);\n setToasts((prev) => (prev.some((t) => t.id === id) ? prev.filter((t) => t.id !== id) : prev));\n },\n [timers],\n );\n\n const dismissAllToasts = React.useCallback(() => {\n timers.clear();\n setToasts((prev) => (prev.length === 0 ? prev : []));\n }, [timers]);\n\n const controller = React.useMemo<ToastController>(\n () => ({ dispatchToast, dismissToast, dismissAllToasts }),\n [dispatchToast, dismissToast, dismissAllToasts],\n );\n\n // Runs after the removed toast is gone (possibly after the whole Toaster): never throws.\n const getFocusFallback = React.useCallback((index: number): HTMLElement | null => {\n const viewport = viewportRef.current;\n const remaining = viewport\n ? Array.from(viewport.children).filter(\n (el): el is HTMLElement =>\n el instanceof HTMLElement && el.hasAttribute('data-wave-toast'),\n )\n : [];\n for (const toast of [remaining[index], remaining[index - 1]]) {\n const target = toast?.isConnected ? getFirstTabbable(toast) : null;\n if (target) return target;\n }\n // Focus leaves the toasts here without a blur of the viewport (the focused node is gone), so\n // the element is forgotten as it is used: a toast focused later from nowhere does not send\n // focus back to it.\n const previous = previousFocusRef.current;\n previousFocusRef.current = null;\n return previous?.isConnected ? previous : null;\n }, []);\n\n // Focus entering the toasts from an element outside: return there when the focused toast goes.\n // Focus that arrives with no related target keeps what is remembered: that is the Toaster's own\n // move to the next toast after a removal (focus passed through `<body>` while the removed node\n // was gone) or the window regaining focus. Moves between toasts change nothing.\n const rememberFocusOrigin = (event: React.FocusEvent<HTMLDivElement>) => {\n const from = event.relatedTarget;\n if (from instanceof HTMLElement && !event.currentTarget.contains(from)) {\n previousFocusRef.current = from;\n }\n };\n\n // Focus leaving the toasts for another element or for `<body>` forgets the element, so a toast\n // focused again later from nowhere never sends focus back to something focused long before.\n // Kept: moves between toasts, a removed toast (its node is gone; the Toaster moves focus itself)\n // and the window losing focus (the element keeps document focus while another window is active).\n const forgetFocusOrigin = (event: React.FocusEvent<HTMLDivElement>) => {\n const viewport = event.currentTarget;\n const to = event.relatedTarget;\n if (to instanceof Node && viewport.contains(to)) return;\n if (to === null) {\n const from = event.target;\n if (!from.isConnected) return;\n const active = from.ownerDocument.activeElement;\n if (active && viewport.contains(active)) return;\n }\n previousFocusRef.current = null;\n };\n\n // Only shown toasts are announced: a waiting toast is announced when it appears.\n const polite: React.ReactNode[] = [];\n const assertive: React.ReactNode[] = [];\n for (const toast of shownToasts) {\n const message = <LiveMessage key={toast.seq} text={getAnnouncement(toast.options)} />;\n (toast.options.status === 'error' ? assertive : polite).push(message);\n }\n\n const viewportStyle =\n sideOffset > 0\n ? ({ ...style, '--wave-toaster-offset': `${sideOffset}px` } as React.CSSProperties)\n : style;\n\n return (\n <ToasterContext.Provider value={controller}>\n {children}\n <Portal layer=\"toast\">\n <div\n ref={viewportRefs}\n role=\"region\"\n aria-label=\"Notifications\"\n data-wave-focus-trap-allow=\"\"\n data-position={position}\n {...rest}\n style={viewportStyle}\n onFocus={(event) => {\n // Bookkeeping always runs (a consumer's preventDefault() cannot cancel a focus change).\n onFocus?.(event);\n rememberFocusOrigin(event);\n }}\n onBlur={(event) => {\n onBlur?.(event);\n forgetFocusOrigin(event);\n }}\n className={cn(\n 'fixed flex w-80 max-w-[calc(100vw-2rem)] flex-col gap-2',\n positionClasses[position],\n className,\n )}\n >\n {/* One message per toast for its first 2 s; not atomic, so only the added one is read. */}\n <div role=\"status\" aria-live=\"polite\" aria-atomic=\"false\" className=\"sr-only\">\n {polite}\n </div>\n <div aria-live=\"assertive\" aria-atomic=\"false\" className=\"sr-only\">\n {assertive}\n </div>\n <ToasterRegionContext.Provider value={true}>\n {/* The index within the rendered (shown) toasts, which getFocusFallback walks. Today the\n shown toasts are a prefix of the entries (appended, promoted oldest first, replaced\n in place, removed in order), so it equals the entry index; the shown list stays the\n source so that a change to that order cannot break focus movement. */}\n {shownToasts.map((toast, index) => (\n <ToasterItem\n key={toast.id}\n entry={toast}\n index={index}\n timers={timers}\n onDismiss={dismissToast}\n getFocusFallback={getFocusFallback}\n />\n ))}\n </ToasterRegionContext.Provider>\n </div>\n </Portal>\n </ToasterContext.Provider>\n );\n};\nToaster.displayName = 'Toaster';\n"],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ "use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/dev.cjs"),r=require("../../lib/slot.cjs"),i=require("../../lib/composeEventHandlers.cjs"),ee=require("../../hooks/useControllable.cjs"),a=require("../../hooks/useId.cjs"),te=require("../../hooks/useMergedRefs.cjs"),o=require("../../lib/aria.cjs"),s=require("../../hooks/useFieldControl.cjs"),c=require("../../lib/styles.cjs"),l=require("../../lib/icons.cjs"),u=require("../../hooks/useFormReset.cjs"),d=require("../internal/HiddenInput.cjs");let f=require("react");f=e.__toESM(f,1);let p=require("react/jsx-runtime");var ne=`forced-colors:border-[Highlight] forced-colors:bg-[Highlight]`,re=`forced-colors:border-[GrayText] forced-colors:bg-[Canvas]`,ie=`forced-colors:text-[GrayText] forced-colors:forced-color-adjust-none`,m=({checked:e,defaultChecked:m=!1,indeterminate:h=!1,onCheckedChange:g,onChange:_,disabled:v=!1,disabledFocusable:y=!1,label:b,labelPosition:x=`after`,name:ae,value:oe,required:S,form:C,id:se,"aria-label":w,"aria-labelledby":T,"aria-describedby":E,"aria-invalid":D,"aria-required":O,"aria-errormessage":k,"aria-details":A,"aria-disabled":j,autoFocus:M,tabIndex:N,onClick:P,onFocus:F,onBlur:I,onKeyDown:L,onKeyUp:R,controlRef:z,className:ce,children:B,ref:V,...H})=>{_!==void 0&&n.warnDeprecated(`Checkbox`,`onChange`,`onCheckedChange`);let U=r.slotRendersContent(B);f.useEffect(()=>{U&&n.warnOnce(`Checkbox:children`,"Checkbox: children are not rendered. Pass the label in `label`.")},[U]);let[W,G]=ee.useControllable(e,m,e=>{g?.(e),_?.(e)}),le=a.useId(`checkbox`),K=a.useId(`checkbox-label`),q=s.useFieldContext(),J=s.useFieldControl({id:se,"aria-label":w,"aria-labelledby":T,"aria-describedby":E,"aria-invalid":D,"aria-required":O??S}),ue=S??q?.required??!1,Y=r.slotRendersContent(b),de=Y&&J[`aria-label`]===void 0?o.joinIds(J[`aria-labelledby`],q&&J.id===q.controlId?q.labelId:void 0,K):J[`aria-labelledby`],X=f.useRef(null),fe=te.useMergedRefs(X,z);u.useFormReset(X,()=>G(m),C);let pe=W||h,Z=v||y,Q=Z?ie:c.forcedColors.selectedLeaf,$=Y?(0,p.jsx)(`span`,{id:K,className:`text-body-1 text-foreground`,children:r.materialiseSlotContent(b)}):null;return(0,p.jsxs)(`label`,{ref:V,"data-label-position":x,className:t.cn(`relative inline-flex items-start gap-2 select-none`,Z?`cursor-not-allowed opacity-50 has-focus-visible:opacity-100`:`cursor-pointer`,ce),...H,children:[x===`before`&&$,(0,p.jsx)(`button`,{id:le,type:`button`,...J,"aria-labelledby":de,"aria-errormessage":k,"aria-details":A,"aria-disabled":j,autoFocus:M,tabIndex:N,onFocus:F,onBlur:I,onKeyDown:L,onKeyUp:R,ref:fe,role:`checkbox`,"aria-checked":h?`mixed`:W,disabled:v&&!y,...o.focusableDisabledProps(y,{reachable:!0}),onClick:y?e=>{e.preventDefault(),e.stopPropagation()}:i.composeEventHandlers(P,()=>G(e=>!e)),className:t.cn(`flex h-[18px] w-[18px] shrink-0 items-center justify-center rounded-xs border p-0 transition-colors motion-reduce:transition-none`,Y&&`mt-px`,c.focusRing,pe?t.cn(`border-primary bg-primary text-primary-foreground`,Z?re:ne):t.cn(`border-stroke-accessible bg-transparent`,Z?c.forcedColors.disabled:c.forcedColors.control)),children:h?(0,p.jsx)(l.SubtractIcon,{size:12,className:Q}):W?(0,p.jsx)(l.CheckIcon,{size:12,className:Q}):null}),x!==`before`&&$,(0,p.jsx)(d.HiddenInput,{type:`checkbox`,name:ae,form:C,disabled:Z,value:oe,checked:W,required:ue,onInvalid:()=>X.current?.focus()})]})};m.displayName=`Checkbox`,exports.Checkbox=m;
2
+ //# sourceMappingURL=Checkbox.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Checkbox.cjs","names":["slotRendersContent","useControllable","useId","useFieldContext","useFieldControl","joinIds","React","useMergedRefs","forcedColors","materialiseSlotContent","cn","focusableDisabledProps","composeEventHandlers","focusRing","SubtractIcon","CheckIcon","HiddenInput","require_runtime","require_cn","require_dev","require_slot","require_composeEventHandlers","require_useControllable","require_useId","require_useMergedRefs","require_aria","require_useFieldControl","require_styles","require_icons","require_useFormReset","require_HiddenInput","react","react_jsx_runtime","checkedBox","disabledCheckedBox","disabledGlyph","Checkbox","checkedProp","ariaLabel","ariaLabelledBy","ariaDescribedBy","ariaInvalid","ariaRequired","ariaErrorMessage","ariaDetails","ariaDisabled","rest","onChange","hasChildren","children","checked","setChecked","defaultChecked","onCheckedChange","next","generatedId","labelTextId","field","fieldProps","required","isRequired","hasLabel","label","labelledBy","buttonRef","mergedControlRef","controlRef","form","on","indeterminate","unavailable","disabled","disabledFocusable","glyphClassName","labelText","labelPosition","className","event","onClick","prev"],"sources":["../../../src/components/input/Checkbox.tsx"],"sourcesContent":["import * as React from 'react';\nimport { focusableDisabledProps, joinIds } from '../../lib/aria';\nimport { cn } from '../../lib/cn';\nimport { composeEventHandlers } from '../../lib/composeEventHandlers';\nimport { warnDeprecated, warnOnce } from '../../lib/dev';\nimport { CheckIcon, SubtractIcon } from '../../lib/icons';\nimport { materialiseSlotContent, slotRendersContent } from '../../lib/slot';\nimport { focusRing, forcedColors } from '../../lib/styles';\nimport type { LabelPosition } from '../../lib/types';\nimport { useControllable } from '../../hooks/useControllable';\nimport { useFieldContext, useFieldControl } from '../../hooks/useFieldControl';\nimport { useFormReset } from '../../hooks/useFormReset';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { HiddenInput } from '../internal/HiddenInput';\n\n/*\n * Forced colors: the focusable box keeps system-color utilities, so the browser still forces its\n * focus outline and border; only the glyph (the leaf indicator) opts out of forced colors. A\n * disabled box draws a GrayText glyph and border on Canvas, without the Highlight fill.\n */\nconst checkedBox = 'forced-colors:border-[Highlight] forced-colors:bg-[Highlight]';\nconst disabledCheckedBox = 'forced-colors:border-[GrayText] forced-colors:bg-[Canvas]';\nconst disabledGlyph = 'forced-colors:text-[GrayText] forced-colors:forced-color-adjust-none';\n\n/** Handlers that run on the `role=\"checkbox\"` button instead of the root label (C-ROUTING). */\ntype CheckboxControlHandlers = 'onClick' | 'onFocus' | 'onBlur' | 'onKeyDown' | 'onKeyUp';\n\n/** Where a Checkbox renders its label: after the box (default) or before it. */\nexport type CheckboxLabelPosition = Extract<LabelPosition, 'before' | 'after'>;\n\n/** Properties for the Checkbox component. */\nexport interface CheckboxProps extends Omit<\n React.HTMLAttributes<HTMLLabelElement>,\n 'onChange' | 'defaultChecked' | CheckboxControlHandlers\n> {\n /** Controlled checked state. */\n checked?: boolean;\n /** Initial checked state for uncontrolled usage (also the value a form reset restores).\n * @default false\n */\n defaultChecked?: boolean;\n /**\n * Shows the mixed state: the dash glyph and `aria-checked=\"mixed\"`, whatever `checked` is. A\n * click still toggles `checked` and calls `onCheckedChange`, but the checkbox keeps showing and\n * announcing \"mixed\" until you clear `indeterminate`. For a tri-state \"select all\", derive\n * `checked` and `indeterminate` from the items and set every item in `onCheckedChange`.\n * @default false\n */\n indeterminate?: boolean;\n /** Called with the new checked state when it changes (not for no-op updates). */\n onCheckedChange?: (checked: boolean) => void;\n /**\n * Called with the new checked state when it changes.\n * @deprecated Use `onCheckedChange`.\n */\n onChange?: (checked: boolean) => void;\n /** Whether the checkbox is disabled and non-interactive. */\n disabled?: boolean;\n /**\n * Marks the checkbox unavailable but keeps it focusable and in the tab order: for a disabled\n * checkbox that needs a Tooltip, or one in a toolbar. Renders `aria-disabled=\"true\"`,\n * `data-disabled` and `data-disabled-focusable` on the checkbox instead of the native `disabled`\n * attribute. The checkbox cannot be toggled and is not submitted with its form; your `onClick`\n * is not called, and a click on the checkbox (or Space and Enter) does not reach ancestor click\n * handlers, as for a natively disabled control. Wins over `disabled` when both are set. In a\n * roving container (a `Toolbar`) it stays in the arrow-key order.\n * @default false\n */\n disabledFocusable?: boolean;\n /**\n * Label next to the control (any phrasing content, links included, but no other form\n * controls). It names the control through `aria-labelledby`, after a consumer or Field\n * `aria-labelledby`; a consumer `aria-label` names it instead. Clicking its text toggles the\n * control; clicking a link inside it follows the link. `children` are not rendered: pass the\n * label here.\n */\n label?: React.ReactNode;\n /**\n * Where the label renders: after the control (default) or before it. The DOM order follows the\n * visual order.\n * @default 'after'\n */\n labelPosition?: CheckboxLabelPosition;\n /**\n * Form field name. With a name, the checkbox takes part in native form submission: it submits\n * `name=value` while checked.\n */\n name?: string;\n /** Value submitted while checked.\n * @default 'on'\n */\n value?: string;\n /** The form must not be submitted while the checkbox is unchecked (native validation). */\n required?: boolean;\n /** Id of the form the checkbox belongs to, when it is rendered outside that form. */\n form?: string;\n /** Click handler of the checkbox control (the `role=\"checkbox\"` button). */\n onClick?: React.MouseEventHandler<HTMLButtonElement>;\n /** Focus handler of the checkbox control. */\n onFocus?: React.FocusEventHandler<HTMLButtonElement>;\n /** Blur handler of the checkbox control. */\n onBlur?: React.FocusEventHandler<HTMLButtonElement>;\n /** Keydown handler of the checkbox control. */\n onKeyDown?: React.KeyboardEventHandler<HTMLButtonElement>;\n /** Keyup handler of the checkbox control. */\n onKeyUp?: React.KeyboardEventHandler<HTMLButtonElement>;\n /** Ref to the focusable `role=\"checkbox\"` button. */\n controlRef?: React.Ref<HTMLButtonElement>;\n /** Ref to the root `<label>` element. */\n ref?: React.Ref<HTMLLabelElement>;\n}\n\n/**\n * A checkbox for a boolean (or mixed) choice, drawn as a `role=\"checkbox\"` button inside a\n * `<label>`.\n *\n * - The root `<label>` receives `ref`, `className`, `style` and `data-*`; the control receives\n * `id`, `aria-label`/`-labelledby`/`-describedby`/`-invalid`/`-required`/`-errormessage`/\n * `-details`/`-disabled`, `tabIndex`, `autoFocus` and the click, focus and key handlers\n * (`controlRef` exposes it). A consumer `onClick` runs once per activation, before the toggle;\n * `preventDefault()` in it cancels the toggle.\n * - Inside a `Field` it is named by the Field label (followed by its own `label` text) and described\n * by the Field message and hint.\n * - With `name` (or `required`) it takes part in native forms like `<input type=\"checkbox\">`, and\n * a form reset restores `defaultChecked`.\n * - `label` takes rich content (a link to the terms) and renders after the box, or before it with\n * `labelPosition=\"before\"` (the root carries `data-label-position`). The box lines up with the\n * first line of a label that wraps or has a second line. `children` are not rendered (a\n * development warning says so).\n */\nexport const Checkbox = ({\n checked: checkedProp,\n defaultChecked = false,\n indeterminate = false,\n onCheckedChange,\n onChange,\n disabled = false,\n disabledFocusable = false,\n label,\n labelPosition = 'after',\n name,\n value,\n required,\n form,\n id,\n 'aria-label': ariaLabel,\n 'aria-labelledby': ariaLabelledBy,\n 'aria-describedby': ariaDescribedBy,\n 'aria-invalid': ariaInvalid,\n 'aria-required': ariaRequired,\n 'aria-errormessage': ariaErrorMessage,\n 'aria-details': ariaDetails,\n 'aria-disabled': ariaDisabled,\n autoFocus,\n tabIndex,\n onClick,\n onFocus,\n onBlur,\n onKeyDown,\n onKeyUp,\n controlRef,\n className,\n children,\n ref,\n ...rest\n}: CheckboxProps) => {\n if (onChange !== undefined) warnDeprecated('Checkbox', 'onChange', 'onCheckedChange');\n const hasChildren = slotRendersContent(children);\n React.useEffect(() => {\n if (hasChildren) {\n warnOnce(\n 'Checkbox:children',\n 'Checkbox: children are not rendered. Pass the label in `label`.',\n );\n }\n }, [hasChildren]);\n const [checked, setChecked] = useControllable(checkedProp, defaultChecked, (next: boolean) => {\n onCheckedChange?.(next);\n onChange?.(next);\n });\n\n const generatedId = useId('checkbox');\n const labelTextId = useId('checkbox-label');\n const field = useFieldContext();\n const fieldProps = useFieldControl({\n id,\n 'aria-label': ariaLabel,\n 'aria-labelledby': ariaLabelledBy,\n 'aria-describedby': ariaDescribedBy,\n 'aria-invalid': ariaInvalid,\n // An explicit `required={false}` wins over a required Field, so aria-required always matches\n // the native validation below (`isRequired`).\n 'aria-required': ariaRequired ?? required,\n });\n const isRequired = required ?? field?.required ?? false;\n // `0` is a label; `null`, `false`, `''` and empty collections are not (C-SLOTS).\n const hasLabel = slotRendersContent(label);\n // The label text names the control through aria-labelledby, disabled or not: axe exempts the\n // dimmed text of a disabled control only when the control references it this way (its <label>\n // exemption covers native inputs only). A consumer aria-label still names the control alone.\n // The ids already there (the consumer's, the Field label from useFieldControl) come first, then\n // the Field label whose <label htmlFor> targets this control (aria-labelledby would hide it), so\n // the name keeps every label.\n const labelledBy =\n hasLabel && fieldProps['aria-label'] === undefined\n ? joinIds(\n fieldProps['aria-labelledby'],\n field && fieldProps.id === field.controlId ? field.labelId : undefined,\n labelTextId,\n )\n : fieldProps['aria-labelledby'];\n\n const buttonRef = React.useRef<HTMLButtonElement>(null);\n const mergedControlRef = useMergedRefs(buttonRef, controlRef);\n useFormReset(buttonRef, () => setChecked(defaultChecked), form);\n\n const on = checked || indeterminate;\n // Focusable-disabled wins over `disabled`: the box stays focusable but looks and acts disabled.\n const unavailable = disabled || disabledFocusable;\n // The glyph is the forced-colors leaf; the box stays on system colors (see `checkedBox`).\n const glyphClassName = unavailable ? disabledGlyph : forcedColors.selectedLeaf;\n const labelText = hasLabel ? (\n <span id={labelTextId} className=\"text-body-1 text-foreground\">\n {materialiseSlotContent(label)}\n </span>\n ) : null;\n\n return (\n <label\n ref={ref}\n data-label-position={labelPosition}\n className={cn(\n // items-start: the box lines up with the first line of a label that wraps or has a second\n // line, not with its middle.\n 'relative inline-flex items-start gap-2 select-none',\n // The dimmed look lifts while a focus ring shows inside the root (the control's, under\n // disabledFocusable, or a link's in the label): opacity would dim the ring below 3:1.\n unavailable\n ? 'cursor-not-allowed opacity-50 has-focus-visible:opacity-100'\n : 'cursor-pointer',\n className,\n )}\n {...rest}\n >\n {labelPosition === 'before' && labelText}\n <button\n id={generatedId}\n type=\"button\"\n {...fieldProps}\n aria-labelledby={labelledBy}\n aria-errormessage={ariaErrorMessage}\n aria-details={ariaDetails}\n aria-disabled={ariaDisabled}\n autoFocus={autoFocus}\n tabIndex={tabIndex}\n onFocus={onFocus}\n onBlur={onBlur}\n onKeyDown={onKeyDown}\n onKeyUp={onKeyUp}\n ref={mergedControlRef}\n role=\"checkbox\"\n aria-checked={indeterminate ? 'mixed' : checked}\n disabled={disabled && !disabledFocusable}\n {...focusableDisabledProps(disabledFocusable, { reachable: true })}\n onClick={\n disabledFocusable\n ? // Clicks, Space and Enter (which click a button) neither toggle nor reach `onClick`,\n // and, as a natively disabled control dispatches no click, no ancestor sees them.\n (event: React.MouseEvent<HTMLButtonElement>) => {\n event.preventDefault();\n event.stopPropagation();\n }\n : composeEventHandlers(onClick, () => setChecked((prev) => !prev))\n }\n className={cn(\n // p-0 and the unchecked bg-transparent are set here, not left to the native reset, which\n // any app button style overrides (C-NATIVE).\n 'flex h-[18px] w-[18px] shrink-0 items-center justify-center rounded-xs border p-0 transition-colors motion-reduce:transition-none',\n // Centred on the 20px first line of the label text.\n hasLabel && 'mt-px',\n focusRing,\n on\n ? cn(\n 'border-primary bg-primary text-primary-foreground',\n unavailable ? disabledCheckedBox : checkedBox,\n )\n : cn(\n 'border-stroke-accessible bg-transparent',\n unavailable ? forcedColors.disabled : forcedColors.control,\n ),\n )}\n >\n {indeterminate ? (\n <SubtractIcon size={12} className={glyphClassName} />\n ) : checked ? (\n <CheckIcon size={12} className={glyphClassName} />\n ) : null}\n </button>\n {labelPosition !== 'before' && labelText}\n <HiddenInput\n type=\"checkbox\"\n name={name}\n form={form}\n disabled={unavailable}\n value={value}\n checked={checked}\n required={isRequired}\n onInvalid={() => buttonRef.current?.focus()}\n />\n </label>\n );\n};\n\nCheckbox.displayName = 'Checkbox';\n"],"mappings":"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"}
@@ -0,0 +1,96 @@
1
+ "use client";
2
+ import { cn as e } from "../../lib/cn.mjs";
3
+ import { warnDeprecated as t, warnOnce as n } from "../../lib/dev.mjs";
4
+ import { materialiseSlotContent as ee, slotRendersContent as r } from "../../lib/slot.mjs";
5
+ import { composeEventHandlers as te } from "../../lib/composeEventHandlers.mjs";
6
+ import { useControllable as ne } from "../../hooks/useControllable.mjs";
7
+ import { useId as i } from "../../hooks/useId.mjs";
8
+ import { useMergedRefs as a } from "../../hooks/useMergedRefs.mjs";
9
+ import { focusableDisabledProps as re, joinIds as ie } from "../../lib/aria.mjs";
10
+ import { useFieldContext as ae, useFieldControl as oe } from "../../hooks/useFieldControl.mjs";
11
+ import { focusRing as se, forcedColors as o } from "../../lib/styles.mjs";
12
+ import { CheckIcon as s, SubtractIcon as c } from "../../lib/icons.mjs";
13
+ import { useFormReset as l } from "../../hooks/useFormReset.mjs";
14
+ import { HiddenInput as ce } from "../internal/HiddenInput.mjs";
15
+ import * as u from "react";
16
+ import { jsx as d, jsxs as f } from "react/jsx-runtime";
17
+ //#region src/components/input/Checkbox.tsx
18
+ var p = "forced-colors:border-[Highlight] forced-colors:bg-[Highlight]", m = "forced-colors:border-[GrayText] forced-colors:bg-[Canvas]", le = "forced-colors:text-[GrayText] forced-colors:forced-color-adjust-none", h = ({ checked: h, defaultChecked: g = !1, indeterminate: _ = !1, onCheckedChange: ue, onChange: v, disabled: y = !1, disabledFocusable: b = !1, label: x, labelPosition: S = "after", name: C, value: w, required: T, form: E, id: D, "aria-label": O, "aria-labelledby": k, "aria-describedby": A, "aria-invalid": j, "aria-required": M, "aria-errormessage": N, "aria-details": P, "aria-disabled": F, autoFocus: I, tabIndex: de, onClick: L, onFocus: R, onBlur: z, onKeyDown: B, onKeyUp: V, controlRef: H, className: fe, children: pe, ref: me, ...he }) => {
19
+ v !== void 0 && t("Checkbox", "onChange", "onCheckedChange");
20
+ let U = r(pe);
21
+ u.useEffect(() => {
22
+ U && n("Checkbox:children", "Checkbox: children are not rendered. Pass the label in `label`.");
23
+ }, [U]);
24
+ let [W, G] = ne(h, g, (e) => {
25
+ ue?.(e), v?.(e);
26
+ }), ge = i("checkbox"), K = i("checkbox-label"), q = ae(), J = oe({
27
+ id: D,
28
+ "aria-label": O,
29
+ "aria-labelledby": k,
30
+ "aria-describedby": A,
31
+ "aria-invalid": j,
32
+ "aria-required": M ?? T
33
+ }), _e = T ?? q?.required ?? !1, Y = r(x), ve = Y && J["aria-label"] === void 0 ? ie(J["aria-labelledby"], q && J.id === q.controlId ? q.labelId : void 0, K) : J["aria-labelledby"], X = u.useRef(null), ye = a(X, H);
34
+ l(X, () => G(g), E);
35
+ let be = W || _, Z = y || b, Q = Z ? le : o.selectedLeaf, $ = Y ? /* @__PURE__ */ d("span", {
36
+ id: K,
37
+ className: "text-body-1 text-foreground",
38
+ children: ee(x)
39
+ }) : null;
40
+ return /* @__PURE__ */ f("label", {
41
+ ref: me,
42
+ "data-label-position": S,
43
+ className: e("relative inline-flex items-start gap-2 select-none", Z ? "cursor-not-allowed opacity-50 has-focus-visible:opacity-100" : "cursor-pointer", fe),
44
+ ...he,
45
+ children: [
46
+ S === "before" && $,
47
+ /* @__PURE__ */ d("button", {
48
+ id: ge,
49
+ type: "button",
50
+ ...J,
51
+ "aria-labelledby": ve,
52
+ "aria-errormessage": N,
53
+ "aria-details": P,
54
+ "aria-disabled": F,
55
+ autoFocus: I,
56
+ tabIndex: de,
57
+ onFocus: R,
58
+ onBlur: z,
59
+ onKeyDown: B,
60
+ onKeyUp: V,
61
+ ref: ye,
62
+ role: "checkbox",
63
+ "aria-checked": _ ? "mixed" : W,
64
+ disabled: y && !b,
65
+ ...re(b, { reachable: !0 }),
66
+ onClick: b ? (e) => {
67
+ e.preventDefault(), e.stopPropagation();
68
+ } : te(L, () => G((e) => !e)),
69
+ className: e("flex h-[18px] w-[18px] shrink-0 items-center justify-center rounded-xs border p-0 transition-colors motion-reduce:transition-none", Y && "mt-px", se, be ? e("border-primary bg-primary text-primary-foreground", Z ? m : p) : e("border-stroke-accessible bg-transparent", Z ? o.disabled : o.control)),
70
+ children: _ ? /* @__PURE__ */ d(c, {
71
+ size: 12,
72
+ className: Q
73
+ }) : W ? /* @__PURE__ */ d(s, {
74
+ size: 12,
75
+ className: Q
76
+ }) : null
77
+ }),
78
+ S !== "before" && $,
79
+ /* @__PURE__ */ d(ce, {
80
+ type: "checkbox",
81
+ name: C,
82
+ form: E,
83
+ disabled: Z,
84
+ value: w,
85
+ checked: W,
86
+ required: _e,
87
+ onInvalid: () => X.current?.focus()
88
+ })
89
+ ]
90
+ });
91
+ };
92
+ h.displayName = "Checkbox";
93
+ //#endregion
94
+ export { h as Checkbox };
95
+
96
+ //# sourceMappingURL=Checkbox.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Checkbox.mjs","names":["useId","useId$1","React","checkedBox","disabledCheckedBox","disabledGlyph","Checkbox","checkedProp","ariaLabel","ariaLabelledBy","ariaDescribedBy","ariaInvalid","ariaRequired","ariaErrorMessage","ariaDetails","ariaDisabled","rest","onChange","warnDeprecated","hasChildren","slotRendersContent","children","warnOnce","checked","setChecked","useControllable","defaultChecked","onCheckedChange","next","generatedId","labelTextId","field","useFieldContext","fieldProps","useFieldControl","required","isRequired","hasLabel","label","labelledBy","joinIds","buttonRef","mergedControlRef","useMergedRefs","controlRef","form","on","indeterminate","unavailable","disabled","disabledFocusable","glyphClassName","forcedColors","labelText","materialiseSlotContent","labelPosition","cn","className","focusableDisabledProps","event","composeEventHandlers","onClick","prev","focusRing","SubtractIcon","CheckIcon","HiddenInput"],"sources":["../../../src/components/input/Checkbox.tsx"],"sourcesContent":["import * as React from 'react';\nimport { focusableDisabledProps, joinIds } from '../../lib/aria';\nimport { cn } from '../../lib/cn';\nimport { composeEventHandlers } from '../../lib/composeEventHandlers';\nimport { warnDeprecated, warnOnce } from '../../lib/dev';\nimport { CheckIcon, SubtractIcon } from '../../lib/icons';\nimport { materialiseSlotContent, slotRendersContent } from '../../lib/slot';\nimport { focusRing, forcedColors } from '../../lib/styles';\nimport type { LabelPosition } from '../../lib/types';\nimport { useControllable } from '../../hooks/useControllable';\nimport { useFieldContext, useFieldControl } from '../../hooks/useFieldControl';\nimport { useFormReset } from '../../hooks/useFormReset';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { HiddenInput } from '../internal/HiddenInput';\n\n/*\n * Forced colors: the focusable box keeps system-color utilities, so the browser still forces its\n * focus outline and border; only the glyph (the leaf indicator) opts out of forced colors. A\n * disabled box draws a GrayText glyph and border on Canvas, without the Highlight fill.\n */\nconst checkedBox = 'forced-colors:border-[Highlight] forced-colors:bg-[Highlight]';\nconst disabledCheckedBox = 'forced-colors:border-[GrayText] forced-colors:bg-[Canvas]';\nconst disabledGlyph = 'forced-colors:text-[GrayText] forced-colors:forced-color-adjust-none';\n\n/** Handlers that run on the `role=\"checkbox\"` button instead of the root label (C-ROUTING). */\ntype CheckboxControlHandlers = 'onClick' | 'onFocus' | 'onBlur' | 'onKeyDown' | 'onKeyUp';\n\n/** Where a Checkbox renders its label: after the box (default) or before it. */\nexport type CheckboxLabelPosition = Extract<LabelPosition, 'before' | 'after'>;\n\n/** Properties for the Checkbox component. */\nexport interface CheckboxProps extends Omit<\n React.HTMLAttributes<HTMLLabelElement>,\n 'onChange' | 'defaultChecked' | CheckboxControlHandlers\n> {\n /** Controlled checked state. */\n checked?: boolean;\n /** Initial checked state for uncontrolled usage (also the value a form reset restores).\n * @default false\n */\n defaultChecked?: boolean;\n /**\n * Shows the mixed state: the dash glyph and `aria-checked=\"mixed\"`, whatever `checked` is. A\n * click still toggles `checked` and calls `onCheckedChange`, but the checkbox keeps showing and\n * announcing \"mixed\" until you clear `indeterminate`. For a tri-state \"select all\", derive\n * `checked` and `indeterminate` from the items and set every item in `onCheckedChange`.\n * @default false\n */\n indeterminate?: boolean;\n /** Called with the new checked state when it changes (not for no-op updates). */\n onCheckedChange?: (checked: boolean) => void;\n /**\n * Called with the new checked state when it changes.\n * @deprecated Use `onCheckedChange`.\n */\n onChange?: (checked: boolean) => void;\n /** Whether the checkbox is disabled and non-interactive. */\n disabled?: boolean;\n /**\n * Marks the checkbox unavailable but keeps it focusable and in the tab order: for a disabled\n * checkbox that needs a Tooltip, or one in a toolbar. Renders `aria-disabled=\"true\"`,\n * `data-disabled` and `data-disabled-focusable` on the checkbox instead of the native `disabled`\n * attribute. The checkbox cannot be toggled and is not submitted with its form; your `onClick`\n * is not called, and a click on the checkbox (or Space and Enter) does not reach ancestor click\n * handlers, as for a natively disabled control. Wins over `disabled` when both are set. In a\n * roving container (a `Toolbar`) it stays in the arrow-key order.\n * @default false\n */\n disabledFocusable?: boolean;\n /**\n * Label next to the control (any phrasing content, links included, but no other form\n * controls). It names the control through `aria-labelledby`, after a consumer or Field\n * `aria-labelledby`; a consumer `aria-label` names it instead. Clicking its text toggles the\n * control; clicking a link inside it follows the link. `children` are not rendered: pass the\n * label here.\n */\n label?: React.ReactNode;\n /**\n * Where the label renders: after the control (default) or before it. The DOM order follows the\n * visual order.\n * @default 'after'\n */\n labelPosition?: CheckboxLabelPosition;\n /**\n * Form field name. With a name, the checkbox takes part in native form submission: it submits\n * `name=value` while checked.\n */\n name?: string;\n /** Value submitted while checked.\n * @default 'on'\n */\n value?: string;\n /** The form must not be submitted while the checkbox is unchecked (native validation). */\n required?: boolean;\n /** Id of the form the checkbox belongs to, when it is rendered outside that form. */\n form?: string;\n /** Click handler of the checkbox control (the `role=\"checkbox\"` button). */\n onClick?: React.MouseEventHandler<HTMLButtonElement>;\n /** Focus handler of the checkbox control. */\n onFocus?: React.FocusEventHandler<HTMLButtonElement>;\n /** Blur handler of the checkbox control. */\n onBlur?: React.FocusEventHandler<HTMLButtonElement>;\n /** Keydown handler of the checkbox control. */\n onKeyDown?: React.KeyboardEventHandler<HTMLButtonElement>;\n /** Keyup handler of the checkbox control. */\n onKeyUp?: React.KeyboardEventHandler<HTMLButtonElement>;\n /** Ref to the focusable `role=\"checkbox\"` button. */\n controlRef?: React.Ref<HTMLButtonElement>;\n /** Ref to the root `<label>` element. */\n ref?: React.Ref<HTMLLabelElement>;\n}\n\n/**\n * A checkbox for a boolean (or mixed) choice, drawn as a `role=\"checkbox\"` button inside a\n * `<label>`.\n *\n * - The root `<label>` receives `ref`, `className`, `style` and `data-*`; the control receives\n * `id`, `aria-label`/`-labelledby`/`-describedby`/`-invalid`/`-required`/`-errormessage`/\n * `-details`/`-disabled`, `tabIndex`, `autoFocus` and the click, focus and key handlers\n * (`controlRef` exposes it). A consumer `onClick` runs once per activation, before the toggle;\n * `preventDefault()` in it cancels the toggle.\n * - Inside a `Field` it is named by the Field label (followed by its own `label` text) and described\n * by the Field message and hint.\n * - With `name` (or `required`) it takes part in native forms like `<input type=\"checkbox\">`, and\n * a form reset restores `defaultChecked`.\n * - `label` takes rich content (a link to the terms) and renders after the box, or before it with\n * `labelPosition=\"before\"` (the root carries `data-label-position`). The box lines up with the\n * first line of a label that wraps or has a second line. `children` are not rendered (a\n * development warning says so).\n */\nexport const Checkbox = ({\n checked: checkedProp,\n defaultChecked = false,\n indeterminate = false,\n onCheckedChange,\n onChange,\n disabled = false,\n disabledFocusable = false,\n label,\n labelPosition = 'after',\n name,\n value,\n required,\n form,\n id,\n 'aria-label': ariaLabel,\n 'aria-labelledby': ariaLabelledBy,\n 'aria-describedby': ariaDescribedBy,\n 'aria-invalid': ariaInvalid,\n 'aria-required': ariaRequired,\n 'aria-errormessage': ariaErrorMessage,\n 'aria-details': ariaDetails,\n 'aria-disabled': ariaDisabled,\n autoFocus,\n tabIndex,\n onClick,\n onFocus,\n onBlur,\n onKeyDown,\n onKeyUp,\n controlRef,\n className,\n children,\n ref,\n ...rest\n}: CheckboxProps) => {\n if (onChange !== undefined) warnDeprecated('Checkbox', 'onChange', 'onCheckedChange');\n const hasChildren = slotRendersContent(children);\n React.useEffect(() => {\n if (hasChildren) {\n warnOnce(\n 'Checkbox:children',\n 'Checkbox: children are not rendered. Pass the label in `label`.',\n );\n }\n }, [hasChildren]);\n const [checked, setChecked] = useControllable(checkedProp, defaultChecked, (next: boolean) => {\n onCheckedChange?.(next);\n onChange?.(next);\n });\n\n const generatedId = useId('checkbox');\n const labelTextId = useId('checkbox-label');\n const field = useFieldContext();\n const fieldProps = useFieldControl({\n id,\n 'aria-label': ariaLabel,\n 'aria-labelledby': ariaLabelledBy,\n 'aria-describedby': ariaDescribedBy,\n 'aria-invalid': ariaInvalid,\n // An explicit `required={false}` wins over a required Field, so aria-required always matches\n // the native validation below (`isRequired`).\n 'aria-required': ariaRequired ?? required,\n });\n const isRequired = required ?? field?.required ?? false;\n // `0` is a label; `null`, `false`, `''` and empty collections are not (C-SLOTS).\n const hasLabel = slotRendersContent(label);\n // The label text names the control through aria-labelledby, disabled or not: axe exempts the\n // dimmed text of a disabled control only when the control references it this way (its <label>\n // exemption covers native inputs only). A consumer aria-label still names the control alone.\n // The ids already there (the consumer's, the Field label from useFieldControl) come first, then\n // the Field label whose <label htmlFor> targets this control (aria-labelledby would hide it), so\n // the name keeps every label.\n const labelledBy =\n hasLabel && fieldProps['aria-label'] === undefined\n ? joinIds(\n fieldProps['aria-labelledby'],\n field && fieldProps.id === field.controlId ? field.labelId : undefined,\n labelTextId,\n )\n : fieldProps['aria-labelledby'];\n\n const buttonRef = React.useRef<HTMLButtonElement>(null);\n const mergedControlRef = useMergedRefs(buttonRef, controlRef);\n useFormReset(buttonRef, () => setChecked(defaultChecked), form);\n\n const on = checked || indeterminate;\n // Focusable-disabled wins over `disabled`: the box stays focusable but looks and acts disabled.\n const unavailable = disabled || disabledFocusable;\n // The glyph is the forced-colors leaf; the box stays on system colors (see `checkedBox`).\n const glyphClassName = unavailable ? disabledGlyph : forcedColors.selectedLeaf;\n const labelText = hasLabel ? (\n <span id={labelTextId} className=\"text-body-1 text-foreground\">\n {materialiseSlotContent(label)}\n </span>\n ) : null;\n\n return (\n <label\n ref={ref}\n data-label-position={labelPosition}\n className={cn(\n // items-start: the box lines up with the first line of a label that wraps or has a second\n // line, not with its middle.\n 'relative inline-flex items-start gap-2 select-none',\n // The dimmed look lifts while a focus ring shows inside the root (the control's, under\n // disabledFocusable, or a link's in the label): opacity would dim the ring below 3:1.\n unavailable\n ? 'cursor-not-allowed opacity-50 has-focus-visible:opacity-100'\n : 'cursor-pointer',\n className,\n )}\n {...rest}\n >\n {labelPosition === 'before' && labelText}\n <button\n id={generatedId}\n type=\"button\"\n {...fieldProps}\n aria-labelledby={labelledBy}\n aria-errormessage={ariaErrorMessage}\n aria-details={ariaDetails}\n aria-disabled={ariaDisabled}\n autoFocus={autoFocus}\n tabIndex={tabIndex}\n onFocus={onFocus}\n onBlur={onBlur}\n onKeyDown={onKeyDown}\n onKeyUp={onKeyUp}\n ref={mergedControlRef}\n role=\"checkbox\"\n aria-checked={indeterminate ? 'mixed' : checked}\n disabled={disabled && !disabledFocusable}\n {...focusableDisabledProps(disabledFocusable, { reachable: true })}\n onClick={\n disabledFocusable\n ? // Clicks, Space and Enter (which click a button) neither toggle nor reach `onClick`,\n // and, as a natively disabled control dispatches no click, no ancestor sees them.\n (event: React.MouseEvent<HTMLButtonElement>) => {\n event.preventDefault();\n event.stopPropagation();\n }\n : composeEventHandlers(onClick, () => setChecked((prev) => !prev))\n }\n className={cn(\n // p-0 and the unchecked bg-transparent are set here, not left to the native reset, which\n // any app button style overrides (C-NATIVE).\n 'flex h-[18px] w-[18px] shrink-0 items-center justify-center rounded-xs border p-0 transition-colors motion-reduce:transition-none',\n // Centred on the 20px first line of the label text.\n hasLabel && 'mt-px',\n focusRing,\n on\n ? cn(\n 'border-primary bg-primary text-primary-foreground',\n unavailable ? disabledCheckedBox : checkedBox,\n )\n : cn(\n 'border-stroke-accessible bg-transparent',\n unavailable ? forcedColors.disabled : forcedColors.control,\n ),\n )}\n >\n {indeterminate ? (\n <SubtractIcon size={12} className={glyphClassName} />\n ) : checked ? (\n <CheckIcon size={12} className={glyphClassName} />\n ) : null}\n </button>\n {labelPosition !== 'before' && labelText}\n <HiddenInput\n type=\"checkbox\"\n name={name}\n form={form}\n disabled={unavailable}\n value={value}\n checked={checked}\n required={isRequired}\n onInvalid={() => buttonRef.current?.focus()}\n />\n </label>\n );\n};\n\nCheckbox.displayName = 'Checkbox';\n"],"mappings":"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"}
@@ -0,0 +1,6 @@
1
+ "use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/dev.cjs"),r=require("../../hooks/useControllable.cjs"),i=require("../../hooks/useId.cjs"),a=require("../../hooks/useMergedRefs.cjs"),o=require("../../lib/aria.cjs"),s=require("../../hooks/useFieldControl.cjs"),c=require("../../lib/styles.cjs"),ee=require("./Input.cjs"),te=require("../../hooks/useFormReset.cjs"),l=require("../internal/HiddenInput.cjs"),u=require("./colorUtils.cjs"),d=require("./SwatchPicker.cjs");let f=require("react");f=e.__toESM(f,1);let p=require("react/jsx-runtime");var m=`#0f6cbd`,h={hex:`Hex`,hexInput:`Hex color value`,hexError:`Enter a hex color such as ${m}.`,presets:`Preset colors`,opacity:`Opacity`},ne=[{color:`#0f6cbd`,label:`Blue`},{color:`#d13438`,label:`Red`},{color:`#107c10`,label:`Green`},{color:`#ffb900`,label:`Yellow`},{color:`#5c2d91`,label:`Purple`},{color:`#008272`,label:`Teal`},{color:`#e3008c`,label:`Pink`},{color:`#242424`,label:`Black`}];function g(e){let t=[],n=[],r=[],i=new Set;for(let a of e){let e=typeof a==`string`?a:a.color,o=u.parseHexColor(e);if(!o){n.push(e);continue}let s=o.alpha!==255;if(s&&r.push(e),i.has(o.rgb))continue;i.add(o.rgb);let c=s?o.rgb:e;t.push({value:o.rgb,color:o.rgb,label:typeof a==`string`?c:a.label})}return{items:t,invalid:n,translucent:r}}function _(e){let t=e.trim();return t===``||t===`#`}function v(e){let t=e.trim().replace(/^#/,``).length;return t===4||t===8}var y=({value:e,defaultValue:y,onValueChange:re,onChange:b,presets:ie=ne,showOpacity:ae=!1,labels:oe,name:se,required:ce,form:x,className:le,id:ue,"aria-label":de,"aria-labelledby":S,"aria-describedby":C,"aria-invalid":fe,"aria-required":w,"aria-errormessage":pe,ref:me,...he})=>{b!==void 0&&n.warnDeprecated(`ColorPicker`,`onChange`,`onValueChange`);let T=y??m,E=u.normalizeHexColor(T)??T,D={...h,...oe},[O,k]=r.useControllable(e,E,e=>{re?.(e),b?.(e)}),A=u.parseHexColor(O),j=A?.alpha??255,M=u.alphaToOpacity(j),N=(e,t)=>k(u.formatHexColor(e,t)),[P,F]=f.useState(null),[I,L]=f.useState(O);O!==I&&(L(O),P?.flagged&&F(null));let R=P?.text??O,z=P!==null&&!_(P.text)&&(P.flagged||!u.isHexDraft(P.text)),{items:B,invalid:ge,translucent:_e}=g(ie),V=ge.join(`
2
+ `),H=_e.join(`
3
+ `),U=A?null:O;f.useEffect(()=>{U!==null&&n.warnOnce(`ColorPicker:invalid-value`,`ColorPicker: "${U}" is not a hex color (#rrggbb or #rrggbbaa). Pass a hex value; the opacity slider is disabled until then.`)},[U]),f.useEffect(()=>{if(V)for(let e of V.split(`
4
+ `))n.warnOnce(`ColorPicker:invalid-preset:${e}`,`ColorPicker: preset "${e}" is not a hex color (#rgb or #rrggbb) and is not shown.`)},[V]),f.useEffect(()=>{if(H)for(let e of H.split(`
5
+ `))n.warnOnce(`ColorPicker:alpha-preset:${e}`,`ColorPicker: preset "${e}" has an alpha byte, which is ignored: picking a preset keeps the current opacity. Pass the color as #rgb or #rrggbb.`)},[H]);let W=f.useRef(null),G=f.useRef(null),ve=a.useMergedRefs(me,W),K=s.useFieldContext(),{"aria-invalid":q,"aria-required":ye,required:be,...xe}=s.useFieldControl({id:ue,"aria-label":de,"aria-labelledby":S,"aria-describedby":C,"aria-invalid":fe},{labelable:!1}),J=q!==void 0&&q!==!1&&q!==`false`,Y=ce??(w===!0||w===`true`||(K?.required??!1)),X=J&&pe||void 0;te.useFormReset(W,()=>{(u.normalizeHexColor(O)??O)!==E&&k(E),F(null)},x);let Z=i.useId(`wave-color-picker-error`),Q=z?!0:J?q:void 0,Se=ee.isInvalidLook(!1,Q),Ce=e=>{let t=e.target.value.trim();t!==``&&!t.startsWith(`#`)&&(t=`#${t}`),F({text:t,flagged:!1});let n=u.parseHexInput(t);n&&N(n.rgb,v(t)?n.alpha:j)},$=()=>{if(P===null||P.flagged)return;let e=u.parseHexColor(P.text);if(e||_(P.text)){e&&!u.parseHexInput(P.text)&&N(e.rgb,v(P.text)?e.alpha:j),F(null);return}F({text:P.text,flagged:!0})},we=e=>{e.key===`Enter`&&!e.defaultPrevented&&!e.nativeEvent.isComposing&&$()},Te=e=>{let t=u.parseHexColor(e);t&&(F(null),N(t.rgb,j))},Ee=e=>{A&&N(A.rgb,u.opacityToAlpha(Number(e.target.value)))},De=A?A.rgb:``;return(0,p.jsxs)(`div`,{role:`group`,...xe,className:t.cn(`relative inline-flex flex-col gap-3 rounded border border-border bg-background p-3 shadow-4`,le),...he,ref:ve,children:[(0,p.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,p.jsx)(`div`,{"data-color-preview":``,className:`h-10 w-10 shrink-0 rounded border border-border`,style:{backgroundColor:A?u.formatHexColor(A.rgb,A.alpha):O},"aria-hidden":`true`}),(0,p.jsxs)(`label`,{className:`flex flex-col gap-1`,children:[(0,p.jsx)(`span`,{className:`text-caption-1 text-muted-foreground`,children:D.hex}),(0,p.jsx)(`input`,{ref:G,type:`text`,value:R,onChange:Ce,onKeyDown:we,onBlur:$,"aria-label":D.hexInput,"aria-invalid":Q,"aria-errormessage":X,"aria-describedby":o.joinIds(z&&Z,K?.validationMessageId??(J?K?.errorId:void 0),X),maxLength:9,spellCheck:!1,autoComplete:`off`,className:t.cn(`w-24 rounded border border-input border-b-stroke-accessible bg-background px-2 py-1 text-body-1 text-foreground`,c.inputFocus,Se&&`border-destructive focus:border-b-destructive`)})]})]}),z&&(0,p.jsx)(`span`,{id:Z,className:`text-caption-1 text-error`,children:D.hexError}),B.length>0&&(0,p.jsx)(s.FieldContext.Provider,{value:null,children:(0,p.jsx)(d.SwatchPicker,{items:B,value:De,onValueChange:Te,"aria-label":D.presets,size:`small`,shape:`rounded`})}),ae&&(0,p.jsxs)(`div`,{className:`flex items-center gap-2`,children:[(0,p.jsx)(`span`,{className:`w-14 text-caption-1 text-muted-foreground`,children:D.opacity}),(0,p.jsx)(`input`,{type:`range`,min:0,max:100,value:M,onChange:Ee,disabled:!A,"aria-label":D.opacity,"aria-valuetext":`${M}%`,className:t.cn(`h-1 flex-1 accent-primary disabled:cursor-not-allowed disabled:opacity-50`,`focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-ring`)}),(0,p.jsxs)(`span`,{className:`w-10 text-end text-caption-1 text-muted-foreground`,children:[M,`%`]})]}),(0,p.jsx)(l.HiddenInput,{type:`text`,name:se,form:x,value:O,required:Y,onInvalid:()=>G.current?.focus()})]})};y.displayName=`ColorPicker`,exports.ColorPicker=y;
6
+ //# sourceMappingURL=ColorPicker.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ColorPicker.cjs","names":["parseHexColor","normalizeHexColor","useControllable","alphaToOpacity","formatHexColor","React","isHexDraft","useMergedRefs","useFieldContext","useFieldControl","useId","isInvalidLook","parseHexInput","opacityToAlpha","cn","joinIds","inputFocus","FieldContext","SwatchPicker","HiddenInput","require_runtime","require_cn","require_dev","require_useControllable","require_useId","require_useMergedRefs","require_aria","require_useFieldControl","require_styles","require_Input","require_useFormReset","require_HiddenInput","require_colorUtils","require_SwatchPicker","react","react_jsx_runtime","DEFAULT_COLOR","DEFAULT_LABELS","DEFAULT_PRESETS","resolvePresets","items","invalid","translucent","seen","preset","presets","color","parsed","hasAlpha","stringLabel","isBlankDraft","trimmed","text","hasAlphaDigits","digits","ColorPicker","valueProp","ariaLabel","ariaLabelledBy","ariaDescribedBy","ariaInvalid","ariaRequired","ariaErrorMessage","rest","onChange","rawDefault","defaultValue","initialValue","strings","labels","setColor","onValueChange","next","alpha","opacity","commit","rgb","nextAlpha","draft","setDraft","syncedColor","setSyncedColor","hexText","draftInvalid","presetItems","invalidPresets","translucentPresets","invalidPresetKey","translucentPresetKey","invalidValue","rootRef","hexInputRef","mergedRef","ref","field","groupInvalid","_ariaRequired","_required","groupProps","fieldInvalid","isRequired","required","errorMessageId","form","errorId","hexAriaInvalid","hexInvalidLook","handleHexChange","typed","finishHexDraft","handleHexKeyDown","handlePreset","handleOpacityChange","selectedPreset","className","showOpacity"],"sources":["../../../src/components/input/ColorPicker.tsx"],"sourcesContent":["import * as React from 'react';\nimport { cn } from '../../lib/cn';\nimport { warnDeprecated, warnOnce } from '../../lib/dev';\nimport { joinIds } from '../../lib/aria';\nimport { focusRing, inputFocus, inputInvalid } from '../../lib/styles';\nimport { useControllable } from '../../hooks/useControllable';\nimport { FieldContext, useFieldContext, useFieldControl } from '../../hooks/useFieldControl';\nimport { useFormReset } from '../../hooks/useFormReset';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { HiddenInput } from '../internal/HiddenInput';\nimport { isInvalidLook } from './Input';\nimport { SwatchPicker } from './SwatchPicker';\nimport type { SwatchItem } from './SwatchPicker';\nimport {\n alphaToOpacity,\n formatHexColor,\n isHexDraft,\n normalizeHexColor,\n opacityToAlpha,\n parseHexColor,\n parseHexInput,\n} from './colorUtils';\n\n/** A named preset color. */\nexport interface ColorPickerPreset {\n /**\n * Hex color (`#rrggbb`; `#rgb` is expanded). A preset has no opacity of its own: picking it keeps\n * the current opacity, so its alpha digits (`#rgba`, `#rrggbbaa`) are ignored. An alpha below\n * `f`/`ff` logs a development warning; an opaque one (`#rgbf`, `#rrggbbff`) changes nothing.\n */\n color: string;\n /** Accessible name of the preset swatch, e.g. `'Cranberry'`. */\n label: string;\n}\n\n/**\n * Texts of the ColorPicker's own parts, for localisation. Every key is optional; missing keys use\n * the English default.\n */\nexport interface ColorPickerLabels {\n /** Visible caption above the hex field.\n * @default 'Hex'\n */\n hex?: string;\n /** Accessible name of the hex text field.\n * @default 'Hex color value'\n */\n hexInput?: string;\n /** Error text shown (and used as the hex field's description) while the typed text can never be\n * a hex color, or when the field is left with text that is not one (such as `#12345`).\n * @default 'Enter a hex color such as #0f6cbd.'\n */\n hexError?: string;\n /** Accessible name of the preset swatches radiogroup.\n * @default 'Preset colors'\n */\n presets?: string;\n /** Visible label and accessible name of the opacity slider.\n * @default 'Opacity'\n */\n opacity?: string;\n}\n\n/** Properties for the ColorPicker component. */\nexport interface ColorPickerProps extends Omit<\n React.HTMLAttributes<HTMLDivElement>,\n 'onChange' | 'defaultValue'\n> {\n /**\n * Controlled hex color: `#rrggbb`, or `#rrggbbaa` with an alpha byte (e.g. `'#0f6cbd80'` for\n * 50% opacity). Other formats are not supported (development warning).\n */\n value?: string;\n /**\n * Initial hex color for uncontrolled usage (also what a form reset restores). Like every edit it\n * is shown, submitted and reported as a lowercase `#rrggbb`, or `#rrggbbaa` when it is not fully\n * opaque (`'#ABC'` becomes `'#aabbcc'`).\n * @default '#0f6cbd'\n */\n defaultValue?: string;\n /**\n * Called with the new color when it changes: a lowercase `#rrggbb`, or `#rrggbbaa` when the color\n * is not fully opaque.\n */\n onValueChange?: (color: string) => void;\n /**\n * Called with the new color when it changes.\n * @deprecated Use `onValueChange`.\n */\n onChange?: (color: string) => void;\n /**\n * Preset colors shown as quick-select swatches. Pass `{ color, label }` objects so screen reader\n * users hear a name; a plain hex string is announced by its hex code. Non-hex presets are\n * skipped (development warning). Picking a preset keeps the current opacity, so a preset's alpha\n * digits are ignored. With an alpha below `f`/`ff` (`#rgba`, `#rrggbbaa`) there is a development\n * warning, and a string preset is announced by the `#rrggbb` color it applies; an opaque alpha\n * (`#rgbf`, `#rrggbbff`) changes nothing, and the string stays the name as written.\n * @default Blue, Red, Green, Yellow, Purple, Teal, Pink and Black (Fluent brand colors)\n */\n presets?: ReadonlyArray<string | ColorPickerPreset>;\n /** Whether to show the opacity slider. The opacity is the alpha byte of `value`.\n * @default false\n */\n showOpacity?: boolean;\n /** Texts of the picker's own parts (hex field, error, presets, opacity), for localisation. */\n labels?: ColorPickerLabels;\n /** Form field name. With a name, the current color is submitted with the form. */\n name?: string;\n /**\n * Marks the hidden form input as required (a color is always chosen, so it never blocks). A\n * consumer `aria-required` has the same effect: `role=\"group\"` does not support it, so it is not\n * rendered on the group.\n */\n required?: boolean;\n /** Id of the form the picker belongs to, when it is rendered outside that form. */\n form?: string;\n /** Ref to the root `role=\"group\"` element. */\n ref?: React.Ref<HTMLDivElement>;\n}\n\n// wave-allow-color: default color value (user color data, C-TOKENS exception)\nconst DEFAULT_COLOR = '#0f6cbd';\n\nconst DEFAULT_LABELS: Required<ColorPickerLabels> = {\n hex: 'Hex',\n hexInput: 'Hex color value',\n hexError: `Enter a hex color such as ${DEFAULT_COLOR}.`,\n presets: 'Preset colors',\n opacity: 'Opacity',\n};\n\nconst DEFAULT_PRESETS: readonly ColorPickerPreset[] = [\n { color: '#0f6cbd', label: 'Blue' }, // wave-allow-color: preset swatch data\n { color: '#d13438', label: 'Red' }, // wave-allow-color: preset swatch data\n { color: '#107c10', label: 'Green' }, // wave-allow-color: preset swatch data\n { color: '#ffb900', label: 'Yellow' }, // wave-allow-color: preset swatch data\n { color: '#5c2d91', label: 'Purple' }, // wave-allow-color: preset swatch data\n { color: '#008272', label: 'Teal' }, // wave-allow-color: preset swatch data\n { color: '#e3008c', label: 'Pink' }, // wave-allow-color: preset swatch data\n { color: '#242424', label: 'Black' }, // wave-allow-color: preset swatch data\n];\n\ninterface ResolvedPresets {\n items: SwatchItem[];\n /** Presets that are not hex colors (skipped). */\n invalid: string[];\n /** Presets with an alpha byte below 255, which a preset cannot apply (ignored). */\n translucent: string[];\n}\n\n/** Normalises presets to swatch items keyed by their lowercase `#rrggbb` (duplicates dropped). */\nfunction resolvePresets(presets: ReadonlyArray<string | ColorPickerPreset>): ResolvedPresets {\n const items: SwatchItem[] = [];\n const invalid: string[] = [];\n const translucent: string[] = [];\n const seen = new Set<string>();\n for (const preset of presets) {\n const color = typeof preset === 'string' ? preset : preset.color;\n const parsed = parseHexColor(color);\n if (!parsed) {\n invalid.push(color);\n continue;\n }\n // Picking a preset keeps the current opacity, so its own alpha never applies.\n const hasAlpha = parsed.alpha !== 255;\n if (hasAlpha) translucent.push(color);\n if (seen.has(parsed.rgb)) continue;\n seen.add(parsed.rgb);\n // A string preset is announced by its hex code: the color it applies, without the alpha.\n const stringLabel = hasAlpha ? parsed.rgb : color;\n items.push({\n value: parsed.rgb,\n color: parsed.rgb,\n label: typeof preset === 'string' ? stringLabel : preset.label,\n });\n }\n return { items, invalid, translucent };\n}\n\n/** The hex field's text while the user edits it (`null` state = the field shows the value). */\ninterface HexDraft {\n /** The typed text. */\n text: string;\n /** Kept after leaving the field because it is not a hex color, so it is flagged as invalid. */\n flagged: boolean;\n}\n\n/** A hex draft without digits (`''` or a lone `#`): leaving the field shows the value again. */\nfunction isBlankDraft(text: string): boolean {\n const trimmed = text.trim();\n return trimmed === '' || trimmed === '#';\n}\n\n/** Whether typed hex text carries its own alpha digits (`#rgba` or `#rrggbbaa`). */\nfunction hasAlphaDigits(text: string): boolean {\n const digits = text.trim().replace(/^#/, '').length;\n return digits === 4 || digits === 8;\n}\n\n/**\n * A color picker: a preview, a hex text field, optional preset swatches and an optional opacity\n * slider, grouped as a named `role=\"group\"`.\n *\n * - **Value**: a hex color, `#rrggbb` or `#rrggbbaa`. The opacity slider shows and edits the\n * value's alpha byte; picking a preset or typing a 6-digit hex keeps the current opacity.\n * - **Hex field**: the text is a draft (surrounding whitespace is dropped). Complete 6- or 8-digit\n * values are applied while typing; text that can never be a hex color is flagged at once\n * (`aria-invalid` plus the `hexError` description). Leaving the field or pressing Enter applies\n * a short `#rgb` (keeping the current opacity) or `#rgba`, then shows the current value again\n * (also when a controlled parent rejected the typed color); an empty field (or a lone `#`) also\n * shows the current value again. Any other text is kept and flagged instead of being thrown\n * away, until it is corrected, cleared, or the value changes from elsewhere (a preset, the\n * opacity slider, the parent, a form reset). Enter still submits the surrounding form, with the\n * color just applied; while the text is flagged, the form submits the last applied color.\n * - **Presets** render as a SwatchPicker radiogroup (\"Preset colors\"): one tab stop, arrow keys\n * move and pick, and the selected preset shows a ring and a check glyph.\n * - **Naming**: `aria-label`/`aria-labelledby` name the group; inside a `Field` its label does, and\n * the Field's hint and error describe the group. The invalid state (`aria-invalid`, from the\n * Field or the prop) is set on the hex field, since `role=\"group\"` does not support it, and the\n * hex field is then also described by the Field's error and by a consumer `aria-errormessage`\n * (which is routed to the hex field too). A consumer `aria-required` makes the hidden form input\n * required instead of reaching the group. The texts of the picker's own parts are localised with\n * `labels`.\n * - **Forms**: with `name` the color is submitted with the form; a form reset restores\n * `defaultValue` and reports it through `onValueChange` only when the color changes.\n *\n * @example\n * <ColorPicker aria-label=\"Accent color\" showOpacity value={color} onValueChange={setColor} />\n */\nexport const ColorPicker = ({\n value: valueProp,\n defaultValue,\n onValueChange,\n onChange,\n presets = DEFAULT_PRESETS,\n showOpacity = false,\n labels,\n name,\n required,\n form,\n className,\n id,\n 'aria-label': ariaLabel,\n 'aria-labelledby': ariaLabelledBy,\n 'aria-describedby': ariaDescribedBy,\n 'aria-invalid': ariaInvalid,\n 'aria-required': ariaRequired,\n 'aria-errormessage': ariaErrorMessage,\n ref,\n ...rest\n}: ColorPickerProps) => {\n if (onChange !== undefined) warnDeprecated('ColorPicker', 'onChange', 'onValueChange');\n // The default is written like every edit (C-FORMS): the picker shows, submits and restores it as\n // a lowercase `#rrggbb`/`#rrggbbaa`. A value that is not a hex color stays as given (warning\n // below).\n const rawDefault = defaultValue ?? DEFAULT_COLOR;\n const initialValue = normalizeHexColor(rawDefault) ?? rawDefault;\n const strings = { ...DEFAULT_LABELS, ...labels };\n const [color, setColor] = useControllable(valueProp, initialValue, (next: string) => {\n onValueChange?.(next);\n onChange?.(next);\n });\n\n const parsed = parseHexColor(color);\n const alpha = parsed?.alpha ?? 255;\n const opacity = alphaToOpacity(alpha);\n\n /** The single commit path: every edit is `#rrggbb` + an alpha byte. */\n const commit = (rgb: string, nextAlpha: number) => setColor(formatHexColor(rgb, nextAlpha));\n\n // The hex text is a draft over `color` while the user edits it (null = show `color`).\n const [draft, setDraft] = React.useState<HexDraft | null>(null);\n // A value change from elsewhere (a preset, the opacity slider, the parent, a form reset) replaces\n // a flagged draft, so the field never shows stale text next to the new preview (input-pickers#25).\n // While the user types, the draft is not flagged and stays.\n const [syncedColor, setSyncedColor] = React.useState(color);\n if (color !== syncedColor) {\n setSyncedColor(color);\n if (draft?.flagged) setDraft(null);\n }\n const hexText = draft?.text ?? color;\n // Text that can never be a hex color is flagged while typing; an incomplete one once the user\n // leaves the field with it (`flagged`).\n const draftInvalid =\n draft !== null && !isBlankDraft(draft.text) && (draft.flagged || !isHexDraft(draft.text));\n\n const {\n items: presetItems,\n invalid: invalidPresets,\n translucent: translucentPresets,\n } = resolvePresets(presets);\n const invalidPresetKey = invalidPresets.join('\\n');\n const translucentPresetKey = translucentPresets.join('\\n');\n const invalidValue = parsed ? null : color;\n\n React.useEffect(() => {\n if (invalidValue !== null) {\n warnOnce(\n 'ColorPicker:invalid-value',\n `ColorPicker: \"${invalidValue}\" is not a hex color (#rrggbb or #rrggbbaa). Pass a hex value; the opacity slider is disabled until then.`,\n );\n }\n }, [invalidValue]);\n React.useEffect(() => {\n if (!invalidPresetKey) return;\n for (const preset of invalidPresetKey.split('\\n')) {\n warnOnce(\n `ColorPicker:invalid-preset:${preset}`,\n `ColorPicker: preset \"${preset}\" is not a hex color (#rgb or #rrggbb) and is not shown.`,\n );\n }\n }, [invalidPresetKey]);\n React.useEffect(() => {\n if (!translucentPresetKey) return;\n for (const preset of translucentPresetKey.split('\\n')) {\n warnOnce(\n `ColorPicker:alpha-preset:${preset}`,\n `ColorPicker: preset \"${preset}\" has an alpha byte, which is ignored: picking a preset keeps the current opacity. Pass the color as #rgb or #rrggbb.`,\n );\n }\n }, [translucentPresetKey]);\n\n const rootRef = React.useRef<HTMLDivElement>(null);\n const hexInputRef = React.useRef<HTMLInputElement>(null);\n const mergedRef = useMergedRefs<HTMLDivElement>(ref, rootRef);\n\n const field = useFieldContext();\n const fieldProps = useFieldControl(\n {\n id,\n 'aria-label': ariaLabel,\n 'aria-labelledby': ariaLabelledBy,\n 'aria-describedby': ariaDescribedBy,\n 'aria-invalid': ariaInvalid,\n },\n { labelable: false },\n );\n // A group supports neither aria-invalid, aria-required nor a native `required` (ARIA 1.2): the\n // invalid state goes to the hex field and the required state to the hidden form input.\n const {\n 'aria-invalid': groupInvalid,\n 'aria-required': _ariaRequired,\n required: _required,\n ...groupProps\n } = fieldProps;\n // Any invalid state from outside (the prop or the Field, `grammar`/`spelling` included) is set on\n // the hex field as is; only `true` shows the error look.\n const fieldInvalid =\n groupInvalid !== undefined && groupInvalid !== false && groupInvalid !== 'false';\n // A consumer aria-required is not supported on the group either: it requires the hidden input.\n const isRequired =\n required ?? (ariaRequired === true || ariaRequired === 'true' || (field?.required ?? false));\n // The consumer's error message belongs to the invalid state set from outside (the prop or the\n // Field), so it is routed to the hex field only while that state is set.\n const errorMessageId = (fieldInvalid && ariaErrorMessage) || undefined;\n\n useFormReset(\n rootRef,\n () => {\n // Only a real change is reported: the same color in another spelling (a controlled `#ABC`\n // against the default `#aabbcc`) is not one.\n if ((normalizeHexColor(color) ?? color) !== initialValue) setColor(initialValue);\n setDraft(null);\n },\n form,\n );\n\n const errorId = useId('wave-color-picker-error');\n // The hex field carries the picker's invalid state: its own flagged text, or the Field's/prop's.\n const hexAriaInvalid = draftInvalid ? true : fieldInvalid ? groupInvalid : undefined;\n const hexInvalidLook = isInvalidLook(false, hexAriaInvalid);\n\n const handleHexChange = (e: React.ChangeEvent<HTMLInputElement>) => {\n // Surrounding whitespace (a pasted `'#abcdef '`) is dropped, so the text that is checked,\n // committed and shown is the same.\n let text = e.target.value.trim();\n if (text !== '' && !text.startsWith('#')) text = `#${text}`;\n setDraft({ text, flagged: false });\n const typed = parseHexInput(text);\n // A 6-digit hex keeps the current opacity; an 8-digit one brings its own alpha.\n if (typed) commit(typed.rgb, hasAlphaDigits(text) ? typed.alpha : alpha);\n };\n\n /** Finishes the hex draft when the field is left or Enter is pressed. */\n const finishHexDraft = () => {\n if (draft === null || draft.flagged) return;\n const typed = parseHexColor(draft.text);\n if (typed || isBlankDraft(draft.text)) {\n // A short `#rgb` (current opacity) or `#rgba` is applied here; complete 6- and 8-digit\n // values were applied while typing, so a rejecting parent is not asked twice. Then the field\n // shows the current value (also when a controlled parent rejected it).\n if (typed && !parseHexInput(draft.text)) {\n commit(typed.rgb, hasAlphaDigits(draft.text) ? typed.alpha : alpha);\n }\n setDraft(null);\n return;\n }\n // Text that is not a hex color is kept and flagged instead of silently thrown away (WCAG 3.3.1).\n setDraft({ text: draft.text, flagged: true });\n };\n\n const handleHexKeyDown = (e: React.KeyboardEvent<HTMLInputElement>) => {\n // Not prevented: Enter still submits the surrounding form, which then carries the color just\n // applied (the submit follows the keydown, after React has rendered the new value).\n if (e.key === 'Enter' && !e.defaultPrevented && !e.nativeEvent.isComposing) finishHexDraft();\n };\n\n const handlePreset = (rgb: string) => {\n // Only a preset color is committed. The presets' own form reset reports `''` (no swatch): it\n // is ignored here, and the picker's reset restores `defaultValue` (input-basic#12).\n const preset = parseHexColor(rgb);\n if (!preset) return;\n setDraft(null);\n commit(preset.rgb, alpha);\n };\n\n const handleOpacityChange = (e: React.ChangeEvent<HTMLInputElement>) => {\n if (!parsed) return;\n commit(parsed.rgb, opacityToAlpha(Number(e.target.value)));\n };\n\n const selectedPreset = parsed ? parsed.rgb : '';\n\n return (\n <div\n role=\"group\"\n {...groupProps}\n className={cn(\n 'relative inline-flex flex-col gap-3 rounded border border-border bg-background p-3 shadow-4',\n className,\n )}\n {...rest}\n ref={mergedRef}\n >\n {/* Color preview and hex input */}\n <div className=\"flex items-center gap-2\">\n <div\n data-color-preview=\"\"\n className=\"h-10 w-10 shrink-0 rounded border border-border\"\n style={{ backgroundColor: parsed ? formatHexColor(parsed.rgb, parsed.alpha) : color }}\n aria-hidden=\"true\"\n />\n <label className=\"flex flex-col gap-1\">\n <span className=\"text-caption-1 text-muted-foreground\">{strings.hex}</span>\n <input\n ref={hexInputRef}\n type=\"text\"\n value={hexText}\n onChange={handleHexChange}\n onKeyDown={handleHexKeyDown}\n onBlur={finishHexDraft}\n aria-label={strings.hexInput}\n aria-invalid={hexAriaInvalid}\n aria-errormessage={errorMessageId}\n aria-describedby={joinIds(\n draftInvalid && errorId,\n field?.validationMessageId ?? (fieldInvalid ? field?.errorId : undefined),\n errorMessageId,\n )}\n maxLength={9}\n spellCheck={false}\n autoComplete=\"off\"\n className={cn(\n 'w-24 rounded border border-input border-b-stroke-accessible bg-background px-2 py-1 text-body-1 text-foreground',\n inputFocus,\n hexInvalidLook && inputInvalid,\n )}\n />\n </label>\n </div>\n {draftInvalid && (\n <span id={errorId} className=\"text-caption-1 text-error\">\n {strings.hexError}\n </span>\n )}\n\n {/* Preset swatches: the Field wiring (id, label, hint/error, invalid, required) stays on the\n group, so the nested radiogroup does not read the surrounding FieldContext. */}\n {presetItems.length > 0 && (\n <FieldContext.Provider value={null}>\n <SwatchPicker\n items={presetItems}\n value={selectedPreset}\n onValueChange={handlePreset}\n aria-label={strings.presets}\n size=\"small\"\n shape=\"rounded\"\n />\n </FieldContext.Provider>\n )}\n\n {/* Opacity slider */}\n {showOpacity && (\n <div className=\"flex items-center gap-2\">\n <span className=\"w-14 text-caption-1 text-muted-foreground\">{strings.opacity}</span>\n <input\n type=\"range\"\n min={0}\n max={100}\n value={opacity}\n onChange={handleOpacityChange}\n disabled={!parsed}\n aria-label={strings.opacity}\n aria-valuetext={`${opacity}%`}\n className={cn(\n 'h-1 flex-1 accent-primary disabled:cursor-not-allowed disabled:opacity-50',\n focusRing,\n )}\n />\n <span className=\"w-10 text-end text-caption-1 text-muted-foreground\">{opacity}%</span>\n </div>\n )}\n\n <HiddenInput\n type=\"text\"\n name={name}\n form={form}\n value={color}\n required={isRequired}\n onInvalid={() => hexInputRef.current?.focus()}\n />\n </div>\n );\n};\n\nColorPicker.displayName = 'ColorPicker';\n"],"mappings":"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"}