@dashforge/tw 1.1.0 → 1.1.1

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 (390) hide show
  1. package/CHANGELOG.md +21 -1
  2. package/dist/index.esm.js +1 -1
  3. package/dist/src/index.d.ts +1 -1
  4. package/package.json +8 -3
  5. package/.swcrc +0 -29
  6. package/A11Y.md +0 -130
  7. package/CONSUMER-VALIDATION.md +0 -130
  8. package/COVERAGE.md +0 -63
  9. package/PARITY.md +0 -481
  10. package/PERFORMANCE.md +0 -227
  11. package/REFINEMENT-NOTES.md +0 -50
  12. package/THEME-AUDIT.md +0 -174
  13. package/dashforge-tw-1.0.0.tgz +0 -0
  14. package/eslint.config.mjs +0 -62
  15. package/project.json +0 -15
  16. package/rollup.config.cjs +0 -16
  17. package/src/components/Accordion/Accordion.test.tsx +0 -95
  18. package/src/components/Accordion/Accordion.tsx +0 -97
  19. package/src/components/Accordion/accordion.types.ts +0 -66
  20. package/src/components/Accordion/accordion.variants.ts +0 -32
  21. package/src/components/Alert/Alert.test.tsx +0 -302
  22. package/src/components/Alert/Alert.tsx +0 -186
  23. package/src/components/Alert/alert.types.ts +0 -144
  24. package/src/components/Alert/alert.variants.ts +0 -71
  25. package/src/components/AppShell/AppShell.test.tsx +0 -223
  26. package/src/components/AppShell/AppShell.tsx +0 -239
  27. package/src/components/AppShell/appShell.types.ts +0 -49
  28. package/src/components/AppShell/appShell.variants.ts +0 -54
  29. package/src/components/AspectRatio/AspectRatio.test.tsx +0 -173
  30. package/src/components/AspectRatio/AspectRatio.tsx +0 -73
  31. package/src/components/AspectRatio/aspectRatio.types.ts +0 -54
  32. package/src/components/Autocomplete/Autocomplete.perf.test.tsx +0 -225
  33. package/src/components/Autocomplete/Autocomplete.test.tsx +0 -556
  34. package/src/components/Autocomplete/Autocomplete.tsx +0 -1069
  35. package/src/components/Autocomplete/autocomplete.types.ts +0 -198
  36. package/src/components/Autocomplete/autocomplete.variants.ts +0 -141
  37. package/src/components/Avatar/Avatar.test.tsx +0 -287
  38. package/src/components/Avatar/Avatar.tsx +0 -304
  39. package/src/components/Avatar/avatar.types.ts +0 -205
  40. package/src/components/Avatar/avatar.variants.ts +0 -194
  41. package/src/components/Badge/Badge.test.tsx +0 -385
  42. package/src/components/Badge/Badge.tsx +0 -174
  43. package/src/components/Badge/badge.types.ts +0 -154
  44. package/src/components/Badge/badge.variants.ts +0 -161
  45. package/src/components/Box/Box.test.tsx +0 -391
  46. package/src/components/Box/Box.tsx +0 -112
  47. package/src/components/Box/box.types.ts +0 -116
  48. package/src/components/Box/box.variants.ts +0 -230
  49. package/src/components/Breadcrumbs/Breadcrumbs.perf.test.tsx +0 -128
  50. package/src/components/Breadcrumbs/Breadcrumbs.test.tsx +0 -231
  51. package/src/components/Breadcrumbs/Breadcrumbs.tsx +0 -203
  52. package/src/components/Breadcrumbs/breadcrumbs.types.ts +0 -87
  53. package/src/components/Breadcrumbs/breadcrumbs.variants.ts +0 -54
  54. package/src/components/Button/Button.test.tsx +0 -204
  55. package/src/components/Button/Button.tsx +0 -151
  56. package/src/components/Button/button.types.ts +0 -110
  57. package/src/components/Button/button.variants.ts +0 -159
  58. package/src/components/Calendar/Calendar.test.tsx +0 -75
  59. package/src/components/Calendar/Calendar.tsx +0 -264
  60. package/src/components/Calendar/calendar.types.ts +0 -65
  61. package/src/components/Calendar/calendar.variants.ts +0 -64
  62. package/src/components/Card/Card.test.tsx +0 -291
  63. package/src/components/Card/Card.tsx +0 -241
  64. package/src/components/Card/card.types.ts +0 -132
  65. package/src/components/Checkbox/Checkbox.test.tsx +0 -146
  66. package/src/components/Checkbox/Checkbox.tsx +0 -286
  67. package/src/components/Checkbox/checkbox.types.ts +0 -88
  68. package/src/components/Checkbox/checkbox.variants.ts +0 -68
  69. package/src/components/Chip/Chip.test.tsx +0 -316
  70. package/src/components/Chip/Chip.tsx +0 -224
  71. package/src/components/Chip/chip.types.ts +0 -128
  72. package/src/components/Chip/chip.variants.ts +0 -173
  73. package/src/components/ConfirmDialog/ConfirmDialog.perf.test.tsx +0 -172
  74. package/src/components/ConfirmDialog/ConfirmDialog.test.tsx +0 -311
  75. package/src/components/ConfirmDialog/ConfirmDialog.tsx +0 -252
  76. package/src/components/ConfirmDialog/confirmDialog.types.ts +0 -70
  77. package/src/components/ConfirmDialog/confirmDialog.variants.ts +0 -76
  78. package/src/components/Container/Container.test.tsx +0 -209
  79. package/src/components/Container/Container.tsx +0 -74
  80. package/src/components/Container/container.types.ts +0 -45
  81. package/src/components/Container/container.variants.ts +0 -81
  82. package/src/components/DataGrid/DataGrid.perf.test.tsx +0 -114
  83. package/src/components/DataGrid/DataGrid.test.tsx +0 -1153
  84. package/src/components/DataGrid/DataGrid.tsx +0 -1282
  85. package/src/components/DataGrid/dataGrid.types.ts +0 -238
  86. package/src/components/DataGrid/dataGrid.variants.ts +0 -152
  87. package/src/components/DataGrid/filters/ColumnFilters.test.tsx +0 -330
  88. package/src/components/DataGrid/filters/ColumnFilters.tsx +0 -456
  89. package/src/components/DataGrid/reorder/useColumnReorder.test.ts +0 -130
  90. package/src/components/DataGrid/reorder/useColumnReorder.ts +0 -144
  91. package/src/components/DataGrid/resize/useColumnResize.test.ts +0 -144
  92. package/src/components/DataGrid/resize/useColumnResize.ts +0 -135
  93. package/src/components/DataGrid/visibility/ColumnVisibilityMenu.tsx +0 -186
  94. package/src/components/DatePicker/DatePicker.test.tsx +0 -76
  95. package/src/components/DatePicker/DatePicker.tsx +0 -305
  96. package/src/components/DatePicker/datePicker.types.ts +0 -77
  97. package/src/components/DatePicker/datePicker.variants.ts +0 -50
  98. package/src/components/DateRangePicker/DateRangePicker.test.tsx +0 -92
  99. package/src/components/DateRangePicker/DateRangePicker.tsx +0 -510
  100. package/src/components/DateRangePicker/dateRangePicker.types.ts +0 -74
  101. package/src/components/DateRangePicker/dateRangePicker.variants.ts +0 -101
  102. package/src/components/DateTimePicker/DateTimePicker.test.tsx +0 -78
  103. package/src/components/DateTimePicker/DateTimePicker.tsx +0 -347
  104. package/src/components/DateTimePicker/dateTimePicker.types.ts +0 -79
  105. package/src/components/DateTimePicker/dateTimePicker.variants.ts +0 -55
  106. package/src/components/Dialog/Dialog.test.tsx +0 -96
  107. package/src/components/Dialog/Dialog.tsx +0 -102
  108. package/src/components/Dialog/dialog.types.ts +0 -62
  109. package/src/components/Dialog/dialog.variants.ts +0 -66
  110. package/src/components/Divider/Divider.test.tsx +0 -243
  111. package/src/components/Divider/Divider.tsx +0 -140
  112. package/src/components/Divider/divider.types.ts +0 -52
  113. package/src/components/Divider/divider.variants.ts +0 -116
  114. package/src/components/Grid/Grid.test.tsx +0 -321
  115. package/src/components/Grid/Grid.tsx +0 -148
  116. package/src/components/Grid/grid.types.ts +0 -112
  117. package/src/components/Grid/grid.variants.ts +0 -133
  118. package/src/components/IconButton/IconButton.test.tsx +0 -367
  119. package/src/components/IconButton/IconButton.tsx +0 -159
  120. package/src/components/IconButton/iconButton.types.ts +0 -106
  121. package/src/components/IconButton/iconButton.variants.ts +0 -31
  122. package/src/components/LeftNav/LeftNav.perf.test.tsx +0 -172
  123. package/src/components/LeftNav/LeftNav.test.tsx +0 -302
  124. package/src/components/LeftNav/LeftNav.tsx +0 -330
  125. package/src/components/LeftNav/leftNav.types.ts +0 -120
  126. package/src/components/LeftNav/leftNav.variants.ts +0 -107
  127. package/src/components/Menu/Menu.test.tsx +0 -408
  128. package/src/components/Menu/Menu.tsx +0 -335
  129. package/src/components/Menu/menu.types.ts +0 -221
  130. package/src/components/Menu/menu.variants.ts +0 -132
  131. package/src/components/NumberField/NumberField.test.tsx +0 -83
  132. package/src/components/NumberField/NumberField.tsx +0 -321
  133. package/src/components/NumberField/numberField.types.ts +0 -72
  134. package/src/components/NumberField/numberField.variants.ts +0 -94
  135. package/src/components/OTPField/OTPField.test.tsx +0 -121
  136. package/src/components/OTPField/OTPField.tsx +0 -250
  137. package/src/components/OTPField/otpField.types.ts +0 -58
  138. package/src/components/OTPField/otpField.variants.ts +0 -72
  139. package/src/components/Pagination/Pagination.test.tsx +0 -314
  140. package/src/components/Pagination/Pagination.tsx +0 -277
  141. package/src/components/Pagination/pagination.helpers.ts +0 -102
  142. package/src/components/Pagination/pagination.types.ts +0 -117
  143. package/src/components/Pagination/pagination.variants.ts +0 -117
  144. package/src/components/Popover/Popover.test.tsx +0 -72
  145. package/src/components/Popover/Popover.tsx +0 -55
  146. package/src/components/Popover/popover.types.ts +0 -42
  147. package/src/components/Popover/popover.variants.ts +0 -24
  148. package/src/components/RadioGroup/RadioGroup.test.tsx +0 -140
  149. package/src/components/RadioGroup/RadioGroup.tsx +0 -283
  150. package/src/components/RadioGroup/radioGroup.types.ts +0 -85
  151. package/src/components/RadioGroup/radioGroup.variants.ts +0 -87
  152. package/src/components/Skeleton/Skeleton.test.tsx +0 -127
  153. package/src/components/Skeleton/Skeleton.tsx +0 -49
  154. package/src/components/Skeleton/skeleton.types.ts +0 -59
  155. package/src/components/Skeleton/skeleton.variants.ts +0 -87
  156. package/src/components/Snackbar/Snackbar.perf.test.tsx +0 -144
  157. package/src/components/Snackbar/Snackbar.test.tsx +0 -327
  158. package/src/components/Snackbar/Snackbar.tsx +0 -316
  159. package/src/components/Snackbar/snackbar.types.ts +0 -127
  160. package/src/components/Snackbar/snackbar.variants.ts +0 -81
  161. package/src/components/Spinner/Spinner.test.tsx +0 -199
  162. package/src/components/Spinner/Spinner.tsx +0 -158
  163. package/src/components/Spinner/spinner.types.ts +0 -113
  164. package/src/components/Spinner/spinner.variants.ts +0 -83
  165. package/src/components/Stack/Stack.test.tsx +0 -309
  166. package/src/components/Stack/Stack.tsx +0 -115
  167. package/src/components/Stack/stack.types.ts +0 -68
  168. package/src/components/Stack/stack.variants.ts +0 -80
  169. package/src/components/Switch/Switch.test.tsx +0 -131
  170. package/src/components/Switch/Switch.tsx +0 -158
  171. package/src/components/Switch/switch.types.ts +0 -36
  172. package/src/components/Switch/switch.variants.ts +0 -70
  173. package/src/components/Table/Table.perf.test.tsx +0 -81
  174. package/src/components/Table/Table.test.tsx +0 -674
  175. package/src/components/Table/Table.tsx +0 -863
  176. package/src/components/Table/cells/RenderButton.tsx +0 -23
  177. package/src/components/Table/cells/RenderChip.tsx +0 -37
  178. package/src/components/Table/cells/RenderText.tsx +0 -37
  179. package/src/components/Table/cells/RenderTwoLine.tsx +0 -34
  180. package/src/components/Table/cells/RowActionsMenu.tsx +0 -147
  181. package/src/components/Table/cells/cells.test.tsx +0 -247
  182. package/src/components/Table/cells/index.ts +0 -14
  183. package/src/components/Table/table.types.ts +0 -438
  184. package/src/components/Table/table.variants.ts +0 -207
  185. package/src/components/Tabs/Tabs.test.tsx +0 -145
  186. package/src/components/Tabs/Tabs.tsx +0 -77
  187. package/src/components/Tabs/tabs.types.ts +0 -55
  188. package/src/components/Tabs/tabs.variants.ts +0 -69
  189. package/src/components/Tabs/useTabs.ts +0 -167
  190. package/src/components/TextField/TextField.test.tsx +0 -198
  191. package/src/components/TextField/TextField.tsx +0 -245
  192. package/src/components/TextField/textField.types.ts +0 -90
  193. package/src/components/TextField/textField.variants.ts +0 -105
  194. package/src/components/Textarea/Textarea.test.tsx +0 -75
  195. package/src/components/Textarea/Textarea.tsx +0 -190
  196. package/src/components/Textarea/textarea.types.ts +0 -60
  197. package/src/components/Textarea/textarea.variants.ts +0 -85
  198. package/src/components/TimePicker/TimePicker.test.tsx +0 -65
  199. package/src/components/TimePicker/TimePicker.tsx +0 -274
  200. package/src/components/TimePicker/timePicker.types.ts +0 -69
  201. package/src/components/TimePicker/timePicker.variants.ts +0 -53
  202. package/src/components/Tooltip/Tooltip.test.tsx +0 -73
  203. package/src/components/Tooltip/Tooltip.tsx +0 -70
  204. package/src/components/Tooltip/tooltip.types.ts +0 -44
  205. package/src/components/Tooltip/tooltip.variants.ts +0 -28
  206. package/src/components/TopBar/TopBar.test.tsx +0 -129
  207. package/src/components/TopBar/TopBar.tsx +0 -66
  208. package/src/components/TopBar/topBar.types.ts +0 -42
  209. package/src/components/TopBar/topBar.variants.ts +0 -38
  210. package/src/components/Typography/Typography.test.tsx +0 -247
  211. package/src/components/Typography/Typography.tsx +0 -112
  212. package/src/components/Typography/typography.types.ts +0 -65
  213. package/src/components/Typography/typography.variants.ts +0 -130
  214. package/src/components/VisuallyHidden/VisuallyHidden.test.tsx +0 -86
  215. package/src/components/VisuallyHidden/VisuallyHidden.tsx +0 -59
  216. package/src/components/VisuallyHidden/visuallyHidden.types.ts +0 -45
  217. package/src/components/_shared/data/getNestedValue.test.ts +0 -50
  218. package/src/components/_shared/data/getNestedValue.ts +0 -32
  219. package/src/components/_shared/data/useColumnAutoDetect.test.ts +0 -123
  220. package/src/components/_shared/data/useColumnAutoDetect.ts +0 -100
  221. package/src/components/_shared/data/useControllableState.ts +0 -48
  222. package/src/components/_shared/data/useDebouncedValue.ts +0 -24
  223. package/src/components/_shared/data/useTableFilter.test.ts +0 -166
  224. package/src/components/_shared/data/useTableFilter.ts +0 -118
  225. package/src/components/_shared/data/useTableSearch.test.ts +0 -115
  226. package/src/components/_shared/data/useTableSearch.ts +0 -66
  227. package/src/components/_shared/data/useTableSelection.test.ts +0 -100
  228. package/src/components/_shared/data/useTableSelection.ts +0 -100
  229. package/src/components/_shared/data/useTableSort.test.ts +0 -150
  230. package/src/components/_shared/data/useTableSort.ts +0 -141
  231. package/src/components/_shared/data/useVirtualizer.test.ts +0 -158
  232. package/src/components/_shared/data/useVirtualizer.ts +0 -199
  233. package/src/components/_shared/resolveValidationState.ts +0 -60
  234. package/src/components/_shared/severity/index.ts +0 -33
  235. package/src/components/_shared/severity/severity.types.ts +0 -50
  236. package/src/components/_shared/severity/severityIcons.tsx +0 -104
  237. package/src/components/_shared/severity/severityVariants.test.ts +0 -136
  238. package/src/components/_shared/severity/severityVariants.ts +0 -115
  239. package/src/components/_shared/themeIdentity.test.ts +0 -113
  240. package/src/hooks/useAccessState.spec.tsx +0 -161
  241. package/src/hooks/useAccessState.ts +0 -81
  242. package/src/index.ts +0 -550
  243. package/src/utils/cn.spec.ts +0 -16
  244. package/src/utils/cn.ts +0 -29
  245. package/test-output/vitest/coverage/base.css +0 -224
  246. package/test-output/vitest/coverage/block-navigation.js +0 -87
  247. package/test-output/vitest/coverage/clover.xml +0 -2418
  248. package/test-output/vitest/coverage/coverage-final.json +0 -89
  249. package/test-output/vitest/coverage/favicon.png +0 -0
  250. package/test-output/vitest/coverage/index.html +0 -746
  251. package/test-output/vitest/coverage/prettify.css +0 -1
  252. package/test-output/vitest/coverage/prettify.js +0 -2
  253. package/test-output/vitest/coverage/sort-arrow-sprite.png +0 -0
  254. package/test-output/vitest/coverage/sorter.js +0 -210
  255. package/test-output/vitest/coverage/src/components/Accordion/Accordion.tsx.html +0 -376
  256. package/test-output/vitest/coverage/src/components/Accordion/accordion.variants.ts.html +0 -181
  257. package/test-output/vitest/coverage/src/components/Accordion/index.html +0 -131
  258. package/test-output/vitest/coverage/src/components/AppShell/AppShell.tsx.html +0 -802
  259. package/test-output/vitest/coverage/src/components/AppShell/appShell.variants.ts.html +0 -247
  260. package/test-output/vitest/coverage/src/components/AppShell/index.html +0 -131
  261. package/test-output/vitest/coverage/src/components/AspectRatio/AspectRatio.tsx.html +0 -304
  262. package/test-output/vitest/coverage/src/components/AspectRatio/index.html +0 -116
  263. package/test-output/vitest/coverage/src/components/Autocomplete/Autocomplete.tsx.html +0 -3292
  264. package/test-output/vitest/coverage/src/components/Autocomplete/autocomplete.variants.ts.html +0 -508
  265. package/test-output/vitest/coverage/src/components/Autocomplete/index.html +0 -131
  266. package/test-output/vitest/coverage/src/components/Box/Box.tsx.html +0 -334
  267. package/test-output/vitest/coverage/src/components/Box/box.variants.ts.html +0 -775
  268. package/test-output/vitest/coverage/src/components/Box/index.html +0 -131
  269. package/test-output/vitest/coverage/src/components/Breadcrumbs/Breadcrumbs.tsx.html +0 -694
  270. package/test-output/vitest/coverage/src/components/Breadcrumbs/breadcrumbs.variants.ts.html +0 -247
  271. package/test-output/vitest/coverage/src/components/Breadcrumbs/index.html +0 -131
  272. package/test-output/vitest/coverage/src/components/Button/Button.tsx.html +0 -535
  273. package/test-output/vitest/coverage/src/components/Button/button.variants.ts.html +0 -562
  274. package/test-output/vitest/coverage/src/components/Button/index.html +0 -131
  275. package/test-output/vitest/coverage/src/components/Checkbox/Checkbox.tsx.html +0 -943
  276. package/test-output/vitest/coverage/src/components/Checkbox/checkbox.variants.ts.html +0 -289
  277. package/test-output/vitest/coverage/src/components/Checkbox/index.html +0 -131
  278. package/test-output/vitest/coverage/src/components/ConfirmDialog/ConfirmDialog.tsx.html +0 -841
  279. package/test-output/vitest/coverage/src/components/ConfirmDialog/confirmDialog.variants.ts.html +0 -313
  280. package/test-output/vitest/coverage/src/components/ConfirmDialog/index.html +0 -131
  281. package/test-output/vitest/coverage/src/components/Container/Container.tsx.html +0 -307
  282. package/test-output/vitest/coverage/src/components/Container/container.variants.ts.html +0 -328
  283. package/test-output/vitest/coverage/src/components/Container/index.html +0 -131
  284. package/test-output/vitest/coverage/src/components/DataGrid/DataGrid.tsx.html +0 -3937
  285. package/test-output/vitest/coverage/src/components/DataGrid/dataGrid.variants.ts.html +0 -541
  286. package/test-output/vitest/coverage/src/components/DataGrid/filters/ColumnFilters.tsx.html +0 -1453
  287. package/test-output/vitest/coverage/src/components/DataGrid/filters/index.html +0 -116
  288. package/test-output/vitest/coverage/src/components/DataGrid/index.html +0 -131
  289. package/test-output/vitest/coverage/src/components/DataGrid/reorder/index.html +0 -116
  290. package/test-output/vitest/coverage/src/components/DataGrid/reorder/useColumnReorder.ts.html +0 -517
  291. package/test-output/vitest/coverage/src/components/DataGrid/resize/index.html +0 -116
  292. package/test-output/vitest/coverage/src/components/DataGrid/resize/useColumnResize.ts.html +0 -490
  293. package/test-output/vitest/coverage/src/components/DataGrid/visibility/ColumnVisibilityMenu.tsx.html +0 -592
  294. package/test-output/vitest/coverage/src/components/DataGrid/visibility/index.html +0 -116
  295. package/test-output/vitest/coverage/src/components/DateTimePicker/DateTimePicker.tsx.html +0 -1042
  296. package/test-output/vitest/coverage/src/components/DateTimePicker/dateTimePicker.variants.ts.html +0 -337
  297. package/test-output/vitest/coverage/src/components/DateTimePicker/index.html +0 -131
  298. package/test-output/vitest/coverage/src/components/Dialog/Dialog.tsx.html +0 -391
  299. package/test-output/vitest/coverage/src/components/Dialog/dialog.variants.ts.html +0 -283
  300. package/test-output/vitest/coverage/src/components/Dialog/index.html +0 -131
  301. package/test-output/vitest/coverage/src/components/Divider/Divider.tsx.html +0 -505
  302. package/test-output/vitest/coverage/src/components/Divider/divider.variants.ts.html +0 -433
  303. package/test-output/vitest/coverage/src/components/Divider/index.html +0 -131
  304. package/test-output/vitest/coverage/src/components/Grid/Grid.tsx.html +0 -529
  305. package/test-output/vitest/coverage/src/components/Grid/grid.variants.ts.html +0 -484
  306. package/test-output/vitest/coverage/src/components/Grid/index.html +0 -131
  307. package/test-output/vitest/coverage/src/components/LeftNav/LeftNav.tsx.html +0 -1075
  308. package/test-output/vitest/coverage/src/components/LeftNav/index.html +0 -131
  309. package/test-output/vitest/coverage/src/components/LeftNav/leftNav.variants.ts.html +0 -406
  310. package/test-output/vitest/coverage/src/components/NumberField/NumberField.tsx.html +0 -1048
  311. package/test-output/vitest/coverage/src/components/NumberField/index.html +0 -131
  312. package/test-output/vitest/coverage/src/components/NumberField/numberField.variants.ts.html +0 -367
  313. package/test-output/vitest/coverage/src/components/OTPField/OTPField.tsx.html +0 -835
  314. package/test-output/vitest/coverage/src/components/OTPField/index.html +0 -131
  315. package/test-output/vitest/coverage/src/components/OTPField/otpField.variants.ts.html +0 -301
  316. package/test-output/vitest/coverage/src/components/Pagination/Pagination.tsx.html +0 -916
  317. package/test-output/vitest/coverage/src/components/Pagination/index.html +0 -146
  318. package/test-output/vitest/coverage/src/components/Pagination/pagination.helpers.ts.html +0 -391
  319. package/test-output/vitest/coverage/src/components/Pagination/pagination.variants.ts.html +0 -436
  320. package/test-output/vitest/coverage/src/components/Popover/Popover.tsx.html +0 -250
  321. package/test-output/vitest/coverage/src/components/Popover/index.html +0 -131
  322. package/test-output/vitest/coverage/src/components/Popover/popover.variants.ts.html +0 -157
  323. package/test-output/vitest/coverage/src/components/RadioGroup/RadioGroup.tsx.html +0 -934
  324. package/test-output/vitest/coverage/src/components/RadioGroup/index.html +0 -131
  325. package/test-output/vitest/coverage/src/components/RadioGroup/radioGroup.variants.ts.html +0 -346
  326. package/test-output/vitest/coverage/src/components/Skeleton/Skeleton.tsx.html +0 -232
  327. package/test-output/vitest/coverage/src/components/Skeleton/index.html +0 -131
  328. package/test-output/vitest/coverage/src/components/Skeleton/skeleton.variants.ts.html +0 -346
  329. package/test-output/vitest/coverage/src/components/Snackbar/Snackbar.tsx.html +0 -979
  330. package/test-output/vitest/coverage/src/components/Snackbar/index.html +0 -131
  331. package/test-output/vitest/coverage/src/components/Snackbar/snackbar.variants.ts.html +0 -307
  332. package/test-output/vitest/coverage/src/components/Stack/Stack.tsx.html +0 -430
  333. package/test-output/vitest/coverage/src/components/Stack/index.html +0 -131
  334. package/test-output/vitest/coverage/src/components/Stack/stack.variants.ts.html +0 -325
  335. package/test-output/vitest/coverage/src/components/Switch/Switch.tsx.html +0 -559
  336. package/test-output/vitest/coverage/src/components/Switch/index.html +0 -131
  337. package/test-output/vitest/coverage/src/components/Switch/switch.variants.ts.html +0 -295
  338. package/test-output/vitest/coverage/src/components/Table/Table.tsx.html +0 -2677
  339. package/test-output/vitest/coverage/src/components/Table/cells/RenderButton.tsx.html +0 -154
  340. package/test-output/vitest/coverage/src/components/Table/cells/RenderChip.tsx.html +0 -385
  341. package/test-output/vitest/coverage/src/components/Table/cells/RenderText.tsx.html +0 -196
  342. package/test-output/vitest/coverage/src/components/Table/cells/RenderTwoLine.tsx.html +0 -187
  343. package/test-output/vitest/coverage/src/components/Table/cells/RowActionsMenu.tsx.html +0 -526
  344. package/test-output/vitest/coverage/src/components/Table/cells/index.html +0 -191
  345. package/test-output/vitest/coverage/src/components/Table/cells/index.ts.html +0 -127
  346. package/test-output/vitest/coverage/src/components/Table/index.html +0 -131
  347. package/test-output/vitest/coverage/src/components/Table/table.variants.ts.html +0 -706
  348. package/test-output/vitest/coverage/src/components/Tabs/Tabs.tsx.html +0 -283
  349. package/test-output/vitest/coverage/src/components/Tabs/index.html +0 -131
  350. package/test-output/vitest/coverage/src/components/Tabs/tabs.variants.ts.html +0 -292
  351. package/test-output/vitest/coverage/src/components/TextField/TextField.tsx.html +0 -820
  352. package/test-output/vitest/coverage/src/components/TextField/index.html +0 -131
  353. package/test-output/vitest/coverage/src/components/TextField/textField.variants.ts.html +0 -400
  354. package/test-output/vitest/coverage/src/components/Textarea/Textarea.tsx.html +0 -655
  355. package/test-output/vitest/coverage/src/components/Textarea/index.html +0 -131
  356. package/test-output/vitest/coverage/src/components/Textarea/textarea.variants.ts.html +0 -340
  357. package/test-output/vitest/coverage/src/components/Tooltip/Tooltip.tsx.html +0 -295
  358. package/test-output/vitest/coverage/src/components/Tooltip/index.html +0 -131
  359. package/test-output/vitest/coverage/src/components/Tooltip/tooltip.variants.ts.html +0 -169
  360. package/test-output/vitest/coverage/src/components/TopBar/TopBar.tsx.html +0 -283
  361. package/test-output/vitest/coverage/src/components/TopBar/index.html +0 -131
  362. package/test-output/vitest/coverage/src/components/TopBar/topBar.variants.ts.html +0 -199
  363. package/test-output/vitest/coverage/src/components/Typography/Typography.tsx.html +0 -421
  364. package/test-output/vitest/coverage/src/components/Typography/index.html +0 -131
  365. package/test-output/vitest/coverage/src/components/Typography/typography.variants.ts.html +0 -436
  366. package/test-output/vitest/coverage/src/components/VisuallyHidden/VisuallyHidden.tsx.html +0 -262
  367. package/test-output/vitest/coverage/src/components/VisuallyHidden/index.html +0 -116
  368. package/test-output/vitest/coverage/src/components/_shared/data/getNestedValue.ts.html +0 -181
  369. package/test-output/vitest/coverage/src/components/_shared/data/index.html +0 -236
  370. package/test-output/vitest/coverage/src/components/_shared/data/useColumnAutoDetect.ts.html +0 -385
  371. package/test-output/vitest/coverage/src/components/_shared/data/useControllableState.ts.html +0 -229
  372. package/test-output/vitest/coverage/src/components/_shared/data/useDebouncedValue.ts.html +0 -157
  373. package/test-output/vitest/coverage/src/components/_shared/data/useTableFilter.ts.html +0 -439
  374. package/test-output/vitest/coverage/src/components/_shared/data/useTableSearch.ts.html +0 -283
  375. package/test-output/vitest/coverage/src/components/_shared/data/useTableSelection.ts.html +0 -385
  376. package/test-output/vitest/coverage/src/components/_shared/data/useTableSort.ts.html +0 -508
  377. package/test-output/vitest/coverage/src/components/_shared/data/useVirtualizer.ts.html +0 -682
  378. package/test-output/vitest/coverage/src/components/_shared/index.html +0 -116
  379. package/test-output/vitest/coverage/src/components/_shared/resolveValidationState.ts.html +0 -265
  380. package/test-output/vitest/coverage/src/hooks/index.html +0 -116
  381. package/test-output/vitest/coverage/src/hooks/useAccessState.ts.html +0 -328
  382. package/test-output/vitest/coverage/src/index.html +0 -116
  383. package/test-output/vitest/coverage/src/index.ts.html +0 -1153
  384. package/test-output/vitest/coverage/src/utils/cn.ts.html +0 -172
  385. package/test-output/vitest/coverage/src/utils/index.html +0 -116
  386. package/tsconfig.json +0 -13
  387. package/tsconfig.lib.json +0 -58
  388. package/tsconfig.spec.json +0 -34
  389. package/vite.config.ts +0 -33
  390. package/vitest.config.mts +0 -29
@@ -1,144 +0,0 @@
1
- import { useCallback, useRef, useState, type DragEvent } from 'react';
2
-
3
- /**
4
- * Native HTML5 drag-and-drop reorder for DataGrid column headers.
5
- *
6
- * Zero new runtime deps — uses the browser's built-in drag events.
7
- * The hook returns handler factories you wire onto each `<th>` plus
8
- * a `dropTarget` state used to render the visual indicator (a left
9
- * or right border on the hovered column).
10
- *
11
- * - `dragStart(field)` → onDragStart; stashes source field in a ref
12
- * + sets `dataTransfer.effectAllowed = 'move'`.
13
- * - `dragOver(field)` → onDragOver; preventDefault + computes
14
- * whether the cursor is over the LEFT or RIGHT half of the
15
- * target → updates dropTarget so the indicator renders.
16
- * - `drop(field)` → onDrop; computes the new order array via
17
- * `moveColumn(source, target, side)` and commits it.
18
- * - `dragEnd()` → onDragEnd; clears state.
19
- *
20
- * Reorder math: when dropping `source` onto the LEFT half of
21
- * `target`, the source is inserted BEFORE the target's position
22
- * in the order list. RIGHT half → AFTER.
23
- */
24
-
25
- export interface UseColumnReorderArgs {
26
- /** The current order. */
27
- order: string[];
28
- /** Commit a new order. */
29
- onChange: (next: string[]) => void;
30
- }
31
-
32
- export interface DropTarget {
33
- field: string;
34
- side: 'left' | 'right';
35
- }
36
-
37
- export interface ColumnReorderHandlers {
38
- /** Current drop target (used by the renderer to show the indicator). */
39
- dropTarget: DropTarget | null;
40
- /** Field currently being dragged (used to dim the source header). */
41
- draggingField: string | null;
42
- dragStart: (field: string) => (e: DragEvent<HTMLElement>) => void;
43
- dragOver: (field: string) => (e: DragEvent<HTMLElement>) => void;
44
- drop: (field: string) => (e: DragEvent<HTMLElement>) => void;
45
- dragEnd: () => void;
46
- }
47
-
48
- export function useColumnReorder(
49
- args: UseColumnReorderArgs,
50
- ): ColumnReorderHandlers {
51
- const { order, onChange } = args;
52
- const sourceRef = useRef<string | null>(null);
53
- const [dropTarget, setDropTarget] = useState<DropTarget | null>(null);
54
- const [draggingField, setDraggingField] = useState<string | null>(null);
55
-
56
- const dragStart = useCallback(
57
- (field: string) => (e: DragEvent<HTMLElement>) => {
58
- sourceRef.current = field;
59
- setDraggingField(field);
60
- try {
61
- e.dataTransfer.effectAllowed = 'move';
62
- // Some browsers refuse to start a drag if no data is set.
63
- e.dataTransfer.setData('text/plain', field);
64
- } catch {
65
- /* noop — jsdom doesn't implement dataTransfer fully. */
66
- }
67
- },
68
- [],
69
- );
70
-
71
- const dragOver = useCallback(
72
- (field: string) => (e: DragEvent<HTMLElement>) => {
73
- if (sourceRef.current == null) return;
74
- if (field === sourceRef.current) return;
75
- e.preventDefault();
76
- e.dataTransfer.dropEffect = 'move';
77
- // Determine LEFT vs RIGHT half of the target.
78
- const rect = e.currentTarget.getBoundingClientRect();
79
- const midpoint = rect.left + rect.width / 2;
80
- const side: 'left' | 'right' = e.clientX < midpoint ? 'left' : 'right';
81
- setDropTarget((prev) =>
82
- prev && prev.field === field && prev.side === side
83
- ? prev
84
- : { field, side },
85
- );
86
- },
87
- [],
88
- );
89
-
90
- const drop = useCallback(
91
- (field: string) => (e: DragEvent<HTMLElement>) => {
92
- e.preventDefault();
93
- const source = sourceRef.current;
94
- sourceRef.current = null;
95
- setDraggingField(null);
96
- const target = dropTarget;
97
- setDropTarget(null);
98
- if (!source || source === field) return;
99
- const side = target?.field === field ? target.side : 'right';
100
- const next = moveColumn(order, source, field, side);
101
- if (!arraysEqual(next, order)) onChange(next);
102
- },
103
- [order, onChange, dropTarget],
104
- );
105
-
106
- const dragEnd = useCallback(() => {
107
- sourceRef.current = null;
108
- setDraggingField(null);
109
- setDropTarget(null);
110
- }, []);
111
-
112
- return { dropTarget, draggingField, dragStart, dragOver, drop, dragEnd };
113
- }
114
-
115
- /**
116
- * Move `source` next to `target` in the `order` list.
117
- * `side='left'` inserts before; `side='right'` inserts after.
118
- * Exposed for unit testing.
119
- */
120
- export function moveColumn(
121
- order: string[],
122
- source: string,
123
- target: string,
124
- side: 'left' | 'right',
125
- ): string[] {
126
- const withoutSource = order.filter((f) => f !== source);
127
- const targetIndex = withoutSource.indexOf(target);
128
- if (targetIndex === -1) return order;
129
- const insertAt = side === 'left' ? targetIndex : targetIndex + 1;
130
- return [
131
- ...withoutSource.slice(0, insertAt),
132
- source,
133
- ...withoutSource.slice(insertAt),
134
- ];
135
- }
136
-
137
- function arraysEqual(a: string[], b: string[]): boolean {
138
- if (a === b) return true;
139
- if (a.length !== b.length) return false;
140
- for (let i = 0; i < a.length; i++) {
141
- if (a[i] !== b[i]) return false;
142
- }
143
- return true;
144
- }
@@ -1,144 +0,0 @@
1
- // @vitest-environment jsdom
2
- /**
3
- * Unit tests for `useColumnResize` — the pointer-drag + keyboard
4
- * column-resize hook (Sprint 4.2-bis, keyboard `nudge` added in
5
- * Sprint 6 P2). Sprint 6 P4 — direct coverage of the clamp logic
6
- * and the drag commit path.
7
- */
8
- import { describe, it, expect, vi } from 'vitest';
9
- import { renderHook } from '@testing-library/react';
10
- import { useColumnResize } from './useColumnResize.js';
11
-
12
- describe('useColumnResize — nudge (keyboard path)', () => {
13
- it('commits currentWidth + delta', () => {
14
- const onChange = vi.fn();
15
- const { result } = renderHook(() =>
16
- useColumnResize({ widths: { a: 100 }, onChange }),
17
- );
18
- result.current.nudge('a', 100, 16, 40, 400);
19
- expect(onChange).toHaveBeenCalledWith({ a: 116 });
20
- });
21
-
22
- it('clamps to the effective minimum', () => {
23
- const onChange = vi.fn();
24
- const { result } = renderHook(() =>
25
- useColumnResize({ widths: { a: 50 }, onChange }),
26
- );
27
- // currentWidth 50, delta -64 → 14, clamped up to min 40.
28
- result.current.nudge('a', 50, -64, 40, 400);
29
- expect(onChange).toHaveBeenCalledWith({ a: 40 });
30
- });
31
-
32
- it('clamps to the effective maximum', () => {
33
- const onChange = vi.fn();
34
- const { result } = renderHook(() =>
35
- useColumnResize({ widths: { a: 380 }, onChange }),
36
- );
37
- // currentWidth 380, delta +64 → 444, clamped down to max 400.
38
- result.current.nudge('a', 380, 64, 40, 400);
39
- expect(onChange).toHaveBeenCalledWith({ a: 400 });
40
- });
41
-
42
- it('honors the hook-level minWidth/maxWidth floor/ceiling', () => {
43
- const onChange = vi.fn();
44
- const { result } = renderHook(() =>
45
- useColumnResize({
46
- widths: {},
47
- onChange,
48
- minWidth: 80,
49
- maxWidth: 200,
50
- }),
51
- );
52
- // clampMin 40 < hook min 80 → effective min is 80.
53
- result.current.nudge('a', 100, -64, 40, 1000);
54
- expect(onChange).toHaveBeenCalledWith({ a: 80 });
55
- });
56
-
57
- it('preserves the other columns in the width map', () => {
58
- const onChange = vi.fn();
59
- const { result } = renderHook(() =>
60
- useColumnResize({ widths: { a: 100, b: 200 }, onChange }),
61
- );
62
- result.current.nudge('a', 100, 16, 40, 400);
63
- expect(onChange).toHaveBeenCalledWith({ a: 116, b: 200 });
64
- });
65
- });
66
-
67
- describe('useColumnResize — startResize (pointer-drag path)', () => {
68
- it('returns an event handler from the factory', () => {
69
- const { result } = renderHook(() =>
70
- useColumnResize({ widths: {}, onChange: () => {} }),
71
- );
72
- const handler = result.current.startResize('a', 100, 40, 400);
73
- expect(typeof handler).toBe('function');
74
- });
75
-
76
- it('a pointer drag commits a clamped new width via pointermove', () => {
77
- const onChange = vi.fn();
78
- const { result } = renderHook(() =>
79
- useColumnResize({ widths: { a: 100 }, onChange }),
80
- );
81
- const el = document.createElement('span');
82
- document.body.appendChild(el);
83
-
84
- // Synthetic pointerdown — shape mirrors React's PointerEvent.
85
- const downEvent = {
86
- pointerType: 'mouse',
87
- button: 0,
88
- clientX: 500,
89
- pointerId: 1,
90
- currentTarget: el,
91
- preventDefault: () => {},
92
- stopPropagation: () => {},
93
- } as unknown as React.PointerEvent<HTMLElement>;
94
-
95
- result.current.startResize('a', 100, 40, 400)(downEvent);
96
-
97
- // Drag 30px to the right → 100 + 30 = 130.
98
- const move = new Event('pointermove') as Event & { clientX: number };
99
- move.clientX = 530;
100
- el.dispatchEvent(move);
101
- expect(onChange).toHaveBeenLastCalledWith({ a: 130 });
102
-
103
- // Drag far left → clamps to min 40.
104
- const move2 = new Event('pointermove') as Event & { clientX: number };
105
- move2.clientX = 0;
106
- el.dispatchEvent(move2);
107
- expect(onChange).toHaveBeenLastCalledWith({ a: 40 });
108
-
109
- // pointerup tears the listeners down — a later move is a no-op.
110
- const up = new Event('pointerup') as Event & { pointerId: number };
111
- up.pointerId = 1;
112
- el.dispatchEvent(up);
113
- onChange.mockClear();
114
- const move3 = new Event('pointermove') as Event & { clientX: number };
115
- move3.clientX = 999;
116
- el.dispatchEvent(move3);
117
- expect(onChange).not.toHaveBeenCalled();
118
-
119
- document.body.removeChild(el);
120
- });
121
-
122
- it('ignores a non-primary mouse button', () => {
123
- const onChange = vi.fn();
124
- const { result } = renderHook(() =>
125
- useColumnResize({ widths: {}, onChange }),
126
- );
127
- const el = document.createElement('span');
128
- const downEvent = {
129
- pointerType: 'mouse',
130
- button: 2, // right-click
131
- clientX: 0,
132
- pointerId: 1,
133
- currentTarget: el,
134
- preventDefault: () => {},
135
- stopPropagation: () => {},
136
- } as unknown as React.PointerEvent<HTMLElement>;
137
- result.current.startResize('a', 100, 40, 400)(downEvent);
138
- const move = new Event('pointermove') as Event & { clientX: number };
139
- move.clientX = 200;
140
- el.dispatchEvent(move);
141
- // No listener was attached → no commit.
142
- expect(onChange).not.toHaveBeenCalled();
143
- });
144
- });
@@ -1,135 +0,0 @@
1
- import { useCallback, useRef, type PointerEvent as RPointerEvent } from 'react';
2
-
3
- /**
4
- * Native column-resize behavior for DataGrid (and Table later if
5
- * promoted to `_shared`).
6
- *
7
- * The returned `startResize` is wired to a `pointerdown` handler on a
8
- * thin grabber positioned at the right edge of a `<th>`. We capture
9
- * the pointer on the target element so `pointermove` / `pointerup`
10
- * keep flowing even if the cursor leaves the grabber.
11
- *
12
- * Why native pointer events vs a drag library:
13
- * - Zero new runtime deps (sprint constraint)
14
- * - Pointer events normalize mouse/touch/pen out of the box
15
- * - Pointer capture means we don't have to track the global
16
- * `mousemove` / `mouseup` — the browser routes events to our
17
- * listener until release.
18
- */
19
-
20
- export interface UseColumnResizeArgs {
21
- /** Current column widths (Record<field, px>). */
22
- widths: Record<string, number>;
23
- /** Commit a new width map. */
24
- onChange: (next: Record<string, number>) => void;
25
- /** Hard floor for any column (px). @default 40 */
26
- minWidth?: number;
27
- /** Hard ceiling for any column (px). @default 1200 */
28
- maxWidth?: number;
29
- }
30
-
31
- export interface ColumnResizeHandlers {
32
- startResize: (
33
- field: string,
34
- startWidth: number,
35
- clampMin: number,
36
- clampMax: number,
37
- ) => (e: RPointerEvent<HTMLElement>) => void;
38
- /**
39
- * Commit a single clamped width delta — the keyboard-resize path.
40
- * Wired to ArrowLeft/ArrowRight on the focused resize handle so the
41
- * feature is reachable without a pointer (WCAG 2.1 — keyboard
42
- * operability). Same clamping as the drag path.
43
- */
44
- nudge: (
45
- field: string,
46
- currentWidth: number,
47
- delta: number,
48
- clampMin: number,
49
- clampMax: number,
50
- ) => void;
51
- }
52
-
53
- export function useColumnResize(args: UseColumnResizeArgs): ColumnResizeHandlers {
54
- const { widths, onChange, minWidth = 40, maxWidth = 1200 } = args;
55
-
56
- // We need the LATEST widths inside the pointermove closure. Stick
57
- // them in a ref so the closure captured at pointerdown stays valid
58
- // for the duration of the drag.
59
- const widthsRef = useRef(widths);
60
- widthsRef.current = widths;
61
-
62
- const startResize = useCallback(
63
- (
64
- field: string,
65
- startWidth: number,
66
- clampMin: number,
67
- clampMax: number,
68
- ) => {
69
- return (e: RPointerEvent<HTMLElement>) => {
70
- // Only respond to the primary mouse button (or touch / pen).
71
- if (e.pointerType === 'mouse' && e.button !== 0) return;
72
-
73
- e.preventDefault();
74
- e.stopPropagation();
75
-
76
- const startX = e.clientX;
77
- const target = e.currentTarget;
78
- try {
79
- target.setPointerCapture(e.pointerId);
80
- } catch {
81
- // jsdom or older browsers — fine to fall back to global listeners.
82
- }
83
-
84
- const effectiveMin = Math.max(minWidth, clampMin);
85
- const effectiveMax = Math.min(maxWidth, clampMax);
86
-
87
- const handleMove = (ev: PointerEvent) => {
88
- const delta = ev.clientX - startX;
89
- const next = clamp(startWidth + delta, effectiveMin, effectiveMax);
90
- onChange({ ...widthsRef.current, [field]: next });
91
- };
92
-
93
- const handleEnd = (ev: PointerEvent) => {
94
- try {
95
- target.releasePointerCapture(ev.pointerId);
96
- } catch {
97
- /* noop */
98
- }
99
- target.removeEventListener('pointermove', handleMove);
100
- target.removeEventListener('pointerup', handleEnd);
101
- target.removeEventListener('pointercancel', handleEnd);
102
- };
103
-
104
- target.addEventListener('pointermove', handleMove);
105
- target.addEventListener('pointerup', handleEnd);
106
- target.addEventListener('pointercancel', handleEnd);
107
- };
108
- },
109
- [onChange, minWidth, maxWidth],
110
- );
111
-
112
- const nudge = useCallback(
113
- (
114
- field: string,
115
- currentWidth: number,
116
- delta: number,
117
- clampMin: number,
118
- clampMax: number,
119
- ) => {
120
- const effectiveMin = Math.max(minWidth, clampMin);
121
- const effectiveMax = Math.min(maxWidth, clampMax);
122
- const next = clamp(currentWidth + delta, effectiveMin, effectiveMax);
123
- onChange({ ...widthsRef.current, [field]: next });
124
- },
125
- [onChange, minWidth, maxWidth],
126
- );
127
-
128
- return { startResize, nudge };
129
- }
130
-
131
- function clamp(n: number, min: number, max: number): number {
132
- if (n < min) return min;
133
- if (n > max) return max;
134
- return n;
135
- }
@@ -1,186 +0,0 @@
1
- import { useState, type ReactNode } from 'react';
2
- import { Popover } from '../../Popover/Popover.js';
3
- import { cn } from '../../../utils/cn.js';
4
- import type { TableColumn } from '../../Table/table.types.js';
5
-
6
- /**
7
- * Column visibility menu for DataGrid.
8
- *
9
- * Renders a toolbar button (the trigger) that opens a `<Popover>`
10
- * with one checkbox per `hideable` column. Auto-commits on every
11
- * toggle — there's no draft / commit step. Outside-click and Esc
12
- * close the popover (Radix-managed).
13
- *
14
- * UX rationale for Popover-over-Dialog:
15
- * - Lightweight, non-modal: the user can keep referring to the grid
16
- * while picking columns. A modal Dialog would interrupt the flow.
17
- * - Auto-commit reads as a "settings panel" rather than a
18
- * "configuration form" — matches AG-Grid / MUI DataGrid v6 /
19
- * TanStack examples.
20
- * - No focus trap on the rest of the page; the user can scroll the
21
- * grid or click the column resize handles without dismissing the
22
- * panel first.
23
- *
24
- * Columns with `hideable: false` are NEVER shown in the menu —
25
- * those are considered structurally required (e.g. an ID column).
26
- *
27
- * RBAC-hidden columns (`access.onUnauthorized === 'hide'`) are also
28
- * excluded — they're already removed from `visibleCols` upstream.
29
- */
30
-
31
- export interface ColumnVisibilityLabels {
32
- columnsButton?: string;
33
- columnsTitle?: string;
34
- /**
35
- * Accessible label for the tri-state master checkbox that
36
- * shows/hides every hideable column at once. Not shown as visible
37
- * text — surfaced to assistive tech via `aria-label`.
38
- */
39
- columnsToggleAll?: string;
40
- }
41
-
42
- const DEFAULT_VISIBILITY_LABELS: Required<ColumnVisibilityLabels> = {
43
- columnsButton: 'Columns',
44
- columnsTitle: 'Toggle columns',
45
- columnsToggleAll: 'Toggle all columns',
46
- };
47
-
48
- export interface ColumnVisibilityTriggerProps<T extends object> {
49
- cols: TableColumn<T>[];
50
- hiddenColumns: string[];
51
- onChange: (next: string[]) => void;
52
- disabled?: boolean;
53
- labels?: ColumnVisibilityLabels;
54
- }
55
-
56
- export function ColumnVisibilityTrigger<T extends object>(
57
- props: ColumnVisibilityTriggerProps<T>,
58
- ) {
59
- const { cols, hiddenColumns, onChange, disabled, labels: labelsProp } = props;
60
- const labels = { ...DEFAULT_VISIBILITY_LABELS, ...labelsProp };
61
- const [open, setOpen] = useState(false);
62
-
63
- // Hideable cols are the only ones the user can toggle. `hideable`
64
- // defaults to `true` — a column is hideable unless explicitly opted
65
- // out with `hideable: false` (structurally required column).
66
- const hideableCols = cols.filter((c) => c.hideable !== false);
67
-
68
- const toggle = (field: string) => {
69
- onChange(
70
- hiddenColumns.includes(field)
71
- ? hiddenColumns.filter((f) => f !== field)
72
- : [...hiddenColumns, field],
73
- );
74
- };
75
-
76
- // Tri-state master: checked = every hideable column visible,
77
- // unchecked = every one hidden, indeterminate = mixed.
78
- const allVisible = hideableCols.every(
79
- (c) => !hiddenColumns.includes(c.field as string),
80
- );
81
- const allHidden =
82
- hideableCols.length > 0 &&
83
- hideableCols.every((c) => hiddenColumns.includes(c.field as string));
84
- const someHidden = !allVisible && !allHidden;
85
-
86
- // Standard select-all semantics: when everything is visible the
87
- // master hides all; otherwise it shows all.
88
- const toggleAll = () => {
89
- onChange(allVisible ? hideableCols.map((c) => c.field as string) : []);
90
- };
91
-
92
- return (
93
- <Popover
94
- open={open}
95
- onOpenChange={setOpen}
96
- side="bottom"
97
- align="end"
98
- content={
99
- <div className="flex flex-col gap-1 min-w-[220px]">
100
- {/*
101
- Header row — the tri-state master checkbox + the title.
102
- The master replaces the old "Show all · Hide all" text
103
- links: one control, no extra copy, consistent with the
104
- DataGrid row select-all checkbox. The title is a heading
105
- (not part of the checkbox label) and stays consumer-
106
- customizable via `labels.columnsTitle`.
107
- */}
108
- <div className="flex items-center gap-2 px-1 pb-2 mb-1 border-b border-neutral-200">
109
- <input
110
- type="checkbox"
111
- aria-label={labels.columnsToggleAll}
112
- checked={allVisible}
113
- ref={(el) => {
114
- if (el) el.indeterminate = someHidden;
115
- }}
116
- onChange={toggleAll}
117
- className="cursor-pointer"
118
- />
119
- <span className="text-xs font-semibold text-neutral-700 uppercase tracking-wide">
120
- {labels.columnsTitle}
121
- </span>
122
- </div>
123
- <ul className="flex flex-col gap-0.5 max-h-72 overflow-auto list-none pl-0 m-0">
124
- {hideableCols.map((col) => {
125
- const field = col.field as string;
126
- const hidden = hiddenColumns.includes(field);
127
- const header =
128
- typeof col.header === 'function' ? col.header() : col.header;
129
- return (
130
- <li key={field}>
131
- <label className="flex items-center gap-2 cursor-pointer py-1 px-1 rounded hover:bg-neutral-100">
132
- <input
133
- type="checkbox"
134
- checked={!hidden}
135
- onChange={() => toggle(field)}
136
- className="cursor-pointer"
137
- />
138
- <span className="text-sm text-neutral-900">{header}</span>
139
- </label>
140
- </li>
141
- );
142
- })}
143
- </ul>
144
- </div>
145
- }
146
- >
147
- <button
148
- type="button"
149
- disabled={disabled}
150
- className={cn(
151
- 'inline-flex items-center gap-1.5 px-2.5 py-1.5 rounded-md',
152
- 'text-sm text-neutral-700 hover:text-neutral-900',
153
- 'border border-neutral-300 bg-neutral-50 hover:bg-neutral-100',
154
- 'focus:outline-none focus-visible:ring-2 focus-visible:ring-primary-500',
155
- 'transition-colors motion-reduce:transition-none',
156
- 'disabled:opacity-50 disabled:cursor-not-allowed',
157
- )}
158
- >
159
- <ColumnsIcon />
160
- <span>{labels.columnsButton}</span>
161
- </button>
162
- </Popover>
163
- );
164
- }
165
-
166
- // ───── Icon ─────
167
-
168
- function ColumnsIcon(): ReactNode {
169
- return (
170
- <svg
171
- width="0.875em"
172
- height="0.875em"
173
- viewBox="0 0 16 16"
174
- fill="none"
175
- stroke="currentColor"
176
- strokeWidth="1.5"
177
- strokeLinecap="round"
178
- strokeLinejoin="round"
179
- aria-hidden="true"
180
- >
181
- <rect x="2" y="3" width="3.5" height="10" rx="0.5" />
182
- <rect x="6.25" y="3" width="3.5" height="10" rx="0.5" />
183
- <rect x="10.5" y="3" width="3.5" height="10" rx="0.5" />
184
- </svg>
185
- );
186
- }
@@ -1,76 +0,0 @@
1
- // @vitest-environment jsdom
2
- import { describe, it, expect, vi, beforeAll } from 'vitest';
3
- import { render, screen, fireEvent } from '@testing-library/react';
4
-
5
- import { DatePicker } from './DatePicker.js';
6
-
7
- beforeAll(() => {
8
- // Radix Popover (Floating UI) needs ResizeObserver — jsdom lacks it.
9
- if (!('ResizeObserver' in globalThis)) {
10
- class ResizeObserverStub {
11
- observe(): void {
12
- /* no-op */
13
- }
14
- unobserve(): void {
15
- /* no-op */
16
- }
17
- disconnect(): void {
18
- /* no-op */
19
- }
20
- }
21
- (globalThis as { ResizeObserver?: unknown }).ResizeObserver =
22
- ResizeObserverStub;
23
- }
24
- });
25
-
26
- describe('DatePicker', () => {
27
- it('renders a labelled trigger with the placeholder', () => {
28
- render(
29
- <DatePicker name="birthday" label="Birthday" placeholder="Pick one" />,
30
- );
31
- expect(screen.queryByText('Birthday')).not.toBeNull();
32
- expect(screen.getByRole('button').textContent).toContain('Pick one');
33
- });
34
-
35
- it('shows a localized controlled value', () => {
36
- render(<DatePicker name="d" value="2026-05-20" />);
37
- expect(screen.getByRole('button').textContent).toContain('May 20, 2026');
38
- });
39
-
40
- it('opens and toggles the calendar popover from the trigger', () => {
41
- render(<DatePicker name="d" defaultValue="2026-05-20" />);
42
- const trigger = screen.getByRole('button');
43
- expect(screen.queryByRole('dialog')).toBeNull();
44
- fireEvent.click(trigger);
45
- expect(screen.queryByRole('dialog')).not.toBeNull();
46
- fireEvent.click(trigger);
47
- expect(screen.queryByRole('dialog')).toBeNull();
48
- });
49
-
50
- it('selects a date from the popover, updates the trigger and closes', () => {
51
- const onChange = vi.fn();
52
- render(
53
- <DatePicker name="d" defaultValue="2026-05-20" onChange={onChange} />,
54
- );
55
- fireEvent.click(screen.getByRole('button'));
56
- fireEvent.click(screen.getByRole('button', { name: /May 15, 2026/ }));
57
- expect(onChange).toHaveBeenCalledWith('2026-05-15');
58
- expect(screen.queryByRole('dialog')).toBeNull();
59
- expect(screen.getByRole('button').textContent).toContain('May 15, 2026');
60
- });
61
-
62
- it('keeps a controlled value fixed but still reports the change', () => {
63
- const onChange = vi.fn();
64
- render(<DatePicker name="d" value="2026-05-20" onChange={onChange} />);
65
- fireEvent.click(screen.getByRole('button'));
66
- fireEvent.click(screen.getByRole('button', { name: /May 15, 2026/ }));
67
- expect(onChange).toHaveBeenCalledWith('2026-05-15');
68
- expect(screen.getByRole('button').textContent).toContain('May 20, 2026');
69
- });
70
-
71
- it('does not open the popover when disabled', () => {
72
- render(<DatePicker name="d" disabled />);
73
- fireEvent.click(screen.getByRole('button'));
74
- expect(screen.queryByRole('dialog')).toBeNull();
75
- });
76
- });