@svgrid/grid 1.2.34 → 2.0.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 (444) hide show
  1. package/README.md +6 -5
  2. package/dist/SvAccordion.svelte +109 -0
  3. package/dist/SvAccordion.svelte.d.ts +28 -0
  4. package/dist/SvAlert.svelte +92 -0
  5. package/dist/SvAlert.svelte.d.ts +27 -0
  6. package/dist/SvAutoComplete.svelte +47 -18
  7. package/dist/SvAutoComplete.svelte.d.ts +2 -5
  8. package/dist/SvAvatar.svelte +75 -0
  9. package/dist/SvAvatar.svelte.d.ts +14 -0
  10. package/dist/SvAvatarGroup.svelte +48 -0
  11. package/dist/SvAvatarGroup.svelte.d.ts +16 -0
  12. package/dist/SvBadge.svelte +54 -0
  13. package/dist/SvBadge.svelte.d.ts +23 -0
  14. package/dist/SvBreadcrumb.svelte +88 -0
  15. package/dist/SvBreadcrumb.svelte.d.ts +23 -0
  16. package/dist/SvButtonGroup.svelte +121 -0
  17. package/dist/SvButtonGroup.svelte.d.ts +16 -0
  18. package/dist/SvCalendar.svelte +72 -9
  19. package/dist/SvCalendar.svelte.d.ts +34 -1
  20. package/dist/SvCard.svelte +71 -0
  21. package/dist/SvCard.svelte.d.ts +28 -0
  22. package/dist/SvCarousel.svelte +134 -0
  23. package/dist/SvCarousel.svelte.d.ts +28 -0
  24. package/dist/SvCheckBox.svelte +36 -21
  25. package/dist/SvCheckBox.svelte.d.ts +2 -5
  26. package/dist/SvChip.svelte +88 -0
  27. package/dist/SvChip.svelte.d.ts +31 -0
  28. package/dist/SvCircularProgress.svelte +109 -0
  29. package/dist/SvCircularProgress.svelte.d.ts +31 -0
  30. package/dist/SvColorInput.svelte +54 -27
  31. package/dist/SvColorInput.svelte.d.ts +10 -6
  32. package/dist/SvComboBox.svelte +119 -33
  33. package/dist/SvComboBox.svelte.d.ts +18 -6
  34. package/dist/SvCommand.svelte +197 -0
  35. package/dist/SvCommand.svelte.d.ts +26 -0
  36. package/dist/SvContextMenu.svelte +96 -0
  37. package/dist/SvContextMenu.svelte.d.ts +25 -0
  38. package/dist/SvCountryInput.svelte +56 -21
  39. package/dist/SvCountryInput.svelte.d.ts +9 -5
  40. package/dist/SvDateRangeInput.svelte +256 -0
  41. package/dist/SvDateRangeInput.svelte.d.ts +37 -0
  42. package/dist/SvDateTimePicker.svelte +57 -20
  43. package/dist/SvDateTimePicker.svelte.d.ts +12 -4
  44. package/dist/SvDivider.svelte +61 -0
  45. package/dist/SvDivider.svelte.d.ts +22 -0
  46. package/dist/SvDrawer.svelte +226 -0
  47. package/dist/SvDrawer.svelte.d.ts +43 -0
  48. package/dist/SvDropDownList.svelte +114 -35
  49. package/dist/SvDropDownList.svelte.d.ts +7 -6
  50. package/dist/SvDurationInput.svelte +108 -0
  51. package/dist/SvDurationInput.svelte.d.ts +15 -0
  52. package/dist/SvEmptyState.svelte +59 -0
  53. package/dist/SvEmptyState.svelte.d.ts +25 -0
  54. package/dist/SvField.svelte +85 -0
  55. package/dist/SvField.svelte.d.ts +30 -0
  56. package/dist/SvFileUpload.svelte +169 -0
  57. package/dist/SvFileUpload.svelte.d.ts +24 -0
  58. package/dist/SvForm.svelte +7 -1
  59. package/dist/SvForm.svelte.d.ts +3 -0
  60. package/dist/SvGauge.svelte +7 -1
  61. package/dist/SvGauge.svelte.d.ts +11 -0
  62. package/dist/SvGrid.controller.svelte.d.ts +6 -0
  63. package/dist/SvGrid.controller.svelte.js +64 -9
  64. package/dist/SvGrid.css +33 -0
  65. package/dist/SvGrid.svelte +116 -3
  66. package/dist/SvGrid.types.d.ts +366 -0
  67. package/dist/SvGridBoard.svelte +2281 -0
  68. package/dist/SvGridBoard.svelte.d.ts +31 -0
  69. package/dist/SvGridDropdown.svelte +2 -1
  70. package/dist/SvGridSelect.svelte +255 -0
  71. package/dist/SvGridSelect.svelte.d.ts +32 -0
  72. package/dist/SvGroupCell.svelte +109 -0
  73. package/dist/SvGroupCell.svelte.d.ts +41 -0
  74. package/dist/SvListBox.svelte +123 -36
  75. package/dist/SvListBox.svelte.d.ts +12 -8
  76. package/dist/SvMaskedInput.svelte +53 -13
  77. package/dist/SvMaskedInput.svelte.d.ts +16 -6
  78. package/dist/SvMenu.svelte +101 -0
  79. package/dist/SvMenu.svelte.d.ts +26 -0
  80. package/dist/SvMenuList.svelte +143 -0
  81. package/dist/SvMenuList.svelte.d.ts +24 -0
  82. package/dist/SvModal.svelte +220 -0
  83. package/dist/SvModal.svelte.d.ts +31 -0
  84. package/dist/SvMultiSelect.svelte +277 -0
  85. package/dist/SvMultiSelect.svelte.d.ts +31 -0
  86. package/dist/SvNavPane.svelte +314 -0
  87. package/dist/SvNavPane.svelte.d.ts +59 -0
  88. package/dist/SvNumberInput.svelte +23 -9
  89. package/dist/SvNumberInput.svelte.d.ts +2 -0
  90. package/dist/SvOtpInput.svelte +157 -0
  91. package/dist/SvOtpInput.svelte.d.ts +16 -0
  92. package/dist/SvPagination.svelte +100 -0
  93. package/dist/SvPagination.svelte.d.ts +16 -0
  94. package/dist/SvPasswordInput.svelte +42 -12
  95. package/dist/SvPasswordInput.svelte.d.ts +13 -6
  96. package/dist/SvPhoneInput.svelte +43 -11
  97. package/dist/SvPhoneInput.svelte.d.ts +10 -11
  98. package/dist/SvPopover.svelte +127 -0
  99. package/dist/SvPopover.svelte.d.ts +35 -0
  100. package/dist/SvProgress.svelte +116 -0
  101. package/dist/SvProgress.svelte.d.ts +32 -0
  102. package/dist/SvRadioGroup.svelte +40 -22
  103. package/dist/SvRadioGroup.svelte.d.ts +2 -10
  104. package/dist/SvRating.svelte +51 -30
  105. package/dist/SvRating.svelte.d.ts +10 -7
  106. package/dist/SvRichText.svelte +192 -0
  107. package/dist/SvRichText.svelte.d.ts +16 -0
  108. package/dist/SvRowGroupPanel.svelte +147 -0
  109. package/dist/SvRowGroupPanel.svelte.d.ts +17 -0
  110. package/dist/SvScrollArea.svelte +50 -0
  111. package/dist/SvScrollArea.svelte.d.ts +22 -0
  112. package/dist/SvSkeleton.svelte +76 -0
  113. package/dist/SvSkeleton.svelte.d.ts +25 -0
  114. package/dist/SvSlider.svelte +41 -9
  115. package/dist/SvSlider.svelte.d.ts +4 -4
  116. package/dist/SvSparkline.svelte +77 -0
  117. package/dist/SvSparkline.svelte.d.ts +28 -0
  118. package/dist/SvSplitter.svelte +138 -0
  119. package/dist/SvSplitter.svelte.d.ts +32 -0
  120. package/dist/SvStat.svelte +86 -0
  121. package/dist/SvStat.svelte.d.ts +30 -0
  122. package/dist/SvStepper.svelte +91 -0
  123. package/dist/SvStepper.svelte.d.ts +24 -0
  124. package/dist/SvSwitchButton.svelte +39 -24
  125. package/dist/SvSwitchButton.svelte.d.ts +2 -5
  126. package/dist/SvTabs.svelte +147 -28
  127. package/dist/SvTabs.svelte.d.ts +16 -4
  128. package/dist/SvTagsInput.svelte +59 -22
  129. package/dist/SvTagsInput.svelte.d.ts +9 -4
  130. package/dist/SvTextArea.svelte +113 -0
  131. package/dist/SvTextArea.svelte.d.ts +18 -0
  132. package/dist/SvTextInput.svelte +115 -0
  133. package/dist/SvTextInput.svelte.d.ts +20 -0
  134. package/dist/SvTimePicker.svelte +19 -5
  135. package/dist/SvTimePicker.svelte.d.ts +12 -0
  136. package/dist/SvTimeline.svelte +75 -0
  137. package/dist/SvTimeline.svelte.d.ts +24 -0
  138. package/dist/SvToaster.svelte +124 -0
  139. package/dist/SvToaster.svelte.d.ts +10 -0
  140. package/dist/SvToggleButton.svelte +37 -12
  141. package/dist/SvToggleButton.svelte.d.ts +2 -4
  142. package/dist/SvTooltip.svelte +113 -0
  143. package/dist/SvTooltip.svelte.d.ts +22 -0
  144. package/dist/SvTour.svelte +151 -0
  145. package/dist/SvTour.svelte.d.ts +25 -0
  146. package/dist/SvTree.svelte +286 -44
  147. package/dist/SvTree.svelte.d.ts +26 -9
  148. package/dist/SvTreeSelect.svelte +222 -0
  149. package/dist/SvTreeSelect.svelte.d.ts +24 -0
  150. package/dist/a11y/dismissable.d.ts +32 -0
  151. package/dist/a11y/dismissable.js +54 -0
  152. package/dist/a11y/focus-trap.d.ts +39 -0
  153. package/dist/a11y/focus-trap.js +142 -0
  154. package/dist/a11y/live-region.d.ts +8 -0
  155. package/dist/a11y/live-region.js +60 -0
  156. package/dist/a11y/scroll-lock.d.ts +4 -0
  157. package/dist/a11y/scroll-lock.js +41 -0
  158. package/dist/a11y.d.ts +3 -1
  159. package/dist/a11y.js +1 -1
  160. package/dist/avatar.d.ts +10 -0
  161. package/dist/avatar.js +22 -0
  162. package/dist/builtin-editors.d.ts +5 -0
  163. package/dist/builtin-editors.js +55 -0
  164. package/dist/cdn/svgrid.js +16021 -8234
  165. package/dist/cdn/svgrid.svelte-external.js +14542 -6764
  166. package/dist/columns.js +3 -2
  167. package/dist/core.d.ts +7 -1
  168. package/dist/countries.d.ts +12 -0
  169. package/dist/countries.js +24 -0
  170. package/dist/createAccordion.svelte.d.ts +71 -0
  171. package/dist/createAccordion.svelte.js +99 -0
  172. package/dist/createAutocomplete.svelte.d.ts +13 -4
  173. package/dist/createAutocomplete.svelte.js +11 -1
  174. package/dist/createButtonGroup.svelte.d.ts +62 -0
  175. package/dist/createButtonGroup.svelte.js +154 -0
  176. package/dist/createCalendar.svelte.d.ts +5 -0
  177. package/dist/createCalendar.svelte.js +2 -0
  178. package/dist/createCheckbox.svelte.d.ts +9 -17
  179. package/dist/createCheckbox.svelte.js +28 -1
  180. package/dist/createColorInput.svelte.d.ts +12 -22
  181. package/dist/createColorInput.svelte.js +13 -0
  182. package/dist/createCombobox.svelte.d.ts +16 -5
  183. package/dist/createCombobox.svelte.js +13 -2
  184. package/dist/createCountryInput.svelte.d.ts +14 -3
  185. package/dist/createCountryInput.svelte.js +12 -2
  186. package/dist/createDateTimePicker.svelte.d.ts +17 -2
  187. package/dist/createDateTimePicker.svelte.js +12 -2
  188. package/dist/createDropdownList.svelte.d.ts +14 -5
  189. package/dist/createDropdownList.svelte.js +50 -1
  190. package/dist/createFileUpload.svelte.d.ts +68 -0
  191. package/dist/createFileUpload.svelte.js +122 -0
  192. package/dist/createListbox.svelte.d.ts +10 -1
  193. package/dist/createListbox.svelte.js +48 -1
  194. package/dist/createMaskedInput.svelte.d.ts +11 -2
  195. package/dist/createMaskedInput.svelte.js +11 -1
  196. package/dist/createNumberInput.svelte.d.ts +1 -0
  197. package/dist/createNumberInput.svelte.js +1 -0
  198. package/dist/createPasswordInput.svelte.d.ts +19 -21
  199. package/dist/createPasswordInput.svelte.js +16 -4
  200. package/dist/createPhoneInput.svelte.d.ts +26 -7
  201. package/dist/createPhoneInput.svelte.js +24 -3
  202. package/dist/createPopoverSelect.svelte.d.ts +86 -0
  203. package/dist/createPopoverSelect.svelte.js +196 -0
  204. package/dist/createRadioGroup.svelte.d.ts +9 -0
  205. package/dist/createRadioGroup.svelte.js +11 -1
  206. package/dist/createRating.svelte.d.ts +11 -0
  207. package/dist/createRating.svelte.js +12 -1
  208. package/dist/createSlider.svelte.d.ts +2 -0
  209. package/dist/createSlider.svelte.js +16 -5
  210. package/dist/createSplitter.svelte.d.ts +67 -0
  211. package/dist/createSplitter.svelte.js +99 -0
  212. package/dist/createSwitch.svelte.d.ts +9 -16
  213. package/dist/createSwitch.svelte.js +28 -1
  214. package/dist/createTabs.svelte.d.ts +7 -0
  215. package/dist/createTabs.svelte.js +17 -2
  216. package/dist/createTagsInput.svelte.d.ts +13 -1
  217. package/dist/createTagsInput.svelte.js +12 -3
  218. package/dist/createToggle.svelte.d.ts +9 -0
  219. package/dist/createToggle.svelte.js +12 -1
  220. package/dist/createTree.svelte.d.ts +19 -0
  221. package/dist/createTree.svelte.js +108 -15
  222. package/dist/debounce.d.ts +11 -0
  223. package/dist/debounce.js +30 -0
  224. package/dist/duration.d.ts +15 -0
  225. package/dist/duration.js +51 -0
  226. package/dist/editor-contract.d.ts +62 -7
  227. package/dist/editor-contract.js +45 -5
  228. package/dist/editor-registry.d.ts +67 -0
  229. package/dist/editor-registry.js +38 -0
  230. package/dist/editors/cell-editors.d.ts +1 -1
  231. package/dist/editors/cell-editors.js +5 -0
  232. package/dist/fuzzy.d.ts +3 -0
  233. package/dist/fuzzy.js +41 -0
  234. package/dist/grid-select.d.ts +9 -0
  235. package/dist/grid-select.js +8 -0
  236. package/dist/index.d.ts +79 -6
  237. package/dist/index.js +78 -4
  238. package/dist/keyboard-handlers.js +19 -0
  239. package/dist/list-option.d.ts +36 -0
  240. package/dist/list-option.js +68 -0
  241. package/dist/otp.d.ts +16 -0
  242. package/dist/otp.js +26 -0
  243. package/dist/paginate.d.ts +20 -0
  244. package/dist/paginate.js +40 -0
  245. package/dist/popover.d.ts +15 -1
  246. package/dist/popover.js +29 -3
  247. package/dist/recurrence.d.ts +36 -0
  248. package/dist/recurrence.js +90 -0
  249. package/dist/server-data-source.d.ts +89 -0
  250. package/dist/server-data-source.js +4 -0
  251. package/dist/server-group-model.d.ts +98 -0
  252. package/dist/server-group-model.js +263 -0
  253. package/dist/toast-store.svelte.d.ts +41 -0
  254. package/dist/toast-store.svelte.js +113 -0
  255. package/dist/tree-select.d.ts +19 -0
  256. package/dist/tree-select.js +40 -0
  257. package/dist/ui-app.types.d.ts +80 -0
  258. package/dist/ui-app.types.js +7 -0
  259. package/dist/validators.d.ts +43 -0
  260. package/dist/validators.js +53 -0
  261. package/dist/virtual.d.ts +35 -0
  262. package/dist/virtual.js +34 -0
  263. package/package.json +1 -1
  264. package/src/SvAccordion.svelte +109 -0
  265. package/src/SvAccordion.test.ts +66 -0
  266. package/src/SvAlert.svelte +92 -0
  267. package/src/SvAutoComplete.svelte +47 -18
  268. package/src/SvAvatar.svelte +75 -0
  269. package/src/SvAvatarGroup.svelte +48 -0
  270. package/src/SvBadge.svelte +54 -0
  271. package/src/SvBreadcrumb.svelte +88 -0
  272. package/src/SvButtonGroup.svelte +121 -0
  273. package/src/SvButtonGroup.test.ts +72 -0
  274. package/src/SvCalendar.svelte +72 -9
  275. package/src/SvCard.svelte +71 -0
  276. package/src/SvCarousel.svelte +134 -0
  277. package/src/SvCheckBox.svelte +36 -21
  278. package/src/SvChip.svelte +88 -0
  279. package/src/SvCircularProgress.svelte +109 -0
  280. package/src/SvColorInput.svelte +54 -27
  281. package/src/SvComboBox.svelte +119 -33
  282. package/src/SvCommand.svelte +197 -0
  283. package/src/SvContextMenu.svelte +96 -0
  284. package/src/SvCountryInput.svelte +56 -21
  285. package/src/SvDateRangeInput.svelte +256 -0
  286. package/src/SvDateRangeInput.test.ts +80 -0
  287. package/src/SvDateTimePicker.svelte +57 -20
  288. package/src/SvDivider.svelte +61 -0
  289. package/src/SvDrawer.svelte +226 -0
  290. package/src/SvDrawer.test.ts +125 -0
  291. package/src/SvDropDownList.svelte +114 -35
  292. package/src/SvDurationInput.svelte +108 -0
  293. package/src/SvEmptyState.svelte +59 -0
  294. package/src/SvField.svelte +85 -0
  295. package/src/SvFileUpload.svelte +169 -0
  296. package/src/SvFileUpload.test.ts +59 -0
  297. package/src/SvForm.svelte +7 -1
  298. package/src/SvGauge.svelte +7 -1
  299. package/src/SvGrid.controller.svelte.ts +68 -9
  300. package/src/SvGrid.css +33 -0
  301. package/src/SvGrid.svelte +116 -3
  302. package/src/SvGrid.types.ts +374 -0
  303. package/src/SvGridBoard.svelte +2281 -0
  304. package/src/SvGridDropdown.svelte +2 -1
  305. package/src/SvGridSelect.svelte +255 -0
  306. package/src/SvGridSelect.test.ts +100 -0
  307. package/src/SvGroupCell.svelte +109 -0
  308. package/src/SvListBox.svelte +123 -36
  309. package/src/SvMaskedInput.svelte +53 -13
  310. package/src/SvMenu.svelte +101 -0
  311. package/src/SvMenu.test.ts +73 -0
  312. package/src/SvMenuList.svelte +143 -0
  313. package/src/SvModal.svelte +220 -0
  314. package/src/SvMultiSelect.svelte +277 -0
  315. package/src/SvMultiSelect.test.ts +167 -0
  316. package/src/SvNavPane.svelte +314 -0
  317. package/src/SvNavPane.test.ts +70 -0
  318. package/src/SvNumberInput.svelte +23 -9
  319. package/src/SvOtpInput.svelte +157 -0
  320. package/src/SvPagination.svelte +100 -0
  321. package/src/SvPasswordInput.svelte +42 -12
  322. package/src/SvPhoneInput.svelte +43 -11
  323. package/src/SvPopover.svelte +127 -0
  324. package/src/SvProgress.svelte +116 -0
  325. package/src/SvRadioGroup.svelte +40 -22
  326. package/src/SvRating.svelte +51 -30
  327. package/src/SvRichText.svelte +192 -0
  328. package/src/SvRowGroupPanel.svelte +147 -0
  329. package/src/SvScrollArea.svelte +50 -0
  330. package/src/SvSkeleton.svelte +76 -0
  331. package/src/SvSlider.svelte +41 -9
  332. package/src/SvSparkline.svelte +77 -0
  333. package/src/SvSplitter.svelte +138 -0
  334. package/src/SvSplitter.test.ts +55 -0
  335. package/src/SvStat.svelte +86 -0
  336. package/src/SvStepper.svelte +91 -0
  337. package/src/SvSwitchButton.svelte +39 -24
  338. package/src/SvTabs.svelte +147 -28
  339. package/src/SvTagsInput.svelte +59 -22
  340. package/src/SvTextArea.svelte +113 -0
  341. package/src/SvTextInput.svelte +115 -0
  342. package/src/SvTimePicker.svelte +19 -5
  343. package/src/SvTimeline.svelte +75 -0
  344. package/src/SvToaster.svelte +124 -0
  345. package/src/SvToaster.test.ts +63 -0
  346. package/src/SvToggleButton.svelte +37 -12
  347. package/src/SvTooltip.svelte +113 -0
  348. package/src/SvTour.svelte +151 -0
  349. package/src/SvTree.svelte +286 -44
  350. package/src/SvTreeSelect.svelte +222 -0
  351. package/src/SvTreeSelect.test.ts +87 -0
  352. package/src/a11y/dismissable.test.ts +95 -0
  353. package/src/a11y/dismissable.ts +94 -0
  354. package/src/a11y/focus-trap.test.ts +110 -0
  355. package/src/a11y/focus-trap.ts +134 -0
  356. package/src/a11y/live-region.test.ts +40 -0
  357. package/src/a11y/live-region.ts +65 -0
  358. package/src/a11y/scroll-lock.test.ts +38 -0
  359. package/src/a11y/scroll-lock.ts +41 -0
  360. package/src/a11y.ts +3 -1
  361. package/src/avatar.test.ts +32 -0
  362. package/src/avatar.ts +21 -0
  363. package/src/board.test.ts +927 -0
  364. package/src/builtin-editors.grid.test.ts +85 -0
  365. package/src/builtin-editors.test.ts +58 -0
  366. package/src/builtin-editors.ts +56 -0
  367. package/src/columns.ts +3 -2
  368. package/src/core.ts +10 -0
  369. package/src/countries.ts +25 -0
  370. package/src/createAccordion.svelte.ts +126 -0
  371. package/src/createAutocomplete.svelte.ts +18 -1
  372. package/src/createButtonGroup.svelte.ts +166 -0
  373. package/src/createCalendar.svelte.ts +6 -0
  374. package/src/createCheckbox.svelte.ts +23 -1
  375. package/src/createColorInput.svelte.ts +20 -0
  376. package/src/createCombobox.svelte.ts +22 -2
  377. package/src/createCountryInput.svelte.ts +21 -2
  378. package/src/createDateTimePicker.svelte.ts +23 -2
  379. package/src/createDropdownList.svelte.ts +31 -2
  380. package/src/createFileUpload.svelte.ts +144 -0
  381. package/src/createListbox.svelte.ts +35 -3
  382. package/src/createMaskedInput.svelte.ts +18 -1
  383. package/src/createNumberInput.svelte.ts +2 -0
  384. package/src/createPasswordInput.svelte.ts +31 -5
  385. package/src/createPhoneInput.svelte.ts +38 -4
  386. package/src/createPopoverSelect.svelte.ts +208 -0
  387. package/src/createRadioGroup.svelte.ts +23 -1
  388. package/src/createRating.svelte.ts +26 -1
  389. package/src/createSlider.svelte.ts +14 -3
  390. package/src/createSplitter.svelte.ts +119 -0
  391. package/src/createSwitch.svelte.ts +26 -3
  392. package/src/createTabs.svelte.ts +20 -3
  393. package/src/createTagsInput.svelte.ts +24 -3
  394. package/src/createToggle.svelte.ts +25 -2
  395. package/src/createTree.svelte.ts +104 -14
  396. package/src/debounce.test.ts +50 -0
  397. package/src/debounce.ts +41 -0
  398. package/src/duration.test.ts +41 -0
  399. package/src/duration.ts +51 -0
  400. package/src/editor-contract.ts +87 -8
  401. package/src/editor-registry.grid.test.ts +98 -0
  402. package/src/editor-registry.test.ts +86 -0
  403. package/src/editor-registry.ts +106 -0
  404. package/src/editors/cell-editors.ts +10 -1
  405. package/src/fuzzy.test.ts +40 -0
  406. package/src/fuzzy.ts +39 -0
  407. package/src/grid-select.test.ts +28 -0
  408. package/src/grid-select.ts +20 -0
  409. package/src/index.ts +150 -5
  410. package/src/keyboard-handlers.ts +20 -0
  411. package/src/list-option.ts +74 -0
  412. package/src/list-power.test.ts +71 -0
  413. package/src/otp.test.ts +28 -0
  414. package/src/otp.ts +28 -0
  415. package/src/overlays.test.ts +85 -0
  416. package/src/paginate.test.ts +41 -0
  417. package/src/paginate.ts +61 -0
  418. package/src/phone-valid.test.ts +26 -0
  419. package/src/popover.ts +31 -3
  420. package/src/progress.test.ts +55 -0
  421. package/src/recurrence.test.ts +91 -0
  422. package/src/recurrence.ts +111 -0
  423. package/src/server-data-source.ts +102 -0
  424. package/src/server-group-model.test.ts +294 -0
  425. package/src/server-group-model.ts +370 -0
  426. package/src/svgrid.responsive.test.ts +72 -0
  427. package/src/toast-store.svelte.ts +148 -0
  428. package/src/toast-store.test.ts +86 -0
  429. package/src/tree-edit.test.ts +49 -0
  430. package/src/tree-filter.test.ts +56 -0
  431. package/src/tree-select.test.ts +48 -0
  432. package/src/tree-select.ts +62 -0
  433. package/src/ui-app.test.ts +130 -0
  434. package/src/ui-app.types.ts +88 -0
  435. package/src/ui-display.test.ts +79 -0
  436. package/src/ui-inputs.test.ts +1 -1
  437. package/src/ui-status.test.ts +141 -0
  438. package/src/ui-tier1.test.ts +142 -0
  439. package/src/ui-tier2.test.ts +124 -0
  440. package/src/ui-tier3.test.ts +139 -0
  441. package/src/validators.test.ts +58 -0
  442. package/src/validators.ts +105 -0
  443. package/src/virtual.test.ts +72 -0
  444. package/src/virtual.ts +67 -0
package/src/popover.ts CHANGED
@@ -16,9 +16,12 @@
16
16
  * any popover panel actually consumes.
17
17
  */
18
18
  export const PANEL_THEME_VARS = [
19
- '--sg-accent', '--sg-bg', '--sg-fg', '--sg-border', '--sg-muted',
20
- '--sg-header-bg', '--sg-row-hover-bg', '--sg-selection-bg',
21
- '--sg-input-bg', '--sg-input-border', '--sg-selection-fg',
19
+ '--sg-accent', '--sg-on-accent', '--sg-bg', '--sg-fg', '--sg-muted', '--sg-border',
20
+ '--sg-header-bg', '--sg-header-fg', '--sg-row-hover-bg', '--sg-row-alt-bg',
21
+ '--sg-selection-bg', '--sg-selection-fg', '--sg-input-bg', '--sg-input-border',
22
+ '--sg-danger', '--sg-focus-ring', '--sg-radius', '--sg-font',
23
+ '--sg-invalid-bg', '--sg-invalid-border', '--sg-invalid-fg',
24
+ '--sg-rating-on', '--sg-rating-empty', '--sg-rating-hover',
22
25
  ] as const
23
26
 
24
27
  /**
@@ -40,6 +43,31 @@ export function portalToBody(node: HTMLElement, vars: ReadonlyArray<string> = PA
40
43
  }
41
44
  }
42
45
 
46
+ /**
47
+ * Svelte action: play a short enter animation when a portalled panel mounts
48
+ * (dropdowns, popovers, dialogs). Slides from the trigger side + fades/scales in.
49
+ * A no-op under `prefers-reduced-motion` and in environments without the Web
50
+ * Animations API (jsdom), so tests and reduced-motion users are unaffected.
51
+ *
52
+ * `use:popIn={{ up: rect.openUpward }}` - pass `up` for panels that flipped above
53
+ * their trigger so the slide direction matches.
54
+ */
55
+ export function popIn(node: HTMLElement, param: { up?: boolean; duration?: number; scale?: number } = {}) {
56
+ if (typeof node.animate !== 'function') return
57
+ const reduce = typeof matchMedia === 'function' && matchMedia('(prefers-reduced-motion: reduce)').matches
58
+ if (reduce) return
59
+ const dy = param.up ? 6 : -6
60
+ const s = param.scale ?? 0.97
61
+ node.animate(
62
+ [
63
+ { opacity: 0, transform: `translateY(${dy}px) scale(${s})` },
64
+ { opacity: 1, transform: 'translateY(0) scale(1)' },
65
+ ],
66
+ { duration: param.duration ?? 140, easing: 'cubic-bezier(0.16, 1, 0.3, 1)' },
67
+ )
68
+ return {}
69
+ }
70
+
43
71
  export type AnchoredRect = { top: number; left: number; width: number; openUpward: boolean }
44
72
 
45
73
  export type AnchorOptions = {
@@ -0,0 +1,55 @@
1
+ /**
2
+ * Component tests for SvProgress + SvCircularProgress: progressbar ARIA,
3
+ * determinate fill width / ring offset, and indeterminate (no valuenow).
4
+ */
5
+ import { describe, expect, it } from 'vitest'
6
+ import { mount, unmount, flushSync } from 'svelte'
7
+ import SvProgress from './SvProgress.svelte'
8
+ import SvCircularProgress from './SvCircularProgress.svelte'
9
+
10
+ function mountC(Comp: any, props: Record<string, unknown>) {
11
+ const target = document.createElement('div')
12
+ document.body.appendChild(target)
13
+ const app = mount(Comp, { target, props: props as any })
14
+ flushSync()
15
+ return { target, destroy: () => { unmount(app); target.remove() } }
16
+ }
17
+
18
+ describe('SvProgress', () => {
19
+ it('exposes progressbar ARIA + fill width for a determinate value', () => {
20
+ const { target, destroy } = mountC(SvProgress, { value: 40, max: 200, showLabel: true })
21
+ try {
22
+ const bar = target.querySelector<HTMLElement>('[role="progressbar"]')!
23
+ expect(bar.getAttribute('aria-valuemin')).toBe('0')
24
+ expect(bar.getAttribute('aria-valuemax')).toBe('200')
25
+ expect(bar.getAttribute('aria-valuenow')).toBe('40')
26
+ expect(target.querySelector<HTMLElement>('.sv-prog__fill')!.style.width).toBe('20%')
27
+ expect(target.querySelector('.sv-prog__label')!.textContent).toBe('20%')
28
+ } finally { destroy() }
29
+ })
30
+
31
+ it('indeterminate drops valuenow and animates', () => {
32
+ const { target, destroy } = mountC(SvProgress, { indeterminate: true })
33
+ try {
34
+ const bar = target.querySelector<HTMLElement>('[role="progressbar"]')!
35
+ expect(bar.getAttribute('aria-valuenow')).toBeNull()
36
+ expect(target.querySelector('.sv-prog__fill.is-indeterminate')).not.toBeNull()
37
+ } finally { destroy() }
38
+ })
39
+ })
40
+
41
+ describe('SvCircularProgress', () => {
42
+ it('sets the ring dashoffset from the value', () => {
43
+ const { target, destroy } = mountC(SvCircularProgress, { value: 75, size: 48, thickness: 4, showLabel: true })
44
+ try {
45
+ const bar = target.querySelector<HTMLElement>('[role="progressbar"]')!
46
+ expect(bar.getAttribute('aria-valuenow')).toBe('75')
47
+ const arc = target.querySelector<SVGCircleElement>('.sv-circ__arc')!
48
+ const circ = 2 * Math.PI * ((48 - 4) / 2)
49
+ expect(Number(arc.getAttribute('stroke-dasharray'))).toBeCloseTo(circ, 3)
50
+ // 75% -> 25% of the circumference remains as offset.
51
+ expect(Number(arc.getAttribute('stroke-dashoffset'))).toBeCloseTo(circ * 0.25, 3)
52
+ expect(target.querySelector('.sv-circ__label')!.textContent).toBe('75%')
53
+ } finally { destroy() }
54
+ })
55
+ })
@@ -0,0 +1,91 @@
1
+ import { describe, expect, it } from 'vitest'
2
+ import { matchesRecurrence, expandRecurrence, type RecurrenceRule } from './recurrence'
3
+
4
+ // Fixed reference dates (local time). 2026-07-01 is a Wednesday.
5
+ const D = (s: string) => new Date(`${s}T00:00:00`)
6
+
7
+ describe('matchesRecurrence - weekly', () => {
8
+ const weekdays: RecurrenceRule = { freq: 'weekly', weekdays: [1, 2, 3, 4, 5] } // Mon..Fri
9
+ it('matches weekdays, not weekends', () => {
10
+ expect(matchesRecurrence(D('2026-07-06'), weekdays)).toBe(true) // Monday
11
+ expect(matchesRecurrence(D('2026-07-10'), weekdays)).toBe(true) // Friday
12
+ expect(matchesRecurrence(D('2026-07-11'), weekdays)).toBe(false) // Saturday
13
+ expect(matchesRecurrence(D('2026-07-12'), weekdays)).toBe(false) // Sunday
14
+ })
15
+
16
+ it('every other Monday with an interval + anchor', () => {
17
+ const r: RecurrenceRule = { freq: 'weekly', weekdays: [1], interval: 2, from: D('2026-07-06') }
18
+ expect(matchesRecurrence(D('2026-07-06'), r)).toBe(true) // anchor Monday
19
+ expect(matchesRecurrence(D('2026-07-13'), r)).toBe(false) // next Monday (odd week)
20
+ expect(matchesRecurrence(D('2026-07-20'), r)).toBe(true) // +2 weeks
21
+ expect(matchesRecurrence(D('2026-07-07'), r)).toBe(false) // Tuesday
22
+ })
23
+
24
+ it("falls back to the anchor's weekday when no weekdays given", () => {
25
+ const r: RecurrenceRule = { freq: 'weekly', from: D('2026-07-01') } // Wednesday
26
+ expect(matchesRecurrence(D('2026-07-08'), r)).toBe(true) // Wednesday
27
+ expect(matchesRecurrence(D('2026-07-09'), r)).toBe(false) // Thursday
28
+ })
29
+ })
30
+
31
+ describe('matchesRecurrence - monthly / yearly / daily', () => {
32
+ it('monthly on a day-of-month', () => {
33
+ const r: RecurrenceRule = { freq: 'monthly', day: 1 }
34
+ expect(matchesRecurrence(D('2026-07-01'), r)).toBe(true)
35
+ expect(matchesRecurrence(D('2026-08-01'), r)).toBe(true)
36
+ expect(matchesRecurrence(D('2026-08-02'), r)).toBe(false)
37
+ })
38
+
39
+ it('monthly with an interval + anchor (every 3 months, the 15th)', () => {
40
+ const r: RecurrenceRule = { freq: 'monthly', day: 15, interval: 3, from: D('2026-01-15') }
41
+ expect(matchesRecurrence(D('2026-01-15'), r)).toBe(true)
42
+ expect(matchesRecurrence(D('2026-02-15'), r)).toBe(false)
43
+ expect(matchesRecurrence(D('2026-04-15'), r)).toBe(true)
44
+ })
45
+
46
+ it('yearly on a month + day', () => {
47
+ const r: RecurrenceRule = { freq: 'yearly', month: 11, day: 25 } // Dec 25
48
+ expect(matchesRecurrence(D('2026-12-25'), r)).toBe(true)
49
+ expect(matchesRecurrence(D('2027-12-25'), r)).toBe(true)
50
+ expect(matchesRecurrence(D('2026-12-24'), r)).toBe(false)
51
+ })
52
+
53
+ it('daily every N days from an anchor', () => {
54
+ const r: RecurrenceRule = { freq: 'daily', interval: 3, from: D('2026-07-01') }
55
+ expect(matchesRecurrence(D('2026-07-01'), r)).toBe(true)
56
+ expect(matchesRecurrence(D('2026-07-02'), r)).toBe(false)
57
+ expect(matchesRecurrence(D('2026-07-04'), r)).toBe(true)
58
+ })
59
+ })
60
+
61
+ describe('matchesRecurrence - bounds + combining', () => {
62
+ it('respects from / until', () => {
63
+ const r: RecurrenceRule = { freq: 'daily', from: D('2026-07-05'), until: D('2026-07-08') }
64
+ expect(matchesRecurrence(D('2026-07-04'), r)).toBe(false) // before
65
+ expect(matchesRecurrence(D('2026-07-06'), r)).toBe(true) // inside
66
+ expect(matchesRecurrence(D('2026-07-09'), r)).toBe(false) // after until
67
+ })
68
+
69
+ it('matches if ANY rule in a list matches', () => {
70
+ const rules: RecurrenceRule[] = [
71
+ { freq: 'weekly', weekdays: [1] }, // Mondays
72
+ { freq: 'monthly', day: 1 }, // the 1st
73
+ ]
74
+ expect(matchesRecurrence(D('2026-07-06'), rules)).toBe(true) // Monday
75
+ expect(matchesRecurrence(D('2026-07-01'), rules)).toBe(true) // the 1st (a Wednesday)
76
+ expect(matchesRecurrence(D('2026-07-02'), rules)).toBe(false)
77
+ })
78
+
79
+ it('returns false for empty / nullish rules', () => {
80
+ expect(matchesRecurrence(D('2026-07-01'), null)).toBe(false)
81
+ expect(matchesRecurrence(D('2026-07-01'), [])).toBe(false)
82
+ })
83
+ })
84
+
85
+ describe('expandRecurrence', () => {
86
+ it('lists the matching dates in a range', () => {
87
+ const r: RecurrenceRule = { freq: 'weekly', weekdays: [1] } // Mondays
88
+ const dates = expandRecurrence(r, D('2026-07-01'), D('2026-07-31')).map((d) => d.getDate())
89
+ expect(dates).toEqual([6, 13, 20, 27])
90
+ })
91
+ })
@@ -0,0 +1,111 @@
1
+ /**
2
+ * recurrence - a small, pure repeat-pattern engine for SvCalendar (and anywhere
3
+ * you need "does this date match a recurring rule"). Supports daily / weekly /
4
+ * monthly / yearly frequencies with an interval, weekday lists, a day-of-month,
5
+ * an anchor (`from`) and an inclusive `until`. Framework-free + pure so it is
6
+ * unit-tested directly - no RRULE dependency.
7
+ *
8
+ * ```ts
9
+ * const standup = { freq: 'weekly', weekdays: [1, 2, 3, 4, 5] } // every weekday
10
+ * const payday = { freq: 'monthly', day: 1 } // the 1st
11
+ * const sprint = { freq: 'weekly', weekdays: [1], interval: 2, from: '2026-01-05' } // every other Monday
12
+ * matchesRecurrence(someDate, [standup, payday, sprint])
13
+ * ```
14
+ */
15
+ import { startOfDay, startOfWeek, toDate, type DateLike } from './datetime/date-core'
16
+
17
+ export type RecurrenceFreq = 'daily' | 'weekly' | 'monthly' | 'yearly'
18
+
19
+ export type RecurrenceRule = {
20
+ freq: RecurrenceFreq
21
+ /** Repeat every N units of `freq`. Default 1. Uses `from` as the phase anchor. */
22
+ interval?: number
23
+ /** weekly: the weekdays it lands on (0 = Sunday .. 6 = Saturday). */
24
+ weekdays?: ReadonlyArray<number>
25
+ /** monthly / yearly: day of the month (1..31). */
26
+ day?: number
27
+ /** yearly: the month (0 = January .. 11 = December). */
28
+ month?: number
29
+ /** First occurrence + the phase for `interval`. */
30
+ from?: DateLike
31
+ /** Last day the pattern applies (inclusive). */
32
+ until?: DateLike | null
33
+ }
34
+
35
+ const MS_DAY = 86_400_000
36
+ /** Whole-day index, rounded so DST transitions don't shift it. */
37
+ const dayIndex = (d: Date) => Math.round(startOfDay(d).getTime() / MS_DAY)
38
+
39
+ function matchesRule(date: Date, r: RecurrenceRule): boolean {
40
+ const d = startOfDay(date)
41
+ const fromD = r.from != null ? startOfDay(toDate(r.from) ?? d) : null
42
+ const untilD = r.until != null ? startOfDay(toDate(r.until) ?? d) : null
43
+ if (fromD && d < fromD) return false
44
+ if (untilD && d > untilD) return false
45
+ const interval = Math.max(1, Math.floor(r.interval ?? 1))
46
+
47
+ switch (r.freq) {
48
+ case 'daily':
49
+ if (!fromD) return true
50
+ return (dayIndex(d) - dayIndex(fromD)) % interval === 0
51
+
52
+ case 'weekly': {
53
+ // The weekdays it repeats on: an explicit list, else the anchor's weekday.
54
+ const weekdays = r.weekdays && r.weekdays.length ? r.weekdays : fromD ? [fromD.getDay()] : null
55
+ if (!weekdays) return false
56
+ if (!weekdays.includes(d.getDay())) return false
57
+ if (interval > 1 && fromD) {
58
+ const weeks = Math.round(
59
+ (startOfWeek(d, 0).getTime() - startOfWeek(fromD, 0).getTime()) / (MS_DAY * 7),
60
+ )
61
+ if (weeks % interval !== 0) return false
62
+ }
63
+ return true
64
+ }
65
+
66
+ case 'monthly': {
67
+ const dom = r.day ?? fromD?.getDate()
68
+ if (dom != null && d.getDate() !== dom) return false
69
+ if (!fromD) return dom != null
70
+ const months = (d.getFullYear() - fromD.getFullYear()) * 12 + (d.getMonth() - fromD.getMonth())
71
+ return months % interval === 0
72
+ }
73
+
74
+ case 'yearly': {
75
+ if (r.month != null && d.getMonth() !== r.month) return false
76
+ const dom = r.day ?? fromD?.getDate()
77
+ if (dom != null && d.getDate() !== dom) return false
78
+ if (!fromD) return r.month != null || dom != null
79
+ return (d.getFullYear() - fromD.getFullYear()) % interval === 0
80
+ }
81
+ }
82
+ }
83
+
84
+ /** Whether `date` matches any of the given recurrence rule(s). */
85
+ export function matchesRecurrence(
86
+ date: Date,
87
+ rules: RecurrenceRule | ReadonlyArray<RecurrenceRule> | null | undefined,
88
+ ): boolean {
89
+ if (!rules) return false
90
+ const list = Array.isArray(rules) ? rules : [rules as RecurrenceRule]
91
+ return list.some((r) => matchesRule(date, r))
92
+ }
93
+
94
+ /** Every matching date within [start, end] (inclusive), in order - for building
95
+ * event lists / agendas. Bounded to avoid runaway loops. */
96
+ export function expandRecurrence(
97
+ rules: RecurrenceRule | ReadonlyArray<RecurrenceRule> | null | undefined,
98
+ start: Date,
99
+ end: Date,
100
+ ): Date[] {
101
+ if (!rules) return []
102
+ const out: Date[] = []
103
+ const last = startOfDay(end)
104
+ let cur = startOfDay(start)
105
+ let guard = 0
106
+ while (cur <= last && guard++ < 4000) {
107
+ if (matchesRecurrence(cur, rules)) out.push(cur)
108
+ cur = new Date(cur.getFullYear(), cur.getMonth(), cur.getDate() + 1)
109
+ }
110
+ return out
111
+ }
@@ -31,6 +31,9 @@ export type ServerFilterModel = {
31
31
  >
32
32
  }
33
33
 
34
+ /** A value column to roll up per group. */
35
+ export type ServerAggregation = { col: string; fn: 'sum' | 'avg' | 'min' | 'max' | 'count' }
36
+
34
37
  export type ServerRequest = {
35
38
  /** Zero-based index of the first row wanted (inclusive). */
36
39
  startRow: number
@@ -40,8 +43,103 @@ export type ServerRequest = {
40
43
  pageSize: number
41
44
  sortModel: ServerSortModel
42
45
  filterModel: ServerFilterModel
46
+ /**
47
+ * Server-side grouping / tree: the columns being grouped on, outer to inner.
48
+ * Omitted / empty for a flat request.
49
+ */
50
+ groupBy?: string[]
51
+ /**
52
+ * The path of group keys the grid is expanding, e.g. `['Germany', 'Berlin']`.
53
+ * Empty (`[]`) asks for the top level. When `groupKeys.length < groupBy.length`
54
+ * the server returns **group rows** (one per distinct key at this level,
55
+ * carrying the group key + aggregates); when they are equal it returns the
56
+ * **leaf rows** under that path.
57
+ */
58
+ groupKeys?: string[]
59
+ /** Value columns to aggregate per group. */
60
+ aggregations?: ServerAggregation[]
61
+ }
62
+
63
+ /**
64
+ * A group row in the server-side group/tree model - one distinct key at a
65
+ * level, with its rolled-up aggregates. The grid renders it with an expander;
66
+ * expanding it fetches its children through the same `getRows`.
67
+ */
68
+ export type ServerGroupRow<TData> = {
69
+ kind: 'group'
70
+ /** Stable id (the group path). */
71
+ id: string
72
+ /** Group keys from the root to this node, e.g. `['Germany', 'Berlin']`. */
73
+ path: string[]
74
+ /** The column this group is on (the `groupBy` entry for this level). */
75
+ field: string
76
+ /** This group's key value. */
77
+ key: string
78
+ /** Zero-based depth (0 = top level). */
79
+ level: number
80
+ expanded: boolean
81
+ loading: boolean
82
+ /** Aggregate values keyed by column id, read from the group's response row. */
83
+ aggregates: Record<string, unknown>
84
+ /** The raw response row for this group (key + aggregates), for cell rendering. */
85
+ data: TData
86
+ }
87
+
88
+ export type ServerLeafRow<TData> = {
89
+ kind: 'leaf'
90
+ id: string
91
+ level: number
92
+ data: TData
43
93
  }
44
94
 
95
+ /**
96
+ * A "load more" affordance emitted at the end of a group whose children are
97
+ * only partially loaded (intra-group paging). Trigger `loadMoreChildren(path)`
98
+ * to fetch the next block.
99
+ */
100
+ export type ServerMoreRow = {
101
+ kind: 'more'
102
+ id: string
103
+ level: number
104
+ /** Path of the parent group whose children to load more of. */
105
+ path: string[]
106
+ /** How many children remain unloaded. */
107
+ remaining: number
108
+ loading: boolean
109
+ }
110
+
111
+ /**
112
+ * A subtotal / footer row emitted after an expanded group's children when
113
+ * `groupFooters` is on. Carries the group's aggregates a second time so a
114
+ * "Total" line sits under the detail.
115
+ */
116
+ export type ServerFooterRow<TData> = {
117
+ kind: 'footer'
118
+ id: string
119
+ level: number
120
+ path: string[]
121
+ /** The group this footer totals (its key). */
122
+ key: string
123
+ aggregates: Record<string, unknown>
124
+ /** The group's response row (key + aggregates), so value columns show totals. */
125
+ data: TData
126
+ }
127
+
128
+ /** A placeholder row shown while a block of children is being fetched. */
129
+ export type ServerSkeletonRow = {
130
+ kind: 'skeleton'
131
+ id: string
132
+ level: number
133
+ }
134
+
135
+ /** A row in the flattened server-side group/tree display list. */
136
+ export type ServerDisplayRow<TData> =
137
+ | ServerGroupRow<TData>
138
+ | ServerLeafRow<TData>
139
+ | ServerMoreRow
140
+ | ServerFooterRow<TData>
141
+ | ServerSkeletonRow
142
+
45
143
  export type ServerResult<TData> = {
46
144
  rows: ReadonlyArray<TData>
47
145
  /** Total row count after filtering (for the pager). */
@@ -161,6 +259,10 @@ export function createServerDataSource<TData>(
161
259
  pageSize: state.pageSize,
162
260
  sortModel: state.sortModel,
163
261
  filterModel: state.filterModel,
262
+ // Flat mode: no grouping. Group mode lives in createServerGroupModel.
263
+ groupBy: [],
264
+ groupKeys: [],
265
+ aggregations: [],
164
266
  })
165
267
  if (disposed || id !== requestSeq) return // stale
166
268
  state.rows = result.rows