@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.
- package/README.md +49 -3
- package/dist/assets/{LpCommandPalette-DCP5g2ik.css → LpCommandPalette-HzAA4gri.css} +21 -21
- package/dist/assets/{LpRollingText-CR1mb0Vt.css → LpRollingText-BGnE6q9j.css} +3 -0
- package/dist/assets/{LpShortcutsDialog-ChUyU7oV.css → LpShortcutsDialog-CqYX3yy6.css} +28 -7
- package/dist/assets/{LpTable-DDQNdf86.css → LpTable-CPwWxTJS.css} +49 -9
- package/dist/chunks/{ContextMenuItems-CrfeNPWT.js → ContextMenuItems-BtKU7074.js} +2 -1
- package/dist/chunks/{LayoutCanvas-D-jPOAvg.js → LayoutCanvas-BkaGXTjx.js} +1 -1
- package/dist/chunks/{LayoutNode-D8Xy9N-o.js → LayoutNode-B3_9E1Xa.js} +9 -5
- package/dist/chunks/{LpActionBar-BbwCF6l5.js → LpActionBar-CnfFVIwC.js} +3 -3
- package/dist/chunks/{LpAddressInput-BrOqkZqg.js → LpAddressInput-CJOYGZlI.js} +7 -7
- package/dist/chunks/{LpAlert-DkOIjsbq.js → LpAlert-B6ilrM7T.js} +1 -1
- package/dist/chunks/{LpAppShell-BUKPcHco.js → LpAppShell-B07Lf48e.js} +4 -4
- package/dist/chunks/{LpAutocomplete-DxV3Y9h4.js → LpAutocomplete-C8IgSMsi.js} +2 -1
- package/dist/chunks/{LpAvatar-ClBbEYZN.js → LpAvatar-C1XStdOo.js} +3 -3
- package/dist/chunks/{LpBreadcrumbs-B8IJgFIc.js → LpBreadcrumbs-CQJd73Gm.js} +1 -1
- package/dist/chunks/{LpButton-kqJBHIIb.js → LpButton-CKSwC6Mu.js} +1 -1
- package/dist/chunks/{LpCalendar-B7Ko5RdR.js → LpCalendar-DrA2McTU.js} +1 -1
- package/dist/chunks/{LpCard-CpRByR0q.js → LpCard-C2IvucmX.js} +1 -1
- package/dist/chunks/{LpCheckbox-DpqchzH4.js → LpCheckbox-Bkj13CbW.js} +1 -1
- package/dist/chunks/{LpCodeBlock-DeHJPq7p.js → LpCodeBlock-ca7ANFyW.js} +1 -1
- package/dist/chunks/{LpColorPicker-Bhf1qxhB.js → LpColorPicker-zz4VGkG4.js} +46 -20
- package/dist/chunks/{LpConfirmDialog-CIUOSnWo.js → LpConfirmDialog-BTVAR4tF.js} +3 -3
- package/dist/chunks/{LpConfirmHost-CDm0Wtpv.js → LpConfirmHost-Ci_uCHgQ.js} +1 -1
- package/dist/chunks/{LpContextMenu-DQw5dGfG.js → LpContextMenu-BqkAYa9X.js} +2 -1
- package/dist/chunks/{LpDatePicker-Drirx1AK.js → LpDatePicker-BrdFtSTy.js} +16 -10
- package/dist/chunks/LpDateRangePicker-Drd7EbIz.js +210 -0
- package/dist/chunks/{LpDisclosure-ChQYmjlR.js → LpDisclosure-Cc23-JOT.js} +1 -1
- package/dist/chunks/{LpDrawer-bScx-KMO.js → LpDrawer-CfRhHwmE.js} +3 -3
- package/dist/chunks/{LpDropdownMenu-DJpoqRCb.js → LpDropdownMenu-DdJGQzPn.js} +2 -1
- package/dist/chunks/{LpEmptyState-Dsdqz1Wj.js → LpEmptyState-BJbZXC8D.js} +1 -1
- package/dist/chunks/LpFieldNotice-wtieLUTj.js +64 -0
- package/dist/chunks/{LpFileTree-CSI_5SK2.js → LpFileTree-CNurOvkV.js} +3 -3
- package/dist/chunks/{LpFileTreeNode-B4MiSQX2.js → LpFileTreeNode-D_qRRdsH.js} +3 -3
- package/dist/chunks/{LpFormField-CIk5qosh.js → LpFormField-CtVYj6tO.js} +29 -15
- package/dist/chunks/{LpIcon-CCnX5_2j.js → LpIcon-DYtaid0K.js} +20 -6
- package/dist/chunks/{LpInput-C0e8y8_d.js → LpInput-D-YGQbEv.js} +39 -16
- package/dist/chunks/{LpLightbox-Mr0W_6HK.js → LpLightbox-DSDahF23.js} +1 -1
- package/dist/chunks/{LpLogViewer-YBOaFnc_.js → LpLogViewer-KypbgOyo.js} +252 -58
- package/dist/chunks/{LpMapPicker-NUzS9e37.js → LpMapPicker-Cc84LaM3.js} +1 -1
- package/dist/chunks/{LpMediaGallery-DfJmMW0I.js → LpMediaGallery-YKr-cQPN.js} +2 -2
- package/dist/chunks/{LpModal-DPwGKBPv.js → LpModal-BzTVeNqe.js} +3 -3
- package/dist/chunks/{LpModalNav-DPg5H9f3.js → LpModalNav-CjABSGCu.js} +14 -8
- package/dist/chunks/{LpNotificationBell-t5yn-siX.js → LpNotificationBell-CCwyJP5C.js} +26 -14
- package/dist/chunks/{LpNumberField-DWnQKktS.js → LpNumberField-B77O-z28.js} +1 -1
- package/dist/chunks/{LpPagination-DFngX7Xo.js → LpPagination-BcDlo3r_.js} +1 -1
- package/dist/chunks/{LpPasswordInput-CWVDuBJ5.js → LpPasswordInput-eKzQhbQP.js} +2 -2
- package/dist/chunks/{LpPhoneInput-CD-ZTeSd.js → LpPhoneInput-BCbrrhgE.js} +126 -23
- package/dist/chunks/{LpPie-BLco31Nx.js → LpPie-BEJ2SfI6.js} +9 -10
- package/dist/chunks/{LpPopover-p_e_shN3.js → LpPopover-DCKeqiVn.js} +1 -0
- package/dist/chunks/LpRangeCalendar-DZuaRV0W.js +331 -0
- package/dist/chunks/{LpRollingText-CM5gkSeF.js → LpRollingText-DB7upf-5.js} +1 -1
- package/dist/chunks/{LpScrollArea-D8xyKXcF.js → LpScrollArea-Bry1fdOM.js} +14 -2
- package/dist/chunks/{LpSection-aM6J_u51.js → LpSection-tKEH0jYf.js} +1 -1
- package/dist/chunks/{LpSegmented-Dejd7cIx.js → LpSegmented-C09EEam2.js} +1 -1
- package/dist/chunks/{LpSelect-DrRD9I7L.js → LpSelect-DNIL6MB9.js} +20 -23
- package/dist/chunks/{LpSidebar-BgwUNWpJ.js → LpSidebar-Bwws_X29.js} +3 -3
- package/dist/chunks/{LpSidebarNav-Bqxz8aWT.js → LpSidebarNav-kx-LdqNU.js} +3 -3
- package/dist/chunks/{LpStat-dXtyrdX9.js → LpStat-B-7udBRP.js} +1 -1
- package/dist/chunks/{LpStepper-Bk-XaQYU.js → LpStepper-C7XiVKZj.js} +34 -19
- package/dist/chunks/{LpSwitch-B1aLKulj.js → LpSwitch-OrcOJX9m.js} +1 -1
- package/dist/chunks/LpTableFilter-BV8PpLM9.js +158 -0
- package/dist/chunks/{LpTabs-_qMVaZJ6.js → LpTabs-29iW1XOx.js} +1 -1
- package/dist/chunks/LpTagsInput-D1SuqbhB.js +300 -0
- package/dist/chunks/{LpTextarea-yP8hGedR.js → LpTextarea-uuScWo6-.js} +1 -1
- package/dist/chunks/{LpThemeProvider-Wjm7Tuit.js → LpThemeProvider-Be4r2TQX.js} +1 -1
- package/dist/chunks/{LpThemeSwitcher-CKLc10KZ.js → LpThemeSwitcher-B4aVPbNC.js} +19 -22
- package/dist/chunks/{LpTimeField-C5HRgS5H.js → LpTimeField-Cqe7fXnh.js} +1 -1
- package/dist/chunks/{LpToaster--oT6lfhL.js → LpToaster-DTtWuKvq.js} +76 -9
- package/dist/chunks/{LpTooltip-CBdzeKNf.js → LpTooltip-CXVKcOXT.js} +3 -2
- package/dist/chunks/{LpTopologyCanvas-DocsLal3.js → LpTopologyCanvas-6ozNrQKh.js} +2 -1
- package/dist/chunks/{LpUptimeBar-DLtxOMRy.js → LpUptimeBar-ugcv25xj.js} +2 -2
- package/dist/chunks/icons-CkA0njzm.js +43 -0
- package/dist/chunks/{useTheme-C8JHUlPM.js → useTheme-DJm1JSsY.js} +47 -50
- package/dist/component-names.d.ts +1 -1
- package/dist/components/ContextMenuItems.vue.js +1 -1
- package/dist/components/LayoutCanvas.vue.js +1 -1
- package/dist/components/LayoutNode.vue.js +1 -1
- package/dist/components/LpActionBar.vue.js +1 -1
- package/dist/components/LpAddressInput.vue.js +1 -1
- package/dist/components/LpAlert.vue.js +1 -1
- package/dist/components/LpAppShell.vue.js +1 -1
- package/dist/components/LpAutocomplete.vue.js +1 -1
- package/dist/components/LpAvatar.vue.js +1 -1
- package/dist/components/LpBreadcrumbs.vue.js +1 -1
- package/dist/components/LpButton.vue.d.ts +2 -2
- package/dist/components/LpButton.vue.js +1 -1
- package/dist/components/LpCalendar.vue.js +1 -1
- package/dist/components/LpCard.vue.js +1 -1
- package/dist/components/LpChart.vue.d.ts +16 -1
- package/dist/components/LpChart.vue.js +63 -5
- package/dist/components/LpCheckbox.vue.js +1 -1
- package/dist/components/LpCodeBlock.vue.js +1 -1
- package/dist/components/LpColorPicker.vue.d.ts +2 -2
- package/dist/components/LpColorPicker.vue.js +1 -1
- package/dist/components/LpCommandPalette.vue.d.ts +6 -0
- package/dist/components/LpCommandPalette.vue.js +62 -11
- package/dist/components/LpConfirmDialog.vue.js +1 -1
- package/dist/components/LpConfirmHost.vue.js +1 -1
- package/dist/components/LpContextMenu.vue.js +1 -1
- package/dist/components/LpDatePicker.vue.js +1 -1
- package/dist/components/LpDateRangePicker.vue.d.ts +60 -0
- package/dist/components/LpDateRangePicker.vue.js +4 -0
- package/dist/components/LpDisclosure.vue.js +1 -1
- package/dist/components/LpDrawer.vue.js +1 -1
- package/dist/components/LpDropdownMenu.vue.js +1 -1
- package/dist/components/LpDropzone.vue.js +1 -1
- package/dist/components/LpEmptyState.vue.js +1 -1
- package/dist/components/LpFieldNotice.vue.d.ts +8 -0
- package/dist/components/LpFieldNotice.vue.js +4 -0
- package/dist/components/LpFileTree.vue.js +1 -1
- package/dist/components/LpFileTreeNode.vue.js +1 -1
- package/dist/components/LpFormField.vue.d.ts +4 -1
- package/dist/components/LpFormField.vue.js +1 -1
- package/dist/components/LpIcon.vue.d.ts +0 -1
- package/dist/components/LpIcon.vue.js +1 -1
- package/dist/components/LpImageEditor.vue.js +2 -2
- package/dist/components/LpInput.vue.d.ts +19 -0
- package/dist/components/LpInput.vue.js +1 -1
- package/dist/components/LpLightbox.vue.js +1 -1
- package/dist/components/LpLogViewer.vue.d.ts +52 -1
- package/dist/components/LpLogViewer.vue.js +1 -1
- package/dist/components/LpMapPicker.vue.js +1 -1
- package/dist/components/LpMediaGallery.vue.js +1 -1
- package/dist/components/LpModal.vue.js +1 -1
- package/dist/components/LpModalNav.vue.js +1 -1
- package/dist/components/LpNotificationBell.vue.js +1 -1
- package/dist/components/LpNumberField.vue.js +1 -1
- package/dist/components/LpPagination.vue.js +1 -1
- package/dist/components/LpPasswordInput.vue.js +1 -1
- package/dist/components/LpPhoneInput.vue.d.ts +13 -0
- package/dist/components/LpPhoneInput.vue.js +1 -1
- package/dist/components/LpPie.vue.js +1 -1
- package/dist/components/LpPopover.vue.js +1 -1
- package/dist/components/LpProgress.vue.d.ts +1 -1
- package/dist/components/LpRangeCalendar.vue.d.ts +51 -0
- package/dist/components/LpRangeCalendar.vue.js +4 -0
- package/dist/components/LpRollingText.vue.d.ts +1 -1
- package/dist/components/LpRollingText.vue.js +1 -1
- package/dist/components/LpScrollArea.vue.d.ts +2 -2
- package/dist/components/LpScrollArea.vue.js +1 -1
- package/dist/components/LpSection.vue.js +1 -1
- package/dist/components/LpSegmented.vue.js +1 -1
- package/dist/components/LpSelect.vue.js +1 -1
- package/dist/components/LpShortcutsDialog.vue.d.ts +6 -0
- package/dist/components/LpShortcutsDialog.vue.js +56 -14
- package/dist/components/LpSidebar.vue.js +1 -1
- package/dist/components/LpSidebarNav.vue.js +1 -1
- package/dist/components/LpStat.vue.js +1 -1
- package/dist/components/LpStepper.vue.js +1 -1
- package/dist/components/LpSwitch.vue.js +1 -1
- package/dist/components/LpTable.vue.d.ts +84 -2
- package/dist/components/LpTable.vue.js +481 -107
- package/dist/components/LpTableFilter.vue.d.ts +31 -0
- package/dist/components/LpTableFilter.vue.js +4 -0
- package/dist/components/LpTabs.vue.js +1 -1
- package/dist/components/LpTagsInput.vue.d.ts +77 -0
- package/dist/components/LpTagsInput.vue.js +4 -0
- package/dist/components/LpTextarea.vue.js +1 -1
- package/dist/components/LpThemeProvider.vue.js +1 -1
- package/dist/components/LpThemeSwitcher.vue.d.ts +2 -2
- package/dist/components/LpThemeSwitcher.vue.js +1 -1
- package/dist/components/LpTimeField.vue.js +1 -1
- package/dist/components/LpToaster.vue.d.ts +2 -0
- package/dist/components/LpToaster.vue.js +1 -1
- package/dist/components/LpTooltip.vue.js +1 -1
- package/dist/components/LpTopologyCanvas.vue.js +1 -1
- package/dist/components/LpUptimeBar.vue.js +1 -1
- package/dist/components/chart.js +3 -2
- package/dist/components/commandSearch.js +3 -0
- package/dist/components/dateRange.d.ts +43 -0
- package/dist/components/dateRange.js +76 -0
- package/dist/components/exportData.d.ts +58 -0
- package/dist/components/exportData.js +165 -0
- package/dist/components/logSearch.d.ts +18 -0
- package/dist/components/logSearch.js +36 -0
- package/dist/components/phone.d.ts +41 -0
- package/dist/components/phone.js +80 -0
- package/dist/components/tableFilter.d.ts +36 -0
- package/dist/components/tableFilter.js +84 -0
- package/dist/components/tags.d.ts +20 -0
- package/dist/components/tags.js +37 -0
- package/dist/composables/useField.d.ts +4 -0
- package/dist/composables/useFieldNotice.d.ts +17 -0
- package/dist/composables/useFieldNotice.js +28 -0
- package/dist/composables/useForm.d.ts +53 -0
- package/dist/composables/useForm.js +207 -0
- package/dist/composables/useHotkeys.d.ts +65 -5
- package/dist/composables/useHotkeys.js +170 -9
- package/dist/composables/useInputMask.d.ts +59 -0
- package/dist/composables/useInputMask.js +170 -0
- package/dist/composables/useLocale.d.ts +2 -0
- package/dist/composables/useLocale.js +9 -0
- package/dist/composables/usePaintSelect.d.ts +22 -0
- package/dist/composables/usePaintSelect.js +169 -0
- package/dist/composables/useShift.js +7 -2
- package/dist/icons-all.d.ts +1 -0
- package/dist/icons-all.js +3 -0
- package/dist/icons.d.ts +14 -1
- package/dist/index.d.ts +29 -3
- package/dist/index.js +195 -138
- package/dist/kit-icons.d.ts +2 -0
- package/dist/theme/backdrop.d.ts +12 -0
- package/dist/theme/presets.d.ts +0 -2
- package/package.json +13 -4
- package/src/component-names.ts +4 -0
- package/src/components/ContextMenuItems.vue +1 -1
- package/src/components/LayoutNode.vue +11 -2
- package/src/components/LpActionBar.vue +1 -1
- package/src/components/LpAutocomplete.vue +1 -0
- package/src/components/LpAvatar.vue +2 -2
- package/src/components/LpButton.vue +1 -1
- package/src/components/LpChart.vue +80 -1
- package/src/components/LpColorPicker.vue +34 -1
- package/src/components/LpCommandPalette.vue +82 -8
- package/src/components/LpContextMenu.vue +1 -1
- package/src/components/LpDatePicker.vue +11 -4
- package/src/components/LpDateRangePicker.vue +226 -0
- package/src/components/LpDrawer.vue +1 -1
- package/src/components/LpDropdownMenu.vue +1 -0
- package/src/components/LpFieldNotice.vue +65 -0
- package/src/components/LpFormField.vue +33 -4
- package/src/components/LpIcon.vue +22 -4
- package/src/components/LpInput.vue +46 -6
- package/src/components/LpLogViewer.vue +225 -22
- package/src/components/LpModal.vue +2 -2
- package/src/components/LpModalNav.vue +13 -2
- package/src/components/LpNotificationBell.vue +15 -7
- package/src/components/LpPhoneInput.vue +179 -20
- package/src/components/LpPie.vue +8 -5
- package/src/components/LpPopover.vue +1 -0
- package/src/components/LpRangeCalendar.vue +365 -0
- package/src/components/LpRollingText.vue +3 -0
- package/src/components/LpScrollArea.vue +22 -2
- package/src/components/LpSelect.vue +0 -0
- package/src/components/LpShortcutsDialog.vue +77 -8
- package/src/components/LpStepper.vue +23 -10
- package/src/components/LpSwitch.vue +1 -1
- package/src/components/LpTable.vue +584 -65
- package/src/components/LpTableFilter.vue +175 -0
- package/src/components/LpTagsInput.vue +364 -0
- package/src/components/LpThemeSwitcher.vue +19 -23
- package/src/components/LpToaster.vue +91 -5
- package/src/components/LpTooltip.vue +9 -2
- package/src/components/LpTopologyCanvas.vue +7 -1
- package/src/components/chart.ts +5 -3
- package/src/components/commandSearch.ts +6 -0
- package/src/components/dateRange.ts +134 -0
- package/src/components/exportData.ts +228 -0
- package/src/components/logSearch.ts +46 -0
- package/src/components/phone.ts +140 -0
- package/src/components/tableFilter.ts +122 -0
- package/src/components/tags.ts +62 -0
- package/src/composables/useField.ts +4 -0
- package/src/composables/useFieldNotice.ts +59 -0
- package/src/composables/useForm.ts +314 -0
- package/src/composables/useHotkeys.ts +269 -13
- package/src/composables/useInputMask.ts +254 -0
- package/src/composables/useLocale.ts +14 -0
- package/src/composables/usePaintSelect.ts +243 -0
- package/src/composables/useShift.ts +13 -2
- package/src/iconSubset.d.mts +10 -0
- package/src/iconSubset.mjs +51 -0
- package/src/icons-all.ts +10 -0
- package/src/icons.ts +59 -8
- package/src/index.ts +37 -3
- package/src/kit-icons.ts +5 -0
- package/src/nuxt.ts +30 -2
- package/src/runtime/theme.plugin.ts +2 -2
- package/src/theme/backdrop.ts +69 -0
- package/src/theme/presets.ts +6 -64
- 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,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>;
|
|
@@ -13,9 +13,9 @@ type __VLS_Props = {
|
|
|
13
13
|
cycleThemes?: (string | TokenSet)[];
|
|
14
14
|
/**
|
|
15
15
|
* Trigger style:
|
|
16
|
-
* - "swatch" (default): a
|
|
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":
|
|
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,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>;
|
package/dist/components/chart.js
CHANGED
|
@@ -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
|
|
49
|
-
max
|
|
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
|
+
};
|