wickchart 1.6.0 → 2.0.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.
package/types/core.d.ts CHANGED
@@ -190,6 +190,30 @@ export declare const SEC = 1000;
190
190
  export declare const MIN: number;
191
191
  export declare const HOUR: number;
192
192
  export declare const DAY: number;
193
+ /**
194
+ * Interpret a timestamp as milliseconds. Numbers may be seconds or ms, so
195
+ * some threshold is unavoidable; pass a `Date` for anything before 1973,
196
+ * which is unambiguous. Single source of truth — everything that reads a
197
+ * caller-supplied time goes through here.
198
+ * @param {number|Date} t
199
+ * @returns {number} milliseconds
200
+ */
201
+ export declare const toMs: (t: number | Date) => number;
202
+ /** Warn once per distinct message (used by the 2.0 moved-method stubs in
203
+ * wick-chart.js — deleted with them in 3.0). */
204
+ export declare function warnDeprecatedAlias(message: any): void;
205
+ /**
206
+ * Milliseconds east of UTC in `zone` at the instant `at`.
207
+ * 'utc' → 0
208
+ * 'local' / null → the browser's zone (DST-correct via Date)
209
+ * number → a fixed offset in ms (exchange sessions)
210
+ * IANA name → DST-correct via Intl
211
+ * Never throws: an unusable zone reads as UTC.
212
+ * @param {number} at epoch ms
213
+ * @param {string|number|null} [zone]
214
+ * @returns {number} offset in ms
215
+ */
216
+ export declare function zoneOffset(at: number, zone?: string | number | null): number;
193
217
  export declare const TIME_STEPS: {
194
218
  ms: number;
195
219
  label: string;
@@ -308,12 +332,22 @@ export declare function calcTrueRange(bars: Bar[]): Array<number | null>;
308
332
  */
309
333
  export declare function calcATR(bars: Bar[], period?: number): Array<number | null>;
310
334
  /**
311
- * Volume-weighted average price over the hlc3 typical price, anchored to
312
- * each UTC day (resets at the session boundary).
335
+ * Volume-weighted average price over the hlc3 typical price, resetting at
336
+ * each session boundary.
337
+ *
338
+ * The anchor defaults to the UTC day — the crypto convention, and what this
339
+ * has always done. Equities, futures and FX rarely open at UTC midnight, so
340
+ * pass the session's zone (or a fixed offset) to move the reset. Note this is
341
+ * deliberately independent of the chart's `timezone`, which only governs how
342
+ * times are displayed: changing the axis to Stockholm should not silently
343
+ * re-anchor a BTC chart's VWAP.
344
+ *
313
345
  * @param {Bar[]} bars
346
+ * @param {string|number} [anchor='utc'] 'utc' | 'local' | IANA zone | fixed
347
+ * offset in ms — see zoneOffset()
314
348
  * @returns {Array<number|null>}
315
349
  */
316
- export declare function calcVWAP(bars: Bar[]): Array<number | null>;
350
+ export declare function calcVWAP(bars: Bar[], anchor?: string | number): Array<number | null>;
317
351
  /**
318
352
  * On-balance volume: cumulative volume signed by close-to-close direction.
319
353
  * @param {Bar[]} bars
@@ -446,20 +480,6 @@ export declare function detectAnnotations(bars: Bar[], i0: number, i1: number, r
446
480
  i: number;
447
481
  note: string;
448
482
  }>;
449
- /**
450
- * Map a price to a sonification frequency over the visible scale.
451
- * Logarithmic scales map through log-space; result clamped to [lo, hi] Hz.
452
- * @param {number} price
453
- * @param {{min: number, max: number, useLog?: boolean}} scale
454
- * @param {number} [freqLo=180]
455
- * @param {number} [freqHi=880]
456
- * @returns {number} frequency in Hz
457
- */
458
- export declare function priceToFreq(price: number, scale: {
459
- min: number;
460
- max: number;
461
- useLog?: boolean;
462
- }, freqLo?: number, freqHi?: number): number;
463
483
  /**
464
484
  * Volume profile over a visible bar range: volume distributed into price
465
485
  * rows, with POC and the value area (greedy expansion around the POC).
@@ -523,10 +543,10 @@ export declare const BUILTIN_INDICATORS: Map<string, {
523
543
  smooth?: undefined;
524
544
  };
525
545
  compute: (bars: any, p: any) => number[];
526
- color?: undefined;
527
546
  guides?: undefined;
528
547
  range?: undefined;
529
548
  fmt?: undefined;
549
+ color?: undefined;
530
550
  } | {
531
551
  kind: string;
532
552
  params: {
@@ -538,10 +558,10 @@ export declare const BUILTIN_INDICATORS: Map<string, {
538
558
  smooth?: undefined;
539
559
  };
540
560
  compute: (bars: any, p: any) => number[];
541
- color?: undefined;
542
561
  guides?: undefined;
543
562
  range?: undefined;
544
563
  fmt?: undefined;
564
+ color?: undefined;
545
565
  } | {
546
566
  kind: string;
547
567
  params: {
@@ -552,11 +572,11 @@ export declare const BUILTIN_INDICATORS: Map<string, {
552
572
  smooth?: undefined;
553
573
  period?: undefined;
554
574
  };
555
- compute: (bars: any) => number[];
556
- color?: undefined;
575
+ compute: (bars: any, p: any) => number[];
557
576
  guides?: undefined;
558
577
  range?: undefined;
559
578
  fmt?: undefined;
579
+ color?: undefined;
560
580
  } | {
561
581
  kind: string;
562
582
  params: {
@@ -568,10 +588,10 @@ export declare const BUILTIN_INDICATORS: Map<string, {
568
588
  smooth?: undefined;
569
589
  };
570
590
  compute: (bars: any, p: any) => number[];
571
- color?: undefined;
572
591
  guides?: undefined;
573
592
  range?: undefined;
574
593
  fmt?: undefined;
594
+ color?: undefined;
575
595
  } | {
576
596
  kind: string;
577
597
  params: {
@@ -588,10 +608,10 @@ export declare const BUILTIN_INDICATORS: Map<string, {
588
608
  values: number[];
589
609
  }[];
590
610
  };
591
- color?: undefined;
592
611
  guides?: undefined;
593
612
  range?: undefined;
594
613
  fmt?: undefined;
614
+ color?: undefined;
595
615
  } | {
596
616
  kind: string;
597
617
  params: {
@@ -608,10 +628,10 @@ export declare const BUILTIN_INDICATORS: Map<string, {
608
628
  values: number[];
609
629
  }[];
610
630
  };
611
- color?: undefined;
612
631
  guides?: undefined;
613
632
  range?: undefined;
614
633
  fmt?: undefined;
634
+ color?: undefined;
615
635
  } | {
616
636
  kind: string;
617
637
  params: {
@@ -628,10 +648,10 @@ export declare const BUILTIN_INDICATORS: Map<string, {
628
648
  values: number[];
629
649
  }[];
630
650
  };
631
- color?: undefined;
632
651
  guides?: undefined;
633
652
  range?: undefined;
634
653
  fmt?: undefined;
654
+ color?: undefined;
635
655
  } | {
636
656
  kind: string;
637
657
  params: {
@@ -648,7 +668,6 @@ export declare const BUILTIN_INDICATORS: Map<string, {
648
668
  color: string;
649
669
  compute: (bars: any, p: any) => number[];
650
670
  } | {
651
- color?: undefined;
652
671
  kind: string;
653
672
  params: {
654
673
  mult?: undefined;
@@ -668,8 +687,8 @@ export declare const BUILTIN_INDICATORS: Map<string, {
668
687
  histogram: number[];
669
688
  };
670
689
  range?: undefined;
671
- } | {
672
690
  color?: undefined;
691
+ } | {
673
692
  kind: string;
674
693
  params: {
675
694
  mult?: undefined;
@@ -683,8 +702,8 @@ export declare const BUILTIN_INDICATORS: Map<string, {
683
702
  compute: (bars: any, p: any) => number[];
684
703
  guides?: undefined;
685
704
  range?: undefined;
686
- } | {
687
705
  color?: undefined;
706
+ } | {
688
707
  kind: string;
689
708
  params: {
690
709
  mult?: undefined;
@@ -703,8 +722,8 @@ export declare const BUILTIN_INDICATORS: Map<string, {
703
722
  values: number[];
704
723
  }[];
705
724
  };
706
- } | {
707
725
  color?: undefined;
726
+ } | {
708
727
  kind: string;
709
728
  params: {
710
729
  mult?: undefined;
@@ -718,8 +737,8 @@ export declare const BUILTIN_INDICATORS: Map<string, {
718
737
  compute: (bars: any) => number[];
719
738
  guides?: undefined;
720
739
  range?: undefined;
721
- } | {
722
740
  color?: undefined;
741
+ } | {
723
742
  kind: string;
724
743
  params: {
725
744
  mult?: undefined;
@@ -733,8 +752,8 @@ export declare const BUILTIN_INDICATORS: Map<string, {
733
752
  fmt: string;
734
753
  compute: (bars: any, p: any) => number[];
735
754
  range?: undefined;
736
- } | {
737
755
  color?: undefined;
756
+ } | {
738
757
  kind: string;
739
758
  params: {
740
759
  mult?: undefined;
@@ -748,6 +767,7 @@ export declare const BUILTIN_INDICATORS: Map<string, {
748
767
  range: number[];
749
768
  fmt: string;
750
769
  compute: (bars: any, p: any) => number[];
770
+ color?: undefined;
751
771
  }>;
752
772
  /**
753
773
  * Parse an `indicators` attribute string against a registry.
@@ -795,7 +815,7 @@ export declare function evalScript(compiled: {
795
815
  /**
796
816
  * Build an indicator definition from a WickScript expression — used inline by
797
817
  * `indicators="expr:{…}"` / `pexpr:{…}"`, or register it under a name:
798
- * `HabChart.registerIndicator('myspread', scriptIndicator('close - ema(close,21)'))`.
818
+ * `WickChart.registerIndicator('myspread', scriptIndicator('close - ema(close,21)'))`.
799
819
  * @param {string} src
800
820
  * @param {{pane?: boolean}} [opts]
801
821
  * @returns {IndicatorDef}
@@ -814,6 +834,18 @@ export declare function positionPnl(pos: {
814
834
  entry: number;
815
835
  qty?: number;
816
836
  }, price: number): number;
837
+ /**
838
+ * Percent return of a position at `price` — the move per unit, so it does
839
+ * NOT scale with `qty` the way positionPnl() does. Deriving this by dividing
840
+ * positionPnl() by the entry price reports qty × the true return.
841
+ * @param {{side?: 'long'|'short', entry: number}} pos
842
+ * @param {number} price
843
+ * @returns {number} percent (10 means +10%)
844
+ */
845
+ export declare function positionPnlPct(pos: {
846
+ side?: 'long' | 'short';
847
+ entry: number;
848
+ }, price: number): number;
817
849
  /**
818
850
  * Edge-triggered alert crossing test between two consecutive prices.
819
851
  * @param {{price: number, direction?: 'above'|'below'|'cross'}} alert
@@ -944,24 +976,6 @@ export declare function normalizeOverlays(list: any): object[];
944
976
  * @returns {string} a concrete CSS color
945
977
  */
946
978
  export declare function resolveOverlayColor(raw: any, pal: object): string;
947
- /**
948
- * σ-cone projection from realized per-bar volatility: price bands widening
949
- * with √h (GBM-style, exp(±z·σ·√h)) over `horizon` future bars.
950
- * @param {number} lastClose anchor price (bar 0)
951
- * @param {number} volPerBar per-bar stddev of log returns (from calcRealizedVol)
952
- * @param {number} horizon future bars (clamped 1–500, default 48)
953
- * @param {number[]} [levels] σ multipliers, e.g. [1, 2] (each clamped to 0–5)
954
- * @returns {{horizon: number, levels: number[], bands: Record<string, {up: number[], down: number[]}>}}
955
- * bands[z].up/.down are arrays indexed by h = 0…horizon ([0] === lastClose)
956
- */
957
- export declare function calcVolCone(lastClose: number, volPerBar: number, horizon: number, levels?: number[]): {
958
- horizon: number;
959
- levels: number[];
960
- bands: Record<string, {
961
- up: number[];
962
- down: number[];
963
- }>;
964
- };
965
979
  /**
966
980
  * Validate a scenario spec: a ghost path of future prices (bars or API data)
967
981
  * plus optional cone settings. Invalid entries are dropped, never thrown.
@@ -1018,34 +1032,6 @@ export declare function normalizeRiskPlan(spec: any): null | {
1018
1032
  maxK: number;
1019
1033
  label: string;
1020
1034
  };
1021
- /**
1022
- * Turn a bar window into an ordered story: the annotation events (pivot
1023
- * highs/lows, volume spikes, gaps, RSI divergences) plus derived **legs** —
1024
- * the move between consecutive opposite pivots ("+12.4% over 38 bars").
1025
- * The timeline drives the bar-walk player and any caption UI.
1026
- *
1027
- * @param {Bar[]} bars full dataset
1028
- * @param {number} i0 first index of the window
1029
- * @param {number} i1 last index of the window
1030
- * @param {{pivot?: number, volMult?: number, gapMult?: number, rsiPeriod?: number}} [opts]
1031
- * pivot window defaults to 8 (denser than the annotations overlay's 20)
1032
- * @returns {{i: number, time: number, type: string, side: string, note: string,
1033
- * legPct?: number, legBars?: number}[]} sorted by index, capped at 60
1034
- */
1035
- export declare function narrateWindow(bars: Bar[], i0: number, i1: number, opts?: {
1036
- pivot?: number;
1037
- volMult?: number;
1038
- gapMult?: number;
1039
- rsiPeriod?: number;
1040
- }): {
1041
- i: number;
1042
- time: number;
1043
- type: string;
1044
- side: string;
1045
- note: string;
1046
- legPct?: number;
1047
- legBars?: number;
1048
- }[];
1049
1035
  /**
1050
1036
  * Stats for a brushed bar range: net move (open of the first bar → close
1051
1037
  * of the last), extremes, and summed volume. Powers the brush-selection
@@ -1077,72 +1063,6 @@ export declare function brushStats(bars: Bar[], i0: number, i1: number): null |
1077
1063
  low: number;
1078
1064
  volume: number;
1079
1065
  };
1080
- /** Smoothest cheap easing for viewport pans: slow in, slow out. */
1081
- export declare function easeInOutCubic(t: any): number;
1082
- /**
1083
- * Validate one story scene. Every field is optional except that a scene
1084
- * must be an object; omitted fields simply don't change that aspect of
1085
- * the chart when played. `scenario`/`riskPlan` use a 'clear' sentinel for
1086
- * explicit "remove it" (null input means clear too when the KEY is present).
1087
- *
1088
- * { title: 'The breakout', note: 'What happened…',
1089
- * range: { from, to }, // times (s or ms) — the camera pans there
1090
- * indicators: 'sma:20 rsi:14', // optional indicator string
1091
- * type: 'candles', // optional series type
1092
- * overlays: [...], // optional zones/levels (normalizeOverlays)
1093
- * scenario: {...} | null, // set / clear a scenario
1094
- * riskPlan: {...} | null, // set / clear a risk plan
1095
- * dwell: 2200 } // ms to hold after the pan (500–30000)
1096
- *
1097
- * @returns {object|null} normalized scene, or null for non-objects
1098
- */
1099
- export declare function normalizeScene(scene: any): object | null;
1100
- /**
1101
- * Validate a whole story: normalize each scene, drop junk, cap at 20.
1102
- * @returns {object[]} possibly empty
1103
- */
1104
- export declare function sceneList(story: any): object[];
1105
- /**
1106
- * Tracks other charts viewing the same room: last-sighting timestamps per
1107
- * peer plus the viewport each one is looking at. Pure bookkeeping — the
1108
- * transport (BroadcastChannel, WebSocket, …) lives in the component/app.
1109
- *
1110
- * Peers expire `ttl` ms after their last sighting, so a closed tab fades
1111
- * out of the room without an explicit goodbye.
1112
- */
1113
- export declare class PresenceTracker {
1114
- ttl: number;
1115
- /** @type {Map<string, {id: string, name: string|null, range: {from:number,to:number}|null, at: number}>} */
1116
- peers: Map<string, {
1117
- id: string;
1118
- name: string | null;
1119
- range: {
1120
- from: number;
1121
- to: number;
1122
- } | null;
1123
- at: number;
1124
- }>;
1125
- /** @param {number} [ttl=12000] ms a peer survives without a sighting */
1126
- constructor(ttl?: number);
1127
- /**
1128
- * Record a sighting. `patch.range` ({from,to} times) is validated and
1129
- * normalized; a sighting without a range keeps the previous one.
1130
- * @returns {boolean} true when this sighting is a join (new peer)
1131
- */
1132
- track(id: any, patch?: {}, now?: number): boolean;
1133
- /** @returns {object|null} the removed peer entry, or null when unknown */
1134
- drop(id: any): object | null;
1135
- /** Expire peers not seen within the ttl.
1136
- * @returns {object[]} the peer entries that left */
1137
- sweep(now?: number): object[];
1138
- /** @returns {{id: string, name: string|null, range: object|null, at: number}[]} copies, oldest sighting first */
1139
- list(): {
1140
- id: string;
1141
- name: string | null;
1142
- range: object | null;
1143
- at: number;
1144
- }[];
1145
- }
1146
1066
  export declare const tfLabelOf: (dtMs: any) => string;
1147
1067
  /**
1148
1068
  * Compact, LLM-friendly summary of a bar window: structured fields plus a
@@ -1172,110 +1092,3 @@ export declare function encodeStateQuery(state: ChartState | null): string;
1172
1092
  * @returns {ChartState}
1173
1093
  */
1174
1094
  export declare function decodeStateQuery(str: string): ChartState;
1175
- /**
1176
- * Tool manifest for LLM/agent control of a chart. Tools map 1:1 onto the
1177
- * public element API; every op through applyChartOps is validated before it
1178
- * touches the chart (LLM output is untrusted input).
1179
- */
1180
- export declare const AI_TOOLS: ({
1181
- tool: string;
1182
- description: string;
1183
- args: {
1184
- indicators?: undefined;
1185
- overlays?: undefined;
1186
- from?: undefined;
1187
- to?: undefined;
1188
- type?: undefined;
1189
- enabled?: undefined;
1190
- low?: undefined;
1191
- high?: undefined;
1192
- };
1193
- } | {
1194
- tool: string;
1195
- description: string;
1196
- args: {
1197
- indicators: string;
1198
- overlays?: undefined;
1199
- from?: undefined;
1200
- to?: undefined;
1201
- type?: undefined;
1202
- enabled?: undefined;
1203
- low?: undefined;
1204
- high?: undefined;
1205
- };
1206
- } | {
1207
- tool: string;
1208
- description: string;
1209
- args: {
1210
- indicators?: undefined;
1211
- overlays: string;
1212
- from?: undefined;
1213
- to?: undefined;
1214
- type?: undefined;
1215
- enabled?: undefined;
1216
- low?: undefined;
1217
- high?: undefined;
1218
- };
1219
- } | {
1220
- tool: string;
1221
- description: string;
1222
- args: {
1223
- indicators?: undefined;
1224
- overlays?: undefined;
1225
- from: string;
1226
- to: string;
1227
- type?: undefined;
1228
- enabled?: undefined;
1229
- low?: undefined;
1230
- high?: undefined;
1231
- };
1232
- } | {
1233
- tool: string;
1234
- description: string;
1235
- args: {
1236
- indicators?: undefined;
1237
- overlays?: undefined;
1238
- from?: undefined;
1239
- to?: undefined;
1240
- type: string;
1241
- enabled?: undefined;
1242
- low?: undefined;
1243
- high?: undefined;
1244
- };
1245
- } | {
1246
- tool: string;
1247
- description: string;
1248
- args: {
1249
- indicators?: undefined;
1250
- overlays?: undefined;
1251
- from?: undefined;
1252
- to?: undefined;
1253
- type?: undefined;
1254
- enabled: string;
1255
- low: string;
1256
- high: string;
1257
- };
1258
- })[];
1259
- /**
1260
- * Compact system prompt for agent control: paste into any LLM alongside the
1261
- * tool manifest. The model answers with a JSON array of {tool, args} ops.
1262
- * @returns {string}
1263
- */
1264
- export declare function aiPromptText(): string;
1265
- /**
1266
- * Validate + apply a list of {tool, args} ops (typically LLM output) to a
1267
- * chart-like target. Ops are whitelisted and their args validated — an op
1268
- * never throws; it returns {ok: false, error} instead so the agent can
1269
- * self-correct. Target contract: getDataWindow(), setAttribute(k, v),
1270
- * setOverlays(list), clearOverlays(), addAlert(a), setVisibleRange(r),
1271
- * fit(), and (static) _registry() for indicator name checks.
1272
- * @param {object} target chart element (or test double)
1273
- * @param {any} ops
1274
- * @returns {Array<{ok: boolean, tool?: string, result?: any, error?: string}>}
1275
- */
1276
- export declare function applyChartOps(target: object, ops: any): Array<{
1277
- ok: boolean;
1278
- tool?: string;
1279
- result?: any;
1280
- error?: string;
1281
- }>;
package/types/feeds.d.ts CHANGED
@@ -40,6 +40,131 @@ export declare function genSynthetic(key: string, sec: number, n: number, base?:
40
40
  * @param {number} [startPrice] bridge continuity from the last known price
41
41
  */
42
42
  export declare function makeSynthStream(sec: number, startPrice?: number): () => any;
43
+ /** Default thresholds per kind. They are per-instrument — there is no
44
+ * universal "one bar" size, treat these as starting points to tune. */
45
+ export declare const AGG_DEFAULTS: {
46
+ tick: number;
47
+ volume: number;
48
+ dollar: number;
49
+ };
50
+ /**
51
+ * Parse an `aggregate` spec — `tick`, `volume:50`, `dollar:25000` (case and
52
+ * whitespace tolerant; the value is the bar size in trades / base units /
53
+ * quote units respectively).
54
+ * @param {string} spec attribute value
55
+ * @returns {{kind: 'tick'|'volume'|'dollar', threshold: number}|null} null when invalid
56
+ */
57
+ export declare function parseAggregate(spec: string): {
58
+ kind: 'tick' | 'volume' | 'dollar';
59
+ threshold: number;
60
+ } | null;
61
+ /**
62
+ * Streaming aggregator: feed it trades, get bars back. `add()` returns a
63
+ * bar the moment the threshold is crossed ({@link current} keeps exposing
64
+ * the forming bar meanwhile). The completing trade belongs entirely to the
65
+ * closing bar — a whale print is never split across two bars.
66
+ */
67
+ export declare class TickBarAggregator {
68
+ kind: string;
69
+ threshold: any;
70
+ _bar: {
71
+ time: number;
72
+ open: number;
73
+ high: number;
74
+ low: number;
75
+ close: number;
76
+ volume: number;
77
+ n: number;
78
+ notional: number;
79
+ };
80
+ /**
81
+ * @param {'tick'|'volume'|'dollar'} kind what the threshold counts
82
+ * @param {number} threshold bar size (trades / base units / quote units)
83
+ */
84
+ constructor(kind?: 'tick' | 'volume' | 'dollar', threshold?: number);
85
+ /**
86
+ * Feed one trade `{ time, price, size }` (seconds auto-upgraded to ms,
87
+ * same heuristic as the chart). Returns the completed bar —
88
+ * `{ time, open, high, low, close, volume, closed: true }` — when the
89
+ * threshold is reached, else null.
90
+ * @returns {object|null}
91
+ */
92
+ add(trade: any): object | null;
93
+ /** The forming bar as plain chart-bar fields (no internals), or null. */
94
+ current(): {
95
+ time: number;
96
+ open: number;
97
+ high: number;
98
+ low: number;
99
+ close: number;
100
+ volume: number;
101
+ };
102
+ /** Close the forming bar as-is (end of tape / teardown), or null. */
103
+ flush(): {
104
+ time: number;
105
+ open: number;
106
+ high: number;
107
+ low: number;
108
+ close: number;
109
+ volume: number;
110
+ closed: boolean;
111
+ };
112
+ }
113
+ /**
114
+ * One-pass batch aggregation of a trade history. Returns the closed bars,
115
+ * the still-forming remainder, and the live aggregator positioned at the end
116
+ * of the tape so streaming can continue without a seam.
117
+ * @param {Array<object>} trades `{ time, price, size }` prints
118
+ * @param {'tick'|'volume'|'dollar'} kind
119
+ * @param {number} threshold
120
+ */
121
+ export declare function aggregateTrades(trades: Array<object>, kind: 'tick' | 'volume' | 'dollar', threshold: number): {
122
+ bars: any[];
123
+ pending: {
124
+ time: number;
125
+ open: number;
126
+ high: number;
127
+ low: number;
128
+ close: number;
129
+ volume: number;
130
+ };
131
+ aggregator: TickBarAggregator;
132
+ };
133
+ /**
134
+ * Coerce a generic JSON trades array into plain `{ time, price, size }`
135
+ * (ms, seconds auto-upgraded; `size` also read from `qty`/`amount`).
136
+ * Invalid entries are dropped, never thrown — same contract as the chart's
137
+ * other normalizers. Output is sorted by time.
138
+ */
139
+ export declare function normalizeTrades(list: any): any[];
140
+ /**
141
+ * Deterministic synthetic trade prints (random-walk price with volatility
142
+ * regimes, heavy-tailed sizes). Same key → same tape.
143
+ * @param {string} key seed key
144
+ * @param {number} [n=24000] print count
145
+ * @param {number} [base=100] starting price
146
+ */
147
+ export declare function genSyntheticTrades(key: string, n?: number, base?: number): any[];
148
+ /**
149
+ * Stateful synthetic live tape: one print per call, bridging from
150
+ * `startPrice` (e.g. the last price of a seeded history).
151
+ * @param {number} [startPrice=100]
152
+ */
153
+ export declare function makeSynthTradeStream(startPrice?: number): () => {
154
+ time: number;
155
+ price: number;
156
+ size: number;
157
+ };
158
+ /**
159
+ * Expected synthetic prints per bar — used to size the offline seed so a
160
+ * demo chart starts with roughly the requested bar count.
161
+ * @param {{kind: string, threshold: number}} agg
162
+ * @param {number} [base=100]
163
+ */
164
+ export declare function synthTradesPerBar(agg: {
165
+ kind: string;
166
+ threshold: number;
167
+ }, base?: number): number;
43
168
  /**
44
169
  * Fetch klines from Binance's public REST API.
45
170
  * @param {string} symbol e.g. 'BTCUSDT'
@@ -56,3 +181,43 @@ export declare function fetchBinanceKlines(symbol: string, tfId: string, limit?:
56
181
  export declare function openBinanceSocket(symbol: any, tfId: any, onBar: any, onDown: any, timeoutMs?: number): {
57
182
  close(): void;
58
183
  };
184
+ /**
185
+ * Fetch Binance aggTrades, paging backwards from the newest prints (or from
186
+ * below `beforeId`) until `minTrades` prints / `maxPages` requests / the
187
+ * start of the symbol's history. Returns `{ trades, oldestId }` ascending by
188
+ * time; each print carries its Binance id so live streams can resume without
189
+ * overlaps.
190
+ * @param {string} symbol e.g. 'BTCUSDT'
191
+ * @param {number} [minTrades=1000] stop once at least this many prints are held
192
+ * @param {number} [maxPages=25] hard request cap (1000 prints per page)
193
+ * @param {number} [beforeId] only fetch prints with an id lower than this
194
+ */
195
+ export declare function fetchBinanceAggTrades(symbol: string, minTrades?: number, maxPages?: number, beforeId?: number): Promise<{
196
+ trades: any[];
197
+ oldestId: number;
198
+ }>;
199
+ /**
200
+ * One forward window of aggTrades starting at `fromId` — the catch-up call
201
+ * for REST polling after a trade socket drops. Returns `{ trades, latestId }`.
202
+ * @param {string} symbol
203
+ * @param {number} fromId first print id to fetch (use lastSeenId + 1)
204
+ */
205
+ export declare function fetchBinanceAggTradesSince(symbol: string, fromId: number): Promise<{
206
+ trades: {
207
+ id: any;
208
+ time: any;
209
+ price: number;
210
+ size: number;
211
+ }[];
212
+ latestId: any;
213
+ }>;
214
+ /**
215
+ * Open a Binance aggTrade WebSocket — raw prints for information-based bar
216
+ * aggregation. Same lifecycle contract as openBinanceSocket: `onDown(err)`
217
+ * fires on error/close/timeout, after which the socket is dead and the
218
+ * caller should fall back.
219
+ * @returns {{close(): void}}
220
+ */
221
+ export declare function openBinanceTradeSocket(symbol: any, onTrade: any, onDown: any, timeoutMs?: number): {
222
+ close(): void;
223
+ };