insomni-plot 0.1.0-alpha.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 (242) hide show
  1. package/LICENSE.md +674 -0
  2. package/README.md +81 -0
  3. package/dist/core.d.mts +340 -0
  4. package/dist/core.mjs +1047 -0
  5. package/dist/index.d.mts +3426 -0
  6. package/dist/index.mjs +12762 -0
  7. package/dist/interactions-DEFL_F4E.mjs +5395 -0
  8. package/dist/range-presets-CzECsu3V.d.mts +1523 -0
  9. package/package.json +34 -0
  10. package/src/annotations.d.ts +121 -0
  11. package/src/annotations.ts +438 -0
  12. package/src/axis.d.ts +184 -0
  13. package/src/axis.test.ts +131 -0
  14. package/src/axis.ts +765 -0
  15. package/src/colorbar.d.ts +69 -0
  16. package/src/colorbar.ts +294 -0
  17. package/src/colors.d.ts +57 -0
  18. package/src/colors.test.ts +28 -0
  19. package/src/colors.ts +486 -0
  20. package/src/core.ts +299 -0
  21. package/src/format.d.ts +54 -0
  22. package/src/format.ts +138 -0
  23. package/src/grammar/accessibility.d.ts +147 -0
  24. package/src/grammar/accessibility.test.ts +199 -0
  25. package/src/grammar/accessibility.ts +443 -0
  26. package/src/grammar/aes.d.ts +35 -0
  27. package/src/grammar/aes.test.ts +75 -0
  28. package/src/grammar/aes.ts +120 -0
  29. package/src/grammar/annotations.d.ts +86 -0
  30. package/src/grammar/annotations.test.ts +68 -0
  31. package/src/grammar/annotations.ts +336 -0
  32. package/src/grammar/attach-brush.d.ts +44 -0
  33. package/src/grammar/attach-brush.test.ts +214 -0
  34. package/src/grammar/attach-brush.ts +111 -0
  35. package/src/grammar/attach-presets.d.ts +33 -0
  36. package/src/grammar/attach-presets.test.ts +106 -0
  37. package/src/grammar/attach-presets.ts +215 -0
  38. package/src/grammar/chart.d.ts +952 -0
  39. package/src/grammar/chart.test.ts +118 -0
  40. package/src/grammar/chart.ts +1172 -0
  41. package/src/grammar/color-utils.d.ts +29 -0
  42. package/src/grammar/color-utils.test.ts +53 -0
  43. package/src/grammar/color-utils.ts +66 -0
  44. package/src/grammar/constants.d.ts +45 -0
  45. package/src/grammar/constants.ts +61 -0
  46. package/src/grammar/coord.d.ts +183 -0
  47. package/src/grammar/coord.test.ts +355 -0
  48. package/src/grammar/coord.ts +619 -0
  49. package/src/grammar/data/pivot.d.ts +57 -0
  50. package/src/grammar/data/pivot.ts +107 -0
  51. package/src/grammar/emphasis-driver.d.ts +69 -0
  52. package/src/grammar/emphasis-driver.test.ts +199 -0
  53. package/src/grammar/emphasis-driver.ts +205 -0
  54. package/src/grammar/equality.d.ts +3 -0
  55. package/src/grammar/equality.ts +40 -0
  56. package/src/grammar/facet.d.ts +63 -0
  57. package/src/grammar/facet.test.ts +60 -0
  58. package/src/grammar/facet.ts +175 -0
  59. package/src/grammar/geoms/_categorical.d.ts +94 -0
  60. package/src/grammar/geoms/_categorical.ts +0 -0
  61. package/src/grammar/geoms/_distribution.d.ts +52 -0
  62. package/src/grammar/geoms/_distribution.ts +125 -0
  63. package/src/grammar/geoms/_mark.d.ts +69 -0
  64. package/src/grammar/geoms/_mark.ts +136 -0
  65. package/src/grammar/geoms/_shape.d.ts +41 -0
  66. package/src/grammar/geoms/_shape.ts +74 -0
  67. package/src/grammar/geoms/aggregate.d.ts +95 -0
  68. package/src/grammar/geoms/aggregate.test.ts +554 -0
  69. package/src/grammar/geoms/aggregate.ts +840 -0
  70. package/src/grammar/geoms/area.d.ts +32 -0
  71. package/src/grammar/geoms/area.test.ts +165 -0
  72. package/src/grammar/geoms/area.ts +578 -0
  73. package/src/grammar/geoms/band.d.ts +27 -0
  74. package/src/grammar/geoms/band.test.ts +57 -0
  75. package/src/grammar/geoms/band.ts +126 -0
  76. package/src/grammar/geoms/bar.d.ts +56 -0
  77. package/src/grammar/geoms/bar.test.ts +367 -0
  78. package/src/grammar/geoms/bar.ts +1054 -0
  79. package/src/grammar/geoms/boxplot.d.ts +129 -0
  80. package/src/grammar/geoms/boxplot.test.ts +299 -0
  81. package/src/grammar/geoms/boxplot.ts +834 -0
  82. package/src/grammar/geoms/connected-scatter.d.ts +27 -0
  83. package/src/grammar/geoms/connected-scatter.test.ts +157 -0
  84. package/src/grammar/geoms/connected-scatter.ts +63 -0
  85. package/src/grammar/geoms/emphasis.d.ts +76 -0
  86. package/src/grammar/geoms/emphasis.test.ts +135 -0
  87. package/src/grammar/geoms/emphasis.ts +162 -0
  88. package/src/grammar/geoms/histogram.d.ts +75 -0
  89. package/src/grammar/geoms/histogram.test.ts +262 -0
  90. package/src/grammar/geoms/histogram.ts +740 -0
  91. package/src/grammar/geoms/index.d.ts +20 -0
  92. package/src/grammar/geoms/index.ts +77 -0
  93. package/src/grammar/geoms/interval.d.ts +31 -0
  94. package/src/grammar/geoms/interval.test.ts +154 -0
  95. package/src/grammar/geoms/interval.ts +342 -0
  96. package/src/grammar/geoms/line.d.ts +38 -0
  97. package/src/grammar/geoms/line.test.ts +247 -0
  98. package/src/grammar/geoms/line.ts +659 -0
  99. package/src/grammar/geoms/point.d.ts +57 -0
  100. package/src/grammar/geoms/point.test.ts +163 -0
  101. package/src/grammar/geoms/point.ts +545 -0
  102. package/src/grammar/geoms/polar.test.ts +216 -0
  103. package/src/grammar/geoms/ribbon.d.ts +21 -0
  104. package/src/grammar/geoms/ribbon.test.ts +170 -0
  105. package/src/grammar/geoms/ribbon.ts +87 -0
  106. package/src/grammar/geoms/ridgeline.d.ts +89 -0
  107. package/src/grammar/geoms/ridgeline.test.ts +247 -0
  108. package/src/grammar/geoms/ridgeline.ts +1164 -0
  109. package/src/grammar/geoms/rolling.d.ts +43 -0
  110. package/src/grammar/geoms/rolling.test.ts +217 -0
  111. package/src/grammar/geoms/rolling.ts +387 -0
  112. package/src/grammar/geoms/rug.d.ts +28 -0
  113. package/src/grammar/geoms/rug.test.ts +126 -0
  114. package/src/grammar/geoms/rug.ts +214 -0
  115. package/src/grammar/geoms/rule.d.ts +23 -0
  116. package/src/grammar/geoms/rule.test.ts +69 -0
  117. package/src/grammar/geoms/rule.ts +212 -0
  118. package/src/grammar/geoms/smooth.d.ts +54 -0
  119. package/src/grammar/geoms/smooth.test.ts +78 -0
  120. package/src/grammar/geoms/smooth.ts +337 -0
  121. package/src/grammar/geoms/text.d.ts +29 -0
  122. package/src/grammar/geoms/text.test.ts +64 -0
  123. package/src/grammar/geoms/text.ts +234 -0
  124. package/src/grammar/geoms/tile.d.ts +61 -0
  125. package/src/grammar/geoms/tile.test.ts +157 -0
  126. package/src/grammar/geoms/tile.ts +621 -0
  127. package/src/grammar/geoms/types.d.ts +319 -0
  128. package/src/grammar/geoms/types.ts +362 -0
  129. package/src/grammar/geoms/violin.d.ts +85 -0
  130. package/src/grammar/geoms/violin.test.ts +187 -0
  131. package/src/grammar/geoms/violin.ts +672 -0
  132. package/src/grammar/index.d.ts +22 -0
  133. package/src/grammar/index.ts +269 -0
  134. package/src/grammar/interactions/_disposable.d.ts +5 -0
  135. package/src/grammar/interactions/_disposable.ts +23 -0
  136. package/src/grammar/interactions/_z.d.ts +4 -0
  137. package/src/grammar/interactions/_z.ts +16 -0
  138. package/src/grammar/interactions/brush-selection.test.ts +262 -0
  139. package/src/grammar/interactions/brush.d.ts +63 -0
  140. package/src/grammar/interactions/brush.test.ts +483 -0
  141. package/src/grammar/interactions/brush.ts +452 -0
  142. package/src/grammar/interactions/crosshair.d.ts +19 -0
  143. package/src/grammar/interactions/crosshair.test.ts +127 -0
  144. package/src/grammar/interactions/crosshair.ts +76 -0
  145. package/src/grammar/interactions/hit-layer.d.ts +64 -0
  146. package/src/grammar/interactions/hit-layer.ts +246 -0
  147. package/src/grammar/interactions/legend.d.ts +19 -0
  148. package/src/grammar/interactions/legend.ts +101 -0
  149. package/src/grammar/interactions/menu.d.ts +93 -0
  150. package/src/grammar/interactions/menu.test.ts +373 -0
  151. package/src/grammar/interactions/menu.ts +342 -0
  152. package/src/grammar/interactions/selection.d.ts +25 -0
  153. package/src/grammar/interactions/selection.test.ts +289 -0
  154. package/src/grammar/interactions/selection.ts +142 -0
  155. package/src/grammar/interactions/series-readout.d.ts +91 -0
  156. package/src/grammar/interactions/series-readout.test.ts +668 -0
  157. package/src/grammar/interactions/series-readout.ts +422 -0
  158. package/src/grammar/interactions/series-snap.d.ts +70 -0
  159. package/src/grammar/interactions/series-snap.test.ts +214 -0
  160. package/src/grammar/interactions/series-snap.ts +218 -0
  161. package/src/grammar/interactions/tooltip-axis.test.ts +176 -0
  162. package/src/grammar/interactions/tooltip-touch.browser.test.ts +49 -0
  163. package/src/grammar/interactions/tooltip-touch.test.ts +161 -0
  164. package/src/grammar/interactions/tooltip.d.ts +140 -0
  165. package/src/grammar/interactions/tooltip.test.ts +406 -0
  166. package/src/grammar/interactions/tooltip.ts +622 -0
  167. package/src/grammar/interactions/transitions.d.ts +34 -0
  168. package/src/grammar/interactions/transitions.test.ts +172 -0
  169. package/src/grammar/interactions/transitions.ts +160 -0
  170. package/src/grammar/layout.d.ts +68 -0
  171. package/src/grammar/layout.ts +186 -0
  172. package/src/grammar/legend-merge.test.ts +332 -0
  173. package/src/grammar/mount.d.ts +78 -0
  174. package/src/grammar/mount.test.ts +479 -0
  175. package/src/grammar/mount.ts +2112 -0
  176. package/src/grammar/palettes.d.ts +54 -0
  177. package/src/grammar/palettes.test.ts +80 -0
  178. package/src/grammar/palettes.ts +167 -0
  179. package/src/grammar/pan-zoom.test.ts +398 -0
  180. package/src/grammar/phylo.d.ts +65 -0
  181. package/src/grammar/phylo.test.ts +59 -0
  182. package/src/grammar/phylo.ts +112 -0
  183. package/src/grammar/pipeline.auto-ticks.test.ts +40 -0
  184. package/src/grammar/pipeline.d.ts +158 -0
  185. package/src/grammar/pipeline.test.ts +463 -0
  186. package/src/grammar/pipeline.ts +1233 -0
  187. package/src/grammar/profiling.d.ts +8 -0
  188. package/src/grammar/profiling.ts +24 -0
  189. package/src/grammar/scales.d.ts +188 -0
  190. package/src/grammar/scales.test.ts +181 -0
  191. package/src/grammar/scales.ts +800 -0
  192. package/src/grammar/svg.d.ts +3 -0
  193. package/src/grammar/svg.ts +39 -0
  194. package/src/grammar/theme.d.ts +261 -0
  195. package/src/grammar/theme.test.ts +105 -0
  196. package/src/grammar/theme.ts +490 -0
  197. package/src/heatmap/cpu.ts +109 -0
  198. package/src/heatmap/gpu.ts +565 -0
  199. package/src/heatmap/types.ts +177 -0
  200. package/src/heatmap.browser.test.ts +308 -0
  201. package/src/heatmap.test.ts +320 -0
  202. package/src/heatmap.ts +123 -0
  203. package/src/index.d.ts +1 -0
  204. package/src/index.ts +8 -0
  205. package/src/interactions.d.ts +48 -0
  206. package/src/interactions.test.ts +226 -0
  207. package/src/interactions.ts +394 -0
  208. package/src/layout/box.d.ts +48 -0
  209. package/src/layout/box.test.ts +107 -0
  210. package/src/layout/box.ts +143 -0
  211. package/src/legend.d.ts +115 -0
  212. package/src/legend.ts +422 -0
  213. package/src/marks/curve.d.ts +43 -0
  214. package/src/marks/curve.ts +244 -0
  215. package/src/marks/stack.d.ts +53 -0
  216. package/src/marks/stack.ts +184 -0
  217. package/src/marks.d.ts +273 -0
  218. package/src/marks.test.ts +541 -0
  219. package/src/marks.ts +1292 -0
  220. package/src/navigator.test.ts +174 -0
  221. package/src/navigator.ts +393 -0
  222. package/src/range-presets.d.ts +113 -0
  223. package/src/range-presets.test.ts +345 -0
  224. package/src/range-presets.ts +349 -0
  225. package/src/scales.d.ts +98 -0
  226. package/src/scales.test.ts +103 -0
  227. package/src/scales.ts +695 -0
  228. package/src/stats/index.d.ts +200 -0
  229. package/src/stats/index.test.ts +349 -0
  230. package/src/stats/index.ts +740 -0
  231. package/src/stats/regression.d.ts +38 -0
  232. package/src/stats/regression.test.ts +56 -0
  233. package/src/stats/regression.ts +396 -0
  234. package/src/stats/rolling-window.d.ts +55 -0
  235. package/src/stats/rolling-window.test.ts +237 -0
  236. package/src/stats/rolling-window.ts +256 -0
  237. package/src/test-setup.ts +19 -0
  238. package/src/viewport/axis-state.d.ts +72 -0
  239. package/src/viewport/axis-state.ts +476 -0
  240. package/src/viewport.d.ts +170 -0
  241. package/src/viewport.test.ts +363 -0
  242. package/src/viewport.ts +510 -0
package/src/core.ts ADDED
@@ -0,0 +1,299 @@
1
+ // ---------------------------------------------------------------------------
2
+ // Scales
3
+ // ---------------------------------------------------------------------------
4
+
5
+ export {
6
+ bandScale,
7
+ groupedBandScale,
8
+ linearScale,
9
+ logScale,
10
+ sqrtScale,
11
+ timeScale,
12
+ timeTickFormat,
13
+ timeTicks,
14
+ type AxisScale,
15
+ type BandScale,
16
+ type BandScaleOptions,
17
+ type ContinuousScale,
18
+ type DateDomain,
19
+ type GroupedBandScale,
20
+ type GroupedBandScaleOptions,
21
+ type NumericDomain,
22
+ type NumericRange,
23
+ type TickFormatter,
24
+ type TimeIntervalUnit,
25
+ type TimeScale,
26
+ } from "./scales.ts";
27
+
28
+ // ---------------------------------------------------------------------------
29
+ // Axis builders
30
+ // ---------------------------------------------------------------------------
31
+
32
+ export { bottomAxis, leftAxis, rightAxis, topAxis, truncateToWidth } from "./axis.ts";
33
+ export type {
34
+ AxisBuilder,
35
+ AxisLabelConfig,
36
+ AxisMeasurement,
37
+ AxisOptions,
38
+ AxisOrigin,
39
+ AxisTickFormatter,
40
+ AxisTitle,
41
+ TickIntervalSpec,
42
+ TickSpec,
43
+ } from "./axis.ts";
44
+
45
+ // ---------------------------------------------------------------------------
46
+ // Marks
47
+ // ---------------------------------------------------------------------------
48
+
49
+ export {
50
+ areaMark,
51
+ barMark,
52
+ cardinalCurve,
53
+ categoricalBarMark,
54
+ DASHED_PATTERN,
55
+ defineCurve,
56
+ DOTTED_PATTERN,
57
+ groupedBarMark,
58
+ lineMark,
59
+ pointMark,
60
+ resamplePoints,
61
+ stack,
62
+ stackedAreaMark,
63
+ stackedBarMark,
64
+ } from "./marks.ts";
65
+ export type {
66
+ Accessor,
67
+ AreaMarkOptions,
68
+ BarBorderStyle,
69
+ BarMarkOptions,
70
+ BarOrientation,
71
+ CategoricalBarMarkOptions,
72
+ CustomCurve,
73
+ GroupedBarMarkOptions,
74
+ LineCurve,
75
+ LineCurvePreset,
76
+ LineDashStyle,
77
+ LineMarkOptions,
78
+ MarkBuilder,
79
+ MarkOrigin,
80
+ PointBorderStyle,
81
+ PointMarkOptions,
82
+ PointShapeKind,
83
+ StackedAreaMarkOptions,
84
+ StackedBarMarkOptions,
85
+ StackedMarkBuilder,
86
+ StackOffset,
87
+ StackOptions,
88
+ StackOrder,
89
+ StackSegment,
90
+ ValueOrAccessor,
91
+ } from "./marks.ts";
92
+
93
+ // ---------------------------------------------------------------------------
94
+ // Annotations (rule, band, value labels)
95
+ // ---------------------------------------------------------------------------
96
+
97
+ export { bandMark, ruleMark, valueLabelMark } from "./annotations.ts";
98
+ export type {
99
+ BandMarkOptions,
100
+ HorizontalBandOptions,
101
+ HorizontalRuleOptions,
102
+ RuleAnchor,
103
+ RuleMarkOptions,
104
+ ValueLabelAlign,
105
+ ValueLabelMarkOptions,
106
+ VerticalBandOptions,
107
+ VerticalRuleOptions,
108
+ } from "./annotations.ts";
109
+
110
+ // ---------------------------------------------------------------------------
111
+ // Legend
112
+ // ---------------------------------------------------------------------------
113
+
114
+ export { areaSwatch, barSwatch, legend, lineSwatch, pointSwatch } from "./legend.ts";
115
+ export type {
116
+ AreaSwatchSpec,
117
+ BarSwatchSpec,
118
+ LegendAlign,
119
+ LegendBuilder,
120
+ LegendEntry,
121
+ LegendOptions,
122
+ LegendOrientation,
123
+ LineSwatchSpec,
124
+ PointSwatchSpec,
125
+ SwatchSpec,
126
+ } from "./legend.ts";
127
+
128
+ // ---------------------------------------------------------------------------
129
+ // Number / currency / percent formatters
130
+ // ---------------------------------------------------------------------------
131
+
132
+ export { currency, fixed, percent, siNumber } from "./format.ts";
133
+ export type {
134
+ CurrencyOptions,
135
+ FixedNumberOptions,
136
+ PercentOptions,
137
+ SiNumberOptions,
138
+ } from "./format.ts";
139
+
140
+ // ---------------------------------------------------------------------------
141
+ // Heatmap producer
142
+ // ---------------------------------------------------------------------------
143
+
144
+ export { heatmapLayer } from "./heatmap.ts";
145
+ export type { HeatmapProducer, HeatmapSpec } from "./heatmap.ts";
146
+
147
+ // ---------------------------------------------------------------------------
148
+ // Color palettes
149
+ // ---------------------------------------------------------------------------
150
+
151
+ export {
152
+ accent,
153
+ blues,
154
+ brbg,
155
+ categoricalPalette,
156
+ category10,
157
+ cividis,
158
+ colorScale,
159
+ continuousPalette,
160
+ coolwarm,
161
+ dark2,
162
+ greens,
163
+ greys,
164
+ inferno,
165
+ magma,
166
+ oranges,
167
+ paired,
168
+ pastel,
169
+ piyg,
170
+ plasma,
171
+ prgn,
172
+ puor,
173
+ purples,
174
+ rdbu,
175
+ reds,
176
+ set1,
177
+ set2,
178
+ set3,
179
+ spectral,
180
+ tableau10,
181
+ viridis,
182
+ type CategoricalPalette,
183
+ type ContinuousPalette,
184
+ } from "./colors.ts";
185
+
186
+ // ---------------------------------------------------------------------------
187
+ // Data viewport
188
+ // ---------------------------------------------------------------------------
189
+
190
+ export { createDataViewport, linkViewports } from "./viewport.ts";
191
+ export type {
192
+ BandAxisConfig,
193
+ ContinuousAxisConfig,
194
+ DataPanBoundsOptions,
195
+ DataViewport,
196
+ DataViewportOptions,
197
+ LinkViewportsOptions,
198
+ TimeAxisConfig,
199
+ Viewport,
200
+ ViewportAxisConfig,
201
+ VisibleDomainInput,
202
+ } from "./viewport.ts";
203
+
204
+ // ---------------------------------------------------------------------------
205
+ // Data viewport interactions
206
+ // ---------------------------------------------------------------------------
207
+
208
+ export { bindDataViewport } from "./interactions.ts";
209
+ export type {
210
+ AxisSelection,
211
+ BindDataViewportOptions,
212
+ DataViewportBinding,
213
+ } from "./interactions.ts";
214
+
215
+ // ---------------------------------------------------------------------------
216
+ // Distribution statistics (box stats, KDE, jitter helpers)
217
+ // ---------------------------------------------------------------------------
218
+
219
+ export {
220
+ bin,
221
+ binBreaks,
222
+ binBy,
223
+ binWithBreaks,
224
+ boxStats,
225
+ confidenceBand,
226
+ groupBy,
227
+ histogramMeasureValue,
228
+ jitter,
229
+ kde,
230
+ linearFit,
231
+ loessFit,
232
+ polyFit,
233
+ quantile,
234
+ rollingWindow,
235
+ } from "./stats/index.ts";
236
+ export type {
237
+ BinByOptions,
238
+ BinByResult,
239
+ BinClosed,
240
+ BinOptions,
241
+ BinResult,
242
+ BinRule,
243
+ BoxStats,
244
+ BoxStatsOptions,
245
+ ConfidenceBandOptions,
246
+ ConfidenceBandPoint,
247
+ HistogramMeasure,
248
+ KdeBandwidth,
249
+ KdeKernel,
250
+ KdeOptions,
251
+ KdeResult,
252
+ LoessOptions,
253
+ QuantileMethod,
254
+ RegressionFit,
255
+ RollingAxis,
256
+ RollingPoint,
257
+ RollingStatistic,
258
+ RollingStatisticKind,
259
+ RollingWindow,
260
+ RollingWindowOptions,
261
+ WhiskerRule,
262
+ } from "./stats/index.ts";
263
+
264
+ // ---------------------------------------------------------------------------
265
+ // Continuous color-bar legend
266
+ // ---------------------------------------------------------------------------
267
+
268
+ export { colorBar } from "./colorbar.ts";
269
+ export type { ColorBarLabelSide, ColorBarOptions, ColorBarOrientation } from "./colorbar.ts";
270
+
271
+ // ---------------------------------------------------------------------------
272
+ // Data navigator
273
+ // ---------------------------------------------------------------------------
274
+
275
+ export { createDataNavigator } from "./navigator.ts";
276
+ export type {
277
+ DataNavigator,
278
+ DataNavigatorAxes,
279
+ DataNavigatorIndicatorOptions,
280
+ DataNavigatorInteractionOptions,
281
+ DataNavigatorOptions,
282
+ } from "./navigator.ts";
283
+
284
+ // ---------------------------------------------------------------------------
285
+ // Axis-range presets
286
+ // ---------------------------------------------------------------------------
287
+
288
+ export { createRangePresets, linearPreset, logPreset, timePreset } from "./range-presets.ts";
289
+ export type {
290
+ RangePreset,
291
+ RangePresetAxis,
292
+ RangePresetContext,
293
+ RangePresetDataDomain,
294
+ RangePresetDomain,
295
+ RangePresetsController,
296
+ RangePresetsOptions,
297
+ RangePresetsSubscriber,
298
+ TimePresetKey,
299
+ } from "./range-presets.ts";
@@ -0,0 +1,54 @@
1
+ /**
2
+ * Estimated glyph-advance as a fraction of font size, used when a real
3
+ * `GlyphAtlas.measureText` isn't available yet (first frame before font
4
+ * load). Sized for proportional sans fonts at typical UI sizes — over-
5
+ * shoots narrow glyphs and undershoots wide ones, but close enough for
6
+ * tooltip/menu/annotation box layout fallbacks.
7
+ */
8
+ export declare const TEXT_WIDTH_FALLBACK_RATIO = 0.55;
9
+ export interface SiNumberOptions {
10
+ /** Significant fraction digits after auto-scaling. Default `1`. */
11
+ precision?: number;
12
+ /** Trim trailing zeros (e.g. `1.0k` → `1k`). Default `true`. */
13
+ trim?: boolean;
14
+ /** Optional unit appended after the suffix (`siNumber(1500, { unit: "B" })` → `1.5kB`). */
15
+ unit?: string;
16
+ }
17
+ /**
18
+ * Format a number with SI suffix (`k`, `M`, `B`, `T`, `m`, `µ`, `n`).
19
+ * Negatives keep their sign. NaN → `"NaN"`. ±Infinity → `"∞"` / `"-∞"`.
20
+ */
21
+ export declare function siNumber(value: number, options?: SiNumberOptions): string;
22
+ export interface CurrencyOptions {
23
+ /** Currency symbol. Default `"$"`. */
24
+ symbol?: string;
25
+ /** Where the symbol goes. Default `"prefix"`. */
26
+ position?: "prefix" | "suffix";
27
+ /** Significant fraction digits. Default `1`. */
28
+ precision?: number;
29
+ /** Trim trailing zeros. Default `true`. */
30
+ trim?: boolean;
31
+ }
32
+ /**
33
+ * Currency-flavoured `siNumber` — `$1.2B`, `$420M`, `$50k`. The symbol can
34
+ * also go on the right (`1.2B €`) by setting `position: "suffix"`.
35
+ */
36
+ export declare function currency(value: number, options?: CurrencyOptions): string;
37
+ export interface PercentOptions {
38
+ /** Fraction digits. Default `0`. */
39
+ precision?: number;
40
+ /**
41
+ * If `true`, the input is a fraction (`0.42` → `"42%"`). If `false`, the
42
+ * input is already in percent units (`42` → `"42%"`). Default `false`.
43
+ */
44
+ fraction?: boolean;
45
+ }
46
+ /** Format `42` (or `0.42` with `fraction: true`) as `"42%"`. */
47
+ export declare function percent(value: number, options?: PercentOptions): string;
48
+ export interface FixedNumberOptions {
49
+ precision?: number;
50
+ /** Optional unit suffix (e.g. `" ms"`). */
51
+ unit?: string;
52
+ }
53
+ /** Plain `value.toFixed(precision)` plus optional unit. Useful for axes. */
54
+ export declare function fixed(value: number, options?: FixedNumberOptions): string;
package/src/format.ts ADDED
@@ -0,0 +1,138 @@
1
+ // ---------------------------------------------------------------------------
2
+ // Number / currency / percent formatters
3
+ //
4
+ // Useful as `format` arg to `bottomAxis` / `leftAxis`, and as `text`
5
+ // formatters inside `valueLabelMark`. All return `string`.
6
+ // ---------------------------------------------------------------------------
7
+
8
+ /**
9
+ * Estimated glyph-advance as a fraction of font size, used when a real
10
+ * `GlyphAtlas.measureText` isn't available yet (first frame before font
11
+ * load). Sized for proportional sans fonts at typical UI sizes — over-
12
+ * shoots narrow glyphs and undershoots wide ones, but close enough for
13
+ * tooltip/menu/annotation box layout fallbacks.
14
+ */
15
+ export const TEXT_WIDTH_FALLBACK_RATIO = 0.55;
16
+
17
+ export interface SiNumberOptions {
18
+ /** Significant fraction digits after auto-scaling. Default `1`. */
19
+ precision?: number;
20
+ /** Trim trailing zeros (e.g. `1.0k` → `1k`). Default `true`. */
21
+ trim?: boolean;
22
+ /** Optional unit appended after the suffix (`siNumber(1500, { unit: "B" })` → `1.5kB`). */
23
+ unit?: string;
24
+ }
25
+
26
+ const SI_THRESHOLDS: readonly { v: number; s: string }[] = [
27
+ { v: 1e12, s: "T" },
28
+ { v: 1e9, s: "B" },
29
+ { v: 1e6, s: "M" },
30
+ { v: 1e3, s: "k" },
31
+ ];
32
+
33
+ const SI_SMALL: readonly { v: number; s: string }[] = [
34
+ { v: 1e-3, s: "m" },
35
+ { v: 1e-6, s: "µ" },
36
+ { v: 1e-9, s: "n" },
37
+ ];
38
+
39
+ function trimTrailing(s: string): string {
40
+ if (!s.includes(".")) return s;
41
+ return s.replace(/\.?0+$/u, "");
42
+ }
43
+
44
+ /**
45
+ * Format a number with SI suffix (`k`, `M`, `B`, `T`, `m`, `µ`, `n`).
46
+ * Negatives keep their sign. NaN → `"NaN"`. ±Infinity → `"∞"` / `"-∞"`.
47
+ */
48
+ export function siNumber(value: number, options: SiNumberOptions = {}): string {
49
+ const precision = options.precision ?? 1;
50
+ const trim = options.trim ?? true;
51
+ const unitSuffix = options.unit ?? "";
52
+
53
+ if (Number.isNaN(value)) return "NaN";
54
+ if (!Number.isFinite(value)) return value > 0 ? "∞" : "-∞";
55
+ if (value === 0) return `0${unitSuffix}`;
56
+
57
+ const sign = value < 0 ? "-" : "";
58
+ const abs = Math.abs(value);
59
+
60
+ for (const { v, s } of SI_THRESHOLDS) {
61
+ if (abs >= v) {
62
+ const scaled = abs / v;
63
+ const text = scaled.toFixed(precision);
64
+ return `${sign}${trim ? trimTrailing(text) : text}${s}${unitSuffix}`;
65
+ }
66
+ }
67
+ if (abs >= 1) {
68
+ const text = abs.toFixed(precision);
69
+ return `${sign}${trim ? trimTrailing(text) : text}${unitSuffix}`;
70
+ }
71
+ for (const { v, s } of SI_SMALL) {
72
+ if (abs >= v) {
73
+ const scaled = abs / v;
74
+ const text = scaled.toFixed(precision);
75
+ return `${sign}${trim ? trimTrailing(text) : text}${s}${unitSuffix}`;
76
+ }
77
+ }
78
+ // Fallback for very small numbers — exponential.
79
+ return `${sign}${abs.toExponential(precision)}${unitSuffix}`;
80
+ }
81
+
82
+ export interface CurrencyOptions {
83
+ /** Currency symbol. Default `"$"`. */
84
+ symbol?: string;
85
+ /** Where the symbol goes. Default `"prefix"`. */
86
+ position?: "prefix" | "suffix";
87
+ /** Significant fraction digits. Default `1`. */
88
+ precision?: number;
89
+ /** Trim trailing zeros. Default `true`. */
90
+ trim?: boolean;
91
+ }
92
+
93
+ /**
94
+ * Currency-flavoured `siNumber` — `$1.2B`, `$420M`, `$50k`. The symbol can
95
+ * also go on the right (`1.2B €`) by setting `position: "suffix"`.
96
+ */
97
+ export function currency(value: number, options: CurrencyOptions = {}): string {
98
+ const symbol = options.symbol ?? "$";
99
+ const position = options.position ?? "prefix";
100
+ const formatted = siNumber(value, { precision: options.precision, trim: options.trim });
101
+
102
+ if (formatted.startsWith("-")) {
103
+ const body = formatted.slice(1);
104
+ return position === "prefix" ? `-${symbol}${body}` : `-${body}${symbol}`;
105
+ }
106
+ return position === "prefix" ? `${symbol}${formatted}` : `${formatted}${symbol}`;
107
+ }
108
+
109
+ export interface PercentOptions {
110
+ /** Fraction digits. Default `0`. */
111
+ precision?: number;
112
+ /**
113
+ * If `true`, the input is a fraction (`0.42` → `"42%"`). If `false`, the
114
+ * input is already in percent units (`42` → `"42%"`). Default `false`.
115
+ */
116
+ fraction?: boolean;
117
+ }
118
+
119
+ /** Format `42` (or `0.42` with `fraction: true`) as `"42%"`. */
120
+ export function percent(value: number, options: PercentOptions = {}): string {
121
+ const precision = options.precision ?? 0;
122
+ const v = options.fraction ? value * 100 : value;
123
+ if (!Number.isFinite(v)) return Number.isNaN(v) ? "NaN%" : v > 0 ? "∞%" : "-∞%";
124
+ return `${v.toFixed(precision)}%`;
125
+ }
126
+
127
+ export interface FixedNumberOptions {
128
+ precision?: number;
129
+ /** Optional unit suffix (e.g. `" ms"`). */
130
+ unit?: string;
131
+ }
132
+
133
+ /** Plain `value.toFixed(precision)` plus optional unit. Useful for axes. */
134
+ export function fixed(value: number, options: FixedNumberOptions = {}): string {
135
+ const precision = options.precision ?? 0;
136
+ if (!Number.isFinite(value)) return Number.isNaN(value) ? "NaN" : value > 0 ? "∞" : "-∞";
137
+ return `${value.toFixed(precision)}${options.unit ?? ""}`;
138
+ }
@@ -0,0 +1,147 @@
1
+ import { type BlendSpace, type Color } from "insomni";
2
+ import type { Theme } from "./theme.ts";
3
+ export type AccessibilityMode = "auto-color" | "outline" | "shadow" | "none";
4
+ export type ContrastMetric = "wcag" | "apca";
5
+ export interface Accessibility {
6
+ /**
7
+ * Master switch. When `false`, `resolveTextColor` never alters colors —
8
+ * but if `warn` is also true it logs the failing site once per session so
9
+ * authors can see what would have been fixed.
10
+ */
11
+ enabled: boolean;
12
+ /**
13
+ * Which contrast metric to enforce.
14
+ *
15
+ * `"apca"` (default) uses APCA Lc — perceptually uniform and
16
+ * polarity-aware, so equalizing produces labels that read with the same
17
+ * weight whether they sit on a dark or a light cell.
18
+ *
19
+ * `"wcag"` uses the WCAG 2.1 ratio formula. Kept for backwards
20
+ * compatibility; equalizing on WCAG ratio looks visually unbalanced
21
+ * across polarities.
22
+ */
23
+ metric: ContrastMetric;
24
+ /**
25
+ * WCAG-mode target. `"AA"` = 4.5:1 normal / 3:1 large; `"AAA"` = 7:1 / 4.5:1.
26
+ * A raw number sets an absolute minimum ratio (1–21) applied to all text
27
+ * regardless of size. Ignored when `metric === "apca"`.
28
+ */
29
+ wcagLevel: "AA" | "AAA" | number;
30
+ /**
31
+ * APCA-mode target |Lc|. `"auto"` (default) looks up the recommended
32
+ * minimum from APCA's font/weight table for each site (typical body text
33
+ * lands around Lc 75–90). A raw number applies a single |Lc| floor to
34
+ * every site. Ignored when `metric === "wcag"`.
35
+ */
36
+ apcaTarget: number | "auto";
37
+ /**
38
+ * How to fix low-contrast text. `auto-color` nudges the color toward an
39
+ * accessible shade preserving hue/saturation. `outline` / `shadow` are
40
+ * reserved API hooks — both currently degrade to `auto-color` since the
41
+ * SDF text pipeline doesn't render text effects yet. `none` leaves text
42
+ * untouched (and warns when `warn` is on).
43
+ */
44
+ mode: AccessibilityMode;
45
+ /** Whether to console.warn on contrast failures the system isn't fixing. */
46
+ warn: boolean;
47
+ /**
48
+ * When true, every *mark* label (geom-rendered, sitting on a data-driven
49
+ * fill) is normalized to *exactly* the target contrast — not just `>=`.
50
+ * Equalizing prevents cells with high contrast from visually outweighing
51
+ * neighbors. Hue and saturation are preserved; only lightness shifts.
52
+ *
53
+ * Chrome text (titles, axis, legend) skips this — those sit on the
54
+ * panel background and equalizing them just dims legible chrome.
55
+ */
56
+ equalize: boolean;
57
+ /**
58
+ * How strongly the auto-fixer pulls toward colors already in the theme.
59
+ * `0` keeps the original hue/sat untouched. `1` snaps to the nearest
60
+ * passing theme accent. Intermediate values blend in `blendSpace`,
61
+ * keeping the label feeling "of the same family" as the chart's palette.
62
+ *
63
+ * The pull is only applied when at least one accent independently meets
64
+ * the contrast target — biasing toward an unreadable accent would defeat
65
+ * the fix. When `equalize` is on, the L-channel is re-fit after the blend
66
+ * so the final contrast still lands at the target.
67
+ */
68
+ themeBias: number;
69
+ /**
70
+ * Optional explicit accent palette for the bias. When unset, the
71
+ * resolver derives accents from the active theme (text/title/legend
72
+ * colors plus a sample of the categorical palette).
73
+ */
74
+ accents?: readonly Color[];
75
+ /**
76
+ * Color space used for the theme-bias blend. Defaults to `"oklch"` —
77
+ * perceptually uniform with hue preserved along the blend.
78
+ */
79
+ blendSpace: BlendSpace;
80
+ }
81
+ export declare const DEFAULT_ACCESSIBILITY: Accessibility;
82
+ /**
83
+ * Stub for SDF text effects. Setting these on the theme today has no visual
84
+ * effect — the renderer will pick them up once outline/shadow are wired into
85
+ * the text pipeline. Kept on the public API so call sites and themes can
86
+ * declare intent now without a follow-up breaking change.
87
+ */
88
+ export interface TextEffects {
89
+ outline?: {
90
+ color: Color;
91
+ width: number;
92
+ };
93
+ shadow?: {
94
+ color: Color;
95
+ blur?: number;
96
+ dx?: number;
97
+ dy?: number;
98
+ };
99
+ }
100
+ /** Test helper — clears the dedupe cache so repeat warnings fire again. */
101
+ export declare function _resetAccessibilityWarnings(): void;
102
+ /**
103
+ * Compute a layer-wide equalize target — the largest |contrast| the worst
104
+ * cell in `backgrounds` can achieve from a black or white label. Used by
105
+ * geoms that want every label normalized to the same readable level even
106
+ * if that means muting high-contrast cells.
107
+ *
108
+ * Returns `null` when the metric/policy doesn't equalize (so callers can
109
+ * skip the pre-pass cheaply).
110
+ */
111
+ export declare function layerEqualizeTarget(theme: Theme, backgrounds: readonly Color[]): number | null;
112
+ export interface ResolveTextColorOptions {
113
+ /** Font size in CSS pixels. */
114
+ fontSizePx: number;
115
+ /** Treat the text as bold (affects WCAG large-text and APCA weight lookup). */
116
+ bold?: boolean;
117
+ /**
118
+ * Short label identifying the draw site (e.g. `"axis-label"`,
119
+ * `"tile-label"`). Used to namespace dedupe keys for warnings.
120
+ */
121
+ site: string;
122
+ /**
123
+ * Whether this site sits on a *data-driven* background (mark fills,
124
+ * heatmap cells) versus chrome on the panel background. `equalize`
125
+ * normalization applies only to mark sites — chrome text always sits on
126
+ * the same panel background, so equalizing it would just lower legible
127
+ * titles/axis/legend text down toward the contrast floor for no gain.
128
+ * Default `false`.
129
+ */
130
+ markLabel?: boolean;
131
+ /**
132
+ * Override the engine-computed target. When set, the resolver uses this
133
+ * value instead of the font/level lookup. Used by geoms that need to
134
+ * coordinate a layer-wide equalize floor (e.g. tile pulls every label
135
+ * down to the worst cell's max-achievable contrast so the layer reads
136
+ * uniformly, instead of saturating each label at its own per-cell max).
137
+ */
138
+ targetOverride?: number;
139
+ /** @internal — APCA polarity, computed inside the resolver. */
140
+ _apcaReverse?: boolean;
141
+ }
142
+ /**
143
+ * Resolve the actual color that should be drawn for a piece of text given
144
+ * the requested foreground, the known background, and the chart's
145
+ * accessibility policy. Pure — does not draw anything.
146
+ */
147
+ export declare function resolveTextColor(fg: Color, bg: Color, theme: Theme, opts: ResolveTextColorOptions): Color;