@svgrid/grid 3.0.2 → 3.0.4
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 +2 -1
- package/dist/GridMenus.svelte +44 -2
- package/dist/SvChartMenu.svelte +69 -0
- package/dist/SvChartMenu.svelte.d.ts +11 -0
- package/dist/SvChartPanes.svelte +113 -0
- package/dist/SvChartPanes.svelte.d.ts +20 -0
- package/dist/SvGrid.controller.svelte.d.ts +110 -39
- package/dist/SvGrid.controller.svelte.js +655 -200
- package/dist/SvGrid.css +105 -2
- package/dist/SvGrid.svelte +386 -514
- package/dist/SvGrid.types.d.ts +210 -9
- package/dist/SvGridCellEditor.svelte +17 -0
- package/dist/SvGridChart.svelte +2257 -329
- package/dist/SvGridChart.svelte.d.ts +6 -106
- package/dist/SvGridChart.types.d.ts +338 -0
- package/dist/SvGridChart.types.js +1 -0
- package/dist/SvGridChartBuilder.svelte +323 -0
- package/dist/SvGridChartBuilder.svelte.d.ts +34 -0
- package/dist/SvGridChartPanel.svelte +221 -275
- package/dist/SvGridChartPickers.svelte +417 -0
- package/dist/SvGridChartPickers.svelte.d.ts +70 -0
- package/dist/SvGridChartView.svelte +13 -14
- package/dist/SvModal.svelte +7 -1
- package/dist/SvModal.svelte.d.ts +5 -0
- package/dist/ai.d.ts +40 -8
- package/dist/ai.js +135 -24
- package/dist/aria.d.ts +11 -0
- package/dist/build-api.js +108 -22
- package/dist/cdn/GridMenus-7kbpnnBW.js +635 -0
- package/dist/cdn/GridMenus-BL7ZgQvU.js +636 -0
- package/dist/cdn/SvChartMenu-Bl6PBbkT.js +58 -0
- package/dist/cdn/SvChartMenu-FBSMINA6.js +59 -0
- package/dist/cdn/{SvDateRangeInput-DMLKmGEc.js → SvDateRangeInput-BeU_TkbQ.js} +15 -14
- package/dist/cdn/{SvDateRangeInput-CaOuMs8O.js → SvDateRangeInput-yX8vzleW.js} +38 -37
- package/dist/cdn/{SvDateTimePicker-sonaH0oh.js → SvDateTimePicker-DQwt4UAs.js} +139 -180
- package/dist/cdn/SvDateTimePicker-vNU6bZ-q.js +775 -0
- package/dist/cdn/{SvGridCellEditor-CjEJMJKc.js → SvGridCellEditor-B1p-vCK5.js} +188 -178
- package/dist/cdn/{SvGridCellEditor-BWnTi2N7.js → SvGridCellEditor-D_0q4xAu.js} +98 -88
- package/dist/cdn/SvGridChart-C3EWAZaM.js +3574 -0
- package/dist/cdn/SvGridChart-DzLkSwCH.js +3572 -0
- package/dist/cdn/SvGridChartBuilder-BE2T1ykB.js +783 -0
- package/dist/cdn/SvGridChartBuilder-CfII62sZ.js +784 -0
- package/dist/cdn/SvGridChartPanel-CCX5_Wgd.js +675 -0
- package/dist/cdn/SvGridChartPanel-xf4sWVTo.js +699 -0
- package/dist/cdn/SvGridChartView-CfuXmY5I.js +48 -0
- package/dist/cdn/SvGridChartView-DYwabQWj.js +47 -0
- package/dist/cdn/SvMenuList-CLN8OuIK.js +452 -0
- package/dist/cdn/SvMenuList-DkGhNKjf.js +451 -0
- package/dist/cdn/SvModal-BAE-pjZX.js +396 -0
- package/dist/cdn/SvModal-CIZWCcad.js +397 -0
- package/dist/cdn/chart-Dz7SqMXH.js +4341 -0
- package/dist/cdn/chart-export-BXqueeWJ.js +135 -0
- package/dist/cdn/chart-export-pdf-DONFUnNY.js +110 -0
- package/dist/cdn/chart-panel-messages-CUbf2R4i.js +1052 -0
- package/dist/cdn/chart-panel-messages-CmNrMdsr.js +1053 -0
- package/dist/cdn/chart-summary-BJW_tg_X.js +138 -0
- package/dist/cdn/chart-trend-CaN9mDEV.js +50 -0
- package/dist/cdn/chart-validate-HcOVFAfJ.js +188 -0
- package/dist/cdn/{column-resize-DsfNXMom.js → column-resize-DpmOLfRp.js} +3 -3
- package/dist/cdn/{date-format-BnnHlqGw.js → date-format-CtquV-p3.js} +583 -603
- package/dist/cdn/{date-format-BNii4zeD.js → date-format-D6KFzU_W.js} +347 -367
- package/dist/cdn/dismissable-DAHetSNk.js +44 -0
- package/dist/cdn/editor-contract-LXgQJAgd.js +22 -0
- package/dist/cdn/focus-trap-BBOQYBma.js +65 -0
- package/dist/cdn/{row-resize-BRcimkUT.js → row-resize-niQCp040.js} +44 -36
- package/dist/cdn/{src-DNbz94Ct.js → src-BKhZ6eXd.js} +10227 -9787
- package/dist/cdn/{src-BJ2opd0j.js → src-V1uu8iE9.js} +6568 -6128
- package/dist/cdn/svgrid.js +26 -15
- package/dist/cdn/svgrid.svelte-external.js +26 -15
- package/dist/chart-axes.d.ts +53 -0
- package/dist/chart-axes.js +351 -0
- package/dist/chart-cartesian.d.ts +88 -0
- package/dist/chart-cartesian.js +1862 -0
- package/dist/chart-decimate.d.ts +51 -0
- package/dist/chart-decimate.js +199 -0
- package/dist/chart-export-pdf.d.ts +47 -0
- package/dist/chart-export-pdf.js +187 -0
- package/dist/chart-export.d.ts +2 -1
- package/dist/chart-export.js +18 -3
- package/dist/chart-financial.d.ts +91 -0
- package/dist/chart-financial.js +175 -0
- package/dist/chart-flow.d.ts +10 -0
- package/dist/chart-flow.js +298 -0
- package/dist/chart-format.d.ts +18 -0
- package/dist/chart-format.js +65 -0
- package/dist/chart-grid.d.ts +8 -0
- package/dist/chart-grid.js +190 -0
- package/dist/chart-hierarchy.d.ts +17 -0
- package/dist/chart-hierarchy.js +146 -0
- package/dist/chart-indicators.d.ts +115 -0
- package/dist/chart-indicators.js +389 -0
- package/dist/chart-messages.d.ts +95 -0
- package/dist/chart-messages.js +92 -0
- package/dist/chart-motion.d.ts +16 -0
- package/dist/chart-motion.js +141 -0
- package/dist/chart-panel-messages.d.ts +265 -0
- package/dist/chart-panel-messages.js +285 -0
- package/dist/chart-pivot.d.ts +87 -0
- package/dist/chart-pivot.js +156 -0
- package/dist/chart-polar.d.ts +25 -0
- package/dist/chart-polar.js +700 -0
- package/dist/chart-samples.d.ts +16 -0
- package/dist/chart-samples.js +153 -0
- package/dist/chart-scale.d.ts +113 -0
- package/dist/chart-scale.js +405 -0
- package/dist/chart-stats.d.ts +111 -0
- package/dist/chart-stats.js +419 -0
- package/dist/chart-stream.d.ts +45 -0
- package/dist/chart-stream.js +91 -0
- package/dist/chart-summary.d.ts +27 -0
- package/dist/chart-summary.js +205 -0
- package/dist/chart-sync.svelte.d.ts +32 -0
- package/dist/chart-sync.svelte.js +23 -0
- package/dist/chart-table.d.ts +35 -0
- package/dist/chart-table.js +165 -0
- package/dist/chart-trend.d.ts +19 -0
- package/dist/chart-trend.js +61 -0
- package/dist/chart-types.d.ts +1456 -0
- package/dist/chart-types.js +6 -0
- package/dist/chart-validate.d.ts +43 -0
- package/dist/chart-validate.js +272 -0
- package/dist/chart-zoom.d.ts +40 -0
- package/dist/chart-zoom.js +145 -0
- package/dist/chart.d.ts +186 -865
- package/dist/chart.js +460 -2204
- package/dist/clipboard.d.ts +1 -0
- package/dist/clipboard.js +137 -18
- package/dist/column-resize.d.ts +3 -0
- package/dist/column-resize.js +4 -1
- package/dist/columns.js +3 -0
- package/dist/command-context.d.ts +19 -0
- package/dist/command-context.js +116 -0
- package/dist/core.d.ts +7 -0
- package/dist/createPopoverSelect.svelte.d.ts +2 -2
- package/dist/editing.d.ts +2 -8
- package/dist/editing.js +262 -33
- package/dist/fill-patterns.d.ts +0 -5
- package/dist/fill-patterns.js +56 -2
- package/dist/grid-messages.d.ts +10 -3
- package/dist/grid-messages.js +5 -0
- package/dist/history.d.ts +83 -0
- package/dist/history.js +133 -0
- package/dist/index.d.ts +24 -6
- package/dist/index.js +20 -2
- package/dist/keyboard-handlers.js +88 -31
- package/dist/keyboard.d.ts +55 -0
- package/dist/keyboard.js +132 -0
- package/dist/menus.d.ts +3 -1
- package/dist/menus.js +7 -2
- package/dist/merges.d.ts +97 -0
- package/dist/merges.js +147 -0
- package/dist/row-resize.d.ts +3 -0
- package/dist/row-resize.js +14 -0
- package/dist/scroll-sync.d.ts +1 -0
- package/dist/scroll-sync.js +24 -0
- package/dist/selection.d.ts +16 -0
- package/dist/selection.js +108 -16
- package/dist/shortcut-registry.d.ts +145 -0
- package/dist/shortcut-registry.js +44 -0
- package/dist/svgrid-wrapper.types.d.ts +213 -22
- package/dist/virtualization/virtualizer.js +38 -17
- package/package.json +6 -1
- package/src/GridMenus.svelte +44 -2
- package/src/SvChartMenu.svelte +69 -0
- package/src/SvChartPanes.svelte +113 -0
- package/src/SvChartPanes.test.ts +66 -0
- package/src/SvGrid.controller.svelte.ts +629 -172
- package/src/SvGrid.css +105 -2
- package/src/SvGrid.svelte +386 -514
- package/src/SvGrid.types.ts +188 -8
- package/src/SvGridCellEditor.svelte +17 -0
- package/src/SvGridChart.svelte +2257 -329
- package/src/SvGridChart.test.ts +1419 -1
- package/src/SvGridChart.types.ts +336 -0
- package/src/SvGridChartBuilder.svelte +323 -0
- package/src/SvGridChartPanel.svelte +221 -275
- package/src/SvGridChartPickers.svelte +417 -0
- package/src/SvGridChartView.svelte +13 -14
- package/src/SvModal.svelte +7 -1
- package/src/SvModal.test.ts +9 -0
- package/src/ai.test.ts +57 -2
- package/src/ai.ts +166 -22
- package/src/aria.d.ts +11 -0
- package/src/build-api.coverage.test.ts +184 -0
- package/src/build-api.ts +107 -18
- package/src/chart-axes.test.ts +573 -0
- package/src/chart-axes.ts +342 -0
- package/src/chart-cartesian.ts +1863 -0
- package/src/chart-decimate.test.ts +249 -0
- package/src/chart-decimate.ts +186 -0
- package/src/chart-export-pdf.test.ts +91 -0
- package/src/chart-export-pdf.ts +207 -0
- package/src/chart-export.test.ts +14 -0
- package/src/chart-export.ts +13 -3
- package/src/chart-financial.ts +208 -0
- package/src/chart-flow.ts +286 -0
- package/src/chart-format.ts +67 -0
- package/src/chart-grid.ts +179 -0
- package/src/chart-hierarchy.ts +135 -0
- package/src/chart-indicators.test.ts +443 -0
- package/src/chart-indicators.ts +384 -0
- package/src/chart-messages.test.ts +21 -0
- package/src/chart-messages.ts +184 -0
- package/src/chart-motion.test.ts +71 -0
- package/src/chart-motion.ts +148 -0
- package/src/chart-panel-messages.test.ts +29 -0
- package/src/chart-panel-messages.ts +550 -0
- package/src/chart-pivot.test.ts +54 -0
- package/src/chart-pivot.ts +225 -0
- package/src/chart-polar.ts +674 -0
- package/src/chart-samples.ts +106 -0
- package/src/chart-scale.ts +394 -0
- package/src/chart-series-types.test.ts +714 -0
- package/src/chart-stats.ts +409 -0
- package/src/chart-stream.test.ts +75 -0
- package/src/chart-stream.ts +114 -0
- package/src/chart-summary.test.ts +90 -0
- package/src/chart-summary.ts +197 -0
- package/src/chart-sync.svelte.ts +41 -0
- package/src/chart-table.test.ts +76 -0
- package/src/chart-table.ts +178 -0
- package/src/chart-trend.ts +47 -0
- package/src/chart-types.ts +1309 -0
- package/src/chart-validate.test.ts +100 -0
- package/src/chart-validate.ts +247 -0
- package/src/chart-zoom.test.ts +137 -0
- package/src/chart-zoom.ts +124 -0
- package/src/chart.coverage.test.ts +81 -0
- package/src/chart.test.ts +56 -3
- package/src/chart.ts +557 -2784
- package/src/clipboard.test.ts +151 -0
- package/src/clipboard.ts +145 -16
- package/src/column-resize.ts +7 -1
- package/src/columns.ts +2 -0
- package/src/command-context.test.ts +200 -0
- package/src/command-context.ts +137 -0
- package/src/core.ts +7 -0
- package/src/editing.test.ts +281 -3
- package/src/editing.ts +256 -38
- package/src/fill-patterns.test.ts +35 -0
- package/src/fill-patterns.ts +56 -2
- package/src/grid-messages.ts +16 -3
- package/src/history.test.ts +196 -0
- package/src/history.ts +162 -0
- package/src/icon-seam.test.ts +3 -2
- package/src/index.ts +150 -2
- package/src/keyboard-handlers.coverage.test.ts +126 -6
- package/src/keyboard-handlers.ts +91 -30
- package/src/keyboard-shortcuts.seam.test.ts +200 -0
- package/src/keyboard.test.ts +124 -1
- package/src/keyboard.ts +142 -0
- package/src/menus.test.ts +26 -0
- package/src/menus.ts +10 -3
- package/src/merges.test.ts +112 -0
- package/src/merges.ts +168 -0
- package/src/pivot.grid.test.ts +40 -5
- package/src/row-resize.test.ts +44 -0
- package/src/row-resize.ts +17 -0
- package/src/scroll-sync.test.ts +42 -1
- package/src/scroll-sync.ts +25 -0
- package/src/selection.multi-range.test.ts +34 -0
- package/src/selection.test.ts +30 -2
- package/src/selection.ts +111 -19
- package/src/shortcut-registry.test.ts +97 -0
- package/src/shortcut-registry.ts +181 -0
- package/src/svgrid-wrapper.types.ts +184 -13
- package/src/svgrid.behavior.test.ts +135 -0
- package/src/svgrid.charting.test.ts +513 -3
- package/src/svgrid.context-menu.test.ts +31 -0
- package/src/svgrid.new-features.wrapper.test.ts +10 -3
- package/src/virtualization/virtualizer.ts +39 -17
- package/dist/cdn/GridMenus-DyFA-QxA.js +0 -602
- package/dist/cdn/GridMenus-M2XP9t0_.js +0 -603
- package/dist/cdn/SvDateTimePicker-CCbDZNZB.js +0 -816
- package/dist/cdn/SvGridChart-DAb9RbRs.js +0 -1480
- package/dist/cdn/SvGridChart-Yl-IXZFO.js +0 -1481
- package/dist/cdn/SvGridChartPanel-DayQpDsR.js +0 -834
- package/dist/cdn/SvGridChartPanel-aqf8n-vJ.js +0 -810
- package/dist/cdn/SvGridChartView-CxfakxR0.js +0 -56
- package/dist/cdn/SvGridChartView-Dm_YEx9L.js +0 -55
- package/dist/cdn/chart-CKJRCPOk.js +0 -1652
|
@@ -0,0 +1,323 @@
|
|
|
1
|
+
<script lang="ts" generics="TFeatures extends TableFeatures = TableFeatures, TData extends RowData = RowData">
|
|
2
|
+
/**
|
|
3
|
+
* The chart builder behind the grid panel's Build button: a modal with a
|
|
4
|
+
* type gallery of live thumbnails, the same pickers the panel shows (one
|
|
5
|
+
* component, SvGridChartPickers, laid out as a form), and a Format tab for
|
|
6
|
+
* the things the derived spec does not carry (titles, axis bounds, legend
|
|
7
|
+
* placement, per-series colour / type / axis / stack, label placement,
|
|
8
|
+
* series and crosshair labels, a compact rule for narrow widths, palette,
|
|
9
|
+
* font and colours).
|
|
10
|
+
*
|
|
11
|
+
* Format edits are plain data ({@link ChartFormatState}) on the chart tab,
|
|
12
|
+
* applied by the engine to every spec the panel derives, so they survive a
|
|
13
|
+
* data change and round-trip through the saved view. Loaded lazily by the
|
|
14
|
+
* panel on the first open. Every label comes from the panel's messages, so
|
|
15
|
+
* `localization.text` translates the builder too.
|
|
16
|
+
*/
|
|
17
|
+
import SvModal from "./SvModal.svelte";
|
|
18
|
+
import SvTabs from "./SvTabs.svelte";
|
|
19
|
+
import SvGridChart from "./SvGridChart.svelte";
|
|
20
|
+
import SvGridChartPickers, { type ChartPanelTypeDef } from "./SvGridChartPickers.svelte";
|
|
21
|
+
import { sampleChartThumb } from "./chart-samples";
|
|
22
|
+
import { chartPanelMessage, type GridChartPanelMessages } from "./chart-panel-messages";
|
|
23
|
+
import type { ChartFormatState, ChartMarkerShape, ChartValueFormat, RowData, TableFeatures } from "./index";
|
|
24
|
+
import type { SvGridController } from "./SvGrid.controller.svelte";
|
|
25
|
+
|
|
26
|
+
let {
|
|
27
|
+
ctrl,
|
|
28
|
+
open = $bindable(false),
|
|
29
|
+
types,
|
|
30
|
+
messages: m,
|
|
31
|
+
}: {
|
|
32
|
+
ctrl: SvGridController<TFeatures, TData>;
|
|
33
|
+
open?: boolean;
|
|
34
|
+
/** The types the panel offers for the current columns, in its groups. */
|
|
35
|
+
types: ChartPanelTypeDef[];
|
|
36
|
+
messages: GridChartPanelMessages;
|
|
37
|
+
} = $props();
|
|
38
|
+
|
|
39
|
+
let tab = $state("type");
|
|
40
|
+
const groups = $derived([...new Set(types.map((t) => t.group))]);
|
|
41
|
+
const spec = $derived(ctrl.chartSpec);
|
|
42
|
+
const palette = $derived(ctrl.chartPalette ?? undefined);
|
|
43
|
+
const seriesLabels = $derived(spec?.series.map((s) => s.label) ?? []);
|
|
44
|
+
|
|
45
|
+
const fmt = $derived<ChartFormatState>(ctrl.chartFormat ?? {});
|
|
46
|
+
function patch(p: Partial<ChartFormatState>) {
|
|
47
|
+
ctrl.chartFormat = { ...fmt, ...p };
|
|
48
|
+
}
|
|
49
|
+
function patchAxis(key: "xAxis" | "yAxis" | "y2Axis", p: Record<string, unknown>) {
|
|
50
|
+
patch({ [key]: { ...(fmt[key] ?? {}), ...p } } as Partial<ChartFormatState>);
|
|
51
|
+
}
|
|
52
|
+
function patchSeries(label: string, p: NonNullable<ChartFormatState["series"]>[string]) {
|
|
53
|
+
patch({ series: { ...(fmt.series ?? {}), [label]: { ...(fmt.series?.[label] ?? {}), ...p } } });
|
|
54
|
+
}
|
|
55
|
+
function patchStyle(p: NonNullable<ChartFormatState["style"]>) {
|
|
56
|
+
patch({ style: { ...(fmt.style ?? {}), ...p } });
|
|
57
|
+
}
|
|
58
|
+
const num = (v: string): number | null => (v.trim() === "" ? null : Number(v));
|
|
59
|
+
const hasRightAxis = $derived(!!spec?.series.some((s) => s.axis === "right") || !!fmt.series && Object.values(fmt.series).some((s) => s?.axis === "right"));
|
|
60
|
+
/** Stacks only mean something on bars and areas; the column shows for a chart that has any. */
|
|
61
|
+
const hasStackable = $derived(!!spec && ["bar", "area"].includes(spec.type));
|
|
62
|
+
const MARKERS: ChartMarkerShape[] = ["circle", "square", "diamond", "triangle", "cross", "none"];
|
|
63
|
+
const FORMATS: ChartValueFormat[] = ["number", "currency", "percent", "compact"];
|
|
64
|
+
</script>
|
|
65
|
+
|
|
66
|
+
<SvModal bind:open title={m.chartBuilderTitle} size="lg">
|
|
67
|
+
<div class="sv-grid-chart-builder">
|
|
68
|
+
<SvTabs
|
|
69
|
+
tabs={[{ id: "type", label: m.chartBuilderTabType }, { id: "data", label: m.chartBuilderTabData }, { id: "format", label: m.chartBuilderTabFormat }]}
|
|
70
|
+
bind:value={tab}
|
|
71
|
+
ariaLabel={m.chartBuilderTitle}
|
|
72
|
+
>
|
|
73
|
+
{#snippet panel(id)}
|
|
74
|
+
{#if id === "type"}
|
|
75
|
+
<div class="sv-grid-chart-builder-gallery">
|
|
76
|
+
{#each groups as g (g)}
|
|
77
|
+
<div class="sv-grid-chart-builder-group">{g}</div>
|
|
78
|
+
<div class="sv-grid-chart-builder-cards">
|
|
79
|
+
{#each types.filter((t) => t.group === g) as t (t.value)}
|
|
80
|
+
<button
|
|
81
|
+
type="button"
|
|
82
|
+
class="sv-grid-chart-builder-card"
|
|
83
|
+
class:is-selected={ctrl.chartType === t.value}
|
|
84
|
+
aria-pressed={ctrl.chartType === t.value}
|
|
85
|
+
title={t.label}
|
|
86
|
+
onclick={() => (ctrl.chartType = t.value)}
|
|
87
|
+
>
|
|
88
|
+
<div class="sv-grid-chart-builder-thumb">
|
|
89
|
+
<SvGridChart spec={sampleChartThumb(t.value, palette)} interactive={false} legend={false} toolbar={false} announce={false} />
|
|
90
|
+
</div>
|
|
91
|
+
<span class="sv-grid-chart-builder-card-label">{t.label}</span>
|
|
92
|
+
</button>
|
|
93
|
+
{/each}
|
|
94
|
+
</div>
|
|
95
|
+
{/each}
|
|
96
|
+
</div>
|
|
97
|
+
{:else if id === "data"}
|
|
98
|
+
<div class="sv-grid-chart-builder-form">
|
|
99
|
+
<SvGridChartPickers {ctrl} messages={m} scope="builder" />
|
|
100
|
+
<label class="sv-grid-chart-builder-row">
|
|
101
|
+
<span>{m.chartBuilderLinked}</span>
|
|
102
|
+
<input type="checkbox" checked={!ctrl.chartFrozen} onchange={(e) => (e.currentTarget.checked ? ctrl.unfreezeChart() : ctrl.freezeChart())} />
|
|
103
|
+
<small>{ctrl.chartFrozen ? chartPanelMessage(m.chartBuilderFrozenAt, { time: new Date(ctrl.chartFrozen.at).toLocaleTimeString() }) : m.chartBuilderFollows}</small>
|
|
104
|
+
</label>
|
|
105
|
+
</div>
|
|
106
|
+
{:else}
|
|
107
|
+
<div class="sv-grid-chart-builder-form">
|
|
108
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderTitleField}</span><input type="text" value={fmt.title ?? ""} oninput={(e) => patch({ title: e.currentTarget.value })} /></label>
|
|
109
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderSubtitle}</span><input type="text" value={fmt.subtitle ?? ""} oninput={(e) => patch({ subtitle: e.currentTarget.value })} /></label>
|
|
110
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderCaption}</span><input type="text" value={fmt.caption ?? ""} oninput={(e) => patch({ caption: e.currentTarget.value })} /></label>
|
|
111
|
+
<label class="sv-grid-chart-builder-row">
|
|
112
|
+
<span>{m.chartBuilderLegend}</span>
|
|
113
|
+
<select value={fmt.legend === false ? "none" : (fmt.legend ?? "bottom")} onchange={(e) => patch({ legend: e.currentTarget.value === "none" ? false : (e.currentTarget.value as "top" | "bottom" | "left" | "right") })}>
|
|
114
|
+
<option value="bottom">{m.chartLegendBottom}</option><option value="top">{m.chartLegendTop}</option><option value="left">{m.chartLegendLeft}</option><option value="right">{m.chartLegendRight}</option><option value="none">{m.chartLegendHidden}</option>
|
|
115
|
+
</select>
|
|
116
|
+
</label>
|
|
117
|
+
<label class="sv-grid-chart-builder-row">
|
|
118
|
+
<span>{m.chartBuilderDataLabels}</span>
|
|
119
|
+
<select value={fmt.dataLabels === null ? "none" : (fmt.dataLabels ?? "auto")} onchange={(e) => patch({ dataLabels: e.currentTarget.value === "auto" ? undefined : e.currentTarget.value === "none" ? null : (e.currentTarget.value as "inside" | "outside" | "top" | "center") })}>
|
|
120
|
+
<option value="auto">{m.chartBuilderPanelSetting}</option><option value="top">{m.chartLabelsTop}</option><option value="outside">{m.chartLabelsOutside}</option><option value="inside">{m.chartLabelsInside}</option><option value="center">{m.chartLabelsCenter}</option><option value="none">{m.chartLabelsHidden}</option>
|
|
121
|
+
</select>
|
|
122
|
+
</label>
|
|
123
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderSeriesLabels}</span><input type="checkbox" checked={fmt.seriesLabels === true} onchange={(e) => patch({ seriesLabels: e.currentTarget.checked })} /></label>
|
|
124
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderCrosshairLabels}</span><input type="checkbox" checked={fmt.crosshairLabels !== false} onchange={(e) => patch({ crosshairLabels: e.currentTarget.checked })} /></label>
|
|
125
|
+
<label class="sv-grid-chart-builder-row" title={m.chartBuilderCompactBelowTitle}>
|
|
126
|
+
<span>{m.chartBuilderCompactBelow}</span>
|
|
127
|
+
<input type="number" min="0" step="10" value={fmt.compactBelow ?? ""} placeholder={m.chartBuilderOff} onchange={(e) => patch({ compactBelow: num(e.currentTarget.value) })} />
|
|
128
|
+
</label>
|
|
129
|
+
<fieldset class="sv-grid-chart-builder-fs">
|
|
130
|
+
<legend>{m.chartBuilderValueAxis}</legend>
|
|
131
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderTitleField}</span><input type="text" value={fmt.yAxis?.title ?? ""} oninput={(e) => patchAxis("yAxis", { title: e.currentTarget.value })} /></label>
|
|
132
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderMin}</span><input type="number" value={fmt.yAxis?.min ?? ""} placeholder={m.chartBuilderAuto} onchange={(e) => patchAxis("yAxis", { min: num(e.currentTarget.value) })} /></label>
|
|
133
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderMax}</span><input type="number" value={fmt.yAxis?.max ?? ""} placeholder={m.chartBuilderAuto} onchange={(e) => patchAxis("yAxis", { max: num(e.currentTarget.value) })} /></label>
|
|
134
|
+
<label class="sv-grid-chart-builder-row">
|
|
135
|
+
<span>{m.chartFormat}</span>
|
|
136
|
+
<select value={fmt.yAxis?.format ?? ""} onchange={(e) => patchAxis("yAxis", { format: (e.currentTarget.value || undefined) as ChartValueFormat | undefined })}>
|
|
137
|
+
<option value="">{m.chartBuilderPanelSetting}</option>{#each FORMATS as f (f)}<option value={f}>{f}</option>{/each}
|
|
138
|
+
</select>
|
|
139
|
+
</label>
|
|
140
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderGridLines}</span><input type="checkbox" checked={fmt.yAxis?.gridLines !== false} onchange={(e) => patchAxis("yAxis", { gridLines: e.currentTarget.checked })} /></label>
|
|
141
|
+
</fieldset>
|
|
142
|
+
{#if hasRightAxis}
|
|
143
|
+
<fieldset class="sv-grid-chart-builder-fs">
|
|
144
|
+
<legend>{m.chartBuilderRightAxis}</legend>
|
|
145
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderTitleField}</span><input type="text" value={fmt.y2Axis?.title ?? ""} oninput={(e) => patchAxis("y2Axis", { title: e.currentTarget.value })} /></label>
|
|
146
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderMin}</span><input type="number" value={fmt.y2Axis?.min ?? ""} placeholder={m.chartBuilderAuto} onchange={(e) => patchAxis("y2Axis", { min: num(e.currentTarget.value) })} /></label>
|
|
147
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderMax}</span><input type="number" value={fmt.y2Axis?.max ?? ""} placeholder={m.chartBuilderAuto} onchange={(e) => patchAxis("y2Axis", { max: num(e.currentTarget.value) })} /></label>
|
|
148
|
+
</fieldset>
|
|
149
|
+
{/if}
|
|
150
|
+
<fieldset class="sv-grid-chart-builder-fs">
|
|
151
|
+
<legend>{m.chartBuilderCategoryAxis}</legend>
|
|
152
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderTitleField}</span><input type="text" value={fmt.xAxis?.title ?? ""} oninput={(e) => patchAxis("xAxis", { title: e.currentTarget.value })} /></label>
|
|
153
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderGridLines}</span><input type="checkbox" checked={fmt.xAxis?.gridLines === true} onchange={(e) => patchAxis("xAxis", { gridLines: e.currentTarget.checked })} /></label>
|
|
154
|
+
<label class="sv-grid-chart-builder-row">
|
|
155
|
+
<span>{m.chartBuilderAxisLabels}</span>
|
|
156
|
+
<select value={fmt.xAxis?.labelRotation === undefined ? "auto" : String(fmt.xAxis.labelRotation)} onchange={(e) => patchAxis("xAxis", { labelRotation: e.currentTarget.value === "auto" ? "auto" : Number(e.currentTarget.value) })}>
|
|
157
|
+
<option value="auto">{m.chartBuilderLabelsAuto}</option><option value="0">{m.chartBuilderLabelsHorizontal}</option><option value="-45">{m.chartBuilderLabelsTilted}</option><option value="-90">{m.chartBuilderLabelsVertical}</option>
|
|
158
|
+
</select>
|
|
159
|
+
</label>
|
|
160
|
+
</fieldset>
|
|
161
|
+
{#if seriesLabels.length}
|
|
162
|
+
<fieldset class="sv-grid-chart-builder-fs">
|
|
163
|
+
<legend>{m.chartBuilderSeries}</legend>
|
|
164
|
+
<div class="sv-grid-chart-builder-series-head" class:has-stack={hasStackable}><span>{m.chartBuilderSeries}</span><span>{m.chartBuilderColor}</span><span>{m.chartBuilderSeriesType}</span><span>{m.chartBuilderAxis}</span><span>{m.chartBuilderMarker}</span><span>{m.chartBuilderWidth}</span>{#if hasStackable}<span>{m.chartBuilderStack}</span>{/if}</div>
|
|
165
|
+
{#each seriesLabels as label (label)}
|
|
166
|
+
{@const f = fmt.series?.[label] ?? {}}
|
|
167
|
+
{@const s = spec?.series.find((x) => x.label === label)}
|
|
168
|
+
<div class="sv-grid-chart-builder-series" class:has-stack={hasStackable} data-series={label}>
|
|
169
|
+
<span class="sv-grid-chart-builder-series-name" title={label}>{label}</span>
|
|
170
|
+
<input type="color" value={f.color ?? s?.color ?? "#2563eb"} aria-label={chartPanelMessage(m.chartBuilderSeriesColorLabel, { series: label })} oninput={(e) => patchSeries(label, { color: e.currentTarget.value })} />
|
|
171
|
+
<select value={f.type ?? s?.type ?? ""} aria-label={chartPanelMessage(m.chartBuilderSeriesTypeLabel, { series: label })} onchange={(e) => patchSeries(label, { type: (e.currentTarget.value || undefined) as "bar" | "line" | "area" | undefined })}>
|
|
172
|
+
<option value="">{m.chartBuilderChartType}</option><option value="bar">{m.chartBuilderBar}</option><option value="line">{m.chartBuilderLine}</option><option value="area">{m.chartBuilderArea}</option>
|
|
173
|
+
</select>
|
|
174
|
+
<select value={f.axis ?? s?.axis ?? "left"} aria-label={chartPanelMessage(m.chartBuilderSeriesAxisLabel, { series: label })} onchange={(e) => patchSeries(label, { axis: e.currentTarget.value as "left" | "right" })}>
|
|
175
|
+
<option value="left">{m.chartBuilderLeft}</option><option value="right">{m.chartBuilderRight}</option>
|
|
176
|
+
</select>
|
|
177
|
+
<select value={f.marker ?? "circle"} aria-label={chartPanelMessage(m.chartBuilderSeriesMarkerLabel, { series: label })} onchange={(e) => patchSeries(label, { marker: e.currentTarget.value as ChartMarkerShape })}>
|
|
178
|
+
{#each MARKERS as mk (mk)}<option value={mk}>{mk}</option>{/each}
|
|
179
|
+
</select>
|
|
180
|
+
<input type="number" min="0.5" max="8" step="0.5" value={f.strokeWidth ?? 2} aria-label={chartPanelMessage(m.chartBuilderSeriesWidthLabel, { series: label })} onchange={(e) => patchSeries(label, { strokeWidth: Number(e.currentTarget.value) || 2 })} />
|
|
181
|
+
{#if hasStackable}
|
|
182
|
+
<input type="text" value={f.stack ?? s?.stack ?? ""} placeholder={m.chartBuilderStackPlaceholder} aria-label={chartPanelMessage(m.chartBuilderSeriesStackLabel, { series: label })} onchange={(e) => patchSeries(label, { stack: e.currentTarget.value.trim() })} />
|
|
183
|
+
{/if}
|
|
184
|
+
</div>
|
|
185
|
+
{/each}
|
|
186
|
+
</fieldset>
|
|
187
|
+
{/if}
|
|
188
|
+
<fieldset class="sv-grid-chart-builder-fs">
|
|
189
|
+
<legend>{m.chartBuilderStyle}</legend>
|
|
190
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderFontSize}</span><input type="number" min="8" max="32" value={fmt.style?.fontSize ?? ""} placeholder="12" onchange={(e) => patchStyle({ fontSize: num(e.currentTarget.value) ?? undefined })} /></label>
|
|
191
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderFontFamily}</span><input type="text" value={fmt.style?.fontFamily ?? ""} oninput={(e) => patchStyle({ fontFamily: e.currentTarget.value || undefined })} /></label>
|
|
192
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderBackground}</span><input type="text" value={fmt.style?.background ?? ""} placeholder="transparent" oninput={(e) => patchStyle({ background: e.currentTarget.value || undefined })} /></label>
|
|
193
|
+
<label class="sv-grid-chart-builder-row"><span>{m.chartBuilderTextColor}</span><input type="text" value={fmt.style?.textColor ?? ""} placeholder="inherit" oninput={(e) => patchStyle({ textColor: e.currentTarget.value || undefined })} /></label>
|
|
194
|
+
</fieldset>
|
|
195
|
+
<div class="sv-grid-chart-builder-actions">
|
|
196
|
+
<button type="button" class="sv-grid-chart-btn" onclick={() => (ctrl.chartFormat = null)}>{m.chartBuilderResetFormat}</button>
|
|
197
|
+
</div>
|
|
198
|
+
</div>
|
|
199
|
+
{/if}
|
|
200
|
+
{/snippet}
|
|
201
|
+
</SvTabs>
|
|
202
|
+
</div>
|
|
203
|
+
</SvModal>
|
|
204
|
+
|
|
205
|
+
<style>
|
|
206
|
+
.sv-grid-chart-builder {
|
|
207
|
+
min-height: 420px;
|
|
208
|
+
max-height: 70vh;
|
|
209
|
+
overflow: auto;
|
|
210
|
+
font-size: 12px;
|
|
211
|
+
}
|
|
212
|
+
.sv-grid-chart-builder-group {
|
|
213
|
+
font-size: 11px;
|
|
214
|
+
font-weight: 600;
|
|
215
|
+
color: var(--sg-muted, #64748b);
|
|
216
|
+
text-transform: uppercase;
|
|
217
|
+
letter-spacing: 0.04em;
|
|
218
|
+
margin: 10px 0 6px;
|
|
219
|
+
}
|
|
220
|
+
.sv-grid-chart-builder-cards {
|
|
221
|
+
display: grid;
|
|
222
|
+
grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
|
|
223
|
+
gap: 8px;
|
|
224
|
+
}
|
|
225
|
+
.sv-grid-chart-builder-card {
|
|
226
|
+
display: flex;
|
|
227
|
+
flex-direction: column;
|
|
228
|
+
gap: 4px;
|
|
229
|
+
padding: 6px;
|
|
230
|
+
border: 1px solid var(--sg-border, #e2e8f0);
|
|
231
|
+
border-radius: 8px;
|
|
232
|
+
background: var(--sg-bg, #fff);
|
|
233
|
+
color: var(--sg-fg, #0f172a);
|
|
234
|
+
cursor: pointer;
|
|
235
|
+
text-align: left;
|
|
236
|
+
font: inherit;
|
|
237
|
+
}
|
|
238
|
+
.sv-grid-chart-builder-card:hover { border-color: var(--sg-accent, #2563eb); }
|
|
239
|
+
.sv-grid-chart-builder-card.is-selected {
|
|
240
|
+
border-color: var(--sg-accent, #2563eb);
|
|
241
|
+
box-shadow: 0 0 0 2px color-mix(in srgb, var(--sg-accent, #2563eb) 30%, transparent 70%);
|
|
242
|
+
}
|
|
243
|
+
.sv-grid-chart-builder-thumb {
|
|
244
|
+
height: 92px;
|
|
245
|
+
overflow: hidden;
|
|
246
|
+
pointer-events: none;
|
|
247
|
+
}
|
|
248
|
+
.sv-grid-chart-builder-card-label {
|
|
249
|
+
font-size: 11px;
|
|
250
|
+
font-weight: 600;
|
|
251
|
+
}
|
|
252
|
+
.sv-grid-chart-builder-form {
|
|
253
|
+
display: flex;
|
|
254
|
+
flex-direction: column;
|
|
255
|
+
gap: 8px;
|
|
256
|
+
padding: 8px 2px;
|
|
257
|
+
}
|
|
258
|
+
.sv-grid-chart-builder-row {
|
|
259
|
+
display: grid;
|
|
260
|
+
grid-template-columns: 110px 1fr;
|
|
261
|
+
align-items: center;
|
|
262
|
+
gap: 8px;
|
|
263
|
+
}
|
|
264
|
+
.sv-grid-chart-builder-row > span {
|
|
265
|
+
color: var(--sg-muted, #64748b);
|
|
266
|
+
}
|
|
267
|
+
.sv-grid-chart-builder-row > small {
|
|
268
|
+
grid-column: 2;
|
|
269
|
+
color: var(--sg-muted, #64748b);
|
|
270
|
+
}
|
|
271
|
+
.sv-grid-chart-builder-row > input[type="checkbox"] {
|
|
272
|
+
justify-self: start;
|
|
273
|
+
}
|
|
274
|
+
.sv-grid-chart-builder-row input[type="text"],
|
|
275
|
+
.sv-grid-chart-builder-row input[type="number"],
|
|
276
|
+
.sv-grid-chart-builder-row select,
|
|
277
|
+
.sv-grid-chart-builder-series input,
|
|
278
|
+
.sv-grid-chart-builder-series select {
|
|
279
|
+
font: inherit;
|
|
280
|
+
border: 1px solid var(--sg-border, #e2e8f0);
|
|
281
|
+
border-radius: 6px;
|
|
282
|
+
background: var(--sg-bg, #fff);
|
|
283
|
+
color: var(--sg-fg, #0f172a);
|
|
284
|
+
padding: 3px 6px;
|
|
285
|
+
min-width: 0;
|
|
286
|
+
}
|
|
287
|
+
.sv-grid-chart-builder-fs {
|
|
288
|
+
border: 1px solid var(--sg-border, #e2e8f0);
|
|
289
|
+
border-radius: 8px;
|
|
290
|
+
padding: 6px 10px 10px;
|
|
291
|
+
display: flex;
|
|
292
|
+
flex-direction: column;
|
|
293
|
+
gap: 6px;
|
|
294
|
+
}
|
|
295
|
+
.sv-grid-chart-builder-fs > legend {
|
|
296
|
+
font-weight: 600;
|
|
297
|
+
padding: 0 4px;
|
|
298
|
+
}
|
|
299
|
+
.sv-grid-chart-builder-series,
|
|
300
|
+
.sv-grid-chart-builder-series-head {
|
|
301
|
+
display: grid;
|
|
302
|
+
grid-template-columns: minmax(80px, 1.4fr) 44px 1fr 1fr 1fr 64px;
|
|
303
|
+
gap: 6px;
|
|
304
|
+
align-items: center;
|
|
305
|
+
}
|
|
306
|
+
.sv-grid-chart-builder-series.has-stack,
|
|
307
|
+
.sv-grid-chart-builder-series-head.has-stack {
|
|
308
|
+
grid-template-columns: minmax(80px, 1.4fr) 44px 1fr 1fr 1fr 64px 72px;
|
|
309
|
+
}
|
|
310
|
+
.sv-grid-chart-builder-series-head {
|
|
311
|
+
color: var(--sg-muted, #64748b);
|
|
312
|
+
font-size: 11px;
|
|
313
|
+
}
|
|
314
|
+
.sv-grid-chart-builder-series-name {
|
|
315
|
+
overflow: hidden;
|
|
316
|
+
text-overflow: ellipsis;
|
|
317
|
+
white-space: nowrap;
|
|
318
|
+
}
|
|
319
|
+
.sv-grid-chart-builder-actions {
|
|
320
|
+
display: flex;
|
|
321
|
+
justify-content: flex-end;
|
|
322
|
+
}
|
|
323
|
+
</style>
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { type ChartPanelTypeDef } from "./SvGridChartPickers.svelte";
|
|
2
|
+
import { type GridChartPanelMessages } from "./chart-panel-messages.js";
|
|
3
|
+
import type { RowData, TableFeatures } from "./index.js";
|
|
4
|
+
import type { SvGridController } from "./SvGrid.controller.svelte.js";
|
|
5
|
+
declare function $$render<TFeatures extends TableFeatures = TableFeatures, TData extends RowData = RowData>(): {
|
|
6
|
+
props: {
|
|
7
|
+
ctrl: SvGridController<TFeatures, TData>;
|
|
8
|
+
open?: boolean;
|
|
9
|
+
/** The types the panel offers for the current columns, in its groups. */
|
|
10
|
+
types: ChartPanelTypeDef[];
|
|
11
|
+
messages: GridChartPanelMessages;
|
|
12
|
+
};
|
|
13
|
+
exports: {};
|
|
14
|
+
bindings: "open";
|
|
15
|
+
slots: {};
|
|
16
|
+
events: {};
|
|
17
|
+
};
|
|
18
|
+
declare class __sveltets_Render<TFeatures extends TableFeatures = TableFeatures, TData extends RowData = RowData> {
|
|
19
|
+
props(): ReturnType<typeof $$render<TFeatures, TData>>['props'];
|
|
20
|
+
events(): ReturnType<typeof $$render<TFeatures, TData>>['events'];
|
|
21
|
+
slots(): ReturnType<typeof $$render<TFeatures, TData>>['slots'];
|
|
22
|
+
bindings(): "open";
|
|
23
|
+
exports(): {};
|
|
24
|
+
}
|
|
25
|
+
interface $$IsomorphicComponent {
|
|
26
|
+
new <TFeatures extends TableFeatures = TableFeatures, TData extends RowData = RowData>(options: import('svelte').ComponentConstructorOptions<ReturnType<__sveltets_Render<TFeatures, TData>['props']>>): import('svelte').SvelteComponent<ReturnType<__sveltets_Render<TFeatures, TData>['props']>, ReturnType<__sveltets_Render<TFeatures, TData>['events']>, ReturnType<__sveltets_Render<TFeatures, TData>['slots']>> & {
|
|
27
|
+
$$bindings?: ReturnType<__sveltets_Render<TFeatures, TData>['bindings']>;
|
|
28
|
+
} & ReturnType<__sveltets_Render<TFeatures, TData>['exports']>;
|
|
29
|
+
<TFeatures extends TableFeatures = TableFeatures, TData extends RowData = RowData>(internal: unknown, props: ReturnType<__sveltets_Render<TFeatures, TData>['props']> & {}): ReturnType<__sveltets_Render<TFeatures, TData>['exports']>;
|
|
30
|
+
z_$$bindings?: ReturnType<__sveltets_Render<any, any>['bindings']>;
|
|
31
|
+
}
|
|
32
|
+
declare const SvGridChartBuilder: $$IsomorphicComponent;
|
|
33
|
+
type SvGridChartBuilder<TFeatures extends TableFeatures = TableFeatures, TData extends RowData = RowData> = InstanceType<typeof SvGridChartBuilder<TFeatures, TData>>;
|
|
34
|
+
export default SvGridChartBuilder;
|