react-klinecharts-ui 1.0.0 → 1.1.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/README.md +179 -0
- package/dist/chart.cjs +70 -0
- package/dist/chart.cjs.map +1 -0
- package/dist/chart.d.cts +45 -0
- package/dist/chart.d.ts +45 -0
- package/dist/chart.js +68 -0
- package/dist/chart.js.map +1 -0
- package/dist/chunk-F24D6PWY.cjs +98 -0
- package/dist/chunk-F24D6PWY.cjs.map +1 -0
- package/dist/chunk-O7E57I66.js +92 -0
- package/dist/chunk-O7E57I66.js.map +1 -0
- package/dist/chunk-PZ5AY32C.js +9 -0
- package/dist/chunk-PZ5AY32C.js.map +1 -0
- package/dist/chunk-Q7SFCCGT.cjs +11 -0
- package/dist/chunk-Q7SFCCGT.cjs.map +1 -0
- package/dist/{chunk-JD4NBJ5F.js → chunk-RIT2LJQT.js} +4 -9
- package/dist/chunk-RIT2LJQT.js.map +1 -0
- package/dist/{chunk-LGYYJ2GP.cjs → chunk-SZDU2D3D.cjs} +5 -10
- package/dist/chunk-SZDU2D3D.cjs.map +1 -0
- package/dist/extensions.cjs +10 -9
- package/dist/extensions.js +2 -1
- package/dist/index.cjs +459 -211
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +233 -7
- package/dist/index.d.ts +233 -7
- package/dist/index.js +361 -132
- package/dist/index.js.map +1 -1
- package/package.json +19 -2
- package/dist/chunk-JD4NBJ5F.js.map +0 -1
- package/dist/chunk-LGYYJ2GP.cjs.map +0 -1
package/dist/index.cjs
CHANGED
|
@@ -1,32 +1,12 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var chunkSZDU2D3D_cjs = require('./chunk-SZDU2D3D.cjs');
|
|
4
|
+
var chunkF24D6PWY_cjs = require('./chunk-F24D6PWY.cjs');
|
|
5
|
+
require('./chunk-Q7SFCCGT.cjs');
|
|
4
6
|
var react = require('react');
|
|
5
7
|
var klinecharts = require('klinecharts');
|
|
6
8
|
var jsxRuntime = require('react/jsx-runtime');
|
|
7
9
|
|
|
8
|
-
var KlinechartsUIStateContext = react.createContext(null);
|
|
9
|
-
var KlinechartsUIDispatchContext = react.createContext(null);
|
|
10
|
-
function useKlinechartsUIDispatch() {
|
|
11
|
-
const ctx = react.useContext(KlinechartsUIDispatchContext);
|
|
12
|
-
if (!ctx) {
|
|
13
|
-
throw new Error(
|
|
14
|
-
"useKlinechartsUI must be used within a <KlinechartsUIProvider>"
|
|
15
|
-
);
|
|
16
|
-
}
|
|
17
|
-
return ctx;
|
|
18
|
-
}
|
|
19
|
-
function useKlinechartsUI() {
|
|
20
|
-
const state = react.useContext(KlinechartsUIStateContext);
|
|
21
|
-
const dispatch = react.useContext(KlinechartsUIDispatchContext);
|
|
22
|
-
if (!state || !dispatch) {
|
|
23
|
-
throw new Error(
|
|
24
|
-
"useKlinechartsUI must be used within a <KlinechartsUIProvider>"
|
|
25
|
-
);
|
|
26
|
-
}
|
|
27
|
-
return { state, ...dispatch };
|
|
28
|
-
}
|
|
29
|
-
|
|
30
10
|
// src/data/periods.ts
|
|
31
11
|
var DEFAULT_PERIODS = [
|
|
32
12
|
{ span: 1, type: "minute", label: "1m" },
|
|
@@ -40,6 +20,50 @@ var DEFAULT_PERIODS = [
|
|
|
40
20
|
{ span: 1, type: "month", label: "M" },
|
|
41
21
|
{ span: 1, type: "year", label: "Y" }
|
|
42
22
|
];
|
|
23
|
+
|
|
24
|
+
// src/storage/types.ts
|
|
25
|
+
var DEFAULT_STORAGE_NAMESPACES = [
|
|
26
|
+
"alerts",
|
|
27
|
+
"settings",
|
|
28
|
+
"indicators"
|
|
29
|
+
];
|
|
30
|
+
var DEFAULT_STORAGE_KEY_PREFIX = "rkui:";
|
|
31
|
+
|
|
32
|
+
// src/storage/createDefaultStorage.ts
|
|
33
|
+
var NOOP_ADAPTER = {
|
|
34
|
+
getItem: () => null,
|
|
35
|
+
setItem: () => {
|
|
36
|
+
},
|
|
37
|
+
removeItem: () => {
|
|
38
|
+
}
|
|
39
|
+
};
|
|
40
|
+
function createDefaultStorage() {
|
|
41
|
+
if (typeof localStorage === "undefined") return NOOP_ADAPTER;
|
|
42
|
+
try {
|
|
43
|
+
const probe = localStorage.getItem("__rkui_probe__");
|
|
44
|
+
return probe === null ? localStorage : localStorage;
|
|
45
|
+
} catch {
|
|
46
|
+
return NOOP_ADAPTER;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
function resolveStorage(options) {
|
|
50
|
+
const adapter = options?.adapter ?? createDefaultStorage();
|
|
51
|
+
const keyPrefix = options?.keyPrefix ?? DEFAULT_STORAGE_KEY_PREFIX;
|
|
52
|
+
const namespaces = new Set(
|
|
53
|
+
options?.namespaces ?? DEFAULT_STORAGE_NAMESPACES
|
|
54
|
+
);
|
|
55
|
+
return {
|
|
56
|
+
adapter,
|
|
57
|
+
namespaces,
|
|
58
|
+
keyPrefix,
|
|
59
|
+
key(namespace) {
|
|
60
|
+
return `${keyPrefix}${namespace}`;
|
|
61
|
+
},
|
|
62
|
+
persists(namespace) {
|
|
63
|
+
return namespaces.has(namespace);
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
}
|
|
43
67
|
function reducer(state, action) {
|
|
44
68
|
switch (action.type) {
|
|
45
69
|
case "SET_CHART":
|
|
@@ -103,13 +127,16 @@ function KlinechartsUIProvider({
|
|
|
103
127
|
defaultPeriod,
|
|
104
128
|
defaultTheme = "light",
|
|
105
129
|
defaultTimezone = "Asia/Shanghai",
|
|
106
|
-
|
|
107
|
-
|
|
130
|
+
// NOTE: no destructuring default here — the init function must distinguish
|
|
131
|
+
// "consumer passed default*" (wins) from "use stored value" (hydrate).
|
|
132
|
+
defaultMainIndicators,
|
|
133
|
+
defaultSubIndicators,
|
|
108
134
|
defaultLocale = "en-US",
|
|
109
135
|
periods,
|
|
110
136
|
styles,
|
|
111
137
|
registerExtensions: shouldRegister = true,
|
|
112
138
|
overlays: extraOverlays,
|
|
139
|
+
storage: storageOptions,
|
|
113
140
|
children,
|
|
114
141
|
onStateChange,
|
|
115
142
|
onSymbolChange,
|
|
@@ -120,6 +147,11 @@ function KlinechartsUIProvider({
|
|
|
120
147
|
onSubIndicatorsChange,
|
|
121
148
|
onSettingsChange
|
|
122
149
|
}) {
|
|
150
|
+
const resolvedStorage = react.useMemo(
|
|
151
|
+
() => storageOptions ? resolveStorage(storageOptions) : null,
|
|
152
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
153
|
+
[]
|
|
154
|
+
);
|
|
123
155
|
const [state, dispatch] = react.useReducer(
|
|
124
156
|
reducer,
|
|
125
157
|
{
|
|
@@ -132,41 +164,61 @@ function KlinechartsUIProvider({
|
|
|
132
164
|
defaultSubIndicators,
|
|
133
165
|
defaultLocale,
|
|
134
166
|
periods,
|
|
135
|
-
styles
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
167
|
+
styles,
|
|
168
|
+
storage: resolvedStorage
|
|
169
|
+
},
|
|
170
|
+
(opts) => {
|
|
171
|
+
const s = opts.storage;
|
|
172
|
+
const read = (ns, fallback) => {
|
|
173
|
+
if (!s || !s.persists(ns)) return fallback;
|
|
174
|
+
try {
|
|
175
|
+
const raw = s.adapter.getItem(s.key(ns));
|
|
176
|
+
return raw ? JSON.parse(raw) : fallback;
|
|
177
|
+
} catch {
|
|
178
|
+
return fallback;
|
|
179
|
+
}
|
|
180
|
+
};
|
|
181
|
+
const storedIndicators = read("indicators", {});
|
|
182
|
+
return {
|
|
183
|
+
chart: null,
|
|
184
|
+
datafeed: opts.datafeed,
|
|
185
|
+
symbol: opts.defaultSymbol ?? null,
|
|
186
|
+
period: opts.defaultPeriod ?? (opts.periods ?? DEFAULT_PERIODS)[0],
|
|
187
|
+
theme: opts.defaultTheme ?? "light",
|
|
188
|
+
timezone: opts.defaultTimezone ?? "Asia/Shanghai",
|
|
189
|
+
isLoading: false,
|
|
190
|
+
locale: opts.defaultLocale ?? "en-US",
|
|
191
|
+
periods: opts.periods ?? DEFAULT_PERIODS,
|
|
192
|
+
// Persistence semantics: STORED values win over `default*` props —
|
|
193
|
+
// the user's saved configuration should survive reload even when the
|
|
194
|
+
// app passes defaults. Only when storage is empty/unconfigured do the
|
|
195
|
+
// `default*` props apply, falling back to the built-ins last.
|
|
196
|
+
// (Settings live in useKlinechartsUISettings useState and hydrate
|
|
197
|
+
// separately via the dispatch-context `storage`.)
|
|
198
|
+
mainIndicators: storedIndicators.main ?? opts.defaultMainIndicators ?? ["MA"],
|
|
199
|
+
subIndicators: storedIndicators.sub ?? (opts.defaultSubIndicators ? opts.defaultSubIndicators.reduce(
|
|
200
|
+
(acc, name) => ({ ...acc, [name]: "" }),
|
|
201
|
+
{}
|
|
202
|
+
) : { VOL: "" }),
|
|
203
|
+
indicatorAxes: storedIndicators.axes ?? {},
|
|
204
|
+
indicatorVisibility: storedIndicators.visibility ?? {},
|
|
205
|
+
alerts: read("alerts", []),
|
|
206
|
+
measure: { isActive: false, fromPoint: null, result: null },
|
|
207
|
+
replay: {
|
|
208
|
+
isReplaying: false,
|
|
209
|
+
isPaused: false,
|
|
210
|
+
speed: 1,
|
|
211
|
+
barIndex: 0,
|
|
212
|
+
totalBars: 0
|
|
213
|
+
},
|
|
214
|
+
styles: opts.styles,
|
|
215
|
+
screenshotUrl: null
|
|
216
|
+
};
|
|
217
|
+
}
|
|
166
218
|
);
|
|
167
219
|
const fullscreenContainerRef = react.useRef(null);
|
|
168
220
|
const undoRedoListenerRef = react.useRef(null);
|
|
169
|
-
const
|
|
221
|
+
const alertTriggeredListenersRef = react.useRef(/* @__PURE__ */ new Set());
|
|
170
222
|
const replayIntervalRef = react.useRef(null);
|
|
171
223
|
const replaySavedDataRef = react.useRef([]);
|
|
172
224
|
const replayIndexRef = react.useRef(0);
|
|
@@ -230,7 +282,7 @@ function KlinechartsUIProvider({
|
|
|
230
282
|
});
|
|
231
283
|
react.useEffect(() => {
|
|
232
284
|
if (shouldRegister) {
|
|
233
|
-
|
|
285
|
+
chunkSZDU2D3D_cjs.registerExtensions();
|
|
234
286
|
}
|
|
235
287
|
extraOverlaysRef.current?.forEach((overlay) => klinecharts.registerOverlay(overlay));
|
|
236
288
|
}, [shouldRegister]);
|
|
@@ -244,23 +296,53 @@ function KlinechartsUIProvider({
|
|
|
244
296
|
const chart = state.chart;
|
|
245
297
|
if (!chart || !hasAlerts) return;
|
|
246
298
|
alertPrevCloseRef.current = null;
|
|
299
|
+
const prevValueByAlert = /* @__PURE__ */ new Map();
|
|
247
300
|
const interval = setInterval(() => {
|
|
248
301
|
const dataList = chart.getDataList();
|
|
249
302
|
if (!dataList || dataList.length === 0) return;
|
|
250
|
-
const
|
|
251
|
-
const
|
|
252
|
-
|
|
253
|
-
|
|
303
|
+
const lastIdx = dataList.length - 1;
|
|
304
|
+
const indicatorCache = /* @__PURE__ */ new Map();
|
|
305
|
+
const readIndicatorValue = (indicatorId, figureKey) => {
|
|
306
|
+
const cacheKey = `${indicatorId}:${figureKey}`;
|
|
307
|
+
if (indicatorCache.has(cacheKey)) return indicatorCache.get(cacheKey);
|
|
308
|
+
let value = null;
|
|
309
|
+
try {
|
|
310
|
+
const indicators2 = chart.getIndicators({ id: indicatorId });
|
|
311
|
+
const ind = indicators2?.[0];
|
|
312
|
+
const result = ind?.result;
|
|
313
|
+
const last = Array.isArray(result) ? result[lastIdx] : null;
|
|
314
|
+
if (last && typeof last === "object") {
|
|
315
|
+
const v = last[figureKey];
|
|
316
|
+
value = typeof v === "number" ? v : null;
|
|
317
|
+
}
|
|
318
|
+
} catch {
|
|
319
|
+
value = null;
|
|
320
|
+
}
|
|
321
|
+
indicatorCache.set(cacheKey, value);
|
|
322
|
+
return value;
|
|
323
|
+
};
|
|
254
324
|
const alerts = stateRef.current.alerts;
|
|
255
325
|
const triggeredIds = [];
|
|
256
326
|
for (const alert of alerts) {
|
|
257
327
|
if (alert.triggered) continue;
|
|
258
|
-
const
|
|
259
|
-
|
|
328
|
+
const target = alert.target ?? { type: "price" };
|
|
329
|
+
let currentValue;
|
|
330
|
+
if (target.type === "indicator") {
|
|
331
|
+
currentValue = readIndicatorValue(target.indicatorId, target.figureKey);
|
|
332
|
+
} else {
|
|
333
|
+
currentValue = dataList[lastIdx].close;
|
|
334
|
+
}
|
|
335
|
+
if (currentValue === null || !Number.isFinite(currentValue)) continue;
|
|
336
|
+
const prevValue = prevValueByAlert.get(alert.id) ?? null;
|
|
337
|
+
prevValueByAlert.set(alert.id, currentValue);
|
|
338
|
+
if (prevValue === null) continue;
|
|
339
|
+
const crossedUp = prevValue < alert.price && currentValue >= alert.price;
|
|
340
|
+
const crossedDown = prevValue > alert.price && currentValue <= alert.price;
|
|
260
341
|
const shouldTrigger = alert.condition === "crossing_up" ? crossedUp : alert.condition === "crossing_down" ? crossedDown : crossedUp || crossedDown;
|
|
261
342
|
if (shouldTrigger) {
|
|
262
343
|
triggeredIds.push(alert.id);
|
|
263
|
-
|
|
344
|
+
const fired = { ...alert, triggered: true };
|
|
345
|
+
alertTriggeredListenersRef.current.forEach((cb) => cb(fired));
|
|
264
346
|
}
|
|
265
347
|
}
|
|
266
348
|
if (triggeredIds.length > 0) {
|
|
@@ -275,6 +357,36 @@ function KlinechartsUIProvider({
|
|
|
275
357
|
react.useEffect(() => {
|
|
276
358
|
alertPrevCloseRef.current = null;
|
|
277
359
|
}, [state.symbol, state.period]);
|
|
360
|
+
const writeNs = react.useCallback(
|
|
361
|
+
(ns, value) => {
|
|
362
|
+
if (!resolvedStorage || !resolvedStorage.persists(ns)) return;
|
|
363
|
+
try {
|
|
364
|
+
resolvedStorage.adapter.setItem(
|
|
365
|
+
resolvedStorage.key(ns),
|
|
366
|
+
JSON.stringify(value)
|
|
367
|
+
);
|
|
368
|
+
} catch {
|
|
369
|
+
}
|
|
370
|
+
},
|
|
371
|
+
[resolvedStorage]
|
|
372
|
+
);
|
|
373
|
+
react.useEffect(() => {
|
|
374
|
+
writeNs("alerts", state.alerts);
|
|
375
|
+
}, [state.alerts, writeNs]);
|
|
376
|
+
react.useEffect(() => {
|
|
377
|
+
writeNs("indicators", {
|
|
378
|
+
main: state.mainIndicators,
|
|
379
|
+
sub: state.subIndicators,
|
|
380
|
+
axes: state.indicatorAxes,
|
|
381
|
+
visibility: state.indicatorVisibility
|
|
382
|
+
});
|
|
383
|
+
}, [
|
|
384
|
+
state.mainIndicators,
|
|
385
|
+
state.subIndicators,
|
|
386
|
+
state.indicatorAxes,
|
|
387
|
+
state.indicatorVisibility,
|
|
388
|
+
writeNs
|
|
389
|
+
]);
|
|
278
390
|
react.useEffect(() => {
|
|
279
391
|
return () => {
|
|
280
392
|
if (replayIntervalRef.current !== null) {
|
|
@@ -290,18 +402,19 @@ function KlinechartsUIProvider({
|
|
|
290
402
|
onSettingsChange: onSettingsChangeRef.current,
|
|
291
403
|
fullscreenContainerRef,
|
|
292
404
|
undoRedoListenerRef,
|
|
293
|
-
|
|
405
|
+
alertTriggeredListenersRef,
|
|
294
406
|
replayIntervalRef,
|
|
295
407
|
replaySavedDataRef,
|
|
296
|
-
replayIndexRef
|
|
408
|
+
replayIndexRef,
|
|
409
|
+
storage: resolvedStorage
|
|
297
410
|
}),
|
|
298
411
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
299
|
-
[enhancedDispatch]
|
|
412
|
+
[enhancedDispatch, resolvedStorage]
|
|
300
413
|
);
|
|
301
|
-
return /* @__PURE__ */ jsxRuntime.jsx(KlinechartsUIStateContext.Provider, { value: state, children: /* @__PURE__ */ jsxRuntime.jsx(KlinechartsUIDispatchContext.Provider, { value: dispatchValue, children }) });
|
|
414
|
+
return /* @__PURE__ */ jsxRuntime.jsx(chunkF24D6PWY_cjs.KlinechartsUIStateContext.Provider, { value: state, children: /* @__PURE__ */ jsxRuntime.jsx(chunkF24D6PWY_cjs.KlinechartsUIDispatchContext.Provider, { value: dispatchValue, children }) });
|
|
302
415
|
}
|
|
303
416
|
function useKlinechartsUITheme() {
|
|
304
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
417
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
305
418
|
const setTheme = react.useCallback(
|
|
306
419
|
(theme) => {
|
|
307
420
|
state.chart?.setStyles(theme);
|
|
@@ -322,11 +435,11 @@ function useKlinechartsUITheme() {
|
|
|
322
435
|
|
|
323
436
|
// src/hooks/useKlinechartsUILoading.ts
|
|
324
437
|
function useKlinechartsUILoading() {
|
|
325
|
-
const { state } = useKlinechartsUI();
|
|
438
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
326
439
|
return { isLoading: state.isLoading };
|
|
327
440
|
}
|
|
328
441
|
function usePeriods() {
|
|
329
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
442
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
330
443
|
const setPeriod = react.useCallback(
|
|
331
444
|
(period) => {
|
|
332
445
|
dispatch({ type: "SET_PERIOD", period });
|
|
@@ -364,7 +477,7 @@ var TIMEZONES = [
|
|
|
364
477
|
|
|
365
478
|
// src/hooks/useTimezone.ts
|
|
366
479
|
function useTimezone() {
|
|
367
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
480
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
368
481
|
const timezones = react.useMemo(
|
|
369
482
|
() => TIMEZONES.map((tz) => ({
|
|
370
483
|
key: tz.key,
|
|
@@ -386,7 +499,7 @@ function useTimezone() {
|
|
|
386
499
|
};
|
|
387
500
|
}
|
|
388
501
|
function useSymbolSearch(debounceMs = 300) {
|
|
389
|
-
const { state, dispatch, datafeed } = useKlinechartsUI();
|
|
502
|
+
const { state, dispatch, datafeed } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
390
503
|
const [query, setQueryState] = react.useState("");
|
|
391
504
|
const [results, setResults] = react.useState([]);
|
|
392
505
|
const [isSearching, setIsSearching] = react.useState(false);
|
|
@@ -748,8 +861,8 @@ var INDICATOR_PARAMS = {
|
|
|
748
861
|
// src/hooks/useIndicators.ts
|
|
749
862
|
var COLLAPSED_HEIGHT = 30;
|
|
750
863
|
function useIndicators() {
|
|
751
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
752
|
-
const { undoRedoListenerRef } = useKlinechartsUIDispatch();
|
|
864
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
865
|
+
const { undoRedoListenerRef } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
753
866
|
const paneHeightsRef = react.useRef({});
|
|
754
867
|
const collapsedPanesRef = react.useRef(/* @__PURE__ */ new Set());
|
|
755
868
|
const mainIndicators = react.useMemo(() => {
|
|
@@ -1246,8 +1359,8 @@ var DRAWING_CATEGORIES = [
|
|
|
1246
1359
|
// src/hooks/useDrawingTools.ts
|
|
1247
1360
|
var DRAWING_GROUP_ID = "drawing_tools";
|
|
1248
1361
|
function useDrawingTools() {
|
|
1249
|
-
const { state } = useKlinechartsUI();
|
|
1250
|
-
const { undoRedoListenerRef } = useKlinechartsUIDispatch();
|
|
1362
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
1363
|
+
const { undoRedoListenerRef } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
1251
1364
|
const [activeTool, setActiveTool] = react.useState(null);
|
|
1252
1365
|
const [magnetMode, setMagnetModeState] = react.useState("normal");
|
|
1253
1366
|
const [isLocked, setIsLocked] = react.useState(false);
|
|
@@ -1437,8 +1550,18 @@ var defaultSettings = {
|
|
|
1437
1550
|
tooltipShowRule: "always"
|
|
1438
1551
|
};
|
|
1439
1552
|
function useKlinechartsUISettings() {
|
|
1440
|
-
const { state, onSettingsChange } = useKlinechartsUI();
|
|
1441
|
-
const
|
|
1553
|
+
const { state, onSettingsChange } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
1554
|
+
const { storage } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
1555
|
+
const [settings, setSettings] = react.useState(() => {
|
|
1556
|
+
if (storage && storage.persists("settings")) {
|
|
1557
|
+
try {
|
|
1558
|
+
const raw = storage.adapter.getItem(storage.key("settings"));
|
|
1559
|
+
if (raw) return { ...defaultSettings, ...JSON.parse(raw) };
|
|
1560
|
+
} catch {
|
|
1561
|
+
}
|
|
1562
|
+
}
|
|
1563
|
+
return defaultSettings;
|
|
1564
|
+
});
|
|
1442
1565
|
const isInitialMount = react.useRef(true);
|
|
1443
1566
|
react.useEffect(() => {
|
|
1444
1567
|
if (isInitialMount.current) {
|
|
@@ -1447,6 +1570,14 @@ function useKlinechartsUISettings() {
|
|
|
1447
1570
|
}
|
|
1448
1571
|
onSettingsChange?.({ ...settings });
|
|
1449
1572
|
}, [settings, onSettingsChange]);
|
|
1573
|
+
react.useEffect(() => {
|
|
1574
|
+
if (!storage || !storage.persists("settings")) return;
|
|
1575
|
+
if (isInitialMount.current) return;
|
|
1576
|
+
try {
|
|
1577
|
+
storage.adapter.setItem(storage.key("settings"), JSON.stringify(settings));
|
|
1578
|
+
} catch {
|
|
1579
|
+
}
|
|
1580
|
+
}, [settings, storage]);
|
|
1450
1581
|
const candleTypes = react.useMemo(
|
|
1451
1582
|
() => CANDLE_TYPES.map((ct) => ({
|
|
1452
1583
|
key: ct.key,
|
|
@@ -1688,7 +1819,7 @@ function useKlinechartsUISettings() {
|
|
|
1688
1819
|
};
|
|
1689
1820
|
}
|
|
1690
1821
|
function useScreenshot() {
|
|
1691
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
1822
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
1692
1823
|
const capture = react.useCallback(() => {
|
|
1693
1824
|
if (!state.chart) return;
|
|
1694
1825
|
const url = state.chart.getConvertPictureUrl(true, "jpeg", state.theme === "dark" ? "#151517" : "#ffffff");
|
|
@@ -1717,7 +1848,7 @@ function useScreenshot() {
|
|
|
1717
1848
|
};
|
|
1718
1849
|
}
|
|
1719
1850
|
function useHotkeys() {
|
|
1720
|
-
const { state } = useKlinechartsUI();
|
|
1851
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
1721
1852
|
const registerHotkey = react.useCallback((template) => {
|
|
1722
1853
|
klinecharts.registerHotkey(template);
|
|
1723
1854
|
}, []);
|
|
@@ -1746,7 +1877,7 @@ function useHotkeys() {
|
|
|
1746
1877
|
};
|
|
1747
1878
|
}
|
|
1748
1879
|
function useChartAxes() {
|
|
1749
|
-
const { state } = useKlinechartsUI();
|
|
1880
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
1750
1881
|
const overrideXAxis = react.useCallback(
|
|
1751
1882
|
(override) => {
|
|
1752
1883
|
if (!state.chart) return;
|
|
@@ -1764,7 +1895,7 @@ function useChartAxes() {
|
|
|
1764
1895
|
return { overrideXAxis, overrideYAxis };
|
|
1765
1896
|
}
|
|
1766
1897
|
function useFullscreen() {
|
|
1767
|
-
const { fullscreenContainerRef } = useKlinechartsUIDispatch();
|
|
1898
|
+
const { fullscreenContainerRef } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
1768
1899
|
const [isFullscreen, setIsFullscreen] = react.useState(false);
|
|
1769
1900
|
const enter = react.useCallback(() => {
|
|
1770
1901
|
const el = fullscreenContainerRef.current;
|
|
@@ -1819,7 +1950,7 @@ function useFullscreen() {
|
|
|
1819
1950
|
};
|
|
1820
1951
|
}
|
|
1821
1952
|
function useOrderLines() {
|
|
1822
|
-
const { state } = useKlinechartsUI();
|
|
1953
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
1823
1954
|
const callbacksRef = react.useRef(/* @__PURE__ */ new Map());
|
|
1824
1955
|
const ownedIdsRef = react.useRef(/* @__PURE__ */ new Set());
|
|
1825
1956
|
const createOrderLine = react.useCallback(
|
|
@@ -1916,8 +2047,8 @@ function useOrderLines() {
|
|
|
1916
2047
|
}
|
|
1917
2048
|
var DRAWING_GROUP_ID2 = "drawing_tools";
|
|
1918
2049
|
function useUndoRedo() {
|
|
1919
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
1920
|
-
const { undoRedoListenerRef } = useKlinechartsUIDispatch();
|
|
2050
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
2051
|
+
const { undoRedoListenerRef } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
1921
2052
|
const [undoStack, setUndoStack] = react.useState([]);
|
|
1922
2053
|
const [redoStack, setRedoStack] = react.useState([]);
|
|
1923
2054
|
const isProcessingRef = react.useRef(false);
|
|
@@ -2259,7 +2390,7 @@ function getEntry(id) {
|
|
|
2259
2390
|
}
|
|
2260
2391
|
}
|
|
2261
2392
|
function useLayoutManager() {
|
|
2262
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
2393
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
2263
2394
|
const [layouts, setLayouts] = react.useState(
|
|
2264
2395
|
() => getLayoutIds().map((id) => getEntry(id)).filter((e) => e !== null)
|
|
2265
2396
|
);
|
|
@@ -2563,7 +2694,7 @@ var SHADOW_KEYS = [
|
|
|
2563
2694
|
];
|
|
2564
2695
|
var scriptCounter = 0;
|
|
2565
2696
|
function useScriptEditor() {
|
|
2566
|
-
const { state } = useKlinechartsUI();
|
|
2697
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
2567
2698
|
const [code, setCode] = react.useState(DEFAULT_SCRIPT);
|
|
2568
2699
|
const [scriptName, setScriptName] = react.useState("");
|
|
2569
2700
|
const [params, setParams] = react.useState("14");
|
|
@@ -2600,7 +2731,7 @@ ${code}`
|
|
|
2600
2731
|
const shadowValues = SHADOW_KEYS.map(() => void 0);
|
|
2601
2732
|
const sampleResult = compiledFn(
|
|
2602
2733
|
...shadowValues,
|
|
2603
|
-
|
|
2734
|
+
chunkSZDU2D3D_cjs.TA_default,
|
|
2604
2735
|
dataList,
|
|
2605
2736
|
parsedParams
|
|
2606
2737
|
);
|
|
@@ -2627,7 +2758,7 @@ ${code}`
|
|
|
2627
2758
|
shortName: (scriptName.trim() || `Script #${scriptCounter}`) + (placement === "main" ? " (Main)" : " (Sub)"),
|
|
2628
2759
|
calcParams: parsedParams,
|
|
2629
2760
|
figures,
|
|
2630
|
-
calc: (liveDataList) => compiledFn(...shadowValues,
|
|
2761
|
+
calc: (liveDataList) => compiledFn(...shadowValues, chunkSZDU2D3D_cjs.TA_default, liveDataList, parsedParams),
|
|
2631
2762
|
extendData: {
|
|
2632
2763
|
isCustomScript: true,
|
|
2633
2764
|
code,
|
|
@@ -2738,7 +2869,7 @@ ${code}`
|
|
|
2738
2869
|
};
|
|
2739
2870
|
}
|
|
2740
2871
|
function useCrosshair() {
|
|
2741
|
-
const { state } = useKlinechartsUI();
|
|
2872
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
2742
2873
|
const [barData, setBarData] = react.useState(null);
|
|
2743
2874
|
const rafRef = react.useRef(0);
|
|
2744
2875
|
const handler = react.useCallback(
|
|
@@ -2788,11 +2919,11 @@ function useCrosshair() {
|
|
|
2788
2919
|
}
|
|
2789
2920
|
var alertCounter = 0;
|
|
2790
2921
|
function useAlerts() {
|
|
2791
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
2792
|
-
const {
|
|
2922
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
2923
|
+
const { alertTriggeredListenersRef } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
2793
2924
|
const alerts = state.alerts;
|
|
2794
2925
|
const addAlert = react.useCallback(
|
|
2795
|
-
(price, condition, message, extendData) => {
|
|
2926
|
+
(price, condition, message, extendData, target) => {
|
|
2796
2927
|
const id = `alert_${++alertCounter}`;
|
|
2797
2928
|
const precision = state.chart?.getSymbol()?.pricePrecision ?? 2;
|
|
2798
2929
|
const resolvedExtendData = {
|
|
@@ -2805,11 +2936,14 @@ function useAlerts() {
|
|
|
2805
2936
|
condition,
|
|
2806
2937
|
message,
|
|
2807
2938
|
triggered: false,
|
|
2808
|
-
extendData: resolvedExtendData
|
|
2939
|
+
extendData: resolvedExtendData,
|
|
2940
|
+
// Persist the target only when it's an indicator alert; omit for the
|
|
2941
|
+
// default price target so existing serialized alerts stay compatible.
|
|
2942
|
+
...target && target.type === "indicator" ? { target } : {}
|
|
2809
2943
|
};
|
|
2810
2944
|
dispatch({ type: "ADD_ALERT", alert });
|
|
2811
2945
|
if (state.chart) {
|
|
2812
|
-
|
|
2946
|
+
chunkSZDU2D3D_cjs.ensureAlertLineRegistered();
|
|
2813
2947
|
state.chart.createOverlay({
|
|
2814
2948
|
name: "alertLine",
|
|
2815
2949
|
id,
|
|
@@ -2836,9 +2970,13 @@ function useAlerts() {
|
|
|
2836
2970
|
}, [state.chart, dispatch]);
|
|
2837
2971
|
const onAlertTriggered = react.useCallback(
|
|
2838
2972
|
(callback) => {
|
|
2839
|
-
|
|
2973
|
+
const set = alertTriggeredListenersRef.current;
|
|
2974
|
+
set.add(callback);
|
|
2975
|
+
return () => {
|
|
2976
|
+
set.delete(callback);
|
|
2977
|
+
};
|
|
2840
2978
|
},
|
|
2841
|
-
[
|
|
2979
|
+
[alertTriggeredListenersRef]
|
|
2842
2980
|
);
|
|
2843
2981
|
return {
|
|
2844
2982
|
alerts,
|
|
@@ -2849,7 +2987,7 @@ function useAlerts() {
|
|
|
2849
2987
|
};
|
|
2850
2988
|
}
|
|
2851
2989
|
function useDataExport() {
|
|
2852
|
-
const { state } = useKlinechartsUI();
|
|
2990
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
2853
2991
|
const exportAll = react.useCallback(
|
|
2854
2992
|
(format) => {
|
|
2855
2993
|
if (!state.chart) return;
|
|
@@ -2915,8 +3053,8 @@ function downloadData(dataList, format, ticker) {
|
|
|
2915
3053
|
URL.revokeObjectURL(url);
|
|
2916
3054
|
}
|
|
2917
3055
|
function useWatchlist() {
|
|
2918
|
-
const { state } = useKlinechartsUI();
|
|
2919
|
-
const { dispatch, datafeed } = useKlinechartsUIDispatch();
|
|
3056
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
3057
|
+
const { dispatch, datafeed } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
2920
3058
|
const [items, setItems] = react.useState([]);
|
|
2921
3059
|
const subscriptionsRef = react.useRef(/* @__PURE__ */ new Map());
|
|
2922
3060
|
const activeSymbol = state.symbol?.ticker ?? null;
|
|
@@ -2985,8 +3123,8 @@ function useWatchlist() {
|
|
|
2985
3123
|
};
|
|
2986
3124
|
}
|
|
2987
3125
|
function useReplay() {
|
|
2988
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
2989
|
-
const { replayIntervalRef, replaySavedDataRef, replayIndexRef } = useKlinechartsUIDispatch();
|
|
3126
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
3127
|
+
const { replayIntervalRef, replaySavedDataRef, replayIndexRef } = chunkF24D6PWY_cjs.useKlinechartsUIDispatch();
|
|
2990
3128
|
const { isReplaying, isPaused, speed, barIndex, totalBars } = state.replay;
|
|
2991
3129
|
const clearInterval_ = react.useCallback(() => {
|
|
2992
3130
|
if (replayIntervalRef.current !== null) {
|
|
@@ -3135,7 +3273,7 @@ var DEFAULT_COLORS = [
|
|
|
3135
3273
|
"#8bc34a"
|
|
3136
3274
|
];
|
|
3137
3275
|
function useCompare() {
|
|
3138
|
-
const { state, datafeed } = useKlinechartsUI();
|
|
3276
|
+
const { state, datafeed } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
3139
3277
|
const [symbols, setSymbols] = react.useState([]);
|
|
3140
3278
|
const indicatorsRef = react.useRef(/* @__PURE__ */ new Map());
|
|
3141
3279
|
const instanceSalt = react.useId().replace(/[^a-zA-Z0-9]/g, "");
|
|
@@ -3281,7 +3419,7 @@ function computeResult(from, to) {
|
|
|
3281
3419
|
return { from, to, priceDiff, pricePercent, bars, timeDiff };
|
|
3282
3420
|
}
|
|
3283
3421
|
function useMeasure() {
|
|
3284
|
-
const { state, dispatch } = useKlinechartsUI();
|
|
3422
|
+
const { state, dispatch } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
3285
3423
|
const { isActive, fromPoint, result } = state.measure;
|
|
3286
3424
|
const cleanup = react.useCallback(() => {
|
|
3287
3425
|
state.chart?.removeOverlay({ id: MEASURE_OVERLAY_ID });
|
|
@@ -3362,7 +3500,7 @@ function useMeasure() {
|
|
|
3362
3500
|
}
|
|
3363
3501
|
var annotationCounter = 0;
|
|
3364
3502
|
function useAnnotations() {
|
|
3365
|
-
const { state } = useKlinechartsUI();
|
|
3503
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
3366
3504
|
const [annotations, setAnnotations] = react.useState([]);
|
|
3367
3505
|
const addAnnotation = react.useCallback(
|
|
3368
3506
|
(text, price, timestamp, color) => {
|
|
@@ -3442,265 +3580,375 @@ function useAnnotations() {
|
|
|
3442
3580
|
clearAnnotations
|
|
3443
3581
|
};
|
|
3444
3582
|
}
|
|
3583
|
+
var WorkspaceContext = react.createContext(null);
|
|
3584
|
+
function useWorkspace() {
|
|
3585
|
+
const ctx = react.useContext(WorkspaceContext);
|
|
3586
|
+
if (!ctx) {
|
|
3587
|
+
throw new Error("useWorkspace must be used within a <WorkspaceProvider>");
|
|
3588
|
+
}
|
|
3589
|
+
return ctx;
|
|
3590
|
+
}
|
|
3445
3591
|
|
|
3446
|
-
// src/
|
|
3447
|
-
|
|
3448
|
-
|
|
3449
|
-
|
|
3450
|
-
|
|
3451
|
-
|
|
3592
|
+
// src/workspace/types.ts
|
|
3593
|
+
var DEFAULT_SYNC_CONFIG = {
|
|
3594
|
+
crosshair: true,
|
|
3595
|
+
scroll: true,
|
|
3596
|
+
zoom: true,
|
|
3597
|
+
symbol: true,
|
|
3598
|
+
period: true
|
|
3599
|
+
};
|
|
3600
|
+
function reducer2(state, action) {
|
|
3601
|
+
switch (action.type) {
|
|
3602
|
+
case "SET_CELLS":
|
|
3603
|
+
return { ...state, cells: action.cells };
|
|
3604
|
+
case "ADD_CELL":
|
|
3605
|
+
return { ...state, cells: [...state.cells, action.cell] };
|
|
3606
|
+
case "REMOVE_CELL": {
|
|
3607
|
+
const cells = state.cells.filter((c) => c.id !== action.id);
|
|
3608
|
+
return {
|
|
3609
|
+
cells,
|
|
3610
|
+
activeCellId: state.activeCellId === action.id ? cells[0]?.id ?? null : state.activeCellId
|
|
3611
|
+
};
|
|
3612
|
+
}
|
|
3613
|
+
case "SET_CELL_SYMBOL":
|
|
3614
|
+
return {
|
|
3615
|
+
...state,
|
|
3616
|
+
cells: state.cells.map(
|
|
3617
|
+
(c) => c.id === action.id ? { ...c, symbol: action.symbol } : c
|
|
3618
|
+
)
|
|
3619
|
+
};
|
|
3620
|
+
case "SET_CELL_PERIOD":
|
|
3621
|
+
return {
|
|
3622
|
+
...state,
|
|
3623
|
+
cells: state.cells.map(
|
|
3624
|
+
(c) => c.id === action.id ? { ...c, period: action.period } : c
|
|
3625
|
+
)
|
|
3626
|
+
};
|
|
3627
|
+
case "SET_ACTIVE_CELL":
|
|
3628
|
+
return { ...state, activeCellId: action.id };
|
|
3629
|
+
default:
|
|
3630
|
+
return state;
|
|
3631
|
+
}
|
|
3632
|
+
}
|
|
3633
|
+
function WorkspaceProvider({
|
|
3634
|
+
defaultCells,
|
|
3635
|
+
sync,
|
|
3636
|
+
children
|
|
3637
|
+
}) {
|
|
3638
|
+
const [state, dispatch] = react.useReducer(reducer2, defaultCells, (cells) => ({
|
|
3639
|
+
cells,
|
|
3640
|
+
activeCellId: cells[0]?.id ?? null
|
|
3641
|
+
}));
|
|
3642
|
+
const chartsRef = react.useRef(/* @__PURE__ */ new Map());
|
|
3643
|
+
const broadcastingRef = react.useRef(false);
|
|
3644
|
+
const resolvedSync = react.useMemo(
|
|
3645
|
+
() => ({ ...DEFAULT_SYNC_CONFIG, ...sync }),
|
|
3646
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
3647
|
+
[]
|
|
3648
|
+
);
|
|
3649
|
+
const value = react.useMemo(
|
|
3650
|
+
() => ({
|
|
3651
|
+
state,
|
|
3652
|
+
dispatch,
|
|
3653
|
+
chartsRef,
|
|
3654
|
+
broadcastingRef,
|
|
3655
|
+
sync: resolvedSync
|
|
3656
|
+
}),
|
|
3657
|
+
[state, resolvedSync]
|
|
3658
|
+
);
|
|
3659
|
+
return /* @__PURE__ */ jsxRuntime.jsx(WorkspaceContext.Provider, { value, children });
|
|
3660
|
+
}
|
|
3661
|
+
function useChartSync({ cellId }) {
|
|
3662
|
+
const { chartsRef, broadcastingRef, sync, dispatch: workspaceDispatch } = useWorkspace();
|
|
3663
|
+
const { state } = chunkF24D6PWY_cjs.useKlinechartsUI();
|
|
3664
|
+
const chart = state.chart;
|
|
3665
|
+
react.useEffect(() => {
|
|
3666
|
+
if (!chart) return;
|
|
3667
|
+
chartsRef.current.set(cellId, chart);
|
|
3668
|
+
return () => {
|
|
3669
|
+
chartsRef.current.delete(cellId);
|
|
3670
|
+
};
|
|
3671
|
+
}, [chart, cellId, chartsRef]);
|
|
3672
|
+
react.useEffect(() => {
|
|
3673
|
+
if (!chart) return;
|
|
3674
|
+
const broadcast = (fn) => {
|
|
3675
|
+
if (broadcastingRef.current) return;
|
|
3676
|
+
broadcastingRef.current = true;
|
|
3452
3677
|
try {
|
|
3453
|
-
|
|
3454
|
-
|
|
3455
|
-
|
|
3456
|
-
|
|
3457
|
-
|
|
3458
|
-
|
|
3459
|
-
{ ...params.period, label: "" },
|
|
3460
|
-
0,
|
|
3461
|
-
Date.now()
|
|
3462
|
-
);
|
|
3463
|
-
if (gen !== currentGen) return;
|
|
3464
|
-
if (data.length > 0) {
|
|
3465
|
-
oldestTimestamp = data[0].timestamp;
|
|
3466
|
-
}
|
|
3467
|
-
params.callback(data, {
|
|
3468
|
-
forward: data.length > 0,
|
|
3469
|
-
backward: false
|
|
3470
|
-
});
|
|
3471
|
-
} else if (params.type === "forward" && oldestTimestamp !== null) {
|
|
3472
|
-
const gen = currentGen;
|
|
3473
|
-
const data = await datafeed.getHistoryKLineData(
|
|
3474
|
-
params.symbol,
|
|
3475
|
-
{ ...params.period, label: "" },
|
|
3476
|
-
0,
|
|
3477
|
-
oldestTimestamp - 1
|
|
3478
|
-
);
|
|
3479
|
-
if (gen !== currentGen) return;
|
|
3480
|
-
if (data.length > 0) {
|
|
3481
|
-
oldestTimestamp = data[0].timestamp;
|
|
3678
|
+
chartsRef.current.forEach((target, id) => {
|
|
3679
|
+
if (id !== cellId) {
|
|
3680
|
+
try {
|
|
3681
|
+
fn(target);
|
|
3682
|
+
} catch {
|
|
3683
|
+
}
|
|
3482
3684
|
}
|
|
3483
|
-
|
|
3484
|
-
forward: data.length > 0,
|
|
3485
|
-
backward: false
|
|
3486
|
-
});
|
|
3487
|
-
} else if (params.type === "backward") {
|
|
3488
|
-
params.callback([], { forward: false, backward: false });
|
|
3489
|
-
}
|
|
3490
|
-
} catch (error) {
|
|
3491
|
-
console.error("Failed to load chart data:", error);
|
|
3492
|
-
params.callback([], { forward: false, backward: false });
|
|
3685
|
+
});
|
|
3493
3686
|
} finally {
|
|
3494
|
-
|
|
3687
|
+
broadcastingRef.current = false;
|
|
3495
3688
|
}
|
|
3496
|
-
}
|
|
3497
|
-
|
|
3498
|
-
|
|
3499
|
-
|
|
3500
|
-
|
|
3501
|
-
|
|
3689
|
+
};
|
|
3690
|
+
const onCrosshairChange = (data) => {
|
|
3691
|
+
if (!sync.crosshair) return;
|
|
3692
|
+
const crosshair = data;
|
|
3693
|
+
if (!crosshair) return;
|
|
3694
|
+
broadcast((target) => target.executeAction("onCrosshairChange", crosshair));
|
|
3695
|
+
};
|
|
3696
|
+
const onScroll = () => {
|
|
3697
|
+
if (!sync.scroll) return;
|
|
3698
|
+
let range = null;
|
|
3699
|
+
try {
|
|
3700
|
+
range = chart.getVisibleRange();
|
|
3701
|
+
} catch {
|
|
3702
|
+
return;
|
|
3703
|
+
}
|
|
3704
|
+
if (!range || range.realTo == null) return;
|
|
3705
|
+
broadcast(
|
|
3706
|
+
(target) => target.scrollToTimestamp(range.realTo, 0)
|
|
3502
3707
|
);
|
|
3503
|
-
}
|
|
3504
|
-
|
|
3505
|
-
|
|
3708
|
+
};
|
|
3709
|
+
const onZoom = () => {
|
|
3710
|
+
if (!sync.zoom) return;
|
|
3711
|
+
let bar = 0;
|
|
3712
|
+
try {
|
|
3713
|
+
bar = chart.getBarSpace().bar;
|
|
3714
|
+
} catch {
|
|
3715
|
+
return;
|
|
3716
|
+
}
|
|
3717
|
+
broadcast((target) => target.setBarSpace(bar));
|
|
3718
|
+
};
|
|
3719
|
+
chart.subscribeAction("onCrosshairChange", onCrosshairChange);
|
|
3720
|
+
chart.subscribeAction("onScroll", onScroll);
|
|
3721
|
+
chart.subscribeAction("onZoom", onZoom);
|
|
3722
|
+
return () => {
|
|
3723
|
+
chart.unsubscribeAction("onCrosshairChange", onCrosshairChange);
|
|
3724
|
+
chart.unsubscribeAction("onScroll", onScroll);
|
|
3725
|
+
chart.unsubscribeAction("onZoom", onZoom);
|
|
3726
|
+
};
|
|
3727
|
+
}, [chart, cellId, chartsRef, broadcastingRef, sync.crosshair, sync.scroll, sync.zoom]);
|
|
3728
|
+
react.useEffect(() => {
|
|
3729
|
+
if (state.symbol) {
|
|
3730
|
+
workspaceDispatch({ type: "SET_CELL_SYMBOL", id: cellId, symbol: state.symbol });
|
|
3506
3731
|
}
|
|
3507
|
-
};
|
|
3732
|
+
}, [state.symbol]);
|
|
3733
|
+
react.useEffect(() => {
|
|
3734
|
+
workspaceDispatch({ type: "SET_CELL_PERIOD", id: cellId, period: state.period });
|
|
3735
|
+
}, [state.period]);
|
|
3508
3736
|
}
|
|
3509
3737
|
|
|
3510
3738
|
Object.defineProperty(exports, "TA", {
|
|
3511
3739
|
enumerable: true,
|
|
3512
|
-
get: function () { return
|
|
3740
|
+
get: function () { return chunkSZDU2D3D_cjs.TA_default; }
|
|
3513
3741
|
});
|
|
3514
3742
|
Object.defineProperty(exports, "abcd", {
|
|
3515
3743
|
enumerable: true,
|
|
3516
|
-
get: function () { return
|
|
3744
|
+
get: function () { return chunkSZDU2D3D_cjs.abcd_default; }
|
|
3517
3745
|
});
|
|
3518
3746
|
Object.defineProperty(exports, "alertLine", {
|
|
3519
3747
|
enumerable: true,
|
|
3520
|
-
get: function () { return
|
|
3748
|
+
get: function () { return chunkSZDU2D3D_cjs.alertLine_default; }
|
|
3521
3749
|
});
|
|
3522
3750
|
Object.defineProperty(exports, "anyWaves", {
|
|
3523
3751
|
enumerable: true,
|
|
3524
|
-
get: function () { return
|
|
3752
|
+
get: function () { return chunkSZDU2D3D_cjs.anyWaves_default; }
|
|
3525
3753
|
});
|
|
3526
3754
|
Object.defineProperty(exports, "arrow", {
|
|
3527
3755
|
enumerable: true,
|
|
3528
|
-
get: function () { return
|
|
3756
|
+
get: function () { return chunkSZDU2D3D_cjs.arrow_default; }
|
|
3529
3757
|
});
|
|
3530
3758
|
Object.defineProperty(exports, "bollTv", {
|
|
3531
3759
|
enumerable: true,
|
|
3532
|
-
get: function () { return
|
|
3760
|
+
get: function () { return chunkSZDU2D3D_cjs.bollTv_default; }
|
|
3533
3761
|
});
|
|
3534
3762
|
Object.defineProperty(exports, "brush", {
|
|
3535
3763
|
enumerable: true,
|
|
3536
|
-
get: function () { return
|
|
3764
|
+
get: function () { return chunkSZDU2D3D_cjs.brush_default; }
|
|
3537
3765
|
});
|
|
3538
3766
|
Object.defineProperty(exports, "cci", {
|
|
3539
3767
|
enumerable: true,
|
|
3540
|
-
get: function () { return
|
|
3768
|
+
get: function () { return chunkSZDU2D3D_cjs.cci_default; }
|
|
3541
3769
|
});
|
|
3542
3770
|
Object.defineProperty(exports, "circle", {
|
|
3543
3771
|
enumerable: true,
|
|
3544
|
-
get: function () { return
|
|
3772
|
+
get: function () { return chunkSZDU2D3D_cjs.circle_default; }
|
|
3545
3773
|
});
|
|
3546
3774
|
Object.defineProperty(exports, "depthOverlay", {
|
|
3547
3775
|
enumerable: true,
|
|
3548
|
-
get: function () { return
|
|
3776
|
+
get: function () { return chunkSZDU2D3D_cjs.depthOverlay_default; }
|
|
3549
3777
|
});
|
|
3550
3778
|
Object.defineProperty(exports, "eightWaves", {
|
|
3551
3779
|
enumerable: true,
|
|
3552
|
-
get: function () { return
|
|
3780
|
+
get: function () { return chunkSZDU2D3D_cjs.eightWaves_default; }
|
|
3553
3781
|
});
|
|
3554
3782
|
Object.defineProperty(exports, "elliottWave", {
|
|
3555
3783
|
enumerable: true,
|
|
3556
|
-
get: function () { return
|
|
3784
|
+
get: function () { return chunkSZDU2D3D_cjs.elliottWave_default; }
|
|
3557
3785
|
});
|
|
3558
3786
|
Object.defineProperty(exports, "fibRetracement", {
|
|
3559
3787
|
enumerable: true,
|
|
3560
|
-
get: function () { return
|
|
3788
|
+
get: function () { return chunkSZDU2D3D_cjs.fibRetracement_default; }
|
|
3561
3789
|
});
|
|
3562
3790
|
Object.defineProperty(exports, "fibonacciCircle", {
|
|
3563
3791
|
enumerable: true,
|
|
3564
|
-
get: function () { return
|
|
3792
|
+
get: function () { return chunkSZDU2D3D_cjs.fibonacciCircle_default; }
|
|
3565
3793
|
});
|
|
3566
3794
|
Object.defineProperty(exports, "fibonacciExtension", {
|
|
3567
3795
|
enumerable: true,
|
|
3568
|
-
get: function () { return
|
|
3796
|
+
get: function () { return chunkSZDU2D3D_cjs.fibonacciExtension_default; }
|
|
3569
3797
|
});
|
|
3570
3798
|
Object.defineProperty(exports, "fibonacciSegment", {
|
|
3571
3799
|
enumerable: true,
|
|
3572
|
-
get: function () { return
|
|
3800
|
+
get: function () { return chunkSZDU2D3D_cjs.fibonacciSegment_default; }
|
|
3573
3801
|
});
|
|
3574
3802
|
Object.defineProperty(exports, "fibonacciSpeedResistanceFan", {
|
|
3575
3803
|
enumerable: true,
|
|
3576
|
-
get: function () { return
|
|
3804
|
+
get: function () { return chunkSZDU2D3D_cjs.fibonacciSpeedResistanceFan_default; }
|
|
3577
3805
|
});
|
|
3578
3806
|
Object.defineProperty(exports, "fibonacciSpiral", {
|
|
3579
3807
|
enumerable: true,
|
|
3580
|
-
get: function () { return
|
|
3808
|
+
get: function () { return chunkSZDU2D3D_cjs.fibonacciSpiral_default; }
|
|
3581
3809
|
});
|
|
3582
3810
|
Object.defineProperty(exports, "fiveWaves", {
|
|
3583
3811
|
enumerable: true,
|
|
3584
|
-
get: function () { return
|
|
3812
|
+
get: function () { return chunkSZDU2D3D_cjs.fiveWaves_default; }
|
|
3585
3813
|
});
|
|
3586
3814
|
Object.defineProperty(exports, "gannBox", {
|
|
3587
3815
|
enumerable: true,
|
|
3588
|
-
get: function () { return
|
|
3816
|
+
get: function () { return chunkSZDU2D3D_cjs.gannBox_default; }
|
|
3589
3817
|
});
|
|
3590
3818
|
Object.defineProperty(exports, "gannFan", {
|
|
3591
3819
|
enumerable: true,
|
|
3592
|
-
get: function () { return
|
|
3820
|
+
get: function () { return chunkSZDU2D3D_cjs.gannFan_default; }
|
|
3593
3821
|
});
|
|
3594
3822
|
Object.defineProperty(exports, "hma", {
|
|
3595
3823
|
enumerable: true,
|
|
3596
|
-
get: function () { return
|
|
3824
|
+
get: function () { return chunkSZDU2D3D_cjs.hma_default; }
|
|
3597
3825
|
});
|
|
3598
3826
|
Object.defineProperty(exports, "ichimoku", {
|
|
3599
3827
|
enumerable: true,
|
|
3600
|
-
get: function () { return
|
|
3828
|
+
get: function () { return chunkSZDU2D3D_cjs.ichimoku_default; }
|
|
3601
3829
|
});
|
|
3602
3830
|
Object.defineProperty(exports, "indicators", {
|
|
3603
3831
|
enumerable: true,
|
|
3604
|
-
get: function () { return
|
|
3832
|
+
get: function () { return chunkSZDU2D3D_cjs.indicators; }
|
|
3605
3833
|
});
|
|
3606
3834
|
Object.defineProperty(exports, "longPosition", {
|
|
3607
3835
|
enumerable: true,
|
|
3608
|
-
get: function () { return
|
|
3836
|
+
get: function () { return chunkSZDU2D3D_cjs.longPosition_default; }
|
|
3609
3837
|
});
|
|
3610
3838
|
Object.defineProperty(exports, "maRibbon", {
|
|
3611
3839
|
enumerable: true,
|
|
3612
|
-
get: function () { return
|
|
3840
|
+
get: function () { return chunkSZDU2D3D_cjs.maRibbon_default; }
|
|
3613
3841
|
});
|
|
3614
3842
|
Object.defineProperty(exports, "macdTv", {
|
|
3615
3843
|
enumerable: true,
|
|
3616
|
-
get: function () { return
|
|
3844
|
+
get: function () { return chunkSZDU2D3D_cjs.macdTv_default; }
|
|
3617
3845
|
});
|
|
3618
3846
|
Object.defineProperty(exports, "measure", {
|
|
3619
3847
|
enumerable: true,
|
|
3620
|
-
get: function () { return
|
|
3848
|
+
get: function () { return chunkSZDU2D3D_cjs.measure_default; }
|
|
3621
3849
|
});
|
|
3622
3850
|
Object.defineProperty(exports, "orderLine", {
|
|
3623
3851
|
enumerable: true,
|
|
3624
|
-
get: function () { return
|
|
3852
|
+
get: function () { return chunkSZDU2D3D_cjs.orderLine_default; }
|
|
3625
3853
|
});
|
|
3626
3854
|
Object.defineProperty(exports, "overlays", {
|
|
3627
3855
|
enumerable: true,
|
|
3628
|
-
get: function () { return
|
|
3856
|
+
get: function () { return chunkSZDU2D3D_cjs.overlays; }
|
|
3629
3857
|
});
|
|
3630
3858
|
Object.defineProperty(exports, "parallelChannel", {
|
|
3631
3859
|
enumerable: true,
|
|
3632
|
-
get: function () { return
|
|
3860
|
+
get: function () { return chunkSZDU2D3D_cjs.parallelChannel_default; }
|
|
3633
3861
|
});
|
|
3634
3862
|
Object.defineProperty(exports, "parallelogram", {
|
|
3635
3863
|
enumerable: true,
|
|
3636
|
-
get: function () { return
|
|
3864
|
+
get: function () { return chunkSZDU2D3D_cjs.parallelogram_default; }
|
|
3637
3865
|
});
|
|
3638
3866
|
Object.defineProperty(exports, "pivotPoints", {
|
|
3639
3867
|
enumerable: true,
|
|
3640
|
-
get: function () { return
|
|
3868
|
+
get: function () { return chunkSZDU2D3D_cjs.pivotPoints_default; }
|
|
3641
3869
|
});
|
|
3642
3870
|
Object.defineProperty(exports, "ray", {
|
|
3643
3871
|
enumerable: true,
|
|
3644
|
-
get: function () { return
|
|
3872
|
+
get: function () { return chunkSZDU2D3D_cjs.ray_default; }
|
|
3645
3873
|
});
|
|
3646
3874
|
Object.defineProperty(exports, "rect", {
|
|
3647
3875
|
enumerable: true,
|
|
3648
|
-
get: function () { return
|
|
3876
|
+
get: function () { return chunkSZDU2D3D_cjs.rect_default; }
|
|
3649
3877
|
});
|
|
3650
3878
|
Object.defineProperty(exports, "registerExtensions", {
|
|
3651
3879
|
enumerable: true,
|
|
3652
|
-
get: function () { return
|
|
3880
|
+
get: function () { return chunkSZDU2D3D_cjs.registerExtensions; }
|
|
3653
3881
|
});
|
|
3654
3882
|
Object.defineProperty(exports, "rsiTv", {
|
|
3655
3883
|
enumerable: true,
|
|
3656
|
-
get: function () { return
|
|
3884
|
+
get: function () { return chunkSZDU2D3D_cjs.rsiTv_default; }
|
|
3657
3885
|
});
|
|
3658
3886
|
Object.defineProperty(exports, "shortPosition", {
|
|
3659
3887
|
enumerable: true,
|
|
3660
|
-
get: function () { return
|
|
3888
|
+
get: function () { return chunkSZDU2D3D_cjs.shortPosition_default; }
|
|
3661
3889
|
});
|
|
3662
3890
|
Object.defineProperty(exports, "stochastic", {
|
|
3663
3891
|
enumerable: true,
|
|
3664
|
-
get: function () { return
|
|
3892
|
+
get: function () { return chunkSZDU2D3D_cjs.stochastic_default; }
|
|
3665
3893
|
});
|
|
3666
3894
|
Object.defineProperty(exports, "superTrend", {
|
|
3667
3895
|
enumerable: true,
|
|
3668
|
-
get: function () { return
|
|
3896
|
+
get: function () { return chunkSZDU2D3D_cjs.superTrend_default; }
|
|
3669
3897
|
});
|
|
3670
3898
|
Object.defineProperty(exports, "threeWaves", {
|
|
3671
3899
|
enumerable: true,
|
|
3672
|
-
get: function () { return
|
|
3900
|
+
get: function () { return chunkSZDU2D3D_cjs.threeWaves_default; }
|
|
3673
3901
|
});
|
|
3674
3902
|
Object.defineProperty(exports, "triangle", {
|
|
3675
3903
|
enumerable: true,
|
|
3676
|
-
get: function () { return
|
|
3904
|
+
get: function () { return chunkSZDU2D3D_cjs.triangle_default; }
|
|
3677
3905
|
});
|
|
3678
3906
|
Object.defineProperty(exports, "vwap", {
|
|
3679
3907
|
enumerable: true,
|
|
3680
|
-
get: function () { return
|
|
3908
|
+
get: function () { return chunkSZDU2D3D_cjs.vwap_default; }
|
|
3681
3909
|
});
|
|
3682
3910
|
Object.defineProperty(exports, "xabcd", {
|
|
3683
3911
|
enumerable: true,
|
|
3684
|
-
get: function () { return
|
|
3912
|
+
get: function () { return chunkSZDU2D3D_cjs.xabcd_default; }
|
|
3913
|
+
});
|
|
3914
|
+
Object.defineProperty(exports, "KlinechartsUIDispatchContext", {
|
|
3915
|
+
enumerable: true,
|
|
3916
|
+
get: function () { return chunkF24D6PWY_cjs.KlinechartsUIDispatchContext; }
|
|
3917
|
+
});
|
|
3918
|
+
Object.defineProperty(exports, "KlinechartsUIStateContext", {
|
|
3919
|
+
enumerable: true,
|
|
3920
|
+
get: function () { return chunkF24D6PWY_cjs.KlinechartsUIStateContext; }
|
|
3921
|
+
});
|
|
3922
|
+
Object.defineProperty(exports, "createDataLoader", {
|
|
3923
|
+
enumerable: true,
|
|
3924
|
+
get: function () { return chunkF24D6PWY_cjs.createDataLoader; }
|
|
3925
|
+
});
|
|
3926
|
+
Object.defineProperty(exports, "useKlinechartsUI", {
|
|
3927
|
+
enumerable: true,
|
|
3928
|
+
get: function () { return chunkF24D6PWY_cjs.useKlinechartsUI; }
|
|
3685
3929
|
});
|
|
3686
3930
|
exports.CANDLE_TYPES = CANDLE_TYPES;
|
|
3687
3931
|
exports.COMPARE_RULES = COMPARE_RULES;
|
|
3688
3932
|
exports.DEFAULT_PERIODS = DEFAULT_PERIODS;
|
|
3933
|
+
exports.DEFAULT_STORAGE_KEY_PREFIX = DEFAULT_STORAGE_KEY_PREFIX;
|
|
3934
|
+
exports.DEFAULT_STORAGE_NAMESPACES = DEFAULT_STORAGE_NAMESPACES;
|
|
3935
|
+
exports.DEFAULT_SYNC_CONFIG = DEFAULT_SYNC_CONFIG;
|
|
3689
3936
|
exports.DRAWING_CATEGORIES = DRAWING_CATEGORIES;
|
|
3690
3937
|
exports.INDICATOR_PARAMS = INDICATOR_PARAMS;
|
|
3691
|
-
exports.KlinechartsUIDispatchContext = KlinechartsUIDispatchContext;
|
|
3692
3938
|
exports.KlinechartsUIProvider = KlinechartsUIProvider;
|
|
3693
|
-
exports.KlinechartsUIStateContext = KlinechartsUIStateContext;
|
|
3694
3939
|
exports.MAIN_INDICATORS = MAIN_INDICATORS;
|
|
3695
3940
|
exports.PRICE_AXIS_TYPES = PRICE_AXIS_TYPES;
|
|
3696
3941
|
exports.SUB_INDICATORS = SUB_INDICATORS;
|
|
3697
3942
|
exports.TIMEZONES = TIMEZONES;
|
|
3698
3943
|
exports.TOOLTIP_SHOW_RULES = TOOLTIP_SHOW_RULES;
|
|
3944
|
+
exports.WorkspaceProvider = WorkspaceProvider;
|
|
3699
3945
|
exports.YAXIS_POSITIONS = YAXIS_POSITIONS;
|
|
3700
|
-
exports.
|
|
3946
|
+
exports.createDefaultStorage = createDefaultStorage;
|
|
3947
|
+
exports.resolveStorage = resolveStorage;
|
|
3701
3948
|
exports.useAlerts = useAlerts;
|
|
3702
3949
|
exports.useAnnotations = useAnnotations;
|
|
3703
3950
|
exports.useChartAxes = useChartAxes;
|
|
3951
|
+
exports.useChartSync = useChartSync;
|
|
3704
3952
|
exports.useCompare = useCompare;
|
|
3705
3953
|
exports.useCrosshair = useCrosshair;
|
|
3706
3954
|
exports.useDataExport = useDataExport;
|
|
@@ -3708,7 +3956,6 @@ exports.useDrawingTools = useDrawingTools;
|
|
|
3708
3956
|
exports.useFullscreen = useFullscreen;
|
|
3709
3957
|
exports.useHotkeys = useHotkeys;
|
|
3710
3958
|
exports.useIndicators = useIndicators;
|
|
3711
|
-
exports.useKlinechartsUI = useKlinechartsUI;
|
|
3712
3959
|
exports.useKlinechartsUILoading = useKlinechartsUILoading;
|
|
3713
3960
|
exports.useKlinechartsUISettings = useKlinechartsUISettings;
|
|
3714
3961
|
exports.useKlinechartsUITheme = useKlinechartsUITheme;
|
|
@@ -3723,5 +3970,6 @@ exports.useSymbolSearch = useSymbolSearch;
|
|
|
3723
3970
|
exports.useTimezone = useTimezone;
|
|
3724
3971
|
exports.useUndoRedo = useUndoRedo;
|
|
3725
3972
|
exports.useWatchlist = useWatchlist;
|
|
3973
|
+
exports.useWorkspace = useWorkspace;
|
|
3726
3974
|
//# sourceMappingURL=index.cjs.map
|
|
3727
3975
|
//# sourceMappingURL=index.cjs.map
|