@leavepulse/ui 0.44.0 → 0.45.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (265) hide show
  1. package/README.md +49 -3
  2. package/dist/assets/{LpCommandPalette-DCP5g2ik.css → LpCommandPalette-nGNnzXqQ.css} +21 -21
  3. package/dist/assets/{LpRollingText-CR1mb0Vt.css → LpRollingText-BGnE6q9j.css} +3 -0
  4. package/dist/assets/{LpShortcutsDialog-ChUyU7oV.css → LpShortcutsDialog-CqYX3yy6.css} +28 -7
  5. package/dist/assets/{LpTable-DDQNdf86.css → LpTable-CPwWxTJS.css} +49 -9
  6. package/dist/chunks/{ContextMenuItems-CrfeNPWT.js → ContextMenuItems-BtKU7074.js} +2 -1
  7. package/dist/chunks/{LayoutCanvas-D-jPOAvg.js → LayoutCanvas-BkaGXTjx.js} +1 -1
  8. package/dist/chunks/{LayoutNode-D8Xy9N-o.js → LayoutNode-B3_9E1Xa.js} +9 -5
  9. package/dist/chunks/{LpActionBar-BbwCF6l5.js → LpActionBar-CnfFVIwC.js} +3 -3
  10. package/dist/chunks/{LpAddressInput-BrOqkZqg.js → LpAddressInput-BwX8uo4_.js} +7 -7
  11. package/dist/chunks/{LpAlert-DkOIjsbq.js → LpAlert-B6ilrM7T.js} +1 -1
  12. package/dist/chunks/{LpAppShell-BUKPcHco.js → LpAppShell-C53_RaGF.js} +4 -4
  13. package/dist/chunks/{LpAutocomplete-DxV3Y9h4.js → LpAutocomplete-C8IgSMsi.js} +2 -1
  14. package/dist/chunks/{LpAvatar-ClBbEYZN.js → LpAvatar-C1XStdOo.js} +3 -3
  15. package/dist/chunks/{LpBreadcrumbs-B8IJgFIc.js → LpBreadcrumbs-CQJd73Gm.js} +1 -1
  16. package/dist/chunks/{LpButton-kqJBHIIb.js → LpButton-CKSwC6Mu.js} +1 -1
  17. package/dist/chunks/{LpCalendar-B7Ko5RdR.js → LpCalendar-DrA2McTU.js} +1 -1
  18. package/dist/chunks/{LpCard-CpRByR0q.js → LpCard-C2IvucmX.js} +1 -1
  19. package/dist/chunks/{LpCheckbox-DpqchzH4.js → LpCheckbox-Bkj13CbW.js} +1 -1
  20. package/dist/chunks/{LpCodeBlock-DeHJPq7p.js → LpCodeBlock-ca7ANFyW.js} +1 -1
  21. package/dist/chunks/{LpColorPicker-Bhf1qxhB.js → LpColorPicker-zz4VGkG4.js} +46 -20
  22. package/dist/chunks/{LpConfirmDialog-CIUOSnWo.js → LpConfirmDialog-DCw5jR1t.js} +3 -3
  23. package/dist/chunks/{LpConfirmHost-CDm0Wtpv.js → LpConfirmHost-CbywMpMP.js} +1 -1
  24. package/dist/chunks/{LpContextMenu-DQw5dGfG.js → LpContextMenu-BqkAYa9X.js} +2 -1
  25. package/dist/chunks/{LpDatePicker-Drirx1AK.js → LpDatePicker-DuusgT69.js} +13 -9
  26. package/dist/chunks/LpDateRangePicker-DHeuznfC.js +208 -0
  27. package/dist/chunks/{LpDisclosure-ChQYmjlR.js → LpDisclosure-Cc23-JOT.js} +1 -1
  28. package/dist/chunks/{LpDrawer-bScx-KMO.js → LpDrawer-Dt4aB4Fr.js} +2 -2
  29. package/dist/chunks/{LpDropdownMenu-DJpoqRCb.js → LpDropdownMenu-DdJGQzPn.js} +2 -1
  30. package/dist/chunks/{LpEmptyState-Dsdqz1Wj.js → LpEmptyState-BJbZXC8D.js} +1 -1
  31. package/dist/chunks/LpFieldNotice-wtieLUTj.js +64 -0
  32. package/dist/chunks/{LpFileTree-CSI_5SK2.js → LpFileTree-CNurOvkV.js} +3 -3
  33. package/dist/chunks/{LpFileTreeNode-B4MiSQX2.js → LpFileTreeNode-D_qRRdsH.js} +3 -3
  34. package/dist/chunks/{LpFormField-CIk5qosh.js → LpFormField-CtVYj6tO.js} +29 -15
  35. package/dist/chunks/{LpIcon-CCnX5_2j.js → LpIcon-DYtaid0K.js} +20 -6
  36. package/dist/chunks/{LpInput-C0e8y8_d.js → LpInput-D-YGQbEv.js} +39 -16
  37. package/dist/chunks/{LpLightbox-Mr0W_6HK.js → LpLightbox-DSDahF23.js} +1 -1
  38. package/dist/chunks/{LpLogViewer-YBOaFnc_.js → LpLogViewer-KypbgOyo.js} +252 -58
  39. package/dist/chunks/{LpMapPicker-NUzS9e37.js → LpMapPicker-Cc84LaM3.js} +1 -1
  40. package/dist/chunks/{LpMediaGallery-DfJmMW0I.js → LpMediaGallery-YKr-cQPN.js} +2 -2
  41. package/dist/chunks/{LpModal-DPwGKBPv.js → LpModal-DMMDQHAu.js} +3 -3
  42. package/dist/chunks/{LpModalNav-DPg5H9f3.js → LpModalNav-BVPDyIup.js} +4 -4
  43. package/dist/chunks/{LpNotificationBell-t5yn-siX.js → LpNotificationBell-CCwyJP5C.js} +26 -14
  44. package/dist/chunks/{LpNumberField-DWnQKktS.js → LpNumberField-B77O-z28.js} +1 -1
  45. package/dist/chunks/{LpPagination-DFngX7Xo.js → LpPagination-BcDlo3r_.js} +1 -1
  46. package/dist/chunks/{LpPasswordInput-CWVDuBJ5.js → LpPasswordInput-eKzQhbQP.js} +2 -2
  47. package/dist/chunks/{LpPhoneInput-CD-ZTeSd.js → LpPhoneInput-BCbrrhgE.js} +126 -23
  48. package/dist/chunks/{LpPie-BLco31Nx.js → LpPie-BEJ2SfI6.js} +9 -10
  49. package/dist/chunks/{LpPopover-p_e_shN3.js → LpPopover-DCKeqiVn.js} +1 -0
  50. package/dist/chunks/LpRangeCalendar-DZuaRV0W.js +331 -0
  51. package/dist/chunks/{LpRollingText-CM5gkSeF.js → LpRollingText-DB7upf-5.js} +1 -1
  52. package/dist/chunks/{LpScrollArea-D8xyKXcF.js → LpScrollArea-Bry1fdOM.js} +14 -2
  53. package/dist/chunks/{LpSection-aM6J_u51.js → LpSection-tKEH0jYf.js} +1 -1
  54. package/dist/chunks/{LpSegmented-Dejd7cIx.js → LpSegmented-C09EEam2.js} +1 -1
  55. package/dist/chunks/{LpSelect-DrRD9I7L.js → LpSelect-DNIL6MB9.js} +20 -23
  56. package/dist/chunks/{LpSidebar-BgwUNWpJ.js → LpSidebar-CQNB0-yU.js} +3 -3
  57. package/dist/chunks/{LpSidebarNav-Bqxz8aWT.js → LpSidebarNav-kx-LdqNU.js} +3 -3
  58. package/dist/chunks/{LpStat-dXtyrdX9.js → LpStat-B-7udBRP.js} +1 -1
  59. package/dist/chunks/{LpStepper-Bk-XaQYU.js → LpStepper-C7XiVKZj.js} +34 -19
  60. package/dist/chunks/{LpSwitch-B1aLKulj.js → LpSwitch-OrcOJX9m.js} +1 -1
  61. package/dist/chunks/LpTableFilter-BV8PpLM9.js +158 -0
  62. package/dist/chunks/{LpTabs-_qMVaZJ6.js → LpTabs-29iW1XOx.js} +1 -1
  63. package/dist/chunks/LpTagsInput-D1SuqbhB.js +300 -0
  64. package/dist/chunks/{LpTextarea-yP8hGedR.js → LpTextarea-uuScWo6-.js} +1 -1
  65. package/dist/chunks/{LpThemeProvider-Wjm7Tuit.js → LpThemeProvider-Be4r2TQX.js} +1 -1
  66. package/dist/chunks/{LpThemeSwitcher-CKLc10KZ.js → LpThemeSwitcher-B4aVPbNC.js} +19 -22
  67. package/dist/chunks/{LpTimeField-C5HRgS5H.js → LpTimeField-Cqe7fXnh.js} +1 -1
  68. package/dist/chunks/{LpToaster--oT6lfhL.js → LpToaster-DpJvoCOh.js} +37 -3
  69. package/dist/chunks/{LpTooltip-CBdzeKNf.js → LpTooltip-CXVKcOXT.js} +3 -2
  70. package/dist/chunks/{LpTopologyCanvas-DocsLal3.js → LpTopologyCanvas-6ozNrQKh.js} +2 -1
  71. package/dist/chunks/{LpUptimeBar-DLtxOMRy.js → LpUptimeBar-ugcv25xj.js} +2 -2
  72. package/dist/chunks/icons-CkA0njzm.js +43 -0
  73. package/dist/chunks/{useTheme-C8JHUlPM.js → useTheme-DJm1JSsY.js} +47 -50
  74. package/dist/component-names.d.ts +1 -1
  75. package/dist/components/ContextMenuItems.vue.js +1 -1
  76. package/dist/components/LayoutCanvas.vue.js +1 -1
  77. package/dist/components/LayoutNode.vue.js +1 -1
  78. package/dist/components/LpActionBar.vue.js +1 -1
  79. package/dist/components/LpAddressInput.vue.js +1 -1
  80. package/dist/components/LpAlert.vue.js +1 -1
  81. package/dist/components/LpAppShell.vue.js +1 -1
  82. package/dist/components/LpAutocomplete.vue.js +1 -1
  83. package/dist/components/LpAvatar.vue.js +1 -1
  84. package/dist/components/LpBreadcrumbs.vue.js +1 -1
  85. package/dist/components/LpButton.vue.d.ts +2 -2
  86. package/dist/components/LpButton.vue.js +1 -1
  87. package/dist/components/LpCalendar.vue.js +1 -1
  88. package/dist/components/LpCard.vue.js +1 -1
  89. package/dist/components/LpChart.vue.d.ts +16 -1
  90. package/dist/components/LpChart.vue.js +63 -5
  91. package/dist/components/LpCheckbox.vue.js +1 -1
  92. package/dist/components/LpCodeBlock.vue.js +1 -1
  93. package/dist/components/LpColorPicker.vue.d.ts +2 -2
  94. package/dist/components/LpColorPicker.vue.js +1 -1
  95. package/dist/components/LpCommandPalette.vue.d.ts +6 -0
  96. package/dist/components/LpCommandPalette.vue.js +61 -10
  97. package/dist/components/LpConfirmDialog.vue.js +1 -1
  98. package/dist/components/LpConfirmHost.vue.js +1 -1
  99. package/dist/components/LpContextMenu.vue.js +1 -1
  100. package/dist/components/LpDatePicker.vue.js +1 -1
  101. package/dist/components/LpDateRangePicker.vue.d.ts +60 -0
  102. package/dist/components/LpDateRangePicker.vue.js +4 -0
  103. package/dist/components/LpDisclosure.vue.js +1 -1
  104. package/dist/components/LpDrawer.vue.js +1 -1
  105. package/dist/components/LpDropdownMenu.vue.js +1 -1
  106. package/dist/components/LpDropzone.vue.js +1 -1
  107. package/dist/components/LpEmptyState.vue.js +1 -1
  108. package/dist/components/LpFieldNotice.vue.d.ts +8 -0
  109. package/dist/components/LpFieldNotice.vue.js +4 -0
  110. package/dist/components/LpFileTree.vue.js +1 -1
  111. package/dist/components/LpFileTreeNode.vue.js +1 -1
  112. package/dist/components/LpFormField.vue.d.ts +4 -1
  113. package/dist/components/LpFormField.vue.js +1 -1
  114. package/dist/components/LpIcon.vue.d.ts +0 -1
  115. package/dist/components/LpIcon.vue.js +1 -1
  116. package/dist/components/LpImageEditor.vue.js +2 -2
  117. package/dist/components/LpInput.vue.d.ts +19 -0
  118. package/dist/components/LpInput.vue.js +1 -1
  119. package/dist/components/LpLightbox.vue.js +1 -1
  120. package/dist/components/LpLogViewer.vue.d.ts +52 -1
  121. package/dist/components/LpLogViewer.vue.js +1 -1
  122. package/dist/components/LpMapPicker.vue.js +1 -1
  123. package/dist/components/LpMediaGallery.vue.js +1 -1
  124. package/dist/components/LpModal.vue.js +1 -1
  125. package/dist/components/LpModalNav.vue.js +1 -1
  126. package/dist/components/LpNotificationBell.vue.js +1 -1
  127. package/dist/components/LpNumberField.vue.js +1 -1
  128. package/dist/components/LpPagination.vue.js +1 -1
  129. package/dist/components/LpPasswordInput.vue.js +1 -1
  130. package/dist/components/LpPhoneInput.vue.d.ts +13 -0
  131. package/dist/components/LpPhoneInput.vue.js +1 -1
  132. package/dist/components/LpPie.vue.js +1 -1
  133. package/dist/components/LpPopover.vue.js +1 -1
  134. package/dist/components/LpProgress.vue.d.ts +1 -1
  135. package/dist/components/LpRangeCalendar.vue.d.ts +51 -0
  136. package/dist/components/LpRangeCalendar.vue.js +4 -0
  137. package/dist/components/LpRollingText.vue.d.ts +1 -1
  138. package/dist/components/LpRollingText.vue.js +1 -1
  139. package/dist/components/LpScrollArea.vue.d.ts +2 -2
  140. package/dist/components/LpScrollArea.vue.js +1 -1
  141. package/dist/components/LpSection.vue.js +1 -1
  142. package/dist/components/LpSegmented.vue.js +1 -1
  143. package/dist/components/LpSelect.vue.js +1 -1
  144. package/dist/components/LpShortcutsDialog.vue.d.ts +6 -0
  145. package/dist/components/LpShortcutsDialog.vue.js +56 -14
  146. package/dist/components/LpSidebar.vue.js +1 -1
  147. package/dist/components/LpSidebarNav.vue.js +1 -1
  148. package/dist/components/LpStat.vue.js +1 -1
  149. package/dist/components/LpStepper.vue.js +1 -1
  150. package/dist/components/LpSwitch.vue.js +1 -1
  151. package/dist/components/LpTable.vue.d.ts +84 -2
  152. package/dist/components/LpTable.vue.js +481 -107
  153. package/dist/components/LpTableFilter.vue.d.ts +31 -0
  154. package/dist/components/LpTableFilter.vue.js +4 -0
  155. package/dist/components/LpTabs.vue.js +1 -1
  156. package/dist/components/LpTagsInput.vue.d.ts +77 -0
  157. package/dist/components/LpTagsInput.vue.js +4 -0
  158. package/dist/components/LpTextarea.vue.js +1 -1
  159. package/dist/components/LpThemeProvider.vue.js +1 -1
  160. package/dist/components/LpThemeSwitcher.vue.d.ts +2 -2
  161. package/dist/components/LpThemeSwitcher.vue.js +1 -1
  162. package/dist/components/LpTimeField.vue.js +1 -1
  163. package/dist/components/LpToaster.vue.js +1 -1
  164. package/dist/components/LpTooltip.vue.js +1 -1
  165. package/dist/components/LpTopologyCanvas.vue.js +1 -1
  166. package/dist/components/LpUptimeBar.vue.js +1 -1
  167. package/dist/components/chart.js +3 -2
  168. package/dist/components/commandSearch.js +3 -0
  169. package/dist/components/dateRange.d.ts +43 -0
  170. package/dist/components/dateRange.js +76 -0
  171. package/dist/components/exportData.d.ts +58 -0
  172. package/dist/components/exportData.js +165 -0
  173. package/dist/components/logSearch.d.ts +18 -0
  174. package/dist/components/logSearch.js +36 -0
  175. package/dist/components/phone.d.ts +41 -0
  176. package/dist/components/phone.js +80 -0
  177. package/dist/components/tableFilter.d.ts +36 -0
  178. package/dist/components/tableFilter.js +84 -0
  179. package/dist/components/tags.d.ts +20 -0
  180. package/dist/components/tags.js +37 -0
  181. package/dist/composables/useField.d.ts +4 -0
  182. package/dist/composables/useFieldNotice.d.ts +17 -0
  183. package/dist/composables/useFieldNotice.js +28 -0
  184. package/dist/composables/useForm.d.ts +53 -0
  185. package/dist/composables/useForm.js +207 -0
  186. package/dist/composables/useHotkeys.d.ts +65 -5
  187. package/dist/composables/useHotkeys.js +170 -9
  188. package/dist/composables/useInputMask.d.ts +59 -0
  189. package/dist/composables/useInputMask.js +170 -0
  190. package/dist/composables/usePaintSelect.d.ts +22 -0
  191. package/dist/composables/usePaintSelect.js +169 -0
  192. package/dist/composables/useShift.js +7 -2
  193. package/dist/icons-all.d.ts +1 -0
  194. package/dist/icons-all.js +3 -0
  195. package/dist/icons.d.ts +14 -1
  196. package/dist/index.d.ts +29 -3
  197. package/dist/index.js +195 -138
  198. package/dist/kit-icons.d.ts +2 -0
  199. package/dist/theme/backdrop.d.ts +12 -0
  200. package/dist/theme/presets.d.ts +0 -2
  201. package/package.json +13 -4
  202. package/src/component-names.ts +4 -0
  203. package/src/components/ContextMenuItems.vue +1 -1
  204. package/src/components/LayoutNode.vue +11 -2
  205. package/src/components/LpActionBar.vue +1 -1
  206. package/src/components/LpAutocomplete.vue +1 -0
  207. package/src/components/LpAvatar.vue +2 -2
  208. package/src/components/LpButton.vue +1 -1
  209. package/src/components/LpChart.vue +80 -1
  210. package/src/components/LpColorPicker.vue +34 -1
  211. package/src/components/LpCommandPalette.vue +81 -7
  212. package/src/components/LpContextMenu.vue +1 -1
  213. package/src/components/LpDatePicker.vue +8 -3
  214. package/src/components/LpDateRangePicker.vue +224 -0
  215. package/src/components/LpDropdownMenu.vue +1 -0
  216. package/src/components/LpFieldNotice.vue +65 -0
  217. package/src/components/LpFormField.vue +33 -4
  218. package/src/components/LpIcon.vue +22 -4
  219. package/src/components/LpInput.vue +46 -6
  220. package/src/components/LpLogViewer.vue +225 -22
  221. package/src/components/LpModal.vue +1 -1
  222. package/src/components/LpNotificationBell.vue +15 -7
  223. package/src/components/LpPhoneInput.vue +179 -20
  224. package/src/components/LpPie.vue +8 -5
  225. package/src/components/LpPopover.vue +1 -0
  226. package/src/components/LpRangeCalendar.vue +365 -0
  227. package/src/components/LpRollingText.vue +3 -0
  228. package/src/components/LpScrollArea.vue +22 -2
  229. package/src/components/LpSelect.vue +0 -0
  230. package/src/components/LpShortcutsDialog.vue +77 -8
  231. package/src/components/LpStepper.vue +23 -10
  232. package/src/components/LpSwitch.vue +1 -1
  233. package/src/components/LpTable.vue +584 -65
  234. package/src/components/LpTableFilter.vue +175 -0
  235. package/src/components/LpTagsInput.vue +364 -0
  236. package/src/components/LpThemeSwitcher.vue +19 -23
  237. package/src/components/LpToaster.vue +49 -1
  238. package/src/components/LpTooltip.vue +9 -2
  239. package/src/components/LpTopologyCanvas.vue +7 -1
  240. package/src/components/chart.ts +5 -3
  241. package/src/components/commandSearch.ts +6 -0
  242. package/src/components/dateRange.ts +134 -0
  243. package/src/components/exportData.ts +228 -0
  244. package/src/components/logSearch.ts +46 -0
  245. package/src/components/phone.ts +140 -0
  246. package/src/components/tableFilter.ts +122 -0
  247. package/src/components/tags.ts +62 -0
  248. package/src/composables/useField.ts +4 -0
  249. package/src/composables/useFieldNotice.ts +59 -0
  250. package/src/composables/useForm.ts +314 -0
  251. package/src/composables/useHotkeys.ts +269 -13
  252. package/src/composables/useInputMask.ts +254 -0
  253. package/src/composables/usePaintSelect.ts +243 -0
  254. package/src/composables/useShift.ts +13 -2
  255. package/src/iconSubset.d.mts +10 -0
  256. package/src/iconSubset.mjs +51 -0
  257. package/src/icons-all.ts +10 -0
  258. package/src/icons.ts +59 -8
  259. package/src/index.ts +37 -3
  260. package/src/kit-icons.ts +5 -0
  261. package/src/nuxt.ts +30 -2
  262. package/src/runtime/theme.plugin.ts +2 -2
  263. package/src/theme/backdrop.ts +69 -0
  264. package/src/theme/presets.ts +6 -64
  265. package/src/tokens/tokens.css +46 -0
@@ -0,0 +1,243 @@
1
+ import { onBeforeUnmount, onMounted, readonly, ref, toValue, type MaybeRefOrGetter, type Ref } from "vue"
2
+ import { useHotkeys, type HotkeyHelp } from "./useHotkeys"
3
+
4
+ /*
5
+ * Paint selection: press on one item's tick and sweep across the others, and
6
+ * every item the pointer passes takes the state the first one is switching
7
+ * to. Starting on an unticked item ticks the run, starting on a ticked one
8
+ * clears it, and sweeping back un-paints what the stroke covered, restoring
9
+ * the items as they were before it. Near the edge of the scrolling box the list
10
+ * scrolls on its own, so a stroke can run past what is visible.
11
+ *
12
+ * Items are found in the DOM by `data-paint-key`, in document order, so the
13
+ * run follows what the user sees (sorted, filtered, collapsed groups skipped).
14
+ * A mouse or pen paints at once. A finger holds still for HOLD_MS first, so a
15
+ * swipe through the list still scrolls it.
16
+ *
17
+ * The press itself ticks the first item, so the click the browser sends after
18
+ * the stroke is swallowed before the item's own handler sees it; otherwise the
19
+ * first item would toggle back.
20
+ *
21
+ * `onPointerDown(event, key, { hold })` makes any pointer hold first. That is
22
+ * how a list without visible ticks enters selection: a quick click on the row
23
+ * stays the row's click, a long press selects it and the same press goes on
24
+ * painting.
25
+ */
26
+ export interface UsePaintSelectOptions<K> {
27
+ /** The element that holds the items. */
28
+ root: Ref<HTMLElement | null>
29
+ selection: () => readonly K[]
30
+ set: (keys: K[]) => void
31
+ /** Turn painting off without unmounting (e.g. selection mode is off). */
32
+ enabled?: MaybeRefOrGetter<boolean>
33
+ /** Map an item's `data-paint-key` back to its key. Defaults to the string itself. */
34
+ resolve?: (raw: string) => K | undefined
35
+ /** Every key, for Ctrl+A while the focus is inside `root`. Omit to leave Ctrl+A alone. */
36
+ selectAll?: () => K[]
37
+ /** How Ctrl+A is listed in the shortcuts reference. */
38
+ help?: MaybeRefOrGetter<HotkeyHelp | undefined>
39
+ }
40
+
41
+ const HOLD_MS = 320
42
+ const SLOP_PX = 8
43
+ const EDGE_PX = 40
44
+ const SCROLL_STEP = 14
45
+
46
+ interface Stroke<K> {
47
+ keys: K[]
48
+ anchor: number
49
+ paint: boolean
50
+ before: Set<K>
51
+ x: number
52
+ y: number
53
+ scroller: HTMLElement | null
54
+ }
55
+
56
+ function scrollParent(el: HTMLElement | null): HTMLElement | null {
57
+ for (let node = el?.parentElement; node; node = node.parentElement) {
58
+ const { overflowY } = getComputedStyle(node)
59
+ if ((overflowY === "auto" || overflowY === "scroll") && node.scrollHeight > node.clientHeight) return node
60
+ }
61
+ return null
62
+ }
63
+
64
+ export function usePaintSelect<K = string>(options: UsePaintSelectOptions<K>) {
65
+ const resolve = options.resolve ?? ((raw: string) => raw as unknown as K)
66
+ let stroke: Stroke<K> | null = null
67
+ let pending: { key: K; pointerId: number; x: number; y: number; timer: ReturnType<typeof setTimeout> } | null = null
68
+ let swallowClick = false
69
+ let frame = 0
70
+ /** True while a stroke is painting, for UI that reacts to it (a tick column revealing). */
71
+ const painting = ref(false)
72
+
73
+ const enabled = () => toValue(options.enabled) ?? true
74
+
75
+ function keysInView(): K[] {
76
+ const items = options.root.value?.querySelectorAll<HTMLElement>("[data-paint-key]") ?? []
77
+ const out: K[] = []
78
+ for (const item of items) {
79
+ if (item.offsetParent === null) continue
80
+ const key = resolve(item.dataset.paintKey ?? "")
81
+ if (key !== undefined) out.push(key)
82
+ }
83
+ return out
84
+ }
85
+
86
+ function keyAt(x: number, y: number): K | undefined {
87
+ const item = document.elementFromPoint(x, y)?.closest<HTMLElement>("[data-paint-key]")
88
+ if (!item || !options.root.value?.contains(item)) return undefined
89
+ return resolve(item.dataset.paintKey ?? "")
90
+ }
91
+
92
+ function extend() {
93
+ if (!stroke) return
94
+ const key = keyAt(stroke.x, stroke.y)
95
+ const at = key === undefined ? -1 : stroke.keys.indexOf(key)
96
+ if (at < 0) return
97
+ const [lo, hi] = at < stroke.anchor ? [at, stroke.anchor] : [stroke.anchor, at]
98
+ const next = new Set(stroke.before)
99
+ for (let i = lo; i <= hi; i++) {
100
+ const k = stroke.keys[i]!
101
+ if (stroke.paint) next.add(k)
102
+ else next.delete(k)
103
+ }
104
+ options.set([...next])
105
+ }
106
+
107
+ function tick() {
108
+ frame = 0
109
+ if (!stroke) return
110
+ const box = stroke.scroller?.getBoundingClientRect() ?? { top: 0, bottom: window.innerHeight }
111
+ const delta = stroke.y > box.bottom - EDGE_PX ? SCROLL_STEP : stroke.y < box.top + EDGE_PX ? -SCROLL_STEP : 0
112
+ if (delta) {
113
+ if (stroke.scroller) stroke.scroller.scrollTop += delta
114
+ else window.scrollBy(0, delta)
115
+ extend()
116
+ }
117
+ frame = requestAnimationFrame(tick)
118
+ }
119
+
120
+ function begin(key: K, x: number, y: number) {
121
+ const keys = keysInView()
122
+ const anchor = keys.indexOf(key)
123
+ if (anchor < 0) return
124
+ const before = new Set(options.selection())
125
+ stroke = { keys, anchor, paint: !before.has(key), before, x, y, scroller: scrollParent(options.root.value) }
126
+ painting.value = true
127
+ // A sweep over text would otherwise select it, and a hold that started
128
+ // before the stroke may already have.
129
+ window.getSelection()?.removeAllRanges()
130
+ if (options.root.value) options.root.value.style.userSelect = "none"
131
+ extend()
132
+ if (!frame) frame = requestAnimationFrame(tick)
133
+ }
134
+
135
+ function cancelPending() {
136
+ if (pending) clearTimeout(pending.timer)
137
+ pending = null
138
+ }
139
+
140
+ /** Bind to `pointerdown` on the item's tick (or the whole item). */
141
+ function onPointerDown(event: PointerEvent, key: K, behaviour: { hold?: number } = {}) {
142
+ if (!enabled() || event.button !== 0) return
143
+ cancelPending()
144
+ if (behaviour.hold === undefined && event.pointerType !== "touch") {
145
+ // Keeps the press from starting a text selection or moving focus mid-stroke.
146
+ event.preventDefault()
147
+ begin(key, event.clientX, event.clientY)
148
+ return
149
+ }
150
+ const { pointerId, clientX: x, clientY: y } = event
151
+ pending = {
152
+ key,
153
+ pointerId,
154
+ x,
155
+ y,
156
+ timer: setTimeout(() => {
157
+ pending = null
158
+ begin(key, x, y)
159
+ navigator.vibrate?.(8)
160
+ }, behaviour.hold ?? HOLD_MS),
161
+ }
162
+ }
163
+
164
+ function onMove(event: PointerEvent) {
165
+ if (pending && event.pointerId === pending.pointerId) {
166
+ if (Math.hypot(event.clientX - pending.x, event.clientY - pending.y) > SLOP_PX) cancelPending()
167
+ return
168
+ }
169
+ if (!stroke) return
170
+ stroke.x = event.clientX
171
+ stroke.y = event.clientY
172
+ extend()
173
+ }
174
+
175
+ function onUp() {
176
+ cancelPending()
177
+ if (!stroke) return
178
+ stroke = null
179
+ painting.value = false
180
+ if (options.root.value) options.root.value.style.userSelect = ""
181
+ if (frame) cancelAnimationFrame(frame)
182
+ frame = 0
183
+ swallowClick = true
184
+ setTimeout(() => (swallowClick = false), 0)
185
+ }
186
+
187
+ function onClickCapture(event: MouseEvent) {
188
+ if (!swallowClick) return
189
+ swallowClick = false
190
+ event.stopPropagation()
191
+ event.preventDefault()
192
+ }
193
+
194
+ // A long press is also how a finger asks for the context menu; once it has
195
+ // turned into painting, that menu would open over the stroke.
196
+ function onContextMenu(event: Event) {
197
+ if (!stroke && !swallowClick) return
198
+ event.preventDefault()
199
+ event.stopPropagation()
200
+ }
201
+
202
+ // A finger that has started painting must not scroll the page under it.
203
+ function onTouchMove(event: TouchEvent) {
204
+ if (stroke) event.preventDefault()
205
+ }
206
+
207
+ useHotkeys(
208
+ () =>
209
+ options.selectAll && enabled()
210
+ ? [
211
+ {
212
+ key: "a",
213
+ code: "KeyA",
214
+ ctrl: true,
215
+ help: toValue(options.help),
216
+ handler: () => options.set(options.selectAll!()),
217
+ },
218
+ ]
219
+ : [],
220
+ { scope: options.root },
221
+ )
222
+
223
+ onMounted(() => {
224
+ window.addEventListener("pointermove", onMove)
225
+ window.addEventListener("pointerup", onUp)
226
+ window.addEventListener("pointercancel", onUp)
227
+ window.addEventListener("click", onClickCapture, true)
228
+ window.addEventListener("contextmenu", onContextMenu, true)
229
+ options.root.value?.addEventListener("touchmove", onTouchMove, { passive: false })
230
+ })
231
+ onBeforeUnmount(() => {
232
+ onUp()
233
+ swallowClick = false
234
+ window.removeEventListener("pointermove", onMove)
235
+ window.removeEventListener("pointerup", onUp)
236
+ window.removeEventListener("pointercancel", onUp)
237
+ window.removeEventListener("click", onClickCapture, true)
238
+ window.removeEventListener("contextmenu", onContextMenu, true)
239
+ options.root.value?.removeEventListener("touchmove", onTouchMove)
240
+ })
241
+
242
+ return { onPointerDown, painting: readonly(painting) }
243
+ }
@@ -87,6 +87,13 @@ export function useShift(
87
87
  /** Where the box last settled, so a retune has a size to ease FROM. */
88
88
  let lastHeight = 0
89
89
  let lastWidth = 0
90
+ /**
91
+ * Whether the last measurement was of a box actually laid out. An empty box
92
+ * in the flow measures 0 and is a real size to grow from (a bar or message
93
+ * appearing in it); a box under `display: none` also measures 0 but has no
94
+ * layout yet, and growing from that would animate content in from nothing.
95
+ */
96
+ let laidOut = false
90
97
  /** True while a tween owns the size, so observers don't cancel it midway. */
91
98
  let inFlight = false
92
99
  /** When the in-flight tween started, to tell a duplicate from a follow-up. */
@@ -192,6 +199,8 @@ export function useShift(
192
199
  restoreScroll(tops)
193
200
  lastHeight = toHeight
194
201
  lastWidth = toWidth
202
+ const wasLaidOut = laidOut
203
+ laidOut = node.getClientRects().length > 0
195
204
 
196
205
  // Nothing moved on either axis, so there is nothing to ease — and leaving
197
206
  // the size unset keeps the box free to size itself.
@@ -203,8 +212,8 @@ export function useShift(
203
212
  // different thing it was meant to catch: the box was not in the layout yet,
204
213
  // so there is no size to ease out of.
205
214
  const movesHeight =
206
- wantsHeight() && fromHeight !== 0 && toHeight !== fromHeight
207
- const movesWidth = wantsWidth() && fromWidth !== 0 && toWidth !== fromWidth
215
+ wantsHeight() && (fromHeight !== 0 || wasLaidOut) && toHeight !== fromHeight
216
+ const movesWidth = wantsWidth() && (fromWidth !== 0 || wasLaidOut) && toWidth !== fromWidth
208
217
  if (!movesHeight && !movesWidth) return
209
218
 
210
219
  if (movesHeight) node.style.height = `${fromHeight}px`
@@ -250,6 +259,7 @@ export function useShift(
250
259
  resizing.value = false
251
260
  lastHeight = 0
252
261
  lastWidth = 0
262
+ laidOut = false
253
263
  inFlight = false
254
264
  }
255
265
 
@@ -263,6 +273,7 @@ export function useShift(
263
273
 
264
274
  lastHeight = node.offsetHeight
265
275
  lastWidth = node.offsetWidth
276
+ laidOut = node.getClientRects().length > 0
266
277
  scrollHost = node
267
278
  node.addEventListener("scroll", rememberScroll, { capture: true, passive: true })
268
279
  if (wantsHeight()) node.style.height = `${lastHeight}px`
@@ -0,0 +1,10 @@
1
+ export interface IconCollection {
2
+ prefix: string
3
+ icons: Record<string, { body: string; width?: number; height?: number }>
4
+ aliases?: Record<string, { parent: string }>
5
+ width?: number
6
+ height?: number
7
+ }
8
+ export function namesInText(text: string): string[]
9
+ export function namesInDirs(dirs: string[]): Set<string>
10
+ export function subset(collection: IconCollection, names: Iterable<string>): IconCollection
@@ -0,0 +1,51 @@
1
+ // Shared by the kit's own icon generator and the Nuxt module's app scan: find
2
+ // "lucide:<name>" literals in source text and cut an iconify collection down to
3
+ // just those icons (aliases keep their parent).
4
+ import { readdirSync, readFileSync, statSync } from "node:fs"
5
+ import { join } from "node:path"
6
+
7
+ const NAME = /lucide:([a-z0-9]+(?:-[a-z0-9]+)*)/g
8
+ const SOURCE = /\.(vue|ts|tsx|js|jsx|mjs|md|html)$/
9
+ const SKIP = new Set(["node_modules", "dist", ".nuxt", ".output", ".git"])
10
+
11
+ export function namesInText(text) {
12
+ return [...text.matchAll(NAME)].map((m) => m[1])
13
+ }
14
+
15
+ export function namesInDirs(dirs) {
16
+ const names = new Set()
17
+ const walk = (dir) => {
18
+ let entries
19
+ try {
20
+ entries = readdirSync(dir)
21
+ } catch {
22
+ return
23
+ }
24
+ for (const entry of entries) {
25
+ if (SKIP.has(entry)) continue
26
+ const path = join(dir, entry)
27
+ if (statSync(path).isDirectory()) walk(path)
28
+ else if (SOURCE.test(entry)) for (const n of namesInText(readFileSync(path, "utf8"))) names.add(n)
29
+ }
30
+ }
31
+ for (const dir of dirs) walk(dir)
32
+ return names
33
+ }
34
+
35
+ export function subset(collection, names) {
36
+ const icons = {}
37
+ const aliases = {}
38
+ for (const name of [...names].sort()) {
39
+ if (collection.icons[name]) {
40
+ icons[name] = collection.icons[name]
41
+ continue
42
+ }
43
+ const alias = collection.aliases?.[name]
44
+ if (!alias) continue
45
+ aliases[name] = alias
46
+ if (collection.icons[alias.parent]) icons[alias.parent] = collection.icons[alias.parent]
47
+ }
48
+ const out = { prefix: collection.prefix, icons, width: collection.width, height: collection.height }
49
+ if (Object.keys(aliases).length) out.aliases = aliases
50
+ return out
51
+ }
@@ -0,0 +1,10 @@
1
+ import lucide from "@iconify-json/lucide/icons.json"
2
+ import type { IconifyJSON } from "@iconify/vue"
3
+ import { registerIconCollection } from "./icons"
4
+
5
+ /*
6
+ * Side-effect entry: `import "@leavepulse/ui/icons-all"` registers every lucide
7
+ * icon up front, for apps that render arbitrary icon names during SSR or want
8
+ * no late chunk. Costs the whole collection (~540 KB before compression).
9
+ */
10
+ registerIconCollection(lucide as IconifyJSON)
package/src/icons.ts CHANGED
@@ -1,11 +1,62 @@
1
- import { addCollection } from "@iconify/vue"
2
- import lucide from "@iconify-json/lucide/icons.json"
1
+ import { addCollection, addIcon, iconLoaded, type IconifyIcon, type IconifyJSON } from "@iconify/vue"
2
+ import { ref } from "vue"
3
+ import { KIT_ICONS } from "./kit-icons"
3
4
 
4
5
  /*
5
- * Register the lucide collection offline so <LpIcon name="lucide:*"> resolves
6
- * without hitting the iconify API (required for Tauri / air-gapped use).
7
- *
8
- * This pulls the whole lucide set. If bundle size matters in an app, replace
9
- * this with a curated subset via addIcon() — the LpIcon API is unchanged.
6
+ * Offline icons without the whole lucide set in every bundle. The kit registers
7
+ * only the icons its own components render (KIT_ICONS, generated at build). Any
8
+ * other "lucide:*" name an app renders loads the full collection as a separate
9
+ * chunk on first use, from the app's own bundle, never from the iconify API, so
10
+ * Tauri and air-gapped apps keep working. Apps that need every icon in the
11
+ * server render (or no late chunk at all) register them up front: the Nuxt
12
+ * module's `icons` option, `registerIcons`, or `import "@leavepulse/ui/icons-all"`.
10
13
  */
11
- addCollection(lucide as Parameters<typeof addCollection>[0])
14
+ addCollection(KIT_ICONS)
15
+
16
+ /** Bumped whenever icons are registered, so rendered icons re-resolve. */
17
+ export const iconsVersion = ref(0)
18
+
19
+ let lucide: Promise<IconifyJSON> | undefined
20
+
21
+ function loadLucide(): Promise<IconifyJSON> {
22
+ lucide ??= import("@iconify-json/lucide/icons.json").then((m) => (m.default ?? m) as IconifyJSON)
23
+ return lucide
24
+ }
25
+
26
+ /** Register a whole iconify collection (any prefix) for offline use. */
27
+ export function registerIconCollection(collection: IconifyJSON): void {
28
+ addCollection(collection)
29
+ iconsVersion.value++
30
+ }
31
+
32
+ /**
33
+ * Register lucide icons by name ("check" or "lucide:check") from the bundled
34
+ * collection. Resolves once they render offline.
35
+ */
36
+ export async function registerIcons(names: readonly string[]): Promise<void> {
37
+ const wanted = names.map((n) => n.replace(/^lucide:/, ""))
38
+ if (wanted.every((n) => iconLoaded(`lucide:${n}`))) return
39
+ const all = await loadLucide()
40
+ for (const name of wanted) {
41
+ const parent = all.aliases?.[name]?.parent
42
+ const body = all.icons[name] ?? (parent ? all.icons[parent] : undefined)
43
+ if (!body) continue
44
+ const icon: IconifyIcon = { width: all.width, height: all.height, ...body }
45
+ addIcon(`lucide:${name}`, icon)
46
+ }
47
+ iconsVersion.value++
48
+ }
49
+
50
+ /** Register the full lucide collection. */
51
+ export async function registerAllIcons(): Promise<void> {
52
+ registerIconCollection(await loadLucide())
53
+ }
54
+
55
+ const pending = new Set<string>()
56
+
57
+ /** A lucide name that isn't registered yet: load it from the bundled set. */
58
+ export function requestIcon(name: string): void {
59
+ if (pending.has(name) || typeof window === "undefined") return
60
+ pending.add(name)
61
+ void registerIcons([name]).finally(() => pending.delete(name))
62
+ }
package/src/index.ts CHANGED
@@ -37,6 +37,9 @@ export { default as LpCard } from "./components/LpCard.vue"
37
37
  export { default as LpChart } from "./components/LpChart.vue"
38
38
  export type { ChartPointEvent } from "./components/LpChart.vue"
39
39
  export type { ChartText } from "./components/LpChart.vue"
40
+ export type { ChartExportOptions } from "./components/LpChart.vue"
41
+ export { backgroundOf, csvField, downloadFile, fileStem, inlineSvg, resolveCssColor, svgToPng, toCsv } from "./components/exportData"
42
+ export type { CsvColumn, CsvOptions, RasterOptions } from "./components/exportData"
40
43
  export {
41
44
  CHART_PALETTE,
42
45
  axisTicks,
@@ -79,6 +82,12 @@ export type { ConfirmOptions } from "./components/confirm"
79
82
  export { default as LpContextMenu } from "./components/LpContextMenu.vue"
80
83
  export type { ContextMenuItemDef } from "./components/LpContextMenu.vue"
81
84
  export { default as LpDatePicker } from "./components/LpDatePicker.vue"
85
+ export { default as LpDateRangePicker } from "./components/LpDateRangePicker.vue"
86
+ export type { DateRangePickerLabels } from "./components/LpDateRangePicker.vue"
87
+ export { default as LpRangeCalendar } from "./components/LpRangeCalendar.vue"
88
+ export type { RangeCalendarLabels } from "./components/LpRangeCalendar.vue"
89
+ export { clampRange, defaultRangePresets, formatRange, normalizeRange, sameRange } from "./components/dateRange"
90
+ export type { DateRange, DateRangePreset, DateRangePresetLabels } from "./components/dateRange"
82
91
  export { default as LpDisclosure } from "./components/LpDisclosure.vue"
83
92
  export { default as LpDivider } from "./components/LpDivider.vue"
84
93
  export { default as LpDrawer } from "./components/LpDrawer.vue"
@@ -102,8 +111,10 @@ export {
102
111
  subtreeIds,
103
112
  subtreeSize,
104
113
  } from "./components/fileTree"
114
+ export { default as LpFieldNotice } from "./components/LpFieldNotice.vue"
105
115
  export { default as LpFormField } from "./components/LpFormField.vue"
106
116
  export { default as LpIcon } from "./components/LpIcon.vue"
117
+ export { iconsVersion, registerAllIcons, registerIconCollection, registerIcons } from "./icons"
107
118
  export { default as LpImageEditor } from "./components/LpImageEditor.vue"
108
119
  export { default as LpInfraNode } from "./components/LpInfraNode.vue"
109
120
  export type { InfraNodeData } from "./components/LpInfraNode.vue"
@@ -116,6 +127,7 @@ export { default as LpLink } from "./components/LpLink.vue"
116
127
  export { default as LpLogViewer } from "./components/LpLogViewer.vue"
117
128
  export type { LogLevel, LogLine } from "./components/LpLogViewer.vue"
118
129
  export type { LogViewerLabels } from "./components/LpLogViewer.vue"
130
+ export { countLevels, matchPositions, matchesTerm, ringWindow, stepMatch } from "./components/logSearch"
119
131
  export { default as LpMediaGallery } from "./components/LpMediaGallery.vue"
120
132
  export { default as LpModal } from "./components/LpModal.vue"
121
133
  export { default as LpModalNav } from "./components/LpModalNav.vue"
@@ -167,11 +179,16 @@ export { default as LpSwitch } from "./components/LpSwitch.vue"
167
179
  export { default as LpTable } from "./components/LpTable.vue"
168
180
  export type { SortState, TableColumn, TablePage, TableQuery } from "./components/LpTable.vue"
169
181
  export type { TableLabels } from "./components/LpTable.vue"
182
+ export type { TableExportOptions } from "./components/LpTable.vue"
170
183
  export { compareValues } from "./components/tableSort"
171
184
  export { default as LpTableOfContents } from "./components/LpTableOfContents.vue"
172
185
  export type { TocLink } from "./components/LpTableOfContents.vue"
173
186
  export { default as LpTabs } from "./components/LpTabs.vue"
174
187
  export type { TabItem } from "./components/LpTabs.vue"
188
+ export { default as LpTagsInput } from "./components/LpTagsInput.vue"
189
+ export type { TagsInputLabels } from "./components/LpTagsInput.vue"
190
+ export { addTags, splitTags } from "./components/tags"
191
+ export type { AddTagsOptions, TagDuplicates, TagRejection, TagValidator } from "./components/tags"
175
192
  export { default as LpTextarea } from "./components/LpTextarea.vue"
176
193
  export { default as LpThemeSwitcher } from "./components/LpThemeSwitcher.vue"
177
194
  export { default as LpTilt } from "./components/LpTilt.vue"
@@ -225,7 +242,7 @@ export {
225
242
  useTheme,
226
243
  } from "./theme/useTheme"
227
244
  export type { RevealOrigin } from "./theme/useTheme"
228
- export { detectBackdropFilter, isBrokenBackdropEngine, NO_BACKDROP_ATTR } from "./theme/backdrop"
245
+ export { detectBackdropFilter, GLASS_BACKDROP_ATTR, isBrokenBackdropEngine, NO_BACKDROP_ATTR, setGlassBackdrop } from "./theme/backdrop"
229
246
  export { DEFAULT_SURFACE } from "./theme/tokens"
230
247
  export { defineTheme } from "./theme/define"
231
248
  export type { ThemeOverrides } from "./theme/define"
@@ -237,7 +254,7 @@ export type {
237
254
  SurfaceTokens,
238
255
  TokenSet,
239
256
  } from "./theme/tokens"
240
- export { amber, dark, leavepulse, light, lime, nord, presets, rose, violet } from "./theme/presets"
257
+ export { amber, dark, light, lime, nord, presets, rose, violet } from "./theme/presets"
241
258
  export type { PresetName } from "./theme/presets"
242
259
  export { parseConfig, serializeConfig, UI_CONFIG_VERSION } from "./theme/config"
243
260
  export type { UiConfig } from "./theme/config"
@@ -252,7 +269,16 @@ export {
252
269
  mergeShortcutGroups,
253
270
  } from "./composables/useHotkeys"
254
271
  export type { HotkeyBinding, HotkeyHelp, ShortcutEntry, ShortcutGroup } from "./composables/useHotkeys"
255
- export { matchesHotkey, useAppleKeyboard } from "./composables/useHotkeys"
272
+ export {
273
+ findHotkeyConflicts,
274
+ hotkeyConflicts,
275
+ hotkeySteps,
276
+ matchesHotkey,
277
+ pendingHotkey,
278
+ sequenceProgress,
279
+ useAppleKeyboard,
280
+ } from "./composables/useHotkeys"
281
+ export type { HotkeyConflict, HotkeyStep } from "./composables/useHotkeys"
256
282
  export { anyModalOpen, topModalElement, useModalLayer } from "./components/modalDepth"
257
283
  export type { ModalLayer, ModalLayerOptions } from "./components/modalDepth"
258
284
  export { provideGlass, useGlass } from "./composables/useGlass"
@@ -260,7 +286,11 @@ export { LP_CONFIG, lpConfig, mergeConfig, provideLpConfig, useLabels, useLinkCo
260
286
  export type { LabelScope, LpConfig } from "./composables/useLpConfig"
261
287
  export { useMergedClass, useMergedAttrs, mergeClass } from "./composables/useMergedClass"
262
288
  export { anchorPattern, stripDisallowed, useInputFilter } from "./composables/useInputFilter"
289
+ export { usePaintSelect } from "./composables/usePaintSelect"
290
+ export type { UsePaintSelectOptions } from "./composables/usePaintSelect"
263
291
  export { LP_FIELD, fieldMessageId, provideField, useField, useFieldControl } from "./composables/useField"
292
+ export { FIELD_NOTICE_MS, useFieldNotice } from "./composables/useFieldNotice"
293
+ export type { FieldNotice, FieldNoticeOptions, FieldNoticeTone } from "./composables/useFieldNotice"
264
294
  export type { FieldContext, FieldControlState } from "./composables/useField"
265
295
  export type { UseInputFilterOptions } from "./composables/useInputFilter"
266
296
  export { easeOut, easeTravel, easingToken, prefersReducedMotion } from "./composables/easing"
@@ -271,6 +301,10 @@ export { useRovingFocus } from "./composables/useRovingFocus"
271
301
  export type { RovingItem, UseRovingFocusOptions } from "./composables/useRovingFocus"
272
302
  export { useFormDraft } from "./composables/useFormDraft"
273
303
  export type { UseFormDraft, UseFormDraftOptions } from "./composables/useFormDraft"
304
+ export { DEFAULT_MASK_TOKENS, applyMask, maskDelete, parseMask, useInputMask } from "./composables/useInputMask"
305
+ export type { MaskOptions, MaskResult, MaskSpec, MaskToken, MaskTokens, UseInputMaskOptions } from "./composables/useInputMask"
306
+ export { deepEqual, useForm } from "./composables/useForm"
307
+ export type { FieldBinding, FieldRule, FormErrorMessage, FormErrors, FormRules, UseForm, UseFormOptions } from "./composables/useForm"
274
308
 
275
309
  export { useSettled } from "./composables/useSettled"
276
310
  export type { UseSettledOptions } from "./composables/useSettled"
@@ -0,0 +1,5 @@
1
+ /* AUTO-GENERATED by scripts/gen-kit-icons.mjs — do not edit.
2
+ * The lucide icons kit components render, registered offline by icons.ts. */
3
+ import type { IconifyJSON } from "@iconify/vue"
4
+
5
+ export const KIT_ICONS: IconifyJSON = {"prefix":"lucide","icons":{"activity":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M22 12h-2.48a2 2 0 0 0-1.93 1.46l-2.35 8.36a.25.25 0 0 1-.48 0L9.24 2.18a.25.25 0 0 0-.48 0l-2.35 8.36A2 2 0 0 1 4.49 12H2\"/>"},"arrow-down":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M12 5v14m7-7l-7 7l-7-7\"/>"},"arrow-up":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m5 12l7-7l7 7m-7 7V5\"/>"},"bell":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M10.268 21a2 2 0 0 0 3.464 0m-10.47-5.674A1 1 0 0 0 4 17h16a1 1 0 0 0 .74-1.673C19.41 13.956 18 12.499 18 8A6 6 0 0 0 6 8c0 4.499-1.411 5.956-2.738 7.326\"/>"},"bell-off":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M10.268 21a2 2 0 0 0 3.464 0M17 17H4a1 1 0 0 1-.74-1.673C4.59 13.956 6 12.499 6 8a6 6 0 0 1 .258-1.742M2 2l20 20M8.668 3.01A6 6 0 0 1 18 8c0 2.687.77 4.653 1.707 6.05\"/>"},"calendar":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M8 2v4m8-4v4\"/><rect width=\"18\" height=\"18\" x=\"3\" y=\"4\" rx=\"2\"/><path d=\"M3 10h18\"/></g>"},"calendar-range":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"18\" height=\"18\" x=\"3\" y=\"4\" rx=\"2\"/><path d=\"M16 2v4M3 10h18M8 2v4m9 8h-6m2 4H7m0-4h.01M17 18h.01\"/></g>"},"chart-no-axes-column":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M5 21v-6m7 6V3m7 18V9\"/>"},"chart-pie":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M21 12c.552 0 1.005-.449.95-.998a10 10 0 0 0-8.953-8.951c-.55-.055-.998.398-.998.95v8a1 1 0 0 0 1 1z\"/><path d=\"M21.21 15.89A10 10 0 1 1 8 2.83\"/></g>"},"check":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M20 6L9 17l-5-5\"/>"},"check-check":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M18 6L7 17l-5-5m20-2l-7.5 7.5L13 16\"/>"},"circle-check-big":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M21.801 10A10 10 0 1 1 17 3.335\"/><path d=\"m9 11l3 3L22 4\"/></g>"},"chevron-down":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m6 9l6 6l6-6\"/>"},"chevron-left":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m15 18l-6-6l6-6\"/>"},"chevron-right":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m9 18l6-6l-6-6\"/>"},"chevron-up":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m18 15l-6-6l-6 6\"/>"},"chevrons-up-down":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m7 15l5 5l5-5M7 9l5-5l5 5\"/>"},"circle-alert":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"10\"/><path d=\"M12 8v4m0 4h.01\"/></g>"},"circle-check":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"10\"/><path d=\"m9 12l2 2l4-4\"/></g>"},"circle-x":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"10\"/><path d=\"m15 9l-6 6m0-6l6 6\"/></g>"},"clipboard":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"8\" height=\"4\" x=\"8\" y=\"2\" rx=\"1\" ry=\"1\"/><path d=\"M16 4h2a2 2 0 0 1 2 2v14a2 2 0 0 1-2 2H6a2 2 0 0 1-2-2V6a2 2 0 0 1 2-2h2\"/></g>"},"clipboard-list":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"8\" height=\"4\" x=\"8\" y=\"2\" rx=\"1\" ry=\"1\"/><path d=\"M16 4h2a2 2 0 0 1 2 2v14a2 2 0 0 1-2 2H6a2 2 0 0 1-2-2V6a2 2 0 0 1 2-2h2m4 7h4m-4 5h4m-8-5h.01M8 16h.01\"/></g>"},"clock":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"10\"/><path d=\"M12 6v6l4 2\"/></g>"},"code":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m16 18l6-6l-6-6M8 6l-6 6l6 6\"/>"},"columns-3":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"18\" height=\"18\" x=\"3\" y=\"3\" rx=\"2\"/><path d=\"M9 3v18m6-18v18\"/></g>"},"container":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M22 7.7c0-.6-.4-1.2-.8-1.5l-6.3-3.9a1.72 1.72 0 0 0-1.7 0l-10.3 6c-.5.2-.9.8-.9 1.4v6.6c0 .5.4 1.2.8 1.5l6.3 3.9a1.72 1.72 0 0 0 1.7 0l10.3-6c.5-.3.9-1 .9-1.5Z\"/><path d=\"M10 21.9V14L2.1 9.1M10 14l11.9-6.9M14 19.8v-8.1m4 5.8V9.4\"/></g>"},"copy":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"14\" height=\"14\" x=\"8\" y=\"8\" rx=\"2\" ry=\"2\"/><path d=\"M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2\"/></g>"},"crosshair":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"10\"/><path d=\"M22 12h-4M6 12H2m10-6V2m0 20v-4\"/></g>"},"database":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><ellipse cx=\"12\" cy=\"5\" rx=\"9\" ry=\"3\"/><path d=\"M3 5v14a9 3 0 0 0 18 0V5\"/><path d=\"M3 12a9 3 0 0 0 18 0\"/></g>"},"dot":{"body":"<circle cx=\"12.1\" cy=\"12.1\" r=\"1\" fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"/>"},"download":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M12 15V3m9 12v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4\"/><path d=\"m7 10l5 5l5-5\"/></g>"},"external-link":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M15 3h6v6m-11 5L21 3m-3 10v6a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h6\"/>"},"eye":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M2.062 12.348a1 1 0 0 1 0-.696a10.75 10.75 0 0 1 19.876 0a1 1 0 0 1 0 .696a10.75 10.75 0 0 1-19.876 0\"/><circle cx=\"12\" cy=\"12\" r=\"3\"/></g>"},"eye-off":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M10.733 5.076a10.744 10.744 0 0 1 11.205 6.575a1 1 0 0 1 0 .696a10.8 10.8 0 0 1-1.444 2.49m-6.41-.679a3 3 0 0 1-4.242-4.242\"/><path d=\"M17.479 17.499a10.75 10.75 0 0 1-15.417-5.151a1 1 0 0 1 0-.696a10.75 10.75 0 0 1 4.446-5.143M2 2l20 20\"/></g>"},"file":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5\"/></g>"},"file-archive":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M13.659 22H18a2 2 0 0 0 2-2V8a2.4 2.4 0 0 0-.706-1.706l-3.588-3.588A2.4 2.4 0 0 0 14 2H6a2 2 0 0 0-2 2v11.5\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5M8 12v-1m0 7v-2m0-9V6\"/><circle cx=\"8\" cy=\"20\" r=\"2\"/></g>"},"file-code":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5m-10 4.5L8 15l2 2.5m4-5l2 2.5l-2 2.5\"/></g>"},"file-cog":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M15 8a1 1 0 0 1-1-1V2a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8zm5 0v12a2 2 0 0 1-2 2h-4.182M3.305 19.53l.923-.382M4 10.592V4a2 2 0 0 1 2-2h8M4.228 16.852l-.924-.383m2.548-1.241l-.383-.923m.383 6.467l-.383.924m2.679-6.468l.383-.923m-.001 7.391l-.382-.924m1.625-3.92l.922-.383m-.922 2.679l.922.383\"/><circle cx=\"7\" cy=\"18\" r=\"3\"/></g>"},"file-image":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5\"/><circle cx=\"10\" cy=\"12\" r=\"2\"/><path d=\"m20 17l-1.296-1.296a2.41 2.41 0 0 0-3.408 0L9 22\"/></g>"},"file-json":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M15 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V7Z\"/><path d=\"M14 2v4a2 2 0 0 0 2 2h4m-10 4a1 1 0 0 0-1 1v1a1 1 0 0 1-1 1a1 1 0 0 1 1 1v1a1 1 0 0 0 1 1m4 0a1 1 0 0 0 1-1v-1a1 1 0 0 1 1-1a1 1 0 0 1-1-1v-1a1 1 0 0 0-1-1\"/></g>","hidden":true},"file-key":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M14 2v5a1 1 0 0 0 1 1h5M4 12v6m0-4h2\"/><path d=\"M9.65 22H18a2 2 0 0 0 2-2V8a2.4 2.4 0 0 0-.706-1.706l-3.588-3.588A2.4 2.4 0 0 0 14 2H6a2 2 0 0 0-2 2v4\"/><circle cx=\"4\" cy=\"20\" r=\"2\"/></g>"},"file-lock":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M4 9.8V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.706.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2h-3\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5M9 17v-2a2 2 0 0 0-4 0v2\"/><rect width=\"8\" height=\"5\" x=\"3\" y=\"17\" rx=\"1\"/></g>"},"file-spreadsheet":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5M8 13h2m4 0h2m-8 4h2m4 0h2\"/></g>"},"file-terminal":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5M8 16l2-2l-2-2m4 6h4\"/></g>"},"file-text":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5M10 9H8m8 4H8m8 4H8\"/></g>"},"file-type":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M6 22a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h8a2.4 2.4 0 0 1 1.704.706l3.588 3.588A2.4 2.4 0 0 1 20 8v12a2 2 0 0 1-2 2z\"/><path d=\"M14 2v5a1 1 0 0 0 1 1h5m-9 10h2m-1-6v6m-3-5v-.5a.5.5 0 0 1 .5-.5h5a.5.5 0 0 1 .5.5v.5\"/></g>"},"filter":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M22 3H2l8 9.46V19l4 2v-8.54z\"/>","hidden":true},"filter-x":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M13.013 3H2l8 9.46V19l4 2v-8.54l.9-1.055M22 3l-5 5m0-5l5 5\"/>","hidden":true},"folder":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M20 20a2 2 0 0 0 2-2V8a2 2 0 0 0-2-2h-7.9a2 2 0 0 1-1.69-.9L9.6 3.9A2 2 0 0 0 7.93 3H4a2 2 0 0 0-2 2v13a2 2 0 0 0 2 2Z\"/>"},"folder-open":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m6 14l1.5-2.9A2 2 0 0 1 9.24 10H20a2 2 0 0 1 1.94 2.5l-1.54 6a2 2 0 0 1-1.95 1.5H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h3.9a2 2 0 0 1 1.69.9l.81 1.2a2 2 0 0 0 1.67.9H18a2 2 0 0 1 2 2v2\"/>"},"folder-search":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M10.7 20H4a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h3.9a2 2 0 0 1 1.69.9l.81 1.2a2 2 0 0 0 1.67.9H20a2 2 0 0 1 2 2v4.1M21 21l-1.9-1.9\"/><circle cx=\"17\" cy=\"17\" r=\"3\"/></g>"},"git-branch":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M15 6a9 9 0 0 0-9 9V3\"/><circle cx=\"18\" cy=\"6\" r=\"3\"/><circle cx=\"6\" cy=\"18\" r=\"3\"/></g>"},"image-off":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"m2 2l20 20M10.41 10.41a2 2 0 1 1-2.83-2.83m5.92 5.92L6 21m12-9l3 3\"/><path d=\"M3.59 3.59A2 2 0 0 0 3 5v14a2 2 0 0 0 2 2h14c.55 0 1.052-.22 1.41-.59M21 15V5a2 2 0 0 0-2-2H9\"/></g>"},"inbox":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M22 12h-6l-2 3h-4l-2-3H2\"/><path d=\"M5.45 5.11L2 12v6a2 2 0 0 0 2 2h16a2 2 0 0 0 2-2v-6l-3.45-6.89A2 2 0 0 0 16.76 4H7.24a2 2 0 0 0-1.79 1.11\"/></g>"},"info":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"10\"/><path d=\"M12 16v-4m0-4h.01\"/></g>"},"link":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M10 13a5 5 0 0 0 7.54.54l3-3a5 5 0 0 0-7.07-7.07l-1.72 1.71\"/><path d=\"M14 11a5 5 0 0 0-7.54-.54l-3 3a5 5 0 0 0 7.07 7.07l1.71-1.71\"/></g>"},"list":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M3 5h.01M3 12h.01M3 19h.01M8 5h13M8 12h13M8 19h13\"/>"},"loader-circle":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M21 12a9 9 0 1 1-6.219-8.56\"/>"},"locate-fixed":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M2 12h3m14 0h3M12 2v3m0 14v3\"/><circle cx=\"12\" cy=\"12\" r=\"7\"/><circle cx=\"12\" cy=\"12\" r=\"3\"/></g>"},"lock":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"18\" height=\"11\" x=\"3\" y=\"11\" rx=\"2\" ry=\"2\"/><path d=\"M7 11V7a5 5 0 0 1 10 0v4\"/></g>"},"lock-open":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"18\" height=\"11\" x=\"3\" y=\"11\" rx=\"2\" ry=\"2\"/><path d=\"M7 11V7a5 5 0 0 1 9.9-1\"/></g>"},"map":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M14.106 5.553a2 2 0 0 0 1.788 0l3.659-1.83A1 1 0 0 1 21 4.619v12.764a1 1 0 0 1-.553.894l-4.553 2.277a2 2 0 0 1-1.788 0l-4.212-2.106a2 2 0 0 0-1.788 0l-3.659 1.83A1 1 0 0 1 3 19.381V6.618a1 1 0 0 1 .553-.894l4.553-2.277a2 2 0 0 1 1.788 0zm.894.211v15M9 3.236v15\"/>"},"map-pin":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M20 10c0 4.993-5.539 10.193-7.399 11.799a1 1 0 0 1-1.202 0C9.539 20.193 4 14.993 4 10a8 8 0 0 1 16 0\"/><circle cx=\"12\" cy=\"10\" r=\"3\"/></g>"},"maximize-2":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M15 3h6v6m0-6l-7 7M3 21l7-7m-1 7H3v-6\"/>"},"menu":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M4 5h16M4 12h16M4 19h16\"/>"},"minus":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M5 12h14\"/>"},"monitor":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"20\" height=\"14\" x=\"2\" y=\"3\" rx=\"2\"/><path d=\"M8 21h8m-4-4v4\"/></g>"},"moon":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M20.985 12.486a9 9 0 1 1-9.473-9.472c.405-.022.617.46.402.803a6 6 0 0 0 8.268 8.268c.344-.215.825-.004.803.401\"/>"},"octagon-alert":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M12 16h.01M12 8v4m3.312-10a2 2 0 0 1 1.414.586l4.688 4.688A2 2 0 0 1 22 8.688v6.624a2 2 0 0 1-.586 1.414l-4.688 4.688a2 2 0 0 1-1.414.586H8.688a2 2 0 0 1-1.414-.586l-4.688-4.688A2 2 0 0 1 2 15.312V8.688a2 2 0 0 1 .586-1.414l4.688-4.688A2 2 0 0 1 8.688 2z\"/>"},"package":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M11 21.73a2 2 0 0 0 2 0l7-4A2 2 0 0 0 21 16V8a2 2 0 0 0-1-1.73l-7-4a2 2 0 0 0-2 0l-7 4A2 2 0 0 0 3 8v8a2 2 0 0 0 1 1.73zm1 .27V12\"/><path d=\"M3.29 7L12 12l8.71-5M7.5 4.27l9 5.15\"/></g>"},"palette":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M12 22a1 1 0 0 1 0-20a10 9 0 0 1 10 9a5 5 0 0 1-5 5h-2.25a1.75 1.75 0 0 0-1.4 2.8l.3.4a1.75 1.75 0 0 1-1.4 2.8z\"/><circle cx=\"13.5\" cy=\"6.5\" r=\".5\" fill=\"currentColor\"/><circle cx=\"17.5\" cy=\"10.5\" r=\".5\" fill=\"currentColor\"/><circle cx=\"6.5\" cy=\"12.5\" r=\".5\" fill=\"currentColor\"/><circle cx=\"8.5\" cy=\"7.5\" r=\".5\" fill=\"currentColor\"/></g>"},"plus":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M5 12h14m-7-7v14\"/>"},"rotate-ccw":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M3 12a9 9 0 1 0 9-9a9.75 9.75 0 0 0-6.74 2.74L3 8\"/><path d=\"M3 3v5h5\"/></g>"},"rotate-cw":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M21 12a9 9 0 1 1-9-9c2.52 0 4.93 1 6.74 2.74L21 8\"/><path d=\"M21 3v5h-5\"/></g>"},"scroll-text":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M15 12h-5m5-4h-5m9 9V5a2 2 0 0 0-2-2H4\"/><path d=\"M8 21h12a2 2 0 0 0 2-2v-1a1 1 0 0 0-1-1H11a1 1 0 0 0-1 1v1a2 2 0 1 1-4 0V5a2 2 0 1 0-4 0v2a1 1 0 0 0 1 1h3\"/></g>"},"search":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"m21 21l-4.34-4.34\"/><circle cx=\"11\" cy=\"11\" r=\"8\"/></g>"},"server":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><rect width=\"20\" height=\"8\" x=\"2\" y=\"2\" rx=\"2\" ry=\"2\"/><rect width=\"20\" height=\"8\" x=\"2\" y=\"14\" rx=\"2\" ry=\"2\"/><path d=\"M6 6h.01M6 18h.01\"/></g>"},"sun":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"12\" cy=\"12\" r=\"4\"/><path d=\"M12 2v2m0 16v2M4.93 4.93l1.41 1.41m11.32 11.32l1.41 1.41M2 12h2m16 0h2M6.34 17.66l-1.41 1.41M19.07 4.93l-1.41 1.41\"/></g>"},"trash-2":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M10 11v6m4-6v6m5-11v14a2 2 0 0 1-2 2H7a2 2 0 0 1-2-2V6M3 6h18M8 6V4a2 2 0 0 1 2-2h4a2 2 0 0 1 2 2v2\"/>"},"trending-down":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M16 17h6v-6\"/><path d=\"m22 17l-8.5-8.5l-5 5L2 7\"/></g>"},"trending-up":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M16 7h6v6\"/><path d=\"m22 7l-8.5 8.5l-5-5L2 17\"/></g>"},"triangle-alert":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"m21.73 18l-8-14a2 2 0 0 0-3.48 0l-8 14A2 2 0 0 0 4 21h16a2 2 0 0 0 1.73-3M12 9v4m0 4h.01\"/>"},"undo-2":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><path d=\"M9 14L4 9l5-5\"/><path d=\"M4 9h10.5a5.5 5.5 0 0 1 5.5 5.5a5.5 5.5 0 0 1-5.5 5.5H11\"/></g>"},"upload":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M12 3v12m5-7l-5-5l-5 5m14 7v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4\"/>"},"x":{"body":"<path fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\" d=\"M18 6L6 18M6 6l12 12\"/>"},"zoom-in":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"11\" cy=\"11\" r=\"8\"/><path d=\"m21 21l-4.35-4.35M11 8v6m-3-3h6\"/></g>"},"zoom-out":{"body":"<g fill=\"none\" stroke=\"currentColor\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-width=\"2\"><circle cx=\"11\" cy=\"11\" r=\"8\"/><path d=\"m21 21l-4.35-4.35M8 11h6\"/></g>"}},"width":24,"height":24,"aliases":{"check-circle":{"parent":"circle-check-big"}}}