@pixerate/editor 0.46.1 → 0.48.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (98) hide show
  1. package/THIRD_PARTY_NOTICES.md +20 -0
  2. package/dist/agent/index.cjs +252 -34
  3. package/dist/agent/index.cjs.map +1 -1
  4. package/dist/agent/index.d.cts +19 -7
  5. package/dist/agent/index.d.ts +19 -7
  6. package/dist/agent/index.js +228 -10
  7. package/dist/agent/index.js.map +1 -1
  8. package/dist/{builtins-CZW-aYKS.d.cts → builtins-1kqwLUnb.d.cts} +2 -2
  9. package/dist/{builtins-DghNQbT-.d.ts → builtins-BKYlHH1s.d.ts} +2 -2
  10. package/dist/chart/index.cjs +1596 -1849
  11. package/dist/chart/index.cjs.map +1 -1
  12. package/dist/chart/index.d.cts +760 -548
  13. package/dist/chart/index.d.ts +760 -548
  14. package/dist/chart/index.js +1499 -1752
  15. package/dist/chart/index.js.map +1 -1
  16. package/dist/{chunk-3RPOW4CS.js → chunk-2CJ3LPYQ.js} +12 -10
  17. package/dist/{chunk-3RPOW4CS.js.map → chunk-2CJ3LPYQ.js.map} +1 -1
  18. package/dist/{chunk-PQM5W7ZN.js → chunk-4FX5ACVG.js} +29 -2
  19. package/dist/{chunk-PQM5W7ZN.js.map → chunk-4FX5ACVG.js.map} +1 -1
  20. package/dist/{chunk-HHQ4XJWT.js → chunk-AMWXSYCI.js} +2 -2
  21. package/dist/chunk-EKYHKQPG.js +1895 -0
  22. package/dist/chunk-EKYHKQPG.js.map +1 -0
  23. package/dist/chunk-HXUL3LS7.js +113 -0
  24. package/dist/chunk-HXUL3LS7.js.map +1 -0
  25. package/dist/{chunk-ZRNHGAQT.js → chunk-JQ3BB3E6.js} +43 -1891
  26. package/dist/chunk-JQ3BB3E6.js.map +1 -0
  27. package/dist/chunk-LTUM52X6.js +4074 -0
  28. package/dist/chunk-LTUM52X6.js.map +1 -0
  29. package/dist/{chunk-J3R2OWOE.cjs → chunk-MUCYWI6W.cjs} +608 -15
  30. package/dist/chunk-MUCYWI6W.cjs.map +1 -0
  31. package/dist/chunk-PIMCHMZE.cjs +521 -0
  32. package/dist/chunk-PIMCHMZE.cjs.map +1 -0
  33. package/dist/{chunk-TK2XZK6Z.js → chunk-PKBWLEL7.js} +594 -1
  34. package/dist/chunk-PKBWLEL7.js.map +1 -0
  35. package/dist/chunk-PRSJJZBS.cjs +4074 -0
  36. package/dist/chunk-PRSJJZBS.cjs.map +1 -0
  37. package/dist/{chunk-EFDCLENW.cjs → chunk-RIWPYSKU.cjs} +29 -2
  38. package/dist/chunk-RIWPYSKU.cjs.map +1 -0
  39. package/dist/chunk-U6IZKC7B.cjs +113 -0
  40. package/dist/chunk-U6IZKC7B.cjs.map +1 -0
  41. package/dist/{chunk-EWCOFSCQ.cjs → chunk-UN33YOXW.cjs} +252 -2100
  42. package/dist/chunk-UN33YOXW.cjs.map +1 -0
  43. package/dist/{chunk-Q25ZS4F7.js → chunk-VKPEPWKZ.js} +72 -92
  44. package/dist/chunk-VKPEPWKZ.js.map +1 -0
  45. package/dist/{chunk-N4MLNJPO.cjs → chunk-WXEHCVJQ.cjs} +160 -180
  46. package/dist/chunk-WXEHCVJQ.cjs.map +1 -0
  47. package/dist/{chunk-K2LVZ4FA.cjs → chunk-XFYUFVAX.cjs} +3 -3
  48. package/dist/{chunk-K2LVZ4FA.cjs.map → chunk-XFYUFVAX.cjs.map} +1 -1
  49. package/dist/chunk-XP5IUZUO.cjs +1895 -0
  50. package/dist/chunk-XP5IUZUO.cjs.map +1 -0
  51. package/dist/chunk-XUUD43OV.js +521 -0
  52. package/dist/chunk-XUUD43OV.js.map +1 -0
  53. package/dist/{chunk-U7VGDSNY.cjs → chunk-YU4WQE5M.cjs} +101 -99
  54. package/dist/chunk-YU4WQE5M.cjs.map +1 -0
  55. package/dist/commands/index.cjs +93 -11
  56. package/dist/commands/index.cjs.map +1 -1
  57. package/dist/commands/index.d.cts +9 -7
  58. package/dist/commands/index.d.ts +9 -7
  59. package/dist/commands/index.js +92 -10
  60. package/dist/commands/index.js.map +1 -1
  61. package/dist/controller-ChjCCMLl.d.cts +822 -0
  62. package/dist/controller-DtbEo3om.d.ts +822 -0
  63. package/dist/extensions/index.cjs +32 -3
  64. package/dist/extensions/index.cjs.map +1 -1
  65. package/dist/extensions/index.d.cts +5 -2
  66. package/dist/extensions/index.d.ts +5 -2
  67. package/dist/extensions/index.js +31 -2
  68. package/dist/generation/index.cjs +2 -2
  69. package/dist/generation/index.js +1 -1
  70. package/dist/{index-CfOQf70b.d.cts → index-DoHqT1mq.d.cts} +222 -5
  71. package/dist/{index-jwJ_onWf.d.ts → index-YLZ0fKqE.d.ts} +222 -5
  72. package/dist/index.cjs +38 -10
  73. package/dist/index.cjs.map +1 -1
  74. package/dist/index.d.cts +13 -5
  75. package/dist/index.d.ts +13 -5
  76. package/dist/index.js +52 -24
  77. package/dist/index.js.map +1 -1
  78. package/dist/parameters/index.d.cts +1 -1
  79. package/dist/parameters/index.d.ts +1 -1
  80. package/dist/{registry-vz6HOiiy.d.cts → registry-CaR7LC6W.d.cts} +2 -0
  81. package/dist/{registry-BfVD-vVg.d.ts → registry-rVtFJjRM.d.ts} +2 -0
  82. package/dist/spreadsheet/index.cjs +5 -3
  83. package/dist/spreadsheet/index.cjs.map +1 -1
  84. package/dist/spreadsheet/index.js +24 -22
  85. package/dist/tools/index.cjs +3 -3
  86. package/dist/tools/index.js +2 -2
  87. package/dist/vector/index.d.cts +1 -1
  88. package/dist/vector/index.d.ts +1 -1
  89. package/package.json +2 -1
  90. package/dist/chunk-EFDCLENW.cjs.map +0 -1
  91. package/dist/chunk-EWCOFSCQ.cjs.map +0 -1
  92. package/dist/chunk-J3R2OWOE.cjs.map +0 -1
  93. package/dist/chunk-N4MLNJPO.cjs.map +0 -1
  94. package/dist/chunk-Q25ZS4F7.js.map +0 -1
  95. package/dist/chunk-TK2XZK6Z.js.map +0 -1
  96. package/dist/chunk-U7VGDSNY.cjs.map +0 -1
  97. package/dist/chunk-ZRNHGAQT.js.map +0 -1
  98. /package/dist/{chunk-HHQ4XJWT.js.map → chunk-AMWXSYCI.js.map} +0 -0
@@ -1,301 +1,11 @@
1
- import { H as HistoryManager } from '../HistoryManager-DeQQMBCj.cjs';
2
- import { C as CommandSpec } from '../registry-vz6HOiiy.cjs';
1
+ import { C as ChartNumberFormat, a as ChartValue, b as ChartRect, c as ChartScene, d as ChartSpec, e as ChartLayoutOptions, f as ChartWarning, g as ChartAxis, h as ChartLegend, i as ChartType, j as ChartStacking, k as ChartSeries, l as ChartIssue, m as ChartController, n as ChartValueScale, o as ChartSelection, p as ChartSpecPatch } from '../controller-ChjCCMLl.cjs';
2
+ export { q as CHART_AXIS_KINDS, r as CHART_CURVES, s as CHART_LABEL_POSITIONS, t as CHART_LEGEND_POSITIONS, u as CHART_MARKERS, v as CHART_NUMBER_STYLES, w as CHART_ORIENTATIONS, x as CHART_SERIES_TYPES, y as CHART_STACKINGS, z as CHART_TRENDLINE_TYPES, A as CHART_TYPES, B as CHART_TYPE_LABELS, D as CSS_VARIABLE_CHART_THEME, E as ChartActionResult, F as ChartCircleMark, G as ChartControllerOptions, H as ChartCurve, I as ChartDomSpec, J as ChartEditOptions, K as ChartFamily, L as ChartLabelPosition, M as ChartLegendPosition, N as ChartLineMark, O as ChartMark, P as ChartMarkRole, Q as ChartMarker, R as ChartOrientation, S as ChartPathMark, T as ChartRectMark, U as ChartSeriesInput, V as ChartSeriesPatch, W as ChartSeriesType, X as ChartSparklineKind, Y as ChartSparklineOptions, Z as ChartState, _ as ChartSvgOptions, $ as ChartTableData, a0 as ChartTableOptions, a1 as ChartTextMark, a2 as ChartTextMeasure, a3 as ChartTheme, a4 as ChartTrendFit, a5 as ChartTrendline, a6 as ChartTrendlineType, a7 as DEFAULT_CHART_PALETTE, a8 as DEFAULT_CHART_THEME, a9 as chartColorInputValue, aa as chartColorsByCategory, ab as chartDataFromTable, ac as chartDataToTable, ad as chartFamily, ae as chartMovingAverage, af as chartPointColor, ag as chartSceneToDomSpec, ah as chartSceneToSvg, ai as chartSeriesColor, aj as chartSeriesType, ak as chartSliceColor, al as chartSupportsTrendlines, am as chartTextBaseline, an as chartTextTransform, ao as chartToSvg, ap as chartTrendlineName, aq as cloneChartSeries, ar as cloneChartSpec, as as contrastingTextColor, at as createChartController, au as createChartSpec, av as defaultChartAxis, aw as estimateChartTextWidth, ax as fitChartTrendline, ay as isCartesianChart, az as isXyChart, aA as layoutSparkline, aB as normalizeChartAxis, aC as normalizeChartSpec, aD as normalizeChartTrendline, aE as normalizeChartValues, aF as parseChartValue, aG as sameChartSelection, aH as sparklineToSvg, aI as trendNumberText, aJ as uniqueChartSeriesId } from '../controller-ChjCCMLl.cjs';
3
+ import { C as CommandSpec } from '../registry-CaR7LC6W.cjs';
4
+ import { A as AgentToolProvider } from '../registry-B4l-lYts.cjs';
5
+ import '../HistoryManager-DeQQMBCj.cjs';
3
6
  import '../types-DsiXGmjo.cjs';
4
7
  import '../schema-Di0CS6Pe.cjs';
5
8
 
6
- /** Chart kinds. `bar`, `line`, `area` and `scatter` are cartesian; series may mix them (a combo chart). */
7
- type ChartType = 'bar' | 'line' | 'area' | 'scatter' | 'pie' | 'donut';
8
- /** How a series is drawn in a cartesian chart. */
9
- type ChartSeriesType = 'bar' | 'line' | 'area' | 'scatter';
10
- /** One data value; `null` is a gap (missing value). */
11
- type ChartValue = number | null;
12
- interface ChartSeries {
13
- /** Stable id (unique within the chart). */
14
- id: string;
15
- name: string;
16
- /** One value per category. */
17
- values: ChartValue[];
18
- /** CSS colour (default: the palette colour for the series' position). */
19
- color?: string;
20
- /** Overrides the chart type for this series (cartesian charts only). */
21
- type?: ChartSeriesType;
22
- /** Hidden series keep their data but are not drawn or scaled. */
23
- hidden?: boolean;
24
- }
25
- interface ChartNumberFormat {
26
- /** `number` (default), `percent` (0.25 → 25%), `currency` or `compact` (1.2K). */
27
- style?: 'number' | 'percent' | 'currency' | 'compact';
28
- /** Fixed decimals (default: as many as the ticks need, up to 2). */
29
- decimals?: number;
30
- /** ISO currency code for `currency` (default `USD`). */
31
- currency?: string;
32
- prefix?: string;
33
- suffix?: string;
34
- }
35
- interface ChartAxis {
36
- /** Draw the axis line, ticks and labels (default `true`). */
37
- show: boolean;
38
- title: string;
39
- /** Fixed lower bound (default: from the data, including 0 for bars and areas). */
40
- min: number | null;
41
- /** Fixed upper bound (default: from the data). */
42
- max: number | null;
43
- /** Grid lines at each tick (default: on for the value axis). */
44
- gridlines: boolean;
45
- /** How tick and data labels are written (value axis only). */
46
- format: ChartNumberFormat;
47
- }
48
- type ChartLegendPosition = 'top' | 'bottom' | 'left' | 'right';
49
- interface ChartLegend {
50
- show: boolean;
51
- position: ChartLegendPosition;
52
- }
53
- type ChartStacking = 'none' | 'stacked' | 'percent';
54
- type ChartOrientation = 'vertical' | 'horizontal';
55
- type ChartCurve = 'linear' | 'smooth' | 'step';
56
- /** A whole chart: data plus presentation. Plain JSON, safe to persist. */
57
- interface ChartSpec {
58
- version: 1;
59
- type: ChartType;
60
- title: string;
61
- subtitle: string;
62
- /** Category labels (the x axis, or pie slices). */
63
- categories: string[];
64
- series: ChartSeries[];
65
- /** The category axis. */
66
- xAxis: ChartAxis;
67
- /** The value axis. */
68
- yAxis: ChartAxis;
69
- legend: ChartLegend;
70
- /** Stack bars and areas (`percent` scales each category to 100%). */
71
- stacking: ChartStacking;
72
- /** `horizontal` draws bars sideways (bar charts only). */
73
- orientation: ChartOrientation;
74
- /** Line and area interpolation. */
75
- curve: ChartCurve;
76
- /** Dots on line and area series. */
77
- points: boolean;
78
- /** Value labels on bars, points and slices. */
79
- dataLabels: boolean;
80
- /** Series colours in order (cycled). */
81
- palette: string[];
82
- /** Donut hole as a fraction of the radius (0–0.9). */
83
- innerRadius: number;
84
- }
85
- /** What a click selects. */
86
- type ChartSelection = {
87
- kind: 'chart';
88
- } | {
89
- kind: 'title';
90
- } | {
91
- kind: 'subtitle';
92
- } | {
93
- kind: 'legend';
94
- } | {
95
- kind: 'axis';
96
- axis: 'x' | 'y';
97
- } | {
98
- kind: 'series';
99
- seriesId: string;
100
- } | {
101
- kind: 'point';
102
- seriesId: string;
103
- index: number;
104
- } | {
105
- kind: 'category';
106
- index: number;
107
- };
108
- /** Colours and type used to lay out a chart. Any CSS colour strings work. */
109
- interface ChartTheme {
110
- /** Fill behind the chart (`transparent` lets the page show through). */
111
- background: string;
112
- /** The page colour: slice separators and hollow points (set it when `background` is transparent). */
113
- surface: string;
114
- text: string;
115
- mutedText: string;
116
- grid: string;
117
- axis: string;
118
- /** Outline drawn around the selected mark. */
119
- selection: string;
120
- fontFamily: string;
121
- fontSize: number;
122
- titleSize: number;
123
- }
124
- interface ChartRect {
125
- x: number;
126
- y: number;
127
- width: number;
128
- height: number;
129
- }
130
- /** What a mark is, for styling and tests. */
131
- type ChartMarkRole = 'background' | 'title' | 'subtitle' | 'grid' | 'axis' | 'tick' | 'tick-label' | 'axis-title' | 'bar' | 'line' | 'area' | 'point' | 'slice' | 'data-label' | 'legend-swatch' | 'legend-label' | 'selection' | 'empty';
132
- interface ChartMarkBase {
133
- /** Unique within the scene (a stable key for frameworks). */
134
- key: string;
135
- role: ChartMarkRole;
136
- /** What clicking this mark selects (none: not clickable). */
137
- target?: ChartSelection;
138
- /** Mark belongs to the current selection. */
139
- selected?: boolean;
140
- opacity?: number;
141
- }
142
- interface ChartRectMark extends ChartMarkBase {
143
- kind: 'rect';
144
- x: number;
145
- y: number;
146
- width: number;
147
- height: number;
148
- fill: string;
149
- stroke?: string;
150
- strokeWidth?: number;
151
- radius?: number;
152
- }
153
- interface ChartPathMark extends ChartMarkBase {
154
- kind: 'path';
155
- d: string;
156
- fill?: string;
157
- stroke?: string;
158
- strokeWidth?: number;
159
- dash?: string;
160
- }
161
- interface ChartCircleMark extends ChartMarkBase {
162
- kind: 'circle';
163
- cx: number;
164
- cy: number;
165
- r: number;
166
- fill: string;
167
- stroke?: string;
168
- strokeWidth?: number;
169
- }
170
- interface ChartLineMark extends ChartMarkBase {
171
- kind: 'line';
172
- x1: number;
173
- y1: number;
174
- x2: number;
175
- y2: number;
176
- stroke: string;
177
- strokeWidth?: number;
178
- dash?: string;
179
- }
180
- interface ChartTextMark extends ChartMarkBase {
181
- kind: 'text';
182
- x: number;
183
- y: number;
184
- text: string;
185
- anchor: 'start' | 'middle' | 'end';
186
- /** Vertical alignment of the text box to `y`. */
187
- baseline: 'top' | 'middle' | 'bottom';
188
- size: number;
189
- weight?: number;
190
- fill: string;
191
- /** Degrees, around (x, y). */
192
- rotate?: number;
193
- }
194
- type ChartMark = ChartRectMark | ChartPathMark | ChartCircleMark | ChartLineMark | ChartTextMark;
195
- /** Maps between data values and scene pixels along one axis of the plot. */
196
- interface ChartValueScale {
197
- /** `y` for vertical charts, `x` for horizontal bars. */
198
- axis: 'x' | 'y';
199
- domain: [number, number];
200
- range: [number, number];
201
- ticks: number[];
202
- }
203
- /** A laid-out chart: drawing primitives in scene pixels, ready for SVG, canvas or anything else. */
204
- interface ChartScene {
205
- width: number;
206
- height: number;
207
- /** The plot area (inside the axes). Empty for pies. */
208
- plot: ChartRect;
209
- /** Draw in order. */
210
- marks: ChartMark[];
211
- /** The value scale of a cartesian chart (absent for pies and empty charts). */
212
- valueScale?: ChartValueScale;
213
- /** Percent-stacked: values are shown as shares, so dragging is disabled. */
214
- percent: boolean;
215
- theme: ChartTheme;
216
- }
217
- interface ChartIssue {
218
- path: string;
219
- message: string;
220
- }
221
-
222
- declare const CHART_TYPES: readonly ChartType[];
223
- declare const CHART_SERIES_TYPES: readonly ChartSeriesType[];
224
- declare const CHART_STACKINGS: readonly ChartStacking[];
225
- declare const CHART_CURVES: readonly ChartCurve[];
226
- declare const CHART_ORIENTATIONS: readonly ChartOrientation[];
227
- declare const CHART_LEGEND_POSITIONS: readonly ChartLegendPosition[];
228
- declare const CHART_NUMBER_STYLES: readonly NonNullable<ChartNumberFormat['style']>[];
229
- /** Labels for pickers, shared by the React and Svelte components. */
230
- declare const CHART_TYPE_LABELS: Readonly<Record<ChartType, string>>;
231
- /** A colour-blind-friendly categorical palette (Okabe–Ito order, tuned for light and dark backgrounds). */
232
- declare const DEFAULT_CHART_PALETTE: readonly string[];
233
- declare const DEFAULT_CHART_THEME: ChartTheme;
234
- /**
235
- * A theme that reads the page's `--background`, `--foreground`, `--muted-foreground`,
236
- * `--border` and `--primary` colour variables (full colours, as the other components'
237
- * inline styles use them), with light fallbacks. The React and Svelte canvases use it.
238
- */
239
- declare const CSS_VARIABLE_CHART_THEME: ChartTheme;
240
- declare function isCartesianChart(type: ChartType): boolean;
241
- declare function defaultChartAxis(value: boolean): ChartAxis;
242
- /** A complete spec with every default filled in. */
243
- declare function createChartSpec(partial?: Partial<ChartSpec>): ChartSpec;
244
- /** The colour a series is drawn with. */
245
- declare function chartSeriesColor(spec: Pick<ChartSpec, 'palette' | 'series'>, seriesIndex: number): string;
246
- /** The colour a pie slice is drawn with (by category). */
247
- declare function chartSliceColor(spec: Pick<ChartSpec, 'palette'>, index: number): string;
248
- /** How a series is drawn in a cartesian chart. */
249
- declare function chartSeriesType(spec: Pick<ChartSpec, 'type'>, series: ChartSeries): ChartSeriesType;
250
- /** An id not used by any series (`series-1`, `series-2`, …). */
251
- declare function uniqueChartSeriesId(series: readonly Pick<ChartSeries, 'id'>[], base?: string): string;
252
- /**
253
- * Reads a number the way people type it in a data grid: `1,234.5`, `12%` (→ 0.12),
254
- * `$40`, `(3)` (→ -3). Blank → `null`. Returns `undefined` when it is not a number.
255
- */
256
- declare function parseChartValue(input: unknown): ChartValue | undefined;
257
- declare function normalizeChartAxis(value: unknown, fallback: ChartAxis, path: string, issues?: ChartIssue[]): ChartAxis;
258
- /** Values as numbers or nulls; bad entries become null and are reported. */
259
- declare function normalizeChartValues(value: unknown, length: number | undefined, path: string, issues?: ChartIssue[]): ChartValue[];
260
- /**
261
- * Turns any input (a partial spec, saved JSON, an agent's arguments) into a complete,
262
- * valid `ChartSpec`. Every value is checked; problems are reported as sentences in
263
- * `issues` and replaced by defaults, so the result is always drawable. Series values are
264
- * padded or trimmed to the number of categories.
265
- */
266
- declare function normalizeChartSpec(input: unknown): {
267
- spec: ChartSpec;
268
- issues: ChartIssue[];
269
- };
270
- /** A deep copy (specs are plain JSON). */
271
- declare function cloneChartSpec(spec: ChartSpec): ChartSpec;
272
- declare function cloneChartSeries(series: ChartSeries): ChartSeries;
273
- interface ChartTableOptions {
274
- /**
275
- * `columns` (default): the first column holds categories and each other column is a
276
- * series. `rows`: the first row holds categories and each other row is a series.
277
- */
278
- seriesIn?: 'columns' | 'rows';
279
- /** The first row (or column for `rows`) holds series names (default `true`). */
280
- header?: boolean;
281
- }
282
- interface ChartTableData {
283
- categories: string[];
284
- series: ChartSeries[];
285
- issues: ChartIssue[];
286
- }
287
- /**
288
- * Reads a grid of cells (from CSV, a spreadsheet range or the clipboard) as categories and
289
- * series. Cells that are not numbers become gaps and are reported.
290
- */
291
- declare function chartDataFromTable(rows: ReadonlyArray<ReadonlyArray<unknown>>, options?: ChartTableOptions): ChartTableData;
292
- /** The chart's data as a grid: a header row of series names, then one row per category. */
293
- declare function chartDataToTable(spec: Pick<ChartSpec, 'categories' | 'series'>, options?: {
294
- categoryHeader?: string;
295
- }): (string | number | null)[][];
296
- /** A colour input value (`#rrggbb`) for a CSS colour: `#abc` expands, non-hex colours show as black. */
297
- declare function chartColorInputValue(color: string): string;
298
-
299
9
  /** A "nice" step (1, 2, 2.5 or 5 × 10ⁿ) for about `count` intervals over `span`. */
300
10
  declare function niceStep(span: number, count: number): number;
301
11
  interface NiceScale {
@@ -321,273 +31,389 @@ declare function formatChartNumber(value: number | null | undefined, format?: Ch
321
31
  /** Linear map from `domain` to `range`. */
322
32
  declare function linearMap(value: number, domain: readonly [number, number], range: readonly [number, number]): number;
323
33
 
324
- type ChartTextMeasure = (text: string, size: number, weight?: number) => number;
325
- interface ChartLayoutOptions {
326
- width: number;
327
- height: number;
328
- theme?: Partial<ChartTheme>;
329
- /** Highlighted in the scene (selection outlines, `selected` flags). */
330
- selection?: ChartSelection | null;
331
- /** Text width in pixels (default: an estimate from the character count). */
332
- measureText?: ChartTextMeasure;
333
- /** Shown when there is nothing to draw (default "No data"). */
334
- emptyMessage?: string;
335
- /**
336
- * Fixes the value axis to this range (over `yAxis.min` / `yAxis.max`). Canvases pass
337
- * `ChartPointDrag.valueDomain` during a drag so the axis does not rescale under the pointer.
338
- */
339
- valueDomain?: {
340
- min: number;
341
- max: number;
342
- } | null;
34
+ /**
35
+ * A compiled spreadsheet number format code for chart labels, e.g. `#,##0.00`, `0.0%`,
36
+ * `#,##0,,"M"`, `$#,##0;[Red]($#,##0);"–"` or `yyyy-mm-dd`. Backed by the spreadsheet's
37
+ * format engine (`NumberFormat`), so charts and sheets write numbers the same way; colours
38
+ * such as `[Red]` are ignored on charts.
39
+ */
40
+ interface ChartFormatCode {
41
+ format(value: number): string;
42
+ /** The code is a date or time format (values are serial day numbers from 1899-12-30). */
43
+ isDate: boolean;
44
+ /** The code shows a percentage (values are multiplied by 100). */
45
+ isPercent: boolean;
46
+ }
47
+ /** Compiles a spreadsheet format code (cached). */
48
+ declare function compileChartFormatCode(code: string): ChartFormatCode;
49
+ /** Formats `value` with a spreadsheet format code. */
50
+ declare function formatChartValueWithCode(value: number, code: string): string;
51
+ /** A spreadsheet serial day number (1 = 1900-01-01, with the 1900 leap-year quirk) as a UTC date. */
52
+ declare function chartSerialToDate(serial: number): Date;
53
+ /** A UTC date as a spreadsheet serial day number. */
54
+ declare function chartDateToSerial(date: Date): number;
55
+
56
+ /** An sRGB colour with channels from 0 to 1. */
57
+ type ChartRgb = [number, number, number];
58
+ /**
59
+ * Reads `#rgb`, `#rrggbb`, `#rrggbbaa`, `rgb()` / `rgba()` and a few colour names. Returns
60
+ * `null` for anything else (CSS variables, `hsl()`, …), so callers can leave such colours alone.
61
+ */
62
+ declare function parseChartColor(color: string): ChartRgb | null;
63
+ declare function chartRgbToHex(rgb: ChartRgb): string;
64
+ /**
65
+ * A lighter (`amount` > 0, towards white) or darker (`amount` < 0, towards black) shade of
66
+ * `color`. Colours it cannot read (CSS variables) come back unchanged.
67
+ */
68
+ declare function shadeChartColor(color: string, amount: number): string;
69
+ /** Shades used once a palette is used up: the same hues, lighter then darker (GridCraft's cycle). */
70
+ declare const CHART_PALETTE_SHADES: readonly number[];
71
+ /** The palette colour for the `index`-th item: the palette in order, then lighter and darker rounds of it. */
72
+ declare function cyclePaletteColor(palette: readonly string[], index: number): string;
73
+ /** WCAG relative luminance (0 black – 1 white). */
74
+ declare function chartLuminance(rgb: ChartRgb): number;
75
+ /** WCAG contrast ratio (1–21) between two colours, or `null` when either cannot be read. */
76
+ declare function chartContrastRatio(a: string, b: string): number | null;
77
+ /**
78
+ * Dark or white text, whichever reads better on `fill`; `fallback` when the fill cannot be
79
+ * read (a CSS variable).
80
+ */
81
+ declare function chartTextOn(fill: string, fallback: string, dark?: string, light?: string): string;
82
+ /** OKLab (Ottosson) from sRGB. */
83
+ declare function chartRgbToOklab(rgb: ChartRgb): [number, number, number];
84
+ /** Perceptual distance between two colours (Euclidean in OKLab; ≈0.02 is just noticeable). */
85
+ declare function chartColorDistance(a: ChartRgb, b: ChartRgb): number;
86
+ type ChartVision = 'normal' | 'protanopia' | 'deuteranopia' | 'tritanopia';
87
+ /** How a colour looks with a colour-vision deficiency (Machado et al. 2009, full severity). */
88
+ declare function simulateChartVision(rgb: ChartRgb, vision: ChartVision): ChartRgb;
89
+ interface ChartColorPair {
90
+ a: number;
91
+ b: number;
92
+ colors: [string, string];
93
+ distance: number;
94
+ }
95
+ interface ChartColorCheck {
96
+ /** No problems found. */
97
+ ok: boolean;
98
+ /** Per vision: the closest pair of colours and their OKLab distance. */
99
+ closest: Partial<Record<ChartVision, ChartColorPair>>;
100
+ /** Contrast ratio of each colour against the surface (null when unreadable). */
101
+ contrast: (number | null)[];
102
+ /** Problems, as sentences. */
103
+ issues: string[];
104
+ /** Colours that could not be read (CSS variables, `hsl()`); they are skipped. */
105
+ skipped: string[];
106
+ }
107
+ interface ChartColorCheckOptions {
108
+ /** The page colour behind the marks (default white). */
109
+ surface?: string;
110
+ /** Smallest OKLab distance two series may have (default 0.08). */
111
+ minDistance?: number;
112
+ /** Smallest contrast ratio against the surface (default 1.5; WCAG asks 3 for graphics). */
113
+ minContrast?: number;
114
+ /** Visions to check (default all four). */
115
+ visions?: readonly ChartVision[];
116
+ }
117
+ /**
118
+ * Checks that series colours can be told apart, with normal vision and the three
119
+ * colour-vision deficiencies, and stand out from the surface. Returns the closest pair per
120
+ * vision and problems as sentences.
121
+ */
122
+ declare function checkChartColors(colors: readonly string[], options?: ChartColorCheckOptions): ChartColorCheck;
123
+
124
+ /**
125
+ * Reads a category label as a UTC date: `2024`, `2024-03`, `2024-03-05`, ISO date-times,
126
+ * `2024/03/05`, `Mar 2024` and `5 Mar 2024`. Returns milliseconds since the epoch, or `null`.
127
+ */
128
+ declare function parseChartDate(label: string): number | null;
129
+ /** Calendar steps from fine to coarse. */
130
+ declare const CHART_DATE_STEPS: readonly [{
131
+ readonly unit: "day";
132
+ readonly count: 1;
133
+ }, {
134
+ readonly unit: "day";
135
+ readonly count: 2;
136
+ }, {
137
+ readonly unit: "week";
138
+ readonly count: 1;
139
+ }, {
140
+ readonly unit: "week";
141
+ readonly count: 2;
142
+ }, {
143
+ readonly unit: "month";
144
+ readonly count: 1;
145
+ }, {
146
+ readonly unit: "month";
147
+ readonly count: 3;
148
+ }, {
149
+ readonly unit: "month";
150
+ readonly count: 6;
151
+ }, {
152
+ readonly unit: "year";
153
+ readonly count: 1;
154
+ }, {
155
+ readonly unit: "year";
156
+ readonly count: 2;
157
+ }, {
158
+ readonly unit: "year";
159
+ readonly count: 5;
160
+ }, {
161
+ readonly unit: "year";
162
+ readonly count: 10;
163
+ }, {
164
+ readonly unit: "year";
165
+ readonly count: 25;
166
+ }, {
167
+ readonly unit: "year";
168
+ readonly count: 50;
169
+ }, {
170
+ readonly unit: "year";
171
+ readonly count: 100;
172
+ }];
173
+ type ChartDateStep = (typeof CHART_DATE_STEPS)[number];
174
+ /** A label for a date at `step`: years as `2024`, months as `Mar 2024` (`Mar` within a year), days as `5 Mar`. */
175
+ declare function formatChartDate(t: number, step: ChartDateStep, previous?: number | null): string;
176
+ interface ChartDateLabels {
177
+ /** The calendar step chosen. */
178
+ step: ChartDateStep;
179
+ /** Category indexes that get a label (the first category in each bucket). */
180
+ indexes: number[];
181
+ /** Label text by category index. */
182
+ labels: Map<number, string>;
183
+ }
184
+ /**
185
+ * Picks the finest calendar step whose labels fit along a category axis. Categories are
186
+ * evenly spaced (`band` pixels each), so a label goes on the first category of each bucket,
187
+ * and the step is the first on the ladder whose neighbouring labels are at least their own
188
+ * width plus `gap` apart. Returns `null` when fewer than half the categories read as dates.
189
+ */
190
+ declare function chartDateLabels(categories: readonly string[], band: number, measure: (text: string) => number, gap?: number): ChartDateLabels | null;
191
+
192
+ interface ChartHistogramBin {
193
+ /** Lower edge (exclusive, except for the first bin). */
194
+ from: number;
195
+ /** Upper edge (inclusive). */
196
+ to: number;
197
+ count: number;
198
+ }
199
+ /**
200
+ * Bins values into `bins` equal-width bins (default √n, from 1 to 100). Bins are
201
+ * right-inclusive, the first closed on both sides, so a value on an edge belongs to the bin
202
+ * that ends there. Gaps and non-finite values are ignored.
203
+ */
204
+ declare function chartHistogram(values: readonly ChartValue[], bins?: number | null): ChartHistogramBin[];
205
+ /** The `q` quantile (0–1) of sorted values, interpolating linearly between ranks (`q·(n-1)`). */
206
+ declare function chartQuantile(sorted: readonly number[], q: number): number;
207
+ interface ChartBoxStats {
208
+ min: number;
209
+ max: number;
210
+ q1: number;
211
+ median: number;
212
+ q3: number;
213
+ mean: number;
214
+ /** Whisker ends: the furthest values within 1.5 × IQR of the box. */
215
+ lowerWhisker: number;
216
+ upperWhisker: number;
217
+ /** Values beyond the whiskers. */
218
+ outliers: number[];
219
+ count: number;
343
220
  }
344
- /** A DOM-free text width estimate (average glyph ≈ 0.56 em, bold ≈ 0.6 em). */
345
- declare const estimateChartTextWidth: ChartTextMeasure;
346
- /** Whether two selections point at the same thing. */
347
- declare function sameChartSelection(a: ChartSelection | null | undefined, b: ChartSelection | null | undefined): boolean;
221
+ /** Box-and-whisker statistics (Tukey fences at 1.5 × IQR); `null` without values. */
222
+ declare function chartBoxStats(values: readonly ChartValue[]): ChartBoxStats | null;
223
+ /** Squarified treemap (Bruls et al.): positive `values` packed into `rect`, largest first. Returns one rect per input index (zero-size for values ≤ 0). */
224
+ declare function chartSquarify(values: readonly number[], rect: ChartRect): ChartRect[];
348
225
  /**
349
- * Black or white text for a label drawn on `fill` (#rgb, #rrggbb or rgb()), by perceived
350
- * luminance (0.299 R + 0.587 G + 0.114 B). Unparseable colours (CSS variables) get white.
226
+ * Thins a long polyline (sorted by x) to the first, lowest, highest and last point of each
227
+ * pixel column, which draws identically. Returns the input when it has `max` points or fewer.
351
228
  */
352
- declare function contrastingTextColor(fill: string): string;
229
+ declare function decimateChartPoints<T extends {
230
+ x: number;
231
+ y: number;
232
+ }>(points: readonly T[], max?: number): T[];
233
+ interface ChartSeriesSummary {
234
+ id: string;
235
+ name: string;
236
+ /** Values present (not gaps). */
237
+ count: number;
238
+ gaps: number;
239
+ min: number | null;
240
+ max: number | null;
241
+ mean: number | null;
242
+ sum: number | null;
243
+ /** Category label of the minimum and maximum. */
244
+ minAt: string | null;
245
+ maxAt: string | null;
246
+ /** Direction of a least-squares line through the values in order. */
247
+ trend: 'rising' | 'falling' | 'flat' | null;
248
+ /** Relative change from the first to the last value, e.g. 0.25 for +25%. */
249
+ change: number | null;
250
+ }
251
+ /** Numbers about one series, for agents that check a chart without looking at it. */
252
+ declare function summarizeChartSeries(series: {
253
+ id: string;
254
+ name: string;
255
+ values: readonly ChartValue[];
256
+ }, categories: readonly string[]): ChartSeriesSummary;
257
+
353
258
  /**
354
259
  * Lays a chart out as drawing primitives (rects, paths, circles, lines and text) in a
355
260
  * `width × height` box. Pure and DOM-free: the React and Svelte canvases render the marks
356
261
  * as SVG, `chartSceneToSvg` writes them as a string, and anything else (canvas, PDF) can
357
- * draw them too. Clickable marks carry the `target` they select.
262
+ * draw them too. Clickable marks carry the `target` they select; what had to be left out
263
+ * (hidden labels, thinned lines) is listed in `warnings`.
358
264
  */
359
265
  declare function layoutChart(spec: ChartSpec, options: ChartLayoutOptions): ChartScene;
360
266
  /**
361
267
  * The data value at a scene point along the value axis (for dragging a bar or point), or
362
- * `undefined` when the scene has no value scale or is percent-stacked.
268
+ * `undefined` when the scene has no value scale or is percent-stacked. `secondary` reads the
269
+ * secondary axis.
363
270
  */
364
271
  declare function chartValueAtPoint(scene: ChartScene, point: {
365
272
  x: number;
366
273
  y: number;
274
+ }, secondary?: boolean): number | undefined;
275
+ /** The x value at a scene point on a scatter or bubble chart, or `undefined` without a numeric x axis. */
276
+ declare function chartXAtPoint(scene: ChartScene, point: {
277
+ x: number;
278
+ y: number;
367
279
  }): number | undefined;
368
280
  /** The value a drag should store: snapped to a tenth of the tick step (or `step`) and kept finite. */
369
- declare function snapChartValue(scene: ChartScene, value: number, step?: number): number;
281
+ declare function snapChartValue(scene: ChartScene, value: number, step?: number, ticks?: readonly number[]): number;
370
282
 
371
- /** SVG `dominant-baseline` for a text mark's baseline (shared by every renderer). */
372
- declare function chartTextBaseline(baseline: ChartTextMark['baseline']): 'hanging' | 'central' | 'text-after-edge';
373
- /** SVG `transform` for a rotated text mark, if any. */
374
- declare function chartTextTransform(mark: ChartTextMark): string | undefined;
375
- interface ChartSvgOptions {
376
- /** Leave out selection outlines (default `true`: exports show the chart only). */
377
- hideSelection?: boolean;
378
- /** Accessible title (default: the chart title). */
379
- ariaLabel?: string;
380
- }
381
- /** Writes a laid-out scene as a standalone SVG document string. */
382
- declare function chartSceneToSvg(scene: ChartScene, options?: ChartSvgOptions): string;
383
- /** Lays out and writes a chart as SVG, e.g. for export or server rendering. */
384
- declare function chartToSvg(spec: ChartSpec, options: Omit<ChartLayoutOptions, 'selection'> & ChartSvgOptions): string;
283
+ /** Data labels are skipped on series with more points than this. */
284
+ declare const MAX_CHART_DATA_LABELS = 200;
285
+ /** Lines with more points than this are thinned per pixel column. */
286
+ declare const MAX_CHART_LINE_POINTS = 2000;
287
+ /** Markers beyond this many are thinned to one per 2px cell. */
288
+ declare const MAX_CHART_MARKERS = 1000;
385
289
 
386
- interface ChartControllerOptions {
387
- /** Starting chart (any partial or saved spec; problems are reported in `state.issues`). */
388
- spec?: Partial<ChartSpec> | unknown;
389
- /** History to record into, e.g. one shared with the rest of the app (default: a new one). */
390
- history?: HistoryManager;
391
- /** Called after the spec changes (edit, undo, redo, load). */
392
- onChange?: (spec: Readonly<ChartSpec>) => void;
393
- }
394
- /** A snapshot of the controller. The same object is returned until something changes. */
395
- interface ChartState {
396
- spec: Readonly<ChartSpec>;
397
- selection: ChartSelection | null;
398
- /** The series the selection belongs to (a series or one of its points). */
399
- selectedSeries: ChartSeries | null;
400
- /** The category the selection belongs to (a category or a point). */
401
- selectedIndex: number | null;
402
- /** Problems from the last load or rejected edit, as sentences. */
403
- issues: readonly ChartIssue[];
404
- /** The gesture in progress (e.g. a bar drag), if any. */
405
- gesture: string | null;
406
- canUndo: boolean;
407
- canRedo: boolean;
408
- undoLabel: string;
409
- redoLabel: string;
410
- /** Bumped on every change. */
411
- revision: number;
412
- }
413
- type ChartActionResult = {
290
+ interface ChartSummary {
291
+ type: ChartSpec['type'];
292
+ title: string;
293
+ categories: number;
294
+ series: ChartSeriesSummary[];
295
+ /** The value axis as drawn: range and ticks (absent for pies and treemaps). */
296
+ valueAxis?: {
297
+ min: number;
298
+ max: number;
299
+ ticks: number[];
300
+ };
301
+ secondaryAxis?: {
302
+ min: number;
303
+ max: number;
304
+ ticks: number[];
305
+ };
306
+ xAxis?: {
307
+ min: number;
308
+ max: number;
309
+ ticks: number[];
310
+ };
311
+ /** What the layout left out at this size (hidden labels, thinned lines, …). */
312
+ warnings: ChartWarning[];
313
+ /** Whether the series colours can be told apart (also with colour-blindness). */
314
+ colors: Pick<ChartColorCheck, 'ok' | 'issues'>;
315
+ /** A plain-language description (the SVG `<desc>`). */
316
+ description: string;
317
+ }
318
+ /**
319
+ * Numbers about a chart for agents and screen readers: per-series min / max / mean / trend,
320
+ * the axes as drawn, layout warnings at `size`, a colour check and a one-paragraph
321
+ * description. Lets an agent verify a chart without rendering it.
322
+ */
323
+ declare function summarizeChart(spec: ChartSpec, size?: Pick<ChartLayoutOptions, 'width' | 'height' | 'measureText'>, scene?: ChartScene): ChartSummary;
324
+ /** A plain-language description of a chart: type, what it compares, ranges and notable extremes. */
325
+ declare function describeChart(spec: ChartSpec, series?: ChartSeriesSummary[]): string;
326
+
327
+ /** A partial change several fields at once (what `ChartController.update` takes). */
328
+ type ChartPresetPatch = Partial<Omit<ChartSpec, 'version' | 'xAxis' | 'yAxis' | 'yAxis2' | 'legend' | 'series' | 'categories'>> & {
329
+ xAxis?: Partial<ChartAxis>;
330
+ yAxis?: Partial<ChartAxis>;
331
+ yAxis2?: Partial<ChartAxis>;
332
+ legend?: Partial<ChartLegend>;
333
+ };
334
+ interface ChartLayoutPreset {
335
+ id: string;
336
+ label: string;
337
+ description: string;
338
+ patch: ChartPresetPatch;
339
+ }
340
+ /** Quick layouts: legend, labels and grid lines set together. */
341
+ declare const CHART_LAYOUT_PRESETS: readonly ChartLayoutPreset[];
342
+ interface ChartColorScheme {
343
+ id: string;
344
+ label: string;
345
+ description: string;
346
+ palette: readonly string[];
347
+ }
348
+ /** Shades of one hue, dark to light (for monochrome schemes). */
349
+ declare function monochromeChartPalette(base: string, count?: number): string[];
350
+ /** Named palettes. `default` and `okabe-ito` are colour-blind friendly. */
351
+ declare const CHART_COLOR_SCHEMES: readonly ChartColorScheme[];
352
+ /** The change a named layout and / or colour scheme makes, or a sentence saying which names exist. */
353
+ declare function chartPresetPatch(options: {
354
+ layout?: string;
355
+ colors?: string;
356
+ }): {
414
357
  ok: true;
358
+ patch: ChartPresetPatch;
415
359
  } | {
416
360
  ok: false;
417
361
  message: string;
418
- issues?: ChartIssue[];
419
362
  };
420
- /** Top-level fields with partial axes and legend. */
421
- type ChartSpecPatch = Partial<Omit<ChartSpec, 'version' | 'xAxis' | 'yAxis' | 'legend'>> & {
422
- xAxis?: Partial<ChartAxis>;
423
- yAxis?: Partial<ChartAxis>;
424
- legend?: Partial<ChartLegend>;
425
- };
426
- interface ChartSeriesInput {
427
- id?: string;
428
- name?: string;
429
- values?: readonly unknown[];
430
- color?: string;
431
- type?: ChartSeriesType;
432
- hidden?: boolean;
363
+
364
+ interface ChartTableShape {
365
+ /** The first row holds series names (some text, every value cell text or blank). */
366
+ headerRow: boolean;
367
+ /** The first column holds category labels (all text, or a blank top-left cell above a header row). */
368
+ labelColumn: boolean;
369
+ /** Series run along rows (the block is much wider than tall). */
370
+ byRows: boolean;
371
+ series: number;
372
+ /** Points per series. */
373
+ points: number;
374
+ anyNumber: boolean;
375
+ nonNegative: boolean;
376
+ mixedSigns: boolean;
377
+ /** The category labels read as dates. */
378
+ dates: boolean;
433
379
  }
434
- interface ChartSeriesPatch {
435
- name?: string;
436
- /** `null` goes back to the palette colour. */
437
- color?: string | null;
438
- /** `null` follows the chart type. */
439
- type?: ChartSeriesType | null;
440
- hidden?: boolean;
441
- }
442
- interface ChartEditOptions {
443
- /** Undo step label. */
444
- label?: string;
380
+ /**
381
+ * Reads the shape of a block of cells the way spreadsheets do: a header row when the first
382
+ * row is text, a label column when the first column is text (or the top-left cell is blank
383
+ * above a header row, the convention for years and x values), and series along the longer side.
384
+ */
385
+ declare function analyzeChartTable(rows: ReadonlyArray<ReadonlyArray<unknown>>): ChartTableShape;
386
+ interface ChartRecommendation {
387
+ type: ChartType;
388
+ stacking?: ChartStacking;
389
+ label: string;
390
+ /** Why it suits the data, as a sentence. */
391
+ reason: string;
445
392
  }
446
393
  /**
447
- * Headless state for a chart editor: a validated `ChartSpec`, a selection, and undoable
448
- * edits to data (values, series, categories, pasted grids, CSV) and presentation (type,
449
- * titles, axes, legend, stacking, …). Drags merge into one undo step (`beginGesture`).
450
- * `getState()` returns the same object until something changes, so it works with
451
- * `useSyncExternalStore` and Svelte runes alike.
452
- */
453
- declare class ChartController {
454
- readonly history: HistoryManager;
455
- private spec;
456
- private selection;
457
- private issues;
458
- private gestureKey;
459
- private gestureCount;
460
- private gestureStart;
461
- private revision;
462
- private applying;
463
- private readonly onChange?;
464
- private readonly listeners;
465
- private unsubscribeHistory?;
466
- private state;
467
- constructor(options?: ChartControllerOptions);
468
- private connect;
469
- /** The current snapshot (stable until the next change). */
470
- getState: () => ChartState;
471
- /** Calls `listener` after every change. Returns an unsubscribe function. */
472
- subscribe: (listener: (state: ChartState) => void) => (() => void);
473
- /** The current spec (do not mutate; edit through the controller). */
474
- getSpec(): Readonly<ChartSpec>;
475
- getSeries(id: string): ChartSeries | undefined;
476
- private computeState;
477
- private notify;
478
- /** Drops a selection that no longer points at anything. */
479
- private validSelection;
480
- private applySpec;
481
- private commit;
482
- private reject;
483
- /** A copy of the spec with `edit` applied (series and categories copied as needed). */
484
- private edited;
485
- private unknownSeries;
486
- private badIndex;
487
- /**
488
- * Changes any presentation or data fields as one undo step. All-or-nothing: if anything
489
- * is invalid, nothing changes and every problem is returned (and shown in `state.issues`).
490
- */
491
- update(patch: ChartSpecPatch, options?: ChartEditOptions): ChartActionResult;
492
- setType(type: ChartType): ChartActionResult;
493
- setTitle(title: string): ChartActionResult;
494
- setSubtitle(subtitle: string): ChartActionResult;
495
- /** Changes the category (`x`) or value (`y`) axis. */
496
- setAxis(axis: 'x' | 'y', patch: Partial<ChartAxis>): ChartActionResult;
497
- setLegend(patch: Partial<ChartLegend>): ChartActionResult;
498
- /**
499
- * Replaces categories and / or series as one undo step. Values are validated and padded
500
- * to the categories; all-or-nothing like `update`.
501
- */
502
- setData(data: {
503
- categories?: readonly unknown[];
504
- series?: readonly ChartSeriesInput[];
505
- }, options?: ChartEditOptions): ChartActionResult;
506
- /**
507
- * Sets one value (numbers, numeric text such as `1,200` or `12%`, or blank for a gap).
508
- * One undo step, or part of the current gesture.
509
- */
510
- setValue(seriesId: string, index: number, value: unknown, options?: ChartEditOptions): ChartActionResult;
511
- /** Several values as one undo step (all-or-nothing). */
512
- setValues(cells: readonly {
513
- seriesId: string;
514
- index: number;
515
- value: unknown;
516
- }[], options?: ChartEditOptions): ChartActionResult;
517
- /** Adds a series (values padded to the categories) and selects it. Returns its id. */
518
- addSeries(input?: ChartSeriesInput, options?: {
519
- at?: number;
520
- }): {
521
- ok: true;
522
- id: string;
523
- } | {
524
- ok: false;
525
- message: string;
526
- issues?: ChartIssue[];
527
- };
528
- removeSeries(id: string): ChartActionResult;
529
- updateSeries(id: string, patch: ChartSeriesPatch): ChartActionResult;
530
- toggleSeries(id: string): ChartActionResult;
531
- /** Moves a series to position `to` (drawing and legend order). */
532
- moveSeries(id: string, to: number): ChartActionResult;
533
- /** Inserts a category (with gaps in every series) at `at` (default: the end). Returns its index. */
534
- addCategory(label?: string, options?: {
535
- at?: number;
536
- }): {
537
- ok: true;
538
- index: number;
539
- };
540
- removeCategory(index: number): ChartActionResult;
541
- renameCategory(index: number, label: string): ChartActionResult;
542
- moveCategory(from: number, to: number): ChartActionResult;
543
- /**
544
- * Pastes a block of cells (TSV / CSV text or rows) into the data grid with its top-left at
545
- * `row` (category index) and `column` (series index; `-1` is the category column). The
546
- * grid grows to fit. Non-numeric value cells become gaps and are reported in `issues`.
547
- */
548
- pasteCells(row: number, column: number, cells: string | ReadonlyArray<ReadonlyArray<unknown>>): ChartActionResult & {
549
- issues?: ChartIssue[];
550
- };
551
- /**
552
- * Replaces the data with a grid of cells (see `chartDataFromTable`): one undo step. Series
553
- * colours and types are kept by name.
554
- */
555
- importTable(rows: ReadonlyArray<ReadonlyArray<unknown>>, options?: ChartTableOptions): ChartActionResult & {
556
- issues?: ChartIssue[];
557
- };
558
- /** Imports CSV (or TSV, detected by tabs) text; see `importTable`. */
559
- importCsv(text: string, options?: ChartTableOptions & {
560
- delimiter?: string;
561
- }): ChartActionResult & {
562
- issues?: ChartIssue[];
563
- };
564
- /** Selects a chart element (view state; not an undo step). */
565
- select(selection: ChartSelection | null): void;
566
- /**
567
- * Deletes what is selected: a series or category is removed, a point becomes a gap, a
568
- * title is cleared, the legend or an axis is hidden.
569
- */
570
- deleteSelection(): ChartActionResult;
571
- /** Adds `delta` to a value (a gap counts as 0). */
572
- nudgeValue(seriesId: string, index: number, delta: number): ChartActionResult;
573
- /** Starts a continuous edit (a drag): every change until `endGesture()` is one undo step. */
574
- beginGesture(key: string): void;
575
- endGesture(): void;
576
- /** The spec, for saving (a copy). */
577
- toJSON(): ChartSpec;
578
- /**
579
- * Replaces the chart without an undo step (e.g. when opening a document). Problems are
580
- * fixed with defaults and reported in `state.issues` (and returned).
581
- */
582
- load(input: unknown, options?: {
583
- clearHistory?: boolean;
584
- }): ChartIssue[];
585
- undo(): boolean;
586
- redo(): boolean;
587
- /** Stops listening to the history (reconnected by the next `subscribe`). */
588
- destroy(): void;
589
- }
590
- declare function createChartController(options?: ChartControllerOptions): ChartController;
394
+ * Chart types that suit the shape of a block of cells, best first. A heuristic from the shape
395
+ * (series count, points per series, text or date categories, negative values), not a copy of
396
+ * any spreadsheet's ranking.
397
+ */
398
+ declare function recommendChartTypes(rows: ReadonlyArray<ReadonlyArray<unknown>>): ChartRecommendation[];
399
+ declare function recommendForShape(shape: Omit<ChartTableShape, 'headerRow' | 'byRows'> & Partial<ChartTableShape>): ChartRecommendation[];
400
+ interface ChartFromTable {
401
+ type: ChartType;
402
+ stacking: ChartStacking;
403
+ categories: string[];
404
+ series: ChartSeries[];
405
+ issues: ChartIssue[];
406
+ shape: ChartTableShape;
407
+ }
408
+ /**
409
+ * Builds chart data from a block of cells (CSV, a clipboard grid or a spreadsheet range) using
410
+ * the spreadsheet conventions of `analyzeChartTable`. `type: 'auto'` (the default) takes the
411
+ * first recommendation. A scatter chart of a block without labels takes the first column as
412
+ * the x values of the others.
413
+ */
414
+ declare function chartFromTable(rows: ReadonlyArray<ReadonlyArray<unknown>>, options?: {
415
+ type?: ChartType | 'auto';
416
+ }): ChartFromTable;
591
417
 
592
418
  interface ChartCommandOptions {
593
419
  /** Id prefix (default `chart.`); use one per chart when several are registered. */
@@ -599,9 +425,12 @@ interface ChartCommandOptions {
599
425
  }
600
426
  /**
601
427
  * Palette and agent commands for a chart: describe, update presentation, replace data, set
602
- * values, add / remove series and categories, import CSV and export SVG. Register them in a
603
- * `CommandRegistry` and agents get them through `createCommandToolProvider`. Failures throw
604
- * sentences, which the registry returns as `{ ok: false, code: 'failed', message }`.
428
+ * values, add / remove series, categories and trendlines, apply presets, switch rows and
429
+ * columns, import CSV or Mermaid, export SVG, Mermaid or Office XML, recommend types and
430
+ * check colours. Register them in a `CommandRegistry` and agents get them through
431
+ * `createCommandToolProvider`; `createChartToolProvider` offers the same operations as
432
+ * individual tools. Failures throw sentences, which the registry returns as
433
+ * `{ ok: false, code: 'failed', message }`.
605
434
  */
606
435
  declare function createChartCommands(controller: ChartController, options?: ChartCommandOptions): CommandSpec[];
607
436
 
@@ -615,10 +444,22 @@ declare function chartClientToScene(scene: Pick<ChartScene, 'width' | 'height'>,
615
444
  x: number;
616
445
  y: number;
617
446
  };
618
- /** Whether a point can be dragged to a new value in this scene (cartesian, not percent-stacked, not hidden). */
447
+ /**
448
+ * Whether a point can be dragged to a new value in this scene: bar, line, area and scatter
449
+ * charts (not percent-stacked), scatter and bubble charts with x values (x and y), and
450
+ * waterfall steps. Hidden series and gaps cannot be dragged.
451
+ */
619
452
  declare function canDragChartPoint(controller: ChartController, scene: ChartScene, target: ChartSelection | undefined): target is Extract<ChartSelection, {
620
453
  kind: 'point';
621
454
  }>;
455
+ interface ChartDragMoveOptions {
456
+ /** Move a tenth as far as the pointer (fine adjustment; Alt). */
457
+ fine?: boolean;
458
+ /** Only change the axis the pointer has moved along most (scatter charts; Shift). */
459
+ lockAxis?: boolean;
460
+ /** Skip snapping to nearby values and ticks (e.g. while Ctrl / Cmd is held). */
461
+ noSnap?: boolean;
462
+ }
622
463
  interface ChartPointDrag {
623
464
  /**
624
465
  * The value axis range when the drag started. Pass it to `layoutChart` (`valueDomain`)
@@ -628,25 +469,60 @@ interface ChartPointDrag {
628
469
  min: number;
629
470
  max: number;
630
471
  };
472
+ /** The secondary value axis range when the drag started (`layoutChart`'s `valueDomain2`). */
473
+ readonly valueDomain2?: {
474
+ min: number;
475
+ max: number;
476
+ };
477
+ /** The numeric x range of a scatter or bubble chart when the drag started (`xDomain`). */
478
+ readonly xDomain?: {
479
+ min: number;
480
+ max: number;
481
+ };
482
+ /** The point being dragged, for `layoutChart`'s `readout`. */
483
+ readonly target: {
484
+ seriesId: string;
485
+ index: number;
486
+ };
631
487
  /** Moves the value with the pointer (scene coordinates). */
632
488
  move(point: {
633
489
  x: number;
634
490
  y: number;
635
- }): void;
491
+ }, options?: ChartDragMoveOptions): void;
636
492
  /** Ends the drag (one undo step for the whole drag). */
637
493
  end(): void;
494
+ /** Cancels the drag: the value goes back and no undo step is left (Escape). */
495
+ cancel(): void;
638
496
  }
497
+ interface ChartSnapOptions {
498
+ /** Values to snap to when the pointer is within `tolerancePx` of them. */
499
+ candidates?: readonly number[];
500
+ /** Screen distance that snaps (default 6). */
501
+ tolerancePx?: number;
502
+ /** Fallback step when no candidate is close (default: a tenth of the tick step). */
503
+ step?: number;
504
+ /** The scale the value is on (default: the scene's value scale). */
505
+ scale?: ChartValueScale;
506
+ }
507
+ /**
508
+ * Snaps a dragged value: to the nearest candidate (other series at the same category, the
509
+ * neighbouring values, zero, the start value, ticks) within `tolerancePx` screen pixels, or
510
+ * else to a tenth of the tick step.
511
+ */
512
+ declare function snapChartDragValue(scene: ChartScene, value: number, options?: ChartSnapOptions): number;
639
513
  /**
640
- * Starts dragging a bar or point: the value follows the pointer along the value axis,
641
- * snapped to a tenth of the tick step (`step` overrides), and the whole drag is one undo
642
- * step. Works for stacked bars too (the drag changes the segment by the distance moved).
643
- * Returns `null` when the target cannot be dragged.
514
+ * Starts dragging a bar or point: the value follows the pointer along its value axis (and
515
+ * along x on scatter and bubble charts), snapped to nearby values and then to a tenth of the
516
+ * tick step (`step` overrides), and the whole drag is one undo step. Works for stacked bars
517
+ * too (the drag changes the segment by the distance moved). Returns `null` when the target
518
+ * cannot be dragged.
644
519
  */
645
520
  declare function startChartPointDrag(controller: ChartController, scene: ChartScene, target: ChartSelection | undefined, start: {
646
521
  x: number;
647
522
  y: number;
648
523
  }, options?: {
649
524
  step?: number;
525
+ tolerancePx?: number;
650
526
  }): ChartPointDrag | null;
651
527
  interface ChartKeyInput {
652
528
  key: string;
@@ -657,12 +533,348 @@ interface ChartKeyInput {
657
533
  }
658
534
  /**
659
535
  * Keyboard editing on a focused chart: arrows move a point selection between categories
660
- * (← →) and change its value (↑ ↓, a tenth of the tick step; Shift: a whole step), Delete /
661
- * Backspace deletes the selection, Escape clears it. Returns `true` when the key was used
662
- * (call `preventDefault`).
536
+ * (← →) and change its value (↑ ↓, a tenth of the tick step; Shift: a whole step; Alt: a
537
+ * hundredth), Delete / Backspace deletes the selection, Escape cancels a drag or clears the
538
+ * selection. Returns `true` when the key was used (call `preventDefault`).
663
539
  */
664
540
  declare function handleChartKey(controller: ChartController, scene: ChartScene | null, event: ChartKeyInput): boolean;
665
541
  /** A short description of the selection for an inspector heading or a screen reader. */
666
542
  declare function describeChartSelection(controller: ChartController, selection?: ChartSelection | null): string;
543
+ /**
544
+ * The mark under a scene point (topmost first), for hosts without DOM events and for agents
545
+ * that drive the pointer: rects, circles, lines (within 4 px) and text boxes. Returns the
546
+ * mark's `target`, or `{ kind: 'chart' }` over the background, or `null` outside.
547
+ */
548
+ declare function chartHitTest(scene: ChartScene, point: {
549
+ x: number;
550
+ y: number;
551
+ }, measure?: (text: string, size: number, weight?: number) => number): ChartSelection | null;
552
+
553
+ /** The comment line that carries what Mermaid cannot express. Every Mermaid tool ignores `%%` comments. */
554
+ declare const CHART_MERMAID_META_PREFIX = "%% @pixerate ";
555
+ type ChartMermaidFamily = 'xychart' | 'pie' | 'radar';
556
+ interface ChartMermaidOptions {
557
+ /** Write the `%% @pixerate {…}` line so the chart round-trips exactly (default `true`). */
558
+ meta?: boolean;
559
+ /** Indentation of statements (default four spaces). */
560
+ indent?: string;
561
+ }
562
+ /** The Mermaid family a chart is written as. */
563
+ declare function chartMermaidFamily(spec: Pick<ChartSpec, 'type' | 'series'>): ChartMermaidFamily;
564
+ /**
565
+ * Writes a chart as Mermaid: `xychart-beta` for bar, line, area and scatter charts (areas and
566
+ * scatters drawn as lines), `pie` for pies, donuts, funnels and treemaps, `radar-beta` for
567
+ * radars. Anything Mermaid cannot hold (stacking, colours, formats, gaps, trendlines, other
568
+ * chart types) goes into one `%% @pixerate {…}` comment so `chartFromMermaid` gets the chart
569
+ * back exactly, while any Mermaid renderer still draws the basic chart.
570
+ */
571
+ declare function chartToMermaid(spec: ChartSpec, options?: ChartMermaidOptions): string;
572
+ interface ChartMermaidParseOptions {
573
+ /** Accept a statement that is still being written (an unclosed `[` list): for streaming views. */
574
+ partial?: boolean;
575
+ /** Ignore the `%% @pixerate` line (what the Mermaid text alone says). */
576
+ ignoreMeta?: boolean;
577
+ }
578
+ interface ChartMermaidResult {
579
+ spec: ChartSpec;
580
+ /** Problems, with 1-based `line` numbers. Lines that could not be read are listed and skipped. */
581
+ issues: ChartIssue[];
582
+ family: ChartMermaidFamily | null;
583
+ /** The `%% @pixerate` line was found and applied. */
584
+ hasMeta: boolean;
585
+ }
586
+ /**
587
+ * Reads Mermaid `xychart-beta`, `pie` or `radar-beta` text as a chart. Never throws: lines it
588
+ * cannot read are reported with their line numbers and skipped, and the result always draws.
589
+ * A `%% @pixerate {…}` line written by `chartToMermaid` restores everything Mermaid cannot hold.
590
+ */
591
+ declare function chartFromMermaid(text: string, options?: ChartMermaidParseOptions): ChartMermaidResult;
592
+ interface FoundChartMermaid {
593
+ source: string;
594
+ family: ChartMermaidFamily;
595
+ /** 1-based line where the block starts in the input. */
596
+ line: number;
597
+ }
598
+ /**
599
+ * Finds Mermaid charts in Markdown or chat text: fenced ```mermaid blocks (and unlabelled
600
+ * fences) whose header is xychart-beta, pie or radar-beta, else the whole text when it is one.
601
+ */
602
+ declare function findMermaidCharts(text: string): FoundChartMermaid[];
603
+
604
+ declare const CHART_OOXML_NS = "http://schemas.openxmlformats.org/drawingml/2006/chart";
605
+ declare const CHART_OOXML_CONTENT_TYPE = "application/vnd.openxmlformats-officedocument.drawingml.chart+xml";
606
+ declare const CHART_OOXML_RELATIONSHIP = "http://schemas.openxmlformats.org/officeDocument/2006/relationships/chart";
607
+ type ParserCtor$1 = {
608
+ new (): DOMParser;
609
+ };
610
+ interface ChartOoxmlReadOptions {
611
+ /** `DOMParser` constructor (default: the global one; pass jsdom's or xmldom's in Node). */
612
+ DOMParser?: ParserCtor$1;
613
+ }
614
+ interface ChartOoxmlReadResult {
615
+ spec: ChartSpec;
616
+ /** Problems and simplifications, as sentences. */
617
+ issues: ChartIssue[];
618
+ /** Features the file uses that the spec cannot hold (3-D, stock, surface, gradients, …). */
619
+ unsupported: string[];
620
+ /**
621
+ * Nothing was dropped: writing `spec` back gives an equivalent chart. When false, keep the
622
+ * original part (or show the chart read-only) if the file must stay as it was.
623
+ */
624
+ lossless: boolean;
625
+ }
626
+ /**
627
+ * Reads a DrawingML chart part (`c:chartSpace`, e.g. `word/charts/chart1.xml`) or an Office
628
+ * 2016 chartex part (`cx:chartSpace`: waterfall, funnel, treemap, histogram, box & whisker)
629
+ * as a chart spec. Data comes from the cached values. Never throws for a malformed chart: it
630
+ * returns an empty chart and says why.
631
+ */
632
+ declare function chartFromOoxml(xml: string, options?: ChartOoxmlReadOptions): ChartOoxmlReadResult;
633
+ /** A spreadsheet format code equivalent to a chart number format (`General` when there is none). */
634
+ declare function chartFormatToCode(format: ChartNumberFormat): string;
635
+ interface ChartOoxmlWriteResult {
636
+ /** The `c:chartSpace` part. */
637
+ xml: string;
638
+ /** What could not be written as DrawingML, as sentences (empty when nothing was lost). */
639
+ issues: string[];
640
+ }
641
+ /**
642
+ * Writes a chart as a DrawingML chart part (`c:chartSpace`) with the data as literals (no
643
+ * embedded workbook), for `word/charts/chartN.xml` or `ppt/charts/chartN.xml`. Waterfall,
644
+ * histogram, box, funnel and treemap charts need Office 2016 chartex parts; they are written
645
+ * as the closest classic chart and reported in `issues`.
646
+ */
647
+ declare function chartToOoxml(spec: ChartSpec): ChartOoxmlWriteResult;
648
+
649
+ interface ChartPresenceActor {
650
+ id: string;
651
+ name: string;
652
+ color: string;
653
+ /** Cursor position in scene coordinates. */
654
+ x: number;
655
+ y: number;
656
+ /** The button is down (dragging). */
657
+ pressed: boolean;
658
+ /** A short note shown next to the cursor (what the agent is doing). */
659
+ message?: string;
660
+ }
661
+ interface ChartPresenceState {
662
+ actors: readonly ChartPresenceActor[];
663
+ }
664
+ /** Cursor positions and notes of agents acting on a chart, for an overlay. */
665
+ declare class ChartPresence {
666
+ private state;
667
+ private readonly listeners;
668
+ getState: () => ChartPresenceState;
669
+ subscribe: (listener: (state: ChartPresenceState) => void) => (() => void);
670
+ /** Adds or changes an actor. */
671
+ set(actor: Pick<ChartPresenceActor, 'id'> & Partial<ChartPresenceActor>): void;
672
+ remove(id: string): void;
673
+ }
674
+ declare const CHART_PRESENCE_COLORS: readonly string[];
675
+ /** Time for performances: real timers, or an instant clock for tests and recordings. */
676
+ interface ChartClock {
677
+ now(): number;
678
+ wait(ms: number): Promise<void>;
679
+ }
680
+ declare const realChartClock: ChartClock;
681
+ /** A clock whose waits finish at once while its time still advances (repeatable performances). */
682
+ declare function createInstantChartClock(start?: number): ChartClock & {
683
+ elapsed(): number;
684
+ };
685
+ /** What an agent asks for. Each command commits as one undo step. */
686
+ type ChartAgentCommand = {
687
+ kind: 'setValue';
688
+ seriesId: string;
689
+ index: number;
690
+ value: number;
691
+ note?: string;
692
+ } | {
693
+ kind: 'select';
694
+ selection: ChartSelection | null;
695
+ note?: string;
696
+ } | {
697
+ kind: 'update';
698
+ patch: ChartSpecPatch;
699
+ label?: string;
700
+ note?: string;
701
+ } | {
702
+ kind: 'say';
703
+ text: string;
704
+ };
705
+ type ChartPerformanceStep = {
706
+ type: 'move';
707
+ to: {
708
+ x: number;
709
+ y: number;
710
+ };
711
+ ms: number;
712
+ } | {
713
+ type: 'say';
714
+ text: string;
715
+ ms: number;
716
+ } | {
717
+ type: 'press';
718
+ } | {
719
+ type: 'drag';
720
+ to: {
721
+ x: number;
722
+ y: number;
723
+ };
724
+ ms: number;
725
+ from: number;
726
+ value: number;
727
+ } | {
728
+ type: 'release';
729
+ } | {
730
+ type: 'commit';
731
+ };
732
+ /** Where a point or bar sits in the scene (its top for bars), or null when it is not drawn. */
733
+ declare function chartPointAnchor(scene: ChartScene, seriesId: string, index: number): {
734
+ x: number;
735
+ y: number;
736
+ } | null;
737
+ /**
738
+ * Plans how an agent acts out a command on the chart: cursor moves, a drag along the value
739
+ * axis for a value change (its end at the new value), a note, then a commit. Pure: the same
740
+ * scene and command give the same steps.
741
+ */
742
+ declare function planChartCommand(spec: ChartSpec, scene: ChartScene, command: ChartAgentCommand, speed?: number): ChartPerformanceStep[];
743
+ interface ChartDirectorOptions {
744
+ /** The scene as currently drawn (for cursor targets), e.g. the canvas' last layout. */
745
+ scene: () => ChartScene;
746
+ clock?: ChartClock;
747
+ /** 1 = natural speed; 2 = twice as fast. */
748
+ speed?: number;
749
+ /** Hide each actor's cursor this long after its last command (ms, default 1500; 0 keeps it). */
750
+ linger?: number;
751
+ }
752
+ interface ChartDirectorActor {
753
+ id: string;
754
+ name?: string;
755
+ color?: string;
756
+ }
757
+ type ChartPerformanceResult = {
758
+ ok: true;
759
+ command: ChartAgentCommand;
760
+ } | {
761
+ ok: false;
762
+ command: ChartAgentCommand;
763
+ message: string;
764
+ };
765
+ /**
766
+ * Acts out agent commands on a chart: each actor's cursor moves to the target, drags values
767
+ * into place (the chart updates live) and the command commits as one undo step, while the
768
+ * user keeps editing. Commands queue per actor; a command whose target was deleted meanwhile
769
+ * fails with a sentence instead of editing something else.
770
+ */
771
+ declare class ChartDirector {
772
+ private readonly controller;
773
+ readonly presence: ChartPresence;
774
+ private readonly options;
775
+ private readonly queues;
776
+ private readonly clock;
777
+ private calls;
778
+ constructor(controller: ChartController, presence: ChartPresence, options: ChartDirectorOptions);
779
+ /** Acts out `commands` in order for `actor`. Resolves with one result per command. */
780
+ perform(actor: ChartDirectorActor, commands: readonly ChartAgentCommand[]): Promise<ChartPerformanceResult[]>;
781
+ private stale;
782
+ private move;
783
+ private performOne;
784
+ }
785
+
786
+ type ParserCtor = {
787
+ new (): DOMParser;
788
+ };
789
+ interface ChartToolProviderOptions {
790
+ /** Provider id (unique per registry). Default `chart`. */
791
+ id?: string;
792
+ /** Always prefix tool names with `<namespace>__`. */
793
+ namespace?: string;
794
+ /**
795
+ * The chart cannot be edited: write tools are hidden and `get_chart` says why. A string
796
+ * is the reason ("The report is locked").
797
+ */
798
+ readOnly?: boolean | string | (() => boolean | string);
799
+ /** Size used for summaries, previews and pointer gestures (default 640 × 400). */
800
+ size?: {
801
+ width: number;
802
+ height: number;
803
+ };
804
+ /** Enables `import_chart_ooxml` (reading Office chart XML needs a DOMParser). Default: the global one, if any. */
805
+ DOMParser?: ParserCtor;
806
+ /**
807
+ * Acts out `set_chart_values` and `select_chart_element` with a visible cursor (see
808
+ * `ChartDirector`); each call is still one undo step. Without it, edits apply at once.
809
+ */
810
+ director?: ChartDirector;
811
+ /** Who the cursor belongs to (default `{ id: 'agent', name: 'Agent' }`). */
812
+ actor?: ChartDirectorActor;
813
+ /** Turns SVG into an image so `render_chart` can return PNG (e.g. through a canvas). */
814
+ rasterize?: (svg: string, size: {
815
+ width: number;
816
+ height: number;
817
+ }) => Promise<{
818
+ data: string;
819
+ mimeType: string;
820
+ }> | {
821
+ data: string;
822
+ mimeType: string;
823
+ };
824
+ }
825
+ /**
826
+ * Agent tools for a chart editor, for a `ToolRegistry`: one tool per operation with strict
827
+ * schemas. Reads (`get_chart`, `render_chart`, `check_chart_colors`, `recommend_chart`,
828
+ * `get_chart_trendline`, `list_chart_presets`, `export_chart_mermaid`, `export_chart_ooxml`)
829
+ * are always there; writes (data, series, categories, presentation, trendlines, presets,
830
+ * imports, selection, pointer and key input, undo / redo) are hidden while the chart is
831
+ * read-only. Every write is one undo step and returns what it changed.
832
+ */
833
+ declare function createChartToolProvider(controller: ChartController, options?: ChartToolProviderOptions): AgentToolProvider;
834
+
835
+ /**
836
+ * Reads JSON that is still arriving: closes open strings, arrays and objects and drops a
837
+ * dangling key or comma, so `{"type":"bar","series":[{"name":"A","values":[1,2` reads as far
838
+ * as it goes. Returns `undefined` when nothing usable has arrived yet.
839
+ */
840
+ declare function parsePartialChartJson(text: string): unknown;
841
+ type ChartStreamFormat = 'auto' | 'mermaid' | 'json';
842
+ interface ChartStreamResult {
843
+ /** The chart as far as it has arrived, or `null` before anything can be drawn. */
844
+ spec: ChartSpec | null;
845
+ issues: ChartIssue[];
846
+ /**
847
+ * The value range to lay out with while incomplete: it only grows, so the axis does not
848
+ * jump as values arrive. `null` once complete (the chart's own scale takes over).
849
+ */
850
+ valueDomain: {
851
+ min: number;
852
+ max: number;
853
+ } | null;
854
+ }
855
+ /**
856
+ * Turns a chart source that is still being written (Mermaid or a JSON spec, e.g. streamed
857
+ * from a model) into drawable specs. Series appear once their values start, axis bounds only
858
+ * grow until `complete`, and parse problems are reported only once the source is complete.
859
+ */
860
+ declare class ChartStream {
861
+ private readonly format;
862
+ private lo;
863
+ private hi;
864
+ private last;
865
+ constructor(format?: ChartStreamFormat);
866
+ /** Reads the source so far. `complete` when nothing more will arrive. */
867
+ update(source: string, complete?: boolean): ChartStreamResult;
868
+ /** Forgets the axis bounds (a new source). */
869
+ reset(): void;
870
+ }
871
+ /**
872
+ * A scene between two scenes, for animating changes (streamed data arriving, an agent's
873
+ * edit): marks are matched by `key`; numbers and same-shaped paths move from `from` to `to`;
874
+ * new marks fade in and marks that are gone are dropped. `t` runs from 0 to 1.
875
+ */
876
+ declare function blendChartScenes(from: ChartScene | null, to: ChartScene, t: number): ChartScene;
877
+ /** Ease-out cubic, for tweens. */
878
+ declare const easeChartTween: (t: number) => number;
667
879
 
668
- export { CHART_CURVES, CHART_LEGEND_POSITIONS, CHART_NUMBER_STYLES, CHART_ORIENTATIONS, CHART_SERIES_TYPES, CHART_STACKINGS, CHART_TYPES, CHART_TYPE_LABELS, CSS_VARIABLE_CHART_THEME, type ChartActionResult, type ChartAxis, type ChartCircleMark, type ChartCommandOptions, ChartController, type ChartControllerOptions, type ChartCurve, type ChartEditOptions, type ChartIssue, type ChartKeyInput, type ChartLayoutOptions, type ChartLegend, type ChartLegendPosition, type ChartLineMark, type ChartMark, type ChartMarkRole, type ChartNumberFormat, type ChartOrientation, type ChartPathMark, type ChartPointDrag, type ChartRect, type ChartRectMark, type ChartScene, type ChartSelection, type ChartSeries, type ChartSeriesInput, type ChartSeriesPatch, type ChartSeriesType, type ChartSpec, type ChartSpecPatch, type ChartStacking, type ChartState, type ChartSvgOptions, type ChartTableData, type ChartTableOptions, type ChartTextMark, type ChartTextMeasure, type ChartTheme, type ChartType, type ChartValue, type ChartValueScale, DEFAULT_CHART_PALETTE, DEFAULT_CHART_THEME, type NiceScale, canDragChartPoint, chartClientToScene, chartColorInputValue, chartDataFromTable, chartDataToTable, chartSceneToSvg, chartSeriesColor, chartSeriesType, chartSliceColor, chartTextBaseline, chartTextTransform, chartToSvg, chartValueAtPoint, cloneChartSeries, cloneChartSpec, contrastingTextColor, createChartCommands, createChartController, createChartSpec, defaultChartAxis, describeChartSelection, estimateChartTextWidth, formatChartNumber, handleChartKey, isCartesianChart, layoutChart, linearMap, niceScale, niceStep, normalizeChartAxis, normalizeChartSpec, normalizeChartValues, parseChartValue, sameChartSelection, snapChartValue, startChartPointDrag, stepDecimals, uniqueChartSeriesId };
880
+ export { CHART_COLOR_SCHEMES, CHART_DATE_STEPS, CHART_LAYOUT_PRESETS, CHART_MERMAID_META_PREFIX, CHART_OOXML_CONTENT_TYPE, CHART_OOXML_NS, CHART_OOXML_RELATIONSHIP, CHART_PALETTE_SHADES, CHART_PRESENCE_COLORS, type ChartAgentCommand, ChartAxis, type ChartBoxStats, type ChartClock, type ChartColorCheck, type ChartColorCheckOptions, type ChartColorPair, type ChartColorScheme, type ChartCommandOptions, ChartController, type ChartDateLabels, type ChartDateStep, ChartDirector, type ChartDirectorActor, type ChartDirectorOptions, type ChartDragMoveOptions, type ChartFormatCode, type ChartFromTable, type ChartHistogramBin, ChartIssue, type ChartKeyInput, ChartLayoutOptions, type ChartLayoutPreset, ChartLegend, type ChartMermaidFamily, type ChartMermaidOptions, type ChartMermaidParseOptions, type ChartMermaidResult, ChartNumberFormat, type ChartOoxmlReadOptions, type ChartOoxmlReadResult, type ChartOoxmlWriteResult, type ChartPerformanceResult, type ChartPerformanceStep, type ChartPointDrag, ChartPresence, type ChartPresenceActor, type ChartPresenceState, type ChartPresetPatch, type ChartRecommendation, ChartRect, type ChartRgb, ChartScene, ChartSelection, ChartSeries, type ChartSeriesSummary, type ChartSnapOptions, ChartSpec, ChartSpecPatch, ChartStacking, ChartStream, type ChartStreamFormat, type ChartStreamResult, type ChartSummary, type ChartTableShape, type ChartToolProviderOptions, ChartType, ChartValue, ChartValueScale, type ChartVision, ChartWarning, type FoundChartMermaid, MAX_CHART_DATA_LABELS, MAX_CHART_LINE_POINTS, MAX_CHART_MARKERS, type NiceScale, analyzeChartTable, blendChartScenes, canDragChartPoint, chartBoxStats, chartClientToScene, chartColorDistance, chartContrastRatio, chartDateLabels, chartDateToSerial, chartFormatToCode, chartFromMermaid, chartFromOoxml, chartFromTable, chartHistogram, chartHitTest, chartLuminance, chartMermaidFamily, chartPointAnchor, chartPresetPatch, chartQuantile, chartRgbToHex, chartRgbToOklab, chartSerialToDate, chartSquarify, chartTextOn, chartToMermaid, chartToOoxml, chartValueAtPoint, chartXAtPoint, checkChartColors, compileChartFormatCode, createChartCommands, createChartToolProvider, createInstantChartClock, cyclePaletteColor, decimateChartPoints, describeChart, describeChartSelection, easeChartTween, findMermaidCharts, formatChartDate, formatChartNumber, formatChartValueWithCode, handleChartKey, layoutChart, linearMap, monochromeChartPalette, niceScale, niceStep, parseChartColor, parseChartDate, parsePartialChartJson, planChartCommand, realChartClock, recommendChartTypes, recommendForShape, shadeChartColor, simulateChartVision, snapChartDragValue, snapChartValue, startChartPointDrag, stepDecimals, summarizeChart, summarizeChartSeries };