@leavepulse/ui 0.44.0 → 0.45.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 (271) hide show
  1. package/README.md +49 -3
  2. package/dist/assets/{LpCommandPalette-DCP5g2ik.css → LpCommandPalette-HzAA4gri.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-CJOYGZlI.js} +7 -7
  11. package/dist/chunks/{LpAlert-DkOIjsbq.js → LpAlert-B6ilrM7T.js} +1 -1
  12. package/dist/chunks/{LpAppShell-BUKPcHco.js → LpAppShell-B07Lf48e.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-BTVAR4tF.js} +3 -3
  23. package/dist/chunks/{LpConfirmHost-CDm0Wtpv.js → LpConfirmHost-Ci_uCHgQ.js} +1 -1
  24. package/dist/chunks/{LpContextMenu-DQw5dGfG.js → LpContextMenu-BqkAYa9X.js} +2 -1
  25. package/dist/chunks/{LpDatePicker-Drirx1AK.js → LpDatePicker-BrdFtSTy.js} +16 -10
  26. package/dist/chunks/LpDateRangePicker-Drd7EbIz.js +210 -0
  27. package/dist/chunks/{LpDisclosure-ChQYmjlR.js → LpDisclosure-Cc23-JOT.js} +1 -1
  28. package/dist/chunks/{LpDrawer-bScx-KMO.js → LpDrawer-CfRhHwmE.js} +3 -3
  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-BzTVeNqe.js} +3 -3
  42. package/dist/chunks/{LpModalNav-DPg5H9f3.js → LpModalNav-CjABSGCu.js} +14 -8
  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-Bwws_X29.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-DTtWuKvq.js} +76 -9
  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 +62 -11
  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.d.ts +2 -0
  164. package/dist/components/LpToaster.vue.js +1 -1
  165. package/dist/components/LpTooltip.vue.js +1 -1
  166. package/dist/components/LpTopologyCanvas.vue.js +1 -1
  167. package/dist/components/LpUptimeBar.vue.js +1 -1
  168. package/dist/components/chart.js +3 -2
  169. package/dist/components/commandSearch.js +3 -0
  170. package/dist/components/dateRange.d.ts +43 -0
  171. package/dist/components/dateRange.js +76 -0
  172. package/dist/components/exportData.d.ts +58 -0
  173. package/dist/components/exportData.js +165 -0
  174. package/dist/components/logSearch.d.ts +18 -0
  175. package/dist/components/logSearch.js +36 -0
  176. package/dist/components/phone.d.ts +41 -0
  177. package/dist/components/phone.js +80 -0
  178. package/dist/components/tableFilter.d.ts +36 -0
  179. package/dist/components/tableFilter.js +84 -0
  180. package/dist/components/tags.d.ts +20 -0
  181. package/dist/components/tags.js +37 -0
  182. package/dist/composables/useField.d.ts +4 -0
  183. package/dist/composables/useFieldNotice.d.ts +17 -0
  184. package/dist/composables/useFieldNotice.js +28 -0
  185. package/dist/composables/useForm.d.ts +53 -0
  186. package/dist/composables/useForm.js +207 -0
  187. package/dist/composables/useHotkeys.d.ts +65 -5
  188. package/dist/composables/useHotkeys.js +170 -9
  189. package/dist/composables/useInputMask.d.ts +59 -0
  190. package/dist/composables/useInputMask.js +170 -0
  191. package/dist/composables/useLocale.d.ts +2 -0
  192. package/dist/composables/useLocale.js +9 -0
  193. package/dist/composables/usePaintSelect.d.ts +22 -0
  194. package/dist/composables/usePaintSelect.js +169 -0
  195. package/dist/composables/useShift.js +7 -2
  196. package/dist/icons-all.d.ts +1 -0
  197. package/dist/icons-all.js +3 -0
  198. package/dist/icons.d.ts +14 -1
  199. package/dist/index.d.ts +29 -3
  200. package/dist/index.js +195 -138
  201. package/dist/kit-icons.d.ts +2 -0
  202. package/dist/theme/backdrop.d.ts +12 -0
  203. package/dist/theme/presets.d.ts +0 -2
  204. package/package.json +13 -4
  205. package/src/component-names.ts +4 -0
  206. package/src/components/ContextMenuItems.vue +1 -1
  207. package/src/components/LayoutNode.vue +11 -2
  208. package/src/components/LpActionBar.vue +1 -1
  209. package/src/components/LpAutocomplete.vue +1 -0
  210. package/src/components/LpAvatar.vue +2 -2
  211. package/src/components/LpButton.vue +1 -1
  212. package/src/components/LpChart.vue +80 -1
  213. package/src/components/LpColorPicker.vue +34 -1
  214. package/src/components/LpCommandPalette.vue +82 -8
  215. package/src/components/LpContextMenu.vue +1 -1
  216. package/src/components/LpDatePicker.vue +11 -4
  217. package/src/components/LpDateRangePicker.vue +226 -0
  218. package/src/components/LpDrawer.vue +1 -1
  219. package/src/components/LpDropdownMenu.vue +1 -0
  220. package/src/components/LpFieldNotice.vue +65 -0
  221. package/src/components/LpFormField.vue +33 -4
  222. package/src/components/LpIcon.vue +22 -4
  223. package/src/components/LpInput.vue +46 -6
  224. package/src/components/LpLogViewer.vue +225 -22
  225. package/src/components/LpModal.vue +2 -2
  226. package/src/components/LpModalNav.vue +13 -2
  227. package/src/components/LpNotificationBell.vue +15 -7
  228. package/src/components/LpPhoneInput.vue +179 -20
  229. package/src/components/LpPie.vue +8 -5
  230. package/src/components/LpPopover.vue +1 -0
  231. package/src/components/LpRangeCalendar.vue +365 -0
  232. package/src/components/LpRollingText.vue +3 -0
  233. package/src/components/LpScrollArea.vue +22 -2
  234. package/src/components/LpSelect.vue +0 -0
  235. package/src/components/LpShortcutsDialog.vue +77 -8
  236. package/src/components/LpStepper.vue +23 -10
  237. package/src/components/LpSwitch.vue +1 -1
  238. package/src/components/LpTable.vue +584 -65
  239. package/src/components/LpTableFilter.vue +175 -0
  240. package/src/components/LpTagsInput.vue +364 -0
  241. package/src/components/LpThemeSwitcher.vue +19 -23
  242. package/src/components/LpToaster.vue +91 -5
  243. package/src/components/LpTooltip.vue +9 -2
  244. package/src/components/LpTopologyCanvas.vue +7 -1
  245. package/src/components/chart.ts +5 -3
  246. package/src/components/commandSearch.ts +6 -0
  247. package/src/components/dateRange.ts +134 -0
  248. package/src/components/exportData.ts +228 -0
  249. package/src/components/logSearch.ts +46 -0
  250. package/src/components/phone.ts +140 -0
  251. package/src/components/tableFilter.ts +122 -0
  252. package/src/components/tags.ts +62 -0
  253. package/src/composables/useField.ts +4 -0
  254. package/src/composables/useFieldNotice.ts +59 -0
  255. package/src/composables/useForm.ts +314 -0
  256. package/src/composables/useHotkeys.ts +269 -13
  257. package/src/composables/useInputMask.ts +254 -0
  258. package/src/composables/useLocale.ts +14 -0
  259. package/src/composables/usePaintSelect.ts +243 -0
  260. package/src/composables/useShift.ts +13 -2
  261. package/src/iconSubset.d.mts +10 -0
  262. package/src/iconSubset.mjs +51 -0
  263. package/src/icons-all.ts +10 -0
  264. package/src/icons.ts +59 -8
  265. package/src/index.ts +37 -3
  266. package/src/kit-icons.ts +5 -0
  267. package/src/nuxt.ts +30 -2
  268. package/src/runtime/theme.plugin.ts +2 -2
  269. package/src/theme/backdrop.ts +69 -0
  270. package/src/theme/presets.ts +6 -64
  271. package/src/tokens/tokens.css +53 -4
@@ -0,0 +1,31 @@
1
+ export interface TableFilterOption {
2
+ value: unknown;
3
+ label: string;
4
+ /** Rows holding the value; omitted when unknown (a server-backed table). */
5
+ count?: number;
6
+ }
7
+ export interface TableFilterLabels {
8
+ search: string;
9
+ all: string;
10
+ none: string;
11
+ invert: string;
12
+ only: string;
13
+ onlyShown: string;
14
+ addShown: string;
15
+ noValues: string;
16
+ }
17
+ declare const _default: typeof __VLS_export;
18
+ export default _default;
19
+ declare const __VLS_export: import("vue").DefineComponent<{
20
+ options: TableFilterOption[];
21
+ hidden: ReadonlySet<unknown>;
22
+ labels: TableFilterLabels;
23
+ }, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {} & {
24
+ "update:hidden": (value: Set<unknown>) => any;
25
+ }, string, import("vue").PublicProps, Readonly<{
26
+ options: TableFilterOption[];
27
+ hidden: ReadonlySet<unknown>;
28
+ labels: TableFilterLabels;
29
+ }> & Readonly<{
30
+ "onUpdate:hidden"?: ((value: Set<unknown>) => any) | undefined;
31
+ }>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -0,0 +1,4 @@
1
+ import { _ as _sfc_main } from "../chunks/LpTableFilter-BV8PpLM9.js";
2
+ export {
3
+ _sfc_main as default
4
+ };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpTabs-_qMVaZJ6.js";
1
+ import { _ as _sfc_main } from "../chunks/LpTabs-29iW1XOx.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -0,0 +1,77 @@
1
+ import { type TagDuplicates, type TagRejection, type TagValidator } from "./tags";
2
+ declare const _default: typeof __VLS_export;
3
+ export default _default;
4
+ export type TagsInputLabels = {
5
+ remove: string;
6
+ duplicate: string;
7
+ max: string;
8
+ added: string;
9
+ removed: string;
10
+ };
11
+ declare const __VLS_export: import("vue").DefineComponent<{
12
+ modelValue?: string[];
13
+ placeholder?: string;
14
+ /** Characters (or a RegExp) that end a tag while typing and split a paste. */
15
+ delimiter?: string | readonly string[] | RegExp;
16
+ /** At most this many tags. */
17
+ max?: number;
18
+ /**
19
+ * "reject" keeps a repeat typed with a note, "ignore" drops it with a passing
20
+ * note, "allow" keeps it. Either way the tag it repeats pulses.
21
+ */
22
+ duplicates?: TagDuplicates;
23
+ /** Return an error message to refuse a tag. */
24
+ validate?: TagValidator;
25
+ /** Applied to each tag before it is checked and stored (trim is always applied). */
26
+ normalize?: (tag: string) => string;
27
+ /** Turn leftover text into a tag when the field loses focus. */
28
+ addOnBlur?: boolean;
29
+ disabled?: boolean;
30
+ invalid?: boolean;
31
+ required?: boolean;
32
+ label?: string;
33
+ hint?: string;
34
+ error?: string;
35
+ labels?: Partial<TagsInputLabels>;
36
+ }, {
37
+ focus: () => void | undefined;
38
+ add: (value: string) => string;
39
+ }, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {} & {
40
+ blur: (event: FocusEvent) => any;
41
+ "update:modelValue": (value: string[]) => any;
42
+ reject: (rejected: TagRejection[]) => any;
43
+ }, string, import("vue").PublicProps, Readonly<{
44
+ modelValue?: string[];
45
+ placeholder?: string;
46
+ /** Characters (or a RegExp) that end a tag while typing and split a paste. */
47
+ delimiter?: string | readonly string[] | RegExp;
48
+ /** At most this many tags. */
49
+ max?: number;
50
+ /**
51
+ * "reject" keeps a repeat typed with a note, "ignore" drops it with a passing
52
+ * note, "allow" keeps it. Either way the tag it repeats pulses.
53
+ */
54
+ duplicates?: TagDuplicates;
55
+ /** Return an error message to refuse a tag. */
56
+ validate?: TagValidator;
57
+ /** Applied to each tag before it is checked and stored (trim is always applied). */
58
+ normalize?: (tag: string) => string;
59
+ /** Turn leftover text into a tag when the field loses focus. */
60
+ addOnBlur?: boolean;
61
+ disabled?: boolean;
62
+ invalid?: boolean;
63
+ required?: boolean;
64
+ label?: string;
65
+ hint?: string;
66
+ error?: string;
67
+ labels?: Partial<TagsInputLabels>;
68
+ }> & Readonly<{
69
+ onBlur?: ((event: FocusEvent) => any) | undefined;
70
+ "onUpdate:modelValue"?: ((value: string[]) => any) | undefined;
71
+ onReject?: ((rejected: TagRejection[]) => any) | undefined;
72
+ }>, {
73
+ modelValue: string[];
74
+ delimiter: string | readonly string[] | RegExp;
75
+ duplicates: TagDuplicates;
76
+ addOnBlur: boolean;
77
+ }, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -0,0 +1,4 @@
1
+ import { _ as _sfc_main } from "../chunks/LpTagsInput-D1SuqbhB.js";
2
+ export {
3
+ _sfc_main as default
4
+ };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpTextarea-yP8hGedR.js";
1
+ import { _ as _sfc_main } from "../chunks/LpTextarea-uuScWo6-.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpThemeProvider-Wjm7Tuit.js";
1
+ import { _ as _sfc_main } from "../chunks/LpThemeProvider-Be4r2TQX.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -13,9 +13,9 @@ type __VLS_Props = {
13
13
  cycleThemes?: (string | TokenSet)[];
14
14
  /**
15
15
  * Trigger style:
16
- * - "swatch" (default): a square showing the active theme's brand colour.
16
+ * - "swatch" (default): a round chip previewing the theme's surface and brand.
17
17
  * - "icon": a sun/moon icon following the active theme's mode.
18
- * - "pill": swatch + the theme name in a pill (always shows the label).
18
+ * - "pill": the chip and the theme name in a rounded pill.
19
19
  */
20
20
  variant?: "swatch" | "icon" | "pill";
21
21
  /** Show the active theme's name next to the trigger (forced on for "pill"). */
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpThemeSwitcher-CKLc10KZ.js";
1
+ import { _ as _sfc_main } from "../chunks/LpThemeSwitcher-B4aVPbNC.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpTimeField-C5HRgS5H.js";
1
+ import { _ as _sfc_main } from "../chunks/LpTimeField-Cqe7fXnh.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -1,6 +1,8 @@
1
1
  type __VLS_Props = {
2
2
  labels?: Partial<{
3
3
  dismiss: string;
4
+ copy: string;
5
+ copied: string;
4
6
  }>;
5
7
  };
6
8
  declare const __VLS_export: import("vue").DefineComponent<__VLS_Props, {}, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {}, string, import("vue").PublicProps, Readonly<__VLS_Props> & Readonly<{}>, {}, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpToaster--oT6lfhL.js";
1
+ import { _ as _sfc_main } from "../chunks/LpToaster-DTtWuKvq.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpTooltip-CBdzeKNf.js";
1
+ import { _ as _sfc_main } from "../chunks/LpTooltip-CXVKcOXT.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpTopologyCanvas-DocsLal3.js";
1
+ import { _ as _sfc_main } from "../chunks/LpTopologyCanvas-6ozNrQKh.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -1,4 +1,4 @@
1
- import { _ as _sfc_main } from "../chunks/LpUptimeBar-DLtxOMRy.js";
1
+ import { _ as _sfc_main } from "../chunks/LpUptimeBar-ugcv25xj.js";
2
2
  export {
3
3
  _sfc_main as default
4
4
  };
@@ -45,8 +45,9 @@ const niceScale = (min, max, ticks) => {
45
45
  if (!Number.isFinite(min) || !Number.isFinite(max)) return { min: 0, max: 1, step: 1 };
46
46
  if (min === max) {
47
47
  const pad = Math.abs(min) || 1;
48
- min -= pad / 2;
49
- max += pad / 2;
48
+ min = min >= 0 ? Math.max(0, min - pad / 2) : min - pad / 2;
49
+ max = max <= 0 ? Math.min(0, max + pad / 2) : max + pad / 2;
50
+ if (min === max) max = min + pad;
50
51
  }
51
52
  const raw = (max - min) / Math.max(1, ticks);
52
53
  const mag = 10 ** Math.floor(Math.log10(raw));
@@ -39,6 +39,9 @@ function score(command, terms) {
39
39
  if (!hit) return 0;
40
40
  total += hit;
41
41
  }
42
+ const typed = terms.include.join(" ");
43
+ if (typed && label === typed) total += 6;
44
+ else if (typed && label.startsWith(typed)) total += 2;
42
45
  return total;
43
46
  }
44
47
  function rankCommandItems(items, terms) {
@@ -0,0 +1,43 @@
1
+ import { type CalendarDate } from "@internationalized/date";
2
+ export interface DateRange {
3
+ start: string;
4
+ end: string;
5
+ }
6
+ export interface DateRangePreset {
7
+ label: string;
8
+ range: () => DateRange;
9
+ }
10
+ export interface DateRangePresetLabels {
11
+ today: string;
12
+ last7: string;
13
+ last30: string;
14
+ thisMonth: string;
15
+ lastMonth: string;
16
+ }
17
+ /** The default preset list. `now` is injectable so the set can be tested. */
18
+ export declare function defaultRangePresets(labels: DateRangePresetLabels, now?: () => CalendarDate): DateRangePreset[];
19
+ export declare function parseIsoDay(iso: string | undefined): CalendarDate | undefined;
20
+ /** A range with both ends parsed and in order, or undefined. */
21
+ export declare function normalizeRange(range: Partial<DateRange> | undefined): DateRange | undefined;
22
+ export declare function sameRange(a: Partial<DateRange> | undefined, b: Partial<DateRange> | undefined): boolean;
23
+ /** Clip a preset to the allowed bounds; undefined when nothing of it is left. */
24
+ export declare function clampRange(range: DateRange, min?: string, max?: string): DateRange | undefined;
25
+ /**
26
+ * "Jun 3 – 18, 2026" style text: Intl's own range formatting collapses the
27
+ * shared month and year, which is how a range reads naturally in every locale.
28
+ */
29
+ export declare function formatRange(range: DateRange, locale?: string, format?: Intl.DateTimeFormatOptions): string;
30
+ export interface ReshapeRules {
31
+ /** Whether the moving end may land on this day (min, max, disabled). */
32
+ allowed?: (iso: string) => boolean;
33
+ /** Days a range may not include. */
34
+ unavailable?: (iso: string) => boolean;
35
+ /** Longest range, in days, counting both ends. */
36
+ maximumDays?: number;
37
+ }
38
+ /**
39
+ * The range one end makes when it is dragged to `moving` while the other stays
40
+ * at `anchor`; passing the anchor flips which end is which. Null when the result
41
+ * would break a rule, so a drag simply does not follow onto that day.
42
+ */
43
+ export declare function reshapeRange(anchor: string, moving: string, rules?: ReshapeRules): DateRange | null;
@@ -0,0 +1,76 @@
1
+ import { endOfMonth, startOfMonth, today, getLocalTimeZone, parseDate } from "@internationalized/date";
2
+ function span(start, end) {
3
+ return { start: start.toString(), end: end.toString() };
4
+ }
5
+ function defaultRangePresets(labels, now = () => today(getLocalTimeZone())) {
6
+ return [
7
+ { label: labels.today, range: () => span(now(), now()) },
8
+ { label: labels.last7, range: () => span(now().subtract({ days: 6 }), now()) },
9
+ { label: labels.last30, range: () => span(now().subtract({ days: 29 }), now()) },
10
+ { label: labels.thisMonth, range: () => span(startOfMonth(now()), endOfMonth(now())) },
11
+ {
12
+ label: labels.lastMonth,
13
+ range: () => {
14
+ const previous = now().subtract({ months: 1 });
15
+ return span(startOfMonth(previous), endOfMonth(previous));
16
+ }
17
+ }
18
+ ];
19
+ }
20
+ function parseIsoDay(iso) {
21
+ if (!iso) return void 0;
22
+ try {
23
+ return parseDate(iso.slice(0, 10));
24
+ } catch {
25
+ return void 0;
26
+ }
27
+ }
28
+ function normalizeRange(range) {
29
+ const start = parseIsoDay(range?.start);
30
+ const end = parseIsoDay(range?.end);
31
+ if (!start || !end) return void 0;
32
+ return start.compare(end) <= 0 ? span(start, end) : span(end, start);
33
+ }
34
+ function sameRange(a, b) {
35
+ const x = normalizeRange(a);
36
+ const y = normalizeRange(b);
37
+ return !!x && !!y && x.start === y.start && x.end === y.end;
38
+ }
39
+ function clampRange(range, min, max) {
40
+ const r = normalizeRange(range);
41
+ if (!r) return void 0;
42
+ const start = min && r.start < min ? min : r.start;
43
+ const end = max && r.end > max ? max : r.end;
44
+ return start <= end ? { start, end } : void 0;
45
+ }
46
+ function formatRange(range, locale, format = { year: "numeric", month: "short", day: "numeric" }) {
47
+ const start = parseIsoDay(range.start);
48
+ const end = parseIsoDay(range.end);
49
+ if (!start || !end) return "";
50
+ const zone = "UTC";
51
+ const fmt = new Intl.DateTimeFormat(locale, { ...format, timeZone: zone });
52
+ return fmt.formatRange(start.toDate(zone), end.toDate(zone));
53
+ }
54
+ function reshapeRange(anchor, moving, rules = {}) {
55
+ const a = parseIsoDay(anchor);
56
+ const m = parseIsoDay(moving);
57
+ if (!a || !m) return null;
58
+ if (rules.allowed && !rules.allowed(m.toString())) return null;
59
+ const [start, end] = a.compare(m) <= 0 ? [a, m] : [m, a];
60
+ if (rules.maximumDays && end.compare(start) + 1 > rules.maximumDays) return null;
61
+ if (rules.unavailable) {
62
+ for (let d = start; d.compare(end) <= 0; d = d.add({ days: 1 })) {
63
+ if (rules.unavailable(d.toString())) return null;
64
+ }
65
+ }
66
+ return { start: start.toString(), end: end.toString() };
67
+ }
68
+ export {
69
+ clampRange,
70
+ defaultRangePresets,
71
+ formatRange,
72
+ normalizeRange,
73
+ parseIsoDay,
74
+ reshapeRange,
75
+ sameRange
76
+ };
@@ -0,0 +1,58 @@
1
+ export interface CsvColumn<Row> {
2
+ key: string;
3
+ /** Header cell. Defaults to the key. */
4
+ label?: string;
5
+ /** The value written for a row; the row's `key` field when omitted. */
6
+ value?: (row: Row) => unknown;
7
+ }
8
+ export interface CsvOptions {
9
+ /** Field separator. Default ",". Some locales' spreadsheets expect ";". */
10
+ separator?: string;
11
+ /** Prefix a UTF-8 byte order mark so Excel reads non-ASCII text correctly. */
12
+ bom?: boolean;
13
+ /**
14
+ * Neutralise cells a spreadsheet would run as a formula (leading = + - @,
15
+ * tab or CR) by prefixing a quote. On by default: exported data is often
16
+ * user-supplied, and opening it is enough to trigger a formula.
17
+ */
18
+ guardFormulas?: boolean;
19
+ /** Line ending. Default "\r\n", as RFC 4180 specifies. */
20
+ newline?: string;
21
+ }
22
+ /** One CSV field, quoted when it holds a separator, a quote or a line break. */
23
+ export declare function csvField(value: unknown, options?: CsvOptions): string;
24
+ /** Rows as CSV text, a header line first. */
25
+ export declare function toCsv<Row>(rows: readonly Row[], columns: readonly CsvColumn<Row>[], options?: CsvOptions): string;
26
+ /**
27
+ * Hand the viewer a file to save. Does nothing outside a browser, so a call
28
+ * that runs during SSR is harmless.
29
+ */
30
+ export declare function downloadFile(name: string, data: Blob | string, type?: string): void;
31
+ /**
32
+ * A standalone copy of a live SVG: every element carries its computed paint as
33
+ * an inline style, so CSS custom properties and classes from the page's
34
+ * stylesheet survive being rendered as an image, and running SMIL animations
35
+ * are frozen at their end state.
36
+ */
37
+ export declare function inlineSvg(svg: SVGSVGElement): SVGSVGElement;
38
+ export interface RasterOptions {
39
+ /** Device pixels per CSS pixel. Default: the screen's ratio, at least 2. */
40
+ scale?: number;
41
+ /** Fill behind the drawing; transparent when omitted. */
42
+ background?: string;
43
+ /** Extra space around the drawing, in CSS pixels. */
44
+ padding?: number;
45
+ /** Drawn above the SVG, in the page's own font. */
46
+ header?: (ctx: CanvasRenderingContext2D, width: number) => number;
47
+ }
48
+ /** Rasterise an SVG element to a PNG blob with its theme resolved. */
49
+ export declare function svgToPng(svg: SVGSVGElement, options?: RasterOptions): Promise<Blob>;
50
+ /** The first non-transparent background at or above an element. */
51
+ export declare function backgroundOf(el: Element | null): string | undefined;
52
+ /**
53
+ * A colour as the browser resolves it where `within` sits, for APIs that cannot
54
+ * read custom properties (canvas, an SVG drawn as an image).
55
+ */
56
+ export declare function resolveCssColor(value: string, within: Element): string;
57
+ /** A filesystem-safe name from a title. */
58
+ export declare function fileStem(title: string | undefined, fallback: string): string;
@@ -0,0 +1,165 @@
1
+ const FORMULA_START = /^[=+\-@\t\r]/;
2
+ function cellText(value) {
3
+ if (value == null) return "";
4
+ if (value instanceof Date) return Number.isNaN(value.getTime()) ? "" : value.toISOString();
5
+ if (typeof value === "object") return JSON.stringify(value);
6
+ return String(value);
7
+ }
8
+ function csvField(value, options = {}) {
9
+ const separator = options.separator ?? ",";
10
+ let text = cellText(value);
11
+ if ((options.guardFormulas ?? true) && typeof value === "string" && FORMULA_START.test(text)) {
12
+ text = `'${text}`;
13
+ }
14
+ const needsQuotes = text.includes(separator) || /["\r\n]/.test(text) || /^\s|\s$/.test(text);
15
+ return needsQuotes ? `"${text.replace(/"/g, '""')}"` : text;
16
+ }
17
+ function toCsv(rows, columns, options = {}) {
18
+ const separator = options.separator ?? ",";
19
+ const newline = options.newline ?? "\r\n";
20
+ const line = (cells) => cells.map((c) => csvField(c, options)).join(separator);
21
+ const out = [line(columns.map((c) => c.label ?? c.key))];
22
+ for (const row of rows) {
23
+ out.push(
24
+ line(columns.map((c) => c.value ? c.value(row) : row[c.key]))
25
+ );
26
+ }
27
+ return (options.bom ? "\uFEFF" : "") + out.join(newline) + newline;
28
+ }
29
+ function downloadFile(name, data, type = "text/plain;charset=utf-8") {
30
+ if (typeof document === "undefined" || typeof URL === "undefined") return;
31
+ const blob = typeof data === "string" ? new Blob([data], { type }) : data;
32
+ const url = URL.createObjectURL(blob);
33
+ const a = document.createElement("a");
34
+ a.href = url;
35
+ a.download = name;
36
+ a.rel = "noopener";
37
+ a.style.display = "none";
38
+ document.body.append(a);
39
+ a.click();
40
+ a.remove();
41
+ setTimeout(() => URL.revokeObjectURL(url), 0);
42
+ }
43
+ const PAINT_PROPS = [
44
+ "fill",
45
+ "fill-opacity",
46
+ "fill-rule",
47
+ "stroke",
48
+ "stroke-opacity",
49
+ "stroke-width",
50
+ "stroke-dasharray",
51
+ "stroke-dashoffset",
52
+ "stroke-linecap",
53
+ "stroke-linejoin",
54
+ "opacity",
55
+ "stop-color",
56
+ "stop-opacity",
57
+ "color",
58
+ "font-family",
59
+ "font-size",
60
+ "font-weight",
61
+ "letter-spacing",
62
+ "text-anchor",
63
+ "dominant-baseline",
64
+ "visibility",
65
+ "display"
66
+ ];
67
+ function inlineSvg(svg) {
68
+ const clone = svg.cloneNode(true);
69
+ const source = [svg, ...svg.querySelectorAll("*")];
70
+ const target = [clone, ...clone.querySelectorAll("*")];
71
+ source.forEach((el, i) => {
72
+ const copy = target[i];
73
+ if (!(copy instanceof Element)) return;
74
+ const computed = getComputedStyle(el);
75
+ const style = PAINT_PROPS.map((p) => `${p}:${computed.getPropertyValue(p)}`).filter((d) => !d.endsWith(":")).join(";");
76
+ copy.setAttribute("style", style);
77
+ copy.removeAttribute("class");
78
+ });
79
+ const comments = document.createTreeWalker(clone, NodeFilter.SHOW_COMMENT);
80
+ const dead = [];
81
+ while (comments.nextNode()) dead.push(comments.currentNode);
82
+ for (const node of dead) node.parentNode?.removeChild(node);
83
+ for (const anim of clone.querySelectorAll("animate")) {
84
+ const attr = anim.getAttribute("attributeName");
85
+ const to = anim.getAttribute("to");
86
+ if (attr && to != null) anim.parentElement?.setAttribute(attr, to);
87
+ anim.remove();
88
+ }
89
+ clone.setAttribute("xmlns", "http://www.w3.org/2000/svg");
90
+ const { width, height } = svg.getBoundingClientRect();
91
+ clone.setAttribute("width", String(width));
92
+ clone.setAttribute("height", String(height));
93
+ clone.style.overflow = "visible";
94
+ return clone;
95
+ }
96
+ async function svgToPng(svg, options = {}) {
97
+ const copy = inlineSvg(svg);
98
+ const width = Number(copy.getAttribute("width"));
99
+ const height = Number(copy.getAttribute("height"));
100
+ const markup = new XMLSerializer().serializeToString(copy);
101
+ const url = URL.createObjectURL(new Blob([markup], { type: "image/svg+xml;charset=utf-8" }));
102
+ try {
103
+ const img = new Image();
104
+ img.decoding = "async";
105
+ const loaded = new Promise((resolve, reject) => {
106
+ img.onload = () => resolve();
107
+ img.onerror = () => reject(new Error("SVG could not be rasterised"));
108
+ });
109
+ img.src = url;
110
+ await loaded;
111
+ const scale = options.scale ?? Math.max(2, globalThis.devicePixelRatio || 1);
112
+ const pad = options.padding ?? 0;
113
+ const measure = document.createElement("canvas").getContext("2d");
114
+ const headerHeight = measure && options.header ? options.header(measure, width) : 0;
115
+ const canvas = document.createElement("canvas");
116
+ canvas.width = Math.ceil((width + pad * 2) * scale);
117
+ canvas.height = Math.ceil((height + headerHeight + pad * 2) * scale);
118
+ const ctx = canvas.getContext("2d");
119
+ if (!ctx) throw new Error("Canvas 2D is unavailable");
120
+ ctx.scale(scale, scale);
121
+ if (options.background) {
122
+ ctx.fillStyle = options.background;
123
+ ctx.fillRect(0, 0, width + pad * 2, height + headerHeight + pad * 2);
124
+ }
125
+ ctx.translate(pad, pad);
126
+ if (options.header) options.header(ctx, width);
127
+ ctx.drawImage(img, 0, headerHeight, width, height);
128
+ return await new Promise(
129
+ (resolve, reject) => canvas.toBlob((b) => b ? resolve(b) : reject(new Error("PNG encoding failed")), "image/png")
130
+ );
131
+ } finally {
132
+ URL.revokeObjectURL(url);
133
+ }
134
+ }
135
+ function backgroundOf(el) {
136
+ for (let node = el; node; node = node.parentElement) {
137
+ const bg = getComputedStyle(node).backgroundColor;
138
+ if (bg && bg !== "transparent" && !/rgba\([^)]*,\s*0\)$/.test(bg)) return bg;
139
+ }
140
+ return void 0;
141
+ }
142
+ function resolveCssColor(value, within) {
143
+ if (!value.includes("var(") && !value.toLowerCase().includes("currentcolor")) return value;
144
+ const probe = document.createElement("span");
145
+ probe.style.color = value;
146
+ probe.style.display = "none";
147
+ within.append(probe);
148
+ const resolved = getComputedStyle(probe).color;
149
+ probe.remove();
150
+ return resolved || value;
151
+ }
152
+ function fileStem(title, fallback) {
153
+ const stem = (title ?? "").trim().replace(/[\\/:*?"<>|\u0000-\u001f]+/g, "").replace(/\s+/g, "-");
154
+ return stem || fallback;
155
+ }
156
+ export {
157
+ backgroundOf,
158
+ csvField,
159
+ downloadFile,
160
+ fileStem,
161
+ inlineSvg,
162
+ resolveCssColor,
163
+ svgToPng,
164
+ toCsv
165
+ };
@@ -0,0 +1,18 @@
1
+ /** The last `max` lines, and how many were cut from the front. */
2
+ export declare function ringWindow<T>(lines: readonly T[], max: number | undefined): {
3
+ lines: readonly T[];
4
+ offset: number;
5
+ };
6
+ /** Lines per level, a line with no level counting as `fallback`. */
7
+ export declare function countLevels<L extends string>(lines: readonly {
8
+ level?: L;
9
+ }[], fallback: L): Map<L, number>;
10
+ /** Case-insensitive substring test; an empty term matches nothing. */
11
+ export declare function matchesTerm(message: string, term: string): boolean;
12
+ /** Positions (into `rows`) of the rows whose message or source holds the term. */
13
+ export declare function matchPositions(rows: readonly {
14
+ message: string;
15
+ source?: string;
16
+ }[], term: string): number[];
17
+ /** The next match cursor, wrapping at both ends; -1 when there are none. */
18
+ export declare function stepMatch(current: number, total: number, direction: 1 | -1): number;
@@ -0,0 +1,36 @@
1
+ function ringWindow(lines, max) {
2
+ if (!max || max <= 0 || lines.length <= max) return { lines, offset: 0 };
3
+ return { lines: lines.slice(lines.length - max), offset: lines.length - max };
4
+ }
5
+ function countLevels(lines, fallback) {
6
+ const counts = /* @__PURE__ */ new Map();
7
+ for (const line of lines) {
8
+ const level = line.level ?? fallback;
9
+ counts.set(level, (counts.get(level) ?? 0) + 1);
10
+ }
11
+ return counts;
12
+ }
13
+ function matchesTerm(message, term) {
14
+ const needle = term.trim().toLowerCase();
15
+ return needle.length > 0 && message.toLowerCase().includes(needle);
16
+ }
17
+ function matchPositions(rows, term) {
18
+ if (!term.trim()) return [];
19
+ const out = [];
20
+ rows.forEach((row, i) => {
21
+ if (matchesTerm(row.message, term) || row.source !== void 0 && matchesTerm(row.source, term)) out.push(i);
22
+ });
23
+ return out;
24
+ }
25
+ function stepMatch(current, total, direction) {
26
+ if (total <= 0) return -1;
27
+ if (current < 0 || current >= total) return direction === 1 ? 0 : total - 1;
28
+ return (current + direction + total) % total;
29
+ }
30
+ export {
31
+ countLevels,
32
+ matchPositions,
33
+ matchesTerm,
34
+ ringWindow,
35
+ stepMatch
36
+ };