@luxalgo/vela 0.5.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/LICENSE +201 -0
- package/NOTICE +28 -0
- package/README.md +135 -0
- package/dist/DataProvider-DKNDHpNv.d.cts +134 -0
- package/dist/DataProvider-Dzd-Erlk.d.ts +134 -0
- package/dist/chunk-7UFX5ZIG.js +5976 -0
- package/dist/chunk-GYD2THPV.js +252 -0
- package/dist/chunk-KCCZNKH7.js +19137 -0
- package/dist/chunk-KM6LHB3Y.js +76 -0
- package/dist/chunk-OVQKKXLZ.js +3978 -0
- package/dist/chunk-Q3XQHLIH.js +7 -0
- package/dist/chunk-RHIDOUFL.js +698 -0
- package/dist/contributions-hX3EUyjG.d.ts +1528 -0
- package/dist/contributions-o1GRKPI_.d.cts +1528 -0
- package/dist/history-Dzxz-MQj.d.ts +298 -0
- package/dist/history-LJkz4-sS.d.cts +298 -0
- package/dist/icons-BZYbJXSV.d.cts +10 -0
- package/dist/icons-BZYbJXSV.d.ts +10 -0
- package/dist/index.cjs +25294 -0
- package/dist/index.d.cts +1189 -0
- package/dist/index.d.ts +1189 -0
- package/dist/index.js +5 -0
- package/dist/keymap-CGOz5F5f.d.cts +64 -0
- package/dist/keymap-CGOz5F5f.d.ts +64 -0
- package/dist/options-Q-576hIi.d.cts +1545 -0
- package/dist/options-Q-576hIi.d.ts +1545 -0
- package/dist/plugin-D94muTV-.d.cts +405 -0
- package/dist/plugin-aGUD1epn.d.ts +405 -0
- package/dist/plugin.cjs +5967 -0
- package/dist/plugin.d.cts +7 -0
- package/dist/plugin.d.ts +7 -0
- package/dist/plugin.js +3 -0
- package/dist/providers/binance.cjs +390 -0
- package/dist/providers/binance.d.cts +62 -0
- package/dist/providers/binance.d.ts +62 -0
- package/dist/providers/binance.js +388 -0
- package/dist/providers/coinbase.cjs +462 -0
- package/dist/providers/coinbase.d.cts +59 -0
- package/dist/providers/coinbase.d.ts +59 -0
- package/dist/providers/coinbase.js +460 -0
- package/dist/providers/hyperliquid.cjs +361 -0
- package/dist/providers/hyperliquid.d.cts +54 -0
- package/dist/providers/hyperliquid.d.ts +54 -0
- package/dist/providers/hyperliquid.js +359 -0
- package/dist/side-panel-CT9ZwIGz.d.cts +63 -0
- package/dist/side-panel-CT9ZwIGz.d.ts +63 -0
- package/dist/ui.cjs +1030 -0
- package/dist/ui.d.cts +188 -0
- package/dist/ui.d.ts +188 -0
- package/dist/ui.js +3 -0
- package/dist/vela.global.js +26509 -0
- package/dist/vela.global.min.js +230 -0
- package/dist/widget.cjs +31178 -0
- package/dist/widget.d.cts +799 -0
- package/dist/widget.d.ts +799 -0
- package/dist/widget.js +1060 -0
- package/dist/workspace.cjs +31692 -0
- package/dist/workspace.d.cts +579 -0
- package/dist/workspace.d.ts +579 -0
- package/dist/workspace.js +1694 -0
- package/package.json +95 -0
|
@@ -0,0 +1,579 @@
|
|
|
1
|
+
import { O as OHLCV, V as VisibleRangePreset, a as VisibleRange, b as VelaOptions, c as VelaTheme, N as NativeBackend } from './options-Q-576hIi.cjs';
|
|
2
|
+
import { S as SyncSetting, V as VelaStorage, C as CellState, W as WidgetHistory, R as ResolvedIndicator, a as RangePreset, T as TrackSizes, b as VelaShellOptions, c as SyncOptions, d as SyncKind, e as WorkspaceState } from './history-LJkz4-sS.cjs';
|
|
3
|
+
export { f as ChartState, P as PanelsState, g as decodeState, h as encodeState, s as sanitizeState } from './history-LJkz4-sS.cjs';
|
|
4
|
+
import { K as KeymapManager } from './keymap-CGOz5F5f.cjs';
|
|
5
|
+
import { I as IndicatorHandle, S as ScriptingEngine, W as WidgetContext, V as Vela, a as ScriptRun } from './contributions-o1GRKPI_.cjs';
|
|
6
|
+
import { M as MarketDataFeed } from './DataProvider-DKNDHpNv.cjs';
|
|
7
|
+
|
|
8
|
+
/** The cells that follow `originId` under `setting` — PURE (never includes the origin). */
|
|
9
|
+
declare function syncTargets(originId: string, setting: SyncSetting | undefined, cellIds: readonly string[]): string[];
|
|
10
|
+
/** Whether two visible ranges agree within `epsMs` on both edges — the short-circuit
|
|
11
|
+
* that stops viewport echo (a followers' re-emission never re-propagates). */
|
|
12
|
+
declare function rangesWithin(a: {
|
|
13
|
+
from: number;
|
|
14
|
+
to: number;
|
|
15
|
+
}, b: {
|
|
16
|
+
from: number;
|
|
17
|
+
to: number;
|
|
18
|
+
}, epsMs: number): boolean;
|
|
19
|
+
|
|
20
|
+
/** @deprecated Use {@link VelaStorage} — one storage contract for both shells
|
|
21
|
+
* (`get`/`set`, each synchronous OR promise-returning, so localStorage-like and
|
|
22
|
+
* REST/IndexedDB-like backends both fit). */
|
|
23
|
+
type WorkspaceStorage = VelaStorage;
|
|
24
|
+
/** An in-memory, session-lived {@link VelaStorage} — the OPT-IN alternative to the
|
|
25
|
+
* localStorage default when persisted state must not outlive the page session. */
|
|
26
|
+
declare function memoryStorageAdapter(): VelaStorage;
|
|
27
|
+
|
|
28
|
+
/** The seed/mutable market state of one cell (all optional — an empty cell parks).
|
|
29
|
+
* The SAME vocabulary as the widget's chart options: the workspace's top-level chart
|
|
30
|
+
* options provide every cell's default ({@link seedDefaults}), `cells` overrides per
|
|
31
|
+
* cell. `data`/`visibleRange` are boot-only (they seed the first load, never persist). */
|
|
32
|
+
interface CellSeed {
|
|
33
|
+
/** Bare ticker (provider resolved by declaration order) or `EXCHANGE:`-prefixed. */
|
|
34
|
+
symbol?: string;
|
|
35
|
+
timeframe?: string;
|
|
36
|
+
priceStyle?: string;
|
|
37
|
+
bars?: number;
|
|
38
|
+
/** Offline bars for this cell — replaces the provider (boot-only). */
|
|
39
|
+
data?: OHLCV[];
|
|
40
|
+
/** Initial visible window (boot-only). */
|
|
41
|
+
visibleRange?: VisibleRangePreset | VisibleRange;
|
|
42
|
+
}
|
|
43
|
+
/** A destroyed cell's state, kept by the workspace pool so its slot restores later —
|
|
44
|
+
* the per-cell entry of the SHARED state document (`src/state/document.ts`). */
|
|
45
|
+
type PooledCellState = CellState;
|
|
46
|
+
/** What a cell BOOTS from: a pooled state (restored slot) or an options seed — plus
|
|
47
|
+
* the boot-only extras a pooled state never carries (offline bars, initial window). */
|
|
48
|
+
type CellBoot = PooledCellState & Pick<CellSeed, 'data' | 'visibleRange'>;
|
|
49
|
+
/** Chart options the workspace forwards VERBATIM to every cell's chart — the widget
|
|
50
|
+
* vocabulary minus what the grid manages itself: `height` (the grid sizes cells),
|
|
51
|
+
* `nativeBackend` (the WebGL budget policy, explicit value resolved upstream), the
|
|
52
|
+
* market/view seeds (those flow through {@link CellSeed}), and `drawings`' toolbar
|
|
53
|
+
* sub-key (see {@link cellDrawings}). */
|
|
54
|
+
type CellChartDefaults = Pick<VelaOptions, 'renderer' | 'defaultLanguage' | 'currentPriceLine' | 'logScale' | 'animations' | 'glow' | 'upColor' | 'downColor' | 'drawings'>;
|
|
55
|
+
/** One entry of the shared indicator picker's native catalog, per cell. */
|
|
56
|
+
interface CellNativeInfo {
|
|
57
|
+
type: string;
|
|
58
|
+
title: string;
|
|
59
|
+
supported: boolean;
|
|
60
|
+
present: boolean;
|
|
61
|
+
beta?: boolean;
|
|
62
|
+
}
|
|
63
|
+
/** What every cell shares from the workspace. */
|
|
64
|
+
interface CellDeps {
|
|
65
|
+
/** THE shared market-data feed (one registry, one cache, for every cell). */
|
|
66
|
+
feed: MarketDataFeed;
|
|
67
|
+
/** Scripting-engine factories — instantiated PER CELL (a worker engine per cell). */
|
|
68
|
+
engines: Record<string, () => ScriptingEngine>;
|
|
69
|
+
/** The workspace's top-level chart options every cell's chart starts from. */
|
|
70
|
+
chartDefaults: CellChartDefaults;
|
|
71
|
+
theme: VelaTheme;
|
|
72
|
+
live: boolean;
|
|
73
|
+
volume: boolean;
|
|
74
|
+
statusline: boolean;
|
|
75
|
+
watermark: boolean;
|
|
76
|
+
/** Geometry backend for cells under the current layout (the WebGL budget policy). */
|
|
77
|
+
nativeBackend: NativeBackend;
|
|
78
|
+
/** Where the renderer mounts its MODAL dialogs (chart/indicator settings) — the
|
|
79
|
+
* workspace root, so dialogs center over the whole grid instead of one cell. */
|
|
80
|
+
dialogHost: HTMLElement;
|
|
81
|
+
/** The workspace-global display timezone (applied to every cell's renderer). */
|
|
82
|
+
timezone(): string;
|
|
83
|
+
/** Switch the workspace-global display timezone (a cell's time-axis menu). */
|
|
84
|
+
setTimezone(zone: string): void;
|
|
85
|
+
/** The live widget-context builder (per-cell context menus project contributed actions). */
|
|
86
|
+
context(): WidgetContext;
|
|
87
|
+
/** The shared manifest can no longer change instance sets: it resolved, or the
|
|
88
|
+
* workspace has no `indicators` option so nothing will ever resolve. Gates the
|
|
89
|
+
* ledger's pending fallback in `dehydrate` — once settled, a live empty set means
|
|
90
|
+
* "the user removed everything" and persists so. */
|
|
91
|
+
manifestSettled(): boolean;
|
|
92
|
+
/** Report a pointer-down/focus in this cell (the workspace sets it active). */
|
|
93
|
+
activate(id: string): void;
|
|
94
|
+
/** The cell's market changed in place (chrome/retention refresh upstream). */
|
|
95
|
+
onMarketChanged(id: string): void;
|
|
96
|
+
/** The cell's indicator ledger changed (count/picker refresh upstream). */
|
|
97
|
+
onIndicatorsChanged(id: string): void;
|
|
98
|
+
/** Persistable per-cell state changed outside the market/indicator channels
|
|
99
|
+
* (bars budget, watermark/titles toggles) — the workspace debounces a save. */
|
|
100
|
+
onStateDirty(): void;
|
|
101
|
+
}
|
|
102
|
+
declare class ChartCell {
|
|
103
|
+
readonly id: string;
|
|
104
|
+
private readonly deps;
|
|
105
|
+
/** The grid item this cell renders into (owned; removed on destroy). */
|
|
106
|
+
readonly host: HTMLElement;
|
|
107
|
+
/** This cell's unified app+drawings undo timeline (the shared Ctrl+Z routes here). */
|
|
108
|
+
readonly history: WidgetHistory;
|
|
109
|
+
/** Live manifest-indicator instances on this cell (the SAME entry may repeat). */
|
|
110
|
+
readonly instances: Array<{
|
|
111
|
+
entry: ResolvedIndicator;
|
|
112
|
+
handle: IndicatorHandle | null;
|
|
113
|
+
}>;
|
|
114
|
+
/** The native-indicator catalog with this cell's live supported/present flags. */
|
|
115
|
+
nativeCatalog: CellNativeInfo[];
|
|
116
|
+
/** Last crosshair position in this cell (the alt+H/alt+V shortcuts anchor here). */
|
|
117
|
+
lastCrossTime: number | null;
|
|
118
|
+
lastCrossPrice: number | null;
|
|
119
|
+
/** The bottombar range chip this cell is framed on (null = none). */
|
|
120
|
+
activeRangeId: string | null;
|
|
121
|
+
private inner;
|
|
122
|
+
/** The live app theme — seeded from deps, updated on `theme:changed` (the base the
|
|
123
|
+
* plot-overlay tokens re-derive from). */
|
|
124
|
+
private appTheme;
|
|
125
|
+
private readonly statusline;
|
|
126
|
+
private readonly watermark;
|
|
127
|
+
private readonly contextMenu;
|
|
128
|
+
private readonly offMarket;
|
|
129
|
+
/** The cell's durable market state — the seed vocabulary plus the venue mirror the
|
|
130
|
+
* persisted document carries (`provider` = the symbol's parsed prefix). */
|
|
131
|
+
private state;
|
|
132
|
+
private manifest;
|
|
133
|
+
/** A restored ledger's manifest entry NAMES, waiting for the manifest to resolve
|
|
134
|
+
* (a pool/persisted cell can be built before the shared manifest has loaded). */
|
|
135
|
+
private pendingManifestNames;
|
|
136
|
+
/** The volume auto-add rides the cell's first candles (`load:end`); until then the
|
|
137
|
+
* registry can't show it and the dehydrated ledger reports the INTENT instead. */
|
|
138
|
+
private volumeMayBePending;
|
|
139
|
+
/** Volume intent: the seed's ledger, else the workspace `volume` option. */
|
|
140
|
+
private readonly volumeIntent;
|
|
141
|
+
/** Sync mirror of the chart's present native types — the removal handler diffs
|
|
142
|
+
* against it to identify (and record) whichever type was just removed. */
|
|
143
|
+
private presentNatives;
|
|
144
|
+
private rangeBars;
|
|
145
|
+
private pendingRange;
|
|
146
|
+
private watermarkOn;
|
|
147
|
+
/** Indicator titles (this cell's in-chart legend rows) shown. */
|
|
148
|
+
private indicatorTitlesOn;
|
|
149
|
+
private destroyed;
|
|
150
|
+
constructor(id: string, gridHost: HTMLElement, seed: CellBoot, deps: CellDeps);
|
|
151
|
+
/** Show/hide this cell's symbol watermark (persisted per cell). */
|
|
152
|
+
setWatermarkVisible(visible: boolean): void;
|
|
153
|
+
/** Show/hide this cell's indicator titles — the in-chart legend rows (persisted per cell). */
|
|
154
|
+
setIndicatorTitlesVisible(visible: boolean): void;
|
|
155
|
+
/** The LIVE chart of this cell — never cache it across a layout change (the cell's
|
|
156
|
+
* identity is what endures; the chart dies with the cell). */
|
|
157
|
+
get chart(): Vela;
|
|
158
|
+
get symbol(): string;
|
|
159
|
+
get timeframe(): string;
|
|
160
|
+
get priceStyle(): string;
|
|
161
|
+
/** Manifest instances + present natives — the topbar indicator count. */
|
|
162
|
+
get indicatorCount(): number;
|
|
163
|
+
/** Switch this cell's market in place (the chart instance survives). */
|
|
164
|
+
setSymbol(symbol: string): void;
|
|
165
|
+
setTimeframe(timeframe: string): void;
|
|
166
|
+
/** Applied live (renderer feature) — no reload. */
|
|
167
|
+
setPriceStyle(style: string): void;
|
|
168
|
+
/** OHLC/change ink in the status line follows the ACTIVE price style's configured
|
|
169
|
+
* colors and direction rule (candle bodies by close-vs-open, baseline by position
|
|
170
|
+
* against the live baseline price, …) instead of the fixed theme tokens. */
|
|
171
|
+
private syncStatuslineColors;
|
|
172
|
+
/** The workspace shell keeps the app theme; the cell host's tokens re-derive from
|
|
173
|
+
* the LIVE plot surface (see {@link applyPlotOverlayTokens}). */
|
|
174
|
+
private syncPlotOverlayTokens;
|
|
175
|
+
/**
|
|
176
|
+
* Frame a bottombar range chip: switch to its timeframe, fetch the depth its window
|
|
177
|
+
* needs, and keep it framed (re-asserted once the deeper history is painted).
|
|
178
|
+
*/
|
|
179
|
+
applyRange(preset: RangePreset): void;
|
|
180
|
+
/** Make this cell the active one and put keyboard focus on its chart surface. */
|
|
181
|
+
focus(): void;
|
|
182
|
+
/** Download this cell's chart as a PNG (named after its market). */
|
|
183
|
+
downloadScreenshot(): void;
|
|
184
|
+
/**
|
|
185
|
+
* Hand the cell the workspace's resolved manifest. A RESTORED ledger (pool or
|
|
186
|
+
* persisted state) re-adds its recorded entries by name — held until the manifest
|
|
187
|
+
* actually carries them. Otherwise `seedEnabled` auto-adds the manifest's `enabled`
|
|
188
|
+
* entries (fresh cells only).
|
|
189
|
+
*/
|
|
190
|
+
setManifest(list: readonly ResolvedIndicator[], seedEnabled: boolean): void;
|
|
191
|
+
/** The picker's library rows: supported natives first, then the manifest. */
|
|
192
|
+
libraryRows(): Array<{
|
|
193
|
+
name: string;
|
|
194
|
+
language?: string;
|
|
195
|
+
category?: string;
|
|
196
|
+
native?: boolean;
|
|
197
|
+
nativeType?: string;
|
|
198
|
+
beta?: boolean;
|
|
199
|
+
}>;
|
|
200
|
+
/** The picker's on-chart rows: present natives first, then live instances. */
|
|
201
|
+
onChartRows(): Array<{
|
|
202
|
+
name: string;
|
|
203
|
+
language?: string;
|
|
204
|
+
native?: boolean;
|
|
205
|
+
nativeType?: string;
|
|
206
|
+
}>;
|
|
207
|
+
/** Add by picker LIBRARY index (natives precede the manifest — mirrors libraryRows). */
|
|
208
|
+
addFromLibrary(index: number): void;
|
|
209
|
+
/** Remove by picker ON-CHART index (present natives precede instances). */
|
|
210
|
+
removeFromChart(index: number): void;
|
|
211
|
+
/** Add ONE instance of a manifest entry (repeatable — duplicates are legitimate). */
|
|
212
|
+
addManifestInstance(entry: ResolvedIndicator, opts?: {
|
|
213
|
+
record?: boolean;
|
|
214
|
+
}): void;
|
|
215
|
+
private removeInstance;
|
|
216
|
+
private dropInstance;
|
|
217
|
+
/** Add a native indicator (single-instance per type — the core dedupes). */
|
|
218
|
+
addNative(type: string): void;
|
|
219
|
+
private removeNative;
|
|
220
|
+
/** Sync mirror of the chart's present native types — the removal handler diffs
|
|
221
|
+
* against it to identify (and record) whichever type was just removed. */
|
|
222
|
+
private syncPresentNatives;
|
|
223
|
+
/** Refresh the native catalog (supported/present flags) for this cell's market. */
|
|
224
|
+
refreshNativeCatalog(): void;
|
|
225
|
+
private addToChart;
|
|
226
|
+
/** Snapshot everything the pool needs to restore this slot later. The market fields
|
|
227
|
+
* come from the LIVE config (`chart.market`) — the requested identity — so a switch
|
|
228
|
+
* still loading when the snapshot is taken (persist-on-close) is not lost. */
|
|
229
|
+
dehydrate(): PooledCellState;
|
|
230
|
+
destroy(): void;
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
/** The extended context a workspace hands to contributed actions/attachments. */
|
|
234
|
+
interface WorkspaceWidgetContext extends WidgetContext {
|
|
235
|
+
/** Every live cell (layout order) — id + LIVE chart + market snapshot. */
|
|
236
|
+
cells: ReadonlyArray<{
|
|
237
|
+
id: string;
|
|
238
|
+
chart: Vela;
|
|
239
|
+
symbol: string;
|
|
240
|
+
timeframe: string;
|
|
241
|
+
}>;
|
|
242
|
+
activeCellId: string;
|
|
243
|
+
setActiveCell(id: string): void;
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
/** One registered workspace layout. */
|
|
247
|
+
interface LayoutDefinition {
|
|
248
|
+
/** Stable id (`'4'`, `'2h'`, a plugin's `'6-tall'`, …) — re-registering replaces. */
|
|
249
|
+
id: string;
|
|
250
|
+
/** Human-readable label for layout pickers. */
|
|
251
|
+
label: string;
|
|
252
|
+
/** Column track weights (`fr` units), left to right. */
|
|
253
|
+
cols: number[];
|
|
254
|
+
/** Row track weights, top to bottom. */
|
|
255
|
+
rows: number[];
|
|
256
|
+
/**
|
|
257
|
+
* Optional `grid-template-areas` rows for ASYMMETRIC layouts — one string per row,
|
|
258
|
+
* one area name per column (e.g. `['main a', 'main b']` = a tall left cell besides
|
|
259
|
+
* two stacked ones). Omitted ⇒ cells auto-flow row-major in `cells` order.
|
|
260
|
+
*/
|
|
261
|
+
areas?: string[];
|
|
262
|
+
/** The layout's SLOTS, in order — pure geometry: `id` keys the slot's grid styles
|
|
263
|
+
* and `area` binds it to a named area. A slot id is NOT a cell identity: the cell
|
|
264
|
+
* living in slot i is decided by the workspace (its `cells` declaration order),
|
|
265
|
+
* so two layouts sharing slot geometry need no id coordination. Built-ins use
|
|
266
|
+
* `c1`…`cN`. */
|
|
267
|
+
cells: Array<{
|
|
268
|
+
id: string;
|
|
269
|
+
area?: string;
|
|
270
|
+
}>;
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
/** Register (or replace) a workspace layout. Pickers read the registry live. */
|
|
274
|
+
declare function registerLayout(def: LayoutDefinition): void;
|
|
275
|
+
declare function unregisterLayout(id: string): void;
|
|
276
|
+
/** The definition behind a layout id (undefined for unknown ids). */
|
|
277
|
+
declare function layoutDefinition(id: string): LayoutDefinition | undefined;
|
|
278
|
+
/** Every registered layout (registration order) — drives layout pickers. */
|
|
279
|
+
declare function layouts(): LayoutDefinition[];
|
|
280
|
+
/** Register the built-in presets (idempotent — called by the workspace entry point). */
|
|
281
|
+
declare function registerBuiltinLayouts(): void;
|
|
282
|
+
/** Inline styles for the grid container + each cell — PURE (the workspace applies them). */
|
|
283
|
+
declare function gridStyles(def: LayoutDefinition, trackSizes?: TrackSizes): {
|
|
284
|
+
container: Record<string, string>;
|
|
285
|
+
perCell: Record<string, Record<string, string>>;
|
|
286
|
+
};
|
|
287
|
+
/**
|
|
288
|
+
* The active cell after a layout change: keep it when its slot survives, else fall
|
|
289
|
+
* back to the first slot (the reducer behind `setLayout`; pure for tests).
|
|
290
|
+
*/
|
|
291
|
+
declare function activeAfterLayout(current: string | null, cellIds: readonly string[]): string | null;
|
|
292
|
+
|
|
293
|
+
/**
|
|
294
|
+
* The workspace options: the widget's chart vocabulary + the shared shell surface + the
|
|
295
|
+
* grid's own options. Every chart option given TOP-LEVEL (symbol, timeframe, priceStyle,
|
|
296
|
+
* upColor, glow, defaultLanguage, …) is the DEFAULT of each cell — `cells` overrides it
|
|
297
|
+
* per cell with the same words. `height` is the one chart option a grid cannot honor
|
|
298
|
+
* (the layout sizes cells), so it is omitted from the type.
|
|
299
|
+
*/
|
|
300
|
+
interface VelaWorkspaceOptions extends Omit<VelaOptions, 'height'>, VelaShellOptions {
|
|
301
|
+
/** Initial layout — a registered id (`'1'`, `'2h'`, `'2v'`, `'4'`, `'8'`, or a
|
|
302
|
+
* plugin-registered one) or an inline definition. Default `'4'`. */
|
|
303
|
+
layout?: string | LayoutDefinition;
|
|
304
|
+
/** Per-cell overrides of the top-level chart defaults, keyed by a FREE-FORM cell
|
|
305
|
+
* name — the name is the cell's durable IDENTITY (persistence, `sync` groups,
|
|
306
|
+
* `ws.cell(name)`), never its position: DECLARATION ORDER fills the layout's
|
|
307
|
+
* slots (first declared → first slot). Fewer entries than slots ⇒ the remaining
|
|
308
|
+
* slots boot on the defaults (auto identity); more ⇒ the extras wait in the pool
|
|
309
|
+
* and appear when a larger layout reveals them. Purely-numeric names are rejected
|
|
310
|
+
* (JS object keys would reorder them). Same vocabulary as the widget, reduced to
|
|
311
|
+
* the per-cell seeds ({@link CellSeed}). */
|
|
312
|
+
cells?: Record<string, CellSeed>;
|
|
313
|
+
/** The ONE shared drawing toolbar, docked left of the grid and acting on the active
|
|
314
|
+
* cell (per-cell in-chart bars stay hidden either way; a `drawings` object still
|
|
315
|
+
* configures tools/persistence per cell). Default true. */
|
|
316
|
+
drawingToolbar?: boolean;
|
|
317
|
+
/** Sync links between cells: per kind, `true` = all cells, or a `{cellId: group}`
|
|
318
|
+
* record (only same-group cells follow each other). `crosshair` mirrors the
|
|
319
|
+
* pointer time as ghost crosshairs on the followers (also toggleable from the
|
|
320
|
+
* layout dropdown). Default: everything off. Change at runtime via
|
|
321
|
+
* `ws.sync.set(kind, setting)`. */
|
|
322
|
+
sync?: SyncOptions;
|
|
323
|
+
/** Above this many cells, EVERY cell uses the canvas2d backend (uniform look inside
|
|
324
|
+
* the browser's WebGL-context budget; glow is unavailable there). Default 8; an
|
|
325
|
+
* explicit `nativeBackend` other than `'auto'` wins over this policy. */
|
|
326
|
+
maxWebglCells?: number;
|
|
327
|
+
}
|
|
328
|
+
/** A cell's {@link ScriptRun}, tagged with the cell it ran in. */
|
|
329
|
+
type WorkspaceScriptRun = ScriptRun & {
|
|
330
|
+
cell: string;
|
|
331
|
+
};
|
|
332
|
+
interface WorkspaceEventMap extends Record<string, unknown> {
|
|
333
|
+
/** The active cell changed (click/focus in a cell, or `setActiveCell`). */
|
|
334
|
+
'cell:active': {
|
|
335
|
+
id: string;
|
|
336
|
+
prev: string | null;
|
|
337
|
+
};
|
|
338
|
+
/**
|
|
339
|
+
* A script computed in ANY cell — the per-chart `script:run` relayed up with its cell
|
|
340
|
+
* identity, so one subscription covers the whole grid, cells added by a later layout
|
|
341
|
+
* change included.
|
|
342
|
+
*/
|
|
343
|
+
'script:run': WorkspaceScriptRun;
|
|
344
|
+
/** The grid switched layouts (cells created/destroyed/restored around it). */
|
|
345
|
+
'layout:changed': {
|
|
346
|
+
layout: string;
|
|
347
|
+
};
|
|
348
|
+
'cell:created': {
|
|
349
|
+
id: string;
|
|
350
|
+
};
|
|
351
|
+
'cell:destroyed': {
|
|
352
|
+
id: string;
|
|
353
|
+
};
|
|
354
|
+
/** The persistable state changed (debounced ~500ms) — re-pull `getState()` if you
|
|
355
|
+
* consume it. The signal custom persistence flows build on. */
|
|
356
|
+
'state:changed': undefined;
|
|
357
|
+
}
|
|
358
|
+
declare class VelaWorkspace {
|
|
359
|
+
readonly root: HTMLElement;
|
|
360
|
+
/** The shortcut system — one manager for the whole workspace, routed to the active cell. */
|
|
361
|
+
readonly keymap: KeymapManager;
|
|
362
|
+
private readonly gridEl;
|
|
363
|
+
private readonly events;
|
|
364
|
+
private readonly feed;
|
|
365
|
+
private readonly cellsById;
|
|
366
|
+
private readonly pool;
|
|
367
|
+
private readonly trackSizes;
|
|
368
|
+
private readonly splitters;
|
|
369
|
+
private readonly resizeObserver;
|
|
370
|
+
private readonly opts;
|
|
371
|
+
private def;
|
|
372
|
+
/** Cell identities by SLOT POSITION — `order[i]` lives in the layout's i-th slot.
|
|
373
|
+
* Names come from the `cells` declaration order (then the persisted document);
|
|
374
|
+
* slots beyond the list get auto identities. Grows, never reorders. */
|
|
375
|
+
private order;
|
|
376
|
+
private activeId;
|
|
377
|
+
private cellBackend;
|
|
378
|
+
private destroyed;
|
|
379
|
+
private readonly topbar;
|
|
380
|
+
private readonly bottombar;
|
|
381
|
+
private readonly objectTree;
|
|
382
|
+
private readonly dataWindow;
|
|
383
|
+
/** The side-panel column, shared by the whole grid. */
|
|
384
|
+
private readonly dock;
|
|
385
|
+
private readonly symbolPicker;
|
|
386
|
+
private readonly indicatorPicker;
|
|
387
|
+
private readonly tfQuick;
|
|
388
|
+
private shortcutsHelp;
|
|
389
|
+
private readonly toast;
|
|
390
|
+
private readonly glider;
|
|
391
|
+
private readonly drawToolbar;
|
|
392
|
+
/** The GLOBAL armed tool/magnet/stay (workspace policy) — re-applied to whichever cell
|
|
393
|
+
* takes the focus; only the ACTIVE cell ever holds a non-null tool. Measure/eraser
|
|
394
|
+
* stay transient and per-cell: they exit when the focus leaves. */
|
|
395
|
+
private globalTool;
|
|
396
|
+
private globalSnap;
|
|
397
|
+
private globalStay;
|
|
398
|
+
/** Live subscription to the ACTIVE cell's unified history (rebound on every projection). */
|
|
399
|
+
private historyUnsub;
|
|
400
|
+
/** Favorite drawing tools — a WORKSPACE preference (one star set, every cell). */
|
|
401
|
+
private favs;
|
|
402
|
+
/** Live sync configuration (mutable copy of the option). */
|
|
403
|
+
private readonly syncOpts;
|
|
404
|
+
private readonly persistKey;
|
|
405
|
+
private readonly storage;
|
|
406
|
+
private stateTimer;
|
|
407
|
+
private readonly onUnload;
|
|
408
|
+
/** Re-entrance guard around one propagation tick: followers' synchronous echoes
|
|
409
|
+
* (their setVisibleRange re-emits viewport:changed) must not re-propagate. */
|
|
410
|
+
private syncBusy;
|
|
411
|
+
private manifest;
|
|
412
|
+
/** The shared manifest can no longer change instance sets — resolved, or no
|
|
413
|
+
* `indicators` option so nothing ever will. Gates the cells' ledger fallback. */
|
|
414
|
+
private manifestSettled;
|
|
415
|
+
private timezone;
|
|
416
|
+
private openDialogs;
|
|
417
|
+
private alerts;
|
|
418
|
+
private alertsMenu;
|
|
419
|
+
private readonly attachmentDisposers;
|
|
420
|
+
/** The single grid-wide attribution mark — re-inked on a live theme swap. */
|
|
421
|
+
private attributionMark;
|
|
422
|
+
private readonly onRootKeydown;
|
|
423
|
+
constructor(container: HTMLElement | string, opts?: VelaWorkspaceOptions);
|
|
424
|
+
/** The cell with identity `id` (its declared name, or `c<N>` when undeclared), or
|
|
425
|
+
* undefined when no live cell holds it. */
|
|
426
|
+
cell(id: string): ChartCell | undefined;
|
|
427
|
+
/** Every live cell, in slot order. Enumerated over `order` — the IDENTITY space —
|
|
428
|
+
* never the layout's positional slot ids, which only coincide with it for a
|
|
429
|
+
* workspace whose cells are undeclared. Identities past the current layout size are
|
|
430
|
+
* pooled, not live, so they drop out here. */
|
|
431
|
+
cells(): ChartCell[];
|
|
432
|
+
/** The ACTIVE cell — the one the shared chrome reflects and acts on. */
|
|
433
|
+
get active(): ChartCell;
|
|
434
|
+
/** Shortcut for `active.chart` — the same habit as `widget.chart`. LIVE: read it at
|
|
435
|
+
* the point of use; the durable identity to hold is the cell (or its id). */
|
|
436
|
+
get chart(): Vela;
|
|
437
|
+
setActiveCell(id: string | null): void;
|
|
438
|
+
on<K extends keyof WorkspaceEventMap>(event: K, handler: (payload: WorkspaceEventMap[K]) => void): () => void;
|
|
439
|
+
/** The context handed to contributed actions/attachments (rebuilt per invocation). */
|
|
440
|
+
context(): WorkspaceWidgetContext;
|
|
441
|
+
/** Re-project contributed topbar actions + side panels, and mount late-registered attachments. */
|
|
442
|
+
refreshActions(): void;
|
|
443
|
+
/** The sync-link control surface: `set(kind, true | {cellId: group} | false)`,
|
|
444
|
+
* `get(kind)`, `state()`. Enabling a market/viewport link aligns the followers to
|
|
445
|
+
* the ACTIVE cell once, so the grid starts coherent; `crosshair` mirrors the
|
|
446
|
+
* pointer time as ghost crosshairs on the followers (also a toggle in the layout
|
|
447
|
+
* dropdown). */
|
|
448
|
+
readonly sync: {
|
|
449
|
+
set: (kind: SyncKind, setting: SyncSetting | false | undefined) => void;
|
|
450
|
+
get: (kind: SyncKind) => SyncSetting | undefined;
|
|
451
|
+
state: () => SyncOptions;
|
|
452
|
+
};
|
|
453
|
+
/**
|
|
454
|
+
* Snapshot the COMPLETE workspace state as a versioned, serializable document:
|
|
455
|
+
* layout + splitter sizes, active cell, sync links, timezone, and — per slot, live
|
|
456
|
+
* AND dormant — the market, the renderer's cosmetic config, the user-drawings
|
|
457
|
+
* document, and the indicator ledger. This is what `persist` writes; hosts build
|
|
458
|
+
* custom flows on it (server snapshots, share links, templates).
|
|
459
|
+
*/
|
|
460
|
+
getState(): WorkspaceState;
|
|
461
|
+
/**
|
|
462
|
+
* Restore a state document produced by {@link getState} (untrusted-safe: malformed
|
|
463
|
+
* fields are dropped). Replaces the WHOLE workspace state: prefs, sync links,
|
|
464
|
+
* layout, and every slot — current cells are rebuilt from the document. A layout id
|
|
465
|
+
* that is not registered keeps the current grid (register custom layouts first).
|
|
466
|
+
*/
|
|
467
|
+
applyState(state: unknown): void;
|
|
468
|
+
/** Set the workspace-global display timezone — applied to EVERY cell. */
|
|
469
|
+
setTimezone(zone: string): void;
|
|
470
|
+
/**
|
|
471
|
+
* Swap the workspace theme at runtime — `'dark'`, `'light'`, or a full custom theme,
|
|
472
|
+
* applied to the shared chrome (topbar, panels, drawing toolbar) and EVERY cell.
|
|
473
|
+
* Also reached from any cell's chart settings → Canvas → Theme. The choice sticks:
|
|
474
|
+
* cells rebuilt by later layout switches reconstruct with it.
|
|
475
|
+
*/
|
|
476
|
+
setTheme(theme: NonNullable<VelaWorkspaceOptions['theme']>): void;
|
|
477
|
+
get layout(): LayoutDefinition;
|
|
478
|
+
/**
|
|
479
|
+
* Switch the grid. Cells are diffed BY IDENTITY (`order` head of the next size):
|
|
480
|
+
* surviving cells keep their live charts untouched; cells past the new size
|
|
481
|
+
* dehydrate into the pool; (re)appearing positions hydrate their identity from
|
|
482
|
+
* the pool (or its seed). Crossing the WebGL budget rebuilds every cell through
|
|
483
|
+
* the pool so the backend stays uniform.
|
|
484
|
+
*/
|
|
485
|
+
setLayout(layout: string | LayoutDefinition): void;
|
|
486
|
+
resize(): void;
|
|
487
|
+
destroy(): void;
|
|
488
|
+
/** Re-project the shared chrome from the ACTIVE cell. The chrome holds no state of
|
|
489
|
+
* its own — this is a pure read of the cell, safe to call redundantly. */
|
|
490
|
+
private projectActiveCell;
|
|
491
|
+
/** Put keyboard focus back on the active cell's chart surface (after a toolbar press
|
|
492
|
+
* stole it) so chart/drawing shortcuts keep working. */
|
|
493
|
+
private refocusActive;
|
|
494
|
+
/** Debounced dirty mark: one `state:changed` (+ one storage write in persist mode)
|
|
495
|
+
* per burst of edits, flushed hard on unload/destroy. */
|
|
496
|
+
private markStateDirty;
|
|
497
|
+
/** Write the current state through the storage adapter now (fire-and-forget). */
|
|
498
|
+
private persistNow;
|
|
499
|
+
private resolveLayout;
|
|
500
|
+
private backendFor;
|
|
501
|
+
private currentTracks;
|
|
502
|
+
private applyTracks;
|
|
503
|
+
/** Apply the grid template (+ per-cell areas) and reposition the splitter strips.
|
|
504
|
+
* Geometry is keyed by SLOT (`perCell[slot.id]`); the cell living there is
|
|
505
|
+
* `order[i]` — the identity/position decoupling in one line. */
|
|
506
|
+
private applyGrid;
|
|
507
|
+
/** Create the cells the current layout wants but don't exist yet (pool-first).
|
|
508
|
+
* A slot's CELL IDENTITY is `order[i]` (declaration order — never the slot's own
|
|
509
|
+
* positional id); slots past the declared list mint an auto identity once. */
|
|
510
|
+
private buildCells;
|
|
511
|
+
/** Per-cell chart subscriptions (trigger ② — the chart instance is stable for the
|
|
512
|
+
* cell's whole life, so these live and die with the cell). */
|
|
513
|
+
private wireCell;
|
|
514
|
+
private applySyncSetting;
|
|
515
|
+
/**
|
|
516
|
+
* Mirror an origin cell's pointer time onto its same-group followers as GHOST
|
|
517
|
+
* crosshairs (`renderer.setExternalCrosshair`). Leaving the origin propagates
|
|
518
|
+
* `null` (the event already carries it) and clears every ghost. No busy guard
|
|
519
|
+
* needed: an external crosshair never re-emits `onCrosshairMove` — the flow is
|
|
520
|
+
* one-way by port contract, so no echo loop can exist.
|
|
521
|
+
*/
|
|
522
|
+
private propagateCrosshair;
|
|
523
|
+
/**
|
|
524
|
+
* Push an origin cell's visible range onto its same-group followers. Loop-safe two
|
|
525
|
+
* ways: the busy guard eats the followers' SYNCHRONOUS echoes (their setVisibleRange
|
|
526
|
+
* re-emits `viewport:changed` in the same tick), and the half-bar epsilon
|
|
527
|
+
* short-circuits any async residue — a follower already within half of ITS OWN bar
|
|
528
|
+
* interval is left alone, so cross-timeframe groups settle instead of oscillating.
|
|
529
|
+
*/
|
|
530
|
+
private propagateViewport;
|
|
531
|
+
/**
|
|
532
|
+
* Push an origin cell's symbol/timeframe onto its same-group followers (fired from
|
|
533
|
+
* `market:changed`). Convergence comes from IDEMPOTENCE, not the guard: a follower's
|
|
534
|
+
* own (async) `market:changed` propagates back, but every peer already carries the
|
|
535
|
+
* value, so the cell setters no-op and the wave dies.
|
|
536
|
+
*/
|
|
537
|
+
private propagateMarket;
|
|
538
|
+
/** Trigger ② — a cell's market changed: retention + sync always; chrome only if active. */
|
|
539
|
+
private onCellMarketChanged;
|
|
540
|
+
/** Trigger ② — a cell's indicator ledger changed: count + picker only if active. */
|
|
541
|
+
private onCellIndicatorsChanged;
|
|
542
|
+
/** Timeframe changes routed from the topbar menu / quick entry (chip state follows). */
|
|
543
|
+
private setActiveTimeframe;
|
|
544
|
+
/** The aggregated alerts bell — entries carry their cell; selecting one activates it. */
|
|
545
|
+
private openAlertsMenu;
|
|
546
|
+
/** Mount registered attachments not yet mounted on this workspace (idempotent per id). */
|
|
547
|
+
private mountAttachments;
|
|
548
|
+
/** The default shortcut set — every binding acts on the ACTIVE cell. */
|
|
549
|
+
private registerDefaultKeys;
|
|
550
|
+
/** Bare-typing router: letters → symbol search (seeded), digits → timeframe entry. */
|
|
551
|
+
private routeTyping;
|
|
552
|
+
private trackDialog;
|
|
553
|
+
/** Pool a dehydrated slot state (bounded — oldest entries drop past the cap). */
|
|
554
|
+
private poolSet;
|
|
555
|
+
/**
|
|
556
|
+
* Declare every live cell's symbol to the shared bar cache so one cell's load never
|
|
557
|
+
* evicts the others' history (multi-symbol retention). Keys are CANONICAL tickers —
|
|
558
|
+
* resolved through the registry when its indexes are ready, raw until then (refreshed
|
|
559
|
+
* again on `feed.ready()`).
|
|
560
|
+
*/
|
|
561
|
+
private refreshRetention;
|
|
562
|
+
}
|
|
563
|
+
|
|
564
|
+
/** Even weights for `n` tracks (the double-click reset). */
|
|
565
|
+
declare function evenTracks(n: number): number[];
|
|
566
|
+
/**
|
|
567
|
+
* Resize the boundary between tracks `index` and `index+1` by a pixel delta — PURE.
|
|
568
|
+
* The two neighbors trade weight (their sum, and every other track, is preserved);
|
|
569
|
+
* both are clamped so neither drops under {@link MIN_TRACK_FRAC} of the total.
|
|
570
|
+
* `sizePx` is the container's content size along the axis (gaps excluded).
|
|
571
|
+
*/
|
|
572
|
+
declare function resizeTracks(weights: readonly number[], index: number, deltaPx: number, sizePx: number): number[];
|
|
573
|
+
/**
|
|
574
|
+
* Pixel centers of the INTERNAL track boundaries (`n-1` entries) — where the divider
|
|
575
|
+
* strips sit. PURE: cumulative weights over the gap-corrected content size.
|
|
576
|
+
*/
|
|
577
|
+
declare function trackOffsets(weights: readonly number[], sizePx: number, gapPx: number): number[];
|
|
578
|
+
|
|
579
|
+
export { type CellBoot, type CellChartDefaults, type CellNativeInfo, type CellSeed, CellState, ChartCell, type LayoutDefinition, type PooledCellState, SyncKind, SyncOptions, SyncSetting, TrackSizes, VelaWorkspace, type VelaWorkspaceOptions, type WorkspaceEventMap, type WorkspaceScriptRun, WorkspaceState, type WorkspaceStorage, type WorkspaceWidgetContext, activeAfterLayout, evenTracks, gridStyles, layoutDefinition, layouts, memoryStorageAdapter, rangesWithin, registerBuiltinLayouts, registerLayout, resizeTracks, syncTargets, trackOffsets, unregisterLayout };
|