snice 4.8.0 → 4.9.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/adapters/react/camera-annotate.d.ts +27 -0
- package/adapters/react/camera-annotate.d.ts.map +1 -0
- package/adapters/react/camera-annotate.js +24 -0
- package/adapters/react/camera-annotate.js.map +1 -0
- package/adapters/react/camera-annotate.tsx +35 -0
- package/adapters/react/candlestick.d.ts +34 -0
- package/adapters/react/candlestick.d.ts.map +1 -0
- package/adapters/react/candlestick.js +24 -0
- package/adapters/react/candlestick.js.map +1 -0
- package/adapters/react/candlestick.tsx +42 -0
- package/adapters/react/components.d.ts +14 -0
- package/adapters/react/components.d.ts.map +1 -1
- package/adapters/react/components.js +7 -0
- package/adapters/react/components.js.map +1 -1
- package/adapters/react/components.ts +14 -0
- package/adapters/react/funnel.d.ts +31 -0
- package/adapters/react/funnel.d.ts.map +1 -0
- package/adapters/react/funnel.js +24 -0
- package/adapters/react/funnel.js.map +1 -0
- package/adapters/react/funnel.tsx +39 -0
- package/adapters/react/network-graph.d.ts +32 -0
- package/adapters/react/network-graph.d.ts.map +1 -0
- package/adapters/react/network-graph.js +24 -0
- package/adapters/react/network-graph.js.map +1 -0
- package/adapters/react/network-graph.tsx +40 -0
- package/adapters/react/sankey.d.ts +31 -0
- package/adapters/react/sankey.d.ts.map +1 -0
- package/adapters/react/sankey.js +24 -0
- package/adapters/react/sankey.js.map +1 -0
- package/adapters/react/sankey.tsx +39 -0
- package/adapters/react/time-range-picker.d.ts +33 -0
- package/adapters/react/time-range-picker.d.ts.map +1 -0
- package/adapters/react/time-range-picker.js +24 -0
- package/adapters/react/time-range-picker.js.map +1 -0
- package/adapters/react/time-range-picker.tsx +41 -0
- package/adapters/react/treemap.d.ts +30 -0
- package/adapters/react/treemap.d.ts.map +1 -0
- package/adapters/react/treemap.js +24 -0
- package/adapters/react/treemap.js.map +1 -0
- package/adapters/react/treemap.tsx +38 -0
- package/adapters/react/virtual-scroller.d.ts +1 -0
- package/adapters/react/virtual-scroller.d.ts.map +1 -1
- package/adapters/react/virtual-scroller.js +1 -1
- package/adapters/react/virtual-scroller.js.map +1 -1
- package/adapters/react/virtual-scroller.tsx +2 -1
- package/dist/cdn/accordion/snice-accordion.js +1 -1
- package/dist/cdn/accordion/snice-accordion.min.js +1 -1
- package/dist/cdn/alert/snice-alert.js +1 -1
- package/dist/cdn/alert/snice-alert.min.js +1 -1
- package/dist/cdn/audio-recorder/snice-audio-recorder.js +1 -1
- package/dist/cdn/audio-recorder/snice-audio-recorder.min.js +1 -1
- package/dist/cdn/avatar/snice-avatar.js +1 -1
- package/dist/cdn/avatar/snice-avatar.min.js +1 -1
- package/dist/cdn/badge/snice-badge.js +1 -1
- package/dist/cdn/badge/snice-badge.min.js +1 -1
- package/dist/cdn/banner/snice-banner.js +1 -1
- package/dist/cdn/banner/snice-banner.min.js +1 -1
- package/dist/cdn/breadcrumbs/snice-breadcrumbs.js +2 -2
- package/dist/cdn/breadcrumbs/snice-breadcrumbs.js.map +1 -1
- package/dist/cdn/breadcrumbs/snice-breadcrumbs.min.js +13 -13
- package/dist/cdn/breadcrumbs/snice-breadcrumbs.min.js.map +1 -1
- package/dist/cdn/button/snice-button.js +1 -1
- package/dist/cdn/button/snice-button.min.js +1 -1
- package/dist/cdn/calendar/snice-calendar.js +1 -1
- package/dist/cdn/calendar/snice-calendar.min.js +1 -1
- package/dist/cdn/camera/snice-camera.js +1 -1
- package/dist/cdn/camera/snice-camera.min.js +1 -1
- package/dist/cdn/camera-annotate/README.md +27 -0
- package/dist/cdn/camera-annotate/snice-camera-annotate.js +730 -0
- package/dist/cdn/camera-annotate/snice-camera-annotate.js.map +1 -0
- package/dist/cdn/camera-annotate/snice-camera-annotate.min.js +144 -0
- package/dist/cdn/camera-annotate/snice-camera-annotate.min.js.map +1 -0
- package/dist/cdn/candlestick/README.md +27 -0
- package/dist/cdn/candlestick/snice-candlestick.js +717 -0
- package/dist/cdn/candlestick/snice-candlestick.js.map +1 -0
- package/dist/cdn/candlestick/snice-candlestick.min.js +22 -0
- package/dist/cdn/candlestick/snice-candlestick.min.js.map +1 -0
- package/dist/cdn/card/snice-card.js +1 -1
- package/dist/cdn/card/snice-card.min.js +1 -1
- package/dist/cdn/carousel/snice-carousel.js +1 -1
- package/dist/cdn/carousel/snice-carousel.min.js +1 -1
- package/dist/cdn/chart/snice-chart.js +1 -1
- package/dist/cdn/chart/snice-chart.min.js +1 -1
- package/dist/cdn/chat/snice-chat.js +1 -1
- package/dist/cdn/chat/snice-chat.min.js +1 -1
- package/dist/cdn/checkbox/snice-checkbox.js +1 -1
- package/dist/cdn/checkbox/snice-checkbox.min.js +1 -1
- package/dist/cdn/chip/snice-chip.js +1 -1
- package/dist/cdn/chip/snice-chip.min.js +1 -1
- package/dist/cdn/code-block/snice-code-block.js +1 -1
- package/dist/cdn/code-block/snice-code-block.min.js +1 -1
- package/dist/cdn/color-display/snice-color-display.js +1 -1
- package/dist/cdn/color-display/snice-color-display.min.js +1 -1
- package/dist/cdn/color-picker/snice-color-picker.js +1 -1
- package/dist/cdn/color-picker/snice-color-picker.min.js +1 -1
- package/dist/cdn/command-palette/snice-command-palette.js +1 -1
- package/dist/cdn/command-palette/snice-command-palette.min.js +1 -1
- package/dist/cdn/date-picker/snice-date-picker.js +1 -1
- package/dist/cdn/date-picker/snice-date-picker.min.js +1 -1
- package/dist/cdn/divider/snice-divider.js +1 -1
- package/dist/cdn/divider/snice-divider.min.js +1 -1
- package/dist/cdn/doc/snice-doc.js +1 -1
- package/dist/cdn/doc/snice-doc.min.js +1 -1
- package/dist/cdn/draw/snice-draw.js +1 -1
- package/dist/cdn/draw/snice-draw.min.js +1 -1
- package/dist/cdn/drawer/snice-drawer.js +1 -1
- package/dist/cdn/drawer/snice-drawer.min.js +1 -1
- package/dist/cdn/empty-state/snice-empty-state.js +1 -1
- package/dist/cdn/empty-state/snice-empty-state.min.js +1 -1
- package/dist/cdn/file-gallery/snice-file-gallery.js +1 -1
- package/dist/cdn/file-gallery/snice-file-gallery.min.js +1 -1
- package/dist/cdn/file-upload/snice-file-upload.js +1 -1
- package/dist/cdn/file-upload/snice-file-upload.min.js +1 -1
- package/dist/cdn/funnel/README.md +27 -0
- package/dist/cdn/funnel/snice-funnel.js +424 -0
- package/dist/cdn/funnel/snice-funnel.js.map +1 -0
- package/dist/cdn/funnel/snice-funnel.min.js +20 -0
- package/dist/cdn/funnel/snice-funnel.min.js.map +1 -0
- package/dist/cdn/gauge/snice-gauge.js +1 -1
- package/dist/cdn/gauge/snice-gauge.min.js +1 -1
- package/dist/cdn/heatmap/snice-heatmap.js +1 -1
- package/dist/cdn/heatmap/snice-heatmap.min.js +1 -1
- package/dist/cdn/image/snice-image.js +1 -1
- package/dist/cdn/image/snice-image.min.js +1 -1
- package/dist/cdn/input/snice-input.js +1 -1
- package/dist/cdn/input/snice-input.min.js +1 -1
- package/dist/cdn/kanban/snice-kanban.js +1 -1
- package/dist/cdn/kanban/snice-kanban.min.js +1 -1
- package/dist/cdn/kpi/snice-kpi.js +1 -1
- package/dist/cdn/kpi/snice-kpi.min.js +1 -1
- package/dist/cdn/layout/README.md +2 -2
- package/dist/cdn/layout/snice-layout.js +23 -6
- package/dist/cdn/layout/snice-layout.js.map +1 -1
- package/dist/cdn/layout/snice-layout.min.js +2 -2
- package/dist/cdn/layout/snice-layout.min.js.map +1 -1
- package/dist/cdn/link/snice-link.js +1 -1
- package/dist/cdn/link/snice-link.min.js +1 -1
- package/dist/cdn/link-preview/snice-link-preview.js +1 -1
- package/dist/cdn/link-preview/snice-link-preview.min.js +1 -1
- package/dist/cdn/list/README.md +6 -2
- package/dist/cdn/list/snice-list.js +87 -10
- package/dist/cdn/list/snice-list.js.map +1 -1
- package/dist/cdn/list/snice-list.min.js +20 -6
- package/dist/cdn/list/snice-list.min.js.map +1 -1
- package/dist/cdn/location/snice-location.js +1 -1
- package/dist/cdn/location/snice-location.min.js +1 -1
- package/dist/cdn/login/snice-login.js +1 -1
- package/dist/cdn/login/snice-login.min.js +1 -1
- package/dist/cdn/masonry/snice-masonry.js +1 -1
- package/dist/cdn/masonry/snice-masonry.min.js +1 -1
- package/dist/cdn/menu/snice-menu.js +1 -1
- package/dist/cdn/menu/snice-menu.min.js +1 -1
- package/dist/cdn/modal/snice-modal.js +1 -1
- package/dist/cdn/modal/snice-modal.min.js +1 -1
- package/dist/cdn/music-player/snice-music-player.js +1 -1
- package/dist/cdn/music-player/snice-music-player.min.js +1 -1
- package/dist/cdn/nav/README.md +2 -2
- package/dist/cdn/nav/snice-nav.js +23 -6
- package/dist/cdn/nav/snice-nav.js.map +1 -1
- package/dist/cdn/nav/snice-nav.min.js +2 -2
- package/dist/cdn/nav/snice-nav.min.js.map +1 -1
- package/dist/cdn/network-graph/README.md +27 -0
- package/dist/cdn/network-graph/snice-network-graph.js +788 -0
- package/dist/cdn/network-graph/snice-network-graph.js.map +1 -0
- package/dist/cdn/network-graph/snice-network-graph.min.js +13 -0
- package/dist/cdn/network-graph/snice-network-graph.min.js.map +1 -0
- package/dist/cdn/pagination/README.md +2 -2
- package/dist/cdn/pagination/snice-pagination.js +13 -13
- package/dist/cdn/pagination/snice-pagination.js.map +1 -1
- package/dist/cdn/pagination/snice-pagination.min.js +14 -14
- package/dist/cdn/pagination/snice-pagination.min.js.map +1 -1
- package/dist/cdn/paint/snice-paint.js +1 -1
- package/dist/cdn/paint/snice-paint.min.js +1 -1
- package/dist/cdn/progress/snice-progress.js +1 -1
- package/dist/cdn/progress/snice-progress.min.js +1 -1
- package/dist/cdn/qr-code/snice-qr-code.js +1 -1
- package/dist/cdn/qr-code/snice-qr-code.min.js +1 -1
- package/dist/cdn/qr-reader/snice-qr-reader.js +1 -1
- package/dist/cdn/qr-reader/snice-qr-reader.min.js +1 -1
- package/dist/cdn/radio/snice-radio.js +1 -1
- package/dist/cdn/radio/snice-radio.min.js +1 -1
- package/dist/cdn/runtime/snice-runtime.esm.js +3 -3
- package/dist/cdn/runtime/snice-runtime.esm.js.map +1 -1
- package/dist/cdn/runtime/snice-runtime.esm.min.js +3 -3
- package/dist/cdn/runtime/snice-runtime.esm.min.js.map +1 -1
- package/dist/cdn/runtime/snice-runtime.js +3 -3
- package/dist/cdn/runtime/snice-runtime.js.map +1 -1
- package/dist/cdn/runtime/snice-runtime.min.js +3 -3
- package/dist/cdn/runtime/snice-runtime.min.js.map +1 -1
- package/dist/cdn/sankey/README.md +27 -0
- package/dist/cdn/sankey/snice-sankey.js +679 -0
- package/dist/cdn/sankey/snice-sankey.js.map +1 -0
- package/dist/cdn/sankey/snice-sankey.min.js +21 -0
- package/dist/cdn/sankey/snice-sankey.min.js.map +1 -0
- package/dist/cdn/select/snice-select.js +1 -1
- package/dist/cdn/select/snice-select.min.js +1 -1
- package/dist/cdn/skeleton/snice-skeleton.js +1 -1
- package/dist/cdn/skeleton/snice-skeleton.min.js +1 -1
- package/dist/cdn/slider/snice-slider.js +1 -1
- package/dist/cdn/slider/snice-slider.min.js +1 -1
- package/dist/cdn/sparkline/snice-sparkline.js +1 -1
- package/dist/cdn/sparkline/snice-sparkline.min.js +1 -1
- package/dist/cdn/spinner/snice-spinner.js +1 -1
- package/dist/cdn/spinner/snice-spinner.min.js +1 -1
- package/dist/cdn/split-pane/snice-split-pane.js +1 -1
- package/dist/cdn/split-pane/snice-split-pane.min.js +1 -1
- package/dist/cdn/stepper/README.md +6 -2
- package/dist/cdn/stepper/snice-stepper.js +77 -10
- package/dist/cdn/stepper/snice-stepper.js.map +1 -1
- package/dist/cdn/stepper/snice-stepper.min.js +13 -9
- package/dist/cdn/stepper/snice-stepper.min.js.map +1 -1
- package/dist/cdn/switch/snice-switch.js +1 -1
- package/dist/cdn/switch/snice-switch.min.js +1 -1
- package/dist/cdn/table/snice-table.js +1 -1
- package/dist/cdn/table/snice-table.min.js +1 -1
- package/dist/cdn/tabs/snice-tabs.js +1 -1
- package/dist/cdn/tabs/snice-tabs.min.js +1 -1
- package/dist/cdn/terminal/snice-terminal.js +1 -1
- package/dist/cdn/terminal/snice-terminal.min.js +1 -1
- package/dist/cdn/textarea/snice-textarea.js +1 -1
- package/dist/cdn/textarea/snice-textarea.min.js +1 -1
- package/dist/cdn/time-range-picker/README.md +27 -0
- package/dist/cdn/time-range-picker/snice-time-range-picker.js +635 -0
- package/dist/cdn/time-range-picker/snice-time-range-picker.js.map +1 -0
- package/dist/cdn/time-range-picker/snice-time-range-picker.min.js +34 -0
- package/dist/cdn/time-range-picker/snice-time-range-picker.min.js.map +1 -0
- package/dist/cdn/timeline/snice-timeline.js +1 -1
- package/dist/cdn/timeline/snice-timeline.min.js +1 -1
- package/dist/cdn/timer/snice-timer.js +1 -1
- package/dist/cdn/timer/snice-timer.min.js +1 -1
- package/dist/cdn/toast/snice-toast.js +1 -1
- package/dist/cdn/toast/snice-toast.min.js +1 -1
- package/dist/cdn/tooltip/snice-tooltip.js +1 -1
- package/dist/cdn/tooltip/snice-tooltip.min.js +1 -1
- package/dist/cdn/tree/README.md +5 -1
- package/dist/cdn/tree/snice-tree.js +4 -8
- package/dist/cdn/tree/snice-tree.js.map +1 -1
- package/dist/cdn/tree/snice-tree.min.js +5 -5
- package/dist/cdn/tree/snice-tree.min.js.map +1 -1
- package/dist/cdn/treemap/README.md +27 -0
- package/dist/cdn/treemap/snice-treemap.js +522 -0
- package/dist/cdn/treemap/snice-treemap.js.map +1 -0
- package/dist/cdn/treemap/snice-treemap.min.js +14 -0
- package/dist/cdn/treemap/snice-treemap.min.js.map +1 -0
- package/dist/cdn/virtual-scroller/README.md +2 -2
- package/dist/cdn/virtual-scroller/snice-virtual-scroller.js +47 -16
- package/dist/cdn/virtual-scroller/snice-virtual-scroller.js.map +1 -1
- package/dist/cdn/virtual-scroller/snice-virtual-scroller.min.js +9 -9
- package/dist/cdn/virtual-scroller/snice-virtual-scroller.min.js.map +1 -1
- package/dist/components/breadcrumbs/snice-breadcrumbs.js +1 -1
- package/dist/components/breadcrumbs/snice-breadcrumbs.js.map +1 -1
- package/dist/components/camera-annotate/snice-camera-annotate.d.ts +68 -0
- package/dist/components/camera-annotate/snice-camera-annotate.js +663 -0
- package/dist/components/camera-annotate/snice-camera-annotate.js.map +1 -0
- package/dist/components/camera-annotate/snice-camera-annotate.types.d.ts +50 -0
- package/dist/components/candlestick/snice-candlestick.d.ts +78 -0
- package/dist/components/candlestick/snice-candlestick.js +650 -0
- package/dist/components/candlestick/snice-candlestick.js.map +1 -0
- package/dist/components/candlestick/snice-candlestick.types.d.ts +40 -0
- package/dist/components/funnel/snice-funnel.d.ts +37 -0
- package/dist/components/funnel/snice-funnel.js +357 -0
- package/dist/components/funnel/snice-funnel.js.map +1 -0
- package/dist/components/funnel/snice-funnel.types.d.ts +28 -0
- package/dist/components/list/snice-list-item.d.ts +2 -0
- package/dist/components/list/snice-list-item.js +20 -2
- package/dist/components/list/snice-list-item.js.map +1 -1
- package/dist/components/nav/snice-nav.js +22 -5
- package/dist/components/nav/snice-nav.js.map +1 -1
- package/dist/components/network-graph/snice-network-graph.d.ts +80 -0
- package/dist/components/network-graph/snice-network-graph.js +721 -0
- package/dist/components/network-graph/snice-network-graph.js.map +1 -0
- package/dist/components/network-graph/snice-network-graph.types.d.ts +49 -0
- package/dist/components/pagination/snice-pagination.js +12 -12
- package/dist/components/sankey/snice-sankey.d.ts +46 -0
- package/dist/components/sankey/snice-sankey.js +612 -0
- package/dist/components/sankey/snice-sankey.js.map +1 -0
- package/dist/components/sankey/snice-sankey.types.d.ts +59 -0
- package/dist/components/stepper/snice-stepper.js +9 -3
- package/dist/components/stepper/snice-stepper.js.map +1 -1
- package/dist/components/time-range-picker/snice-time-range-picker.d.ts +67 -0
- package/dist/components/time-range-picker/snice-time-range-picker.js +568 -0
- package/dist/components/time-range-picker/snice-time-range-picker.js.map +1 -0
- package/dist/components/time-range-picker/snice-time-range-picker.types.d.ts +39 -0
- package/dist/components/treemap/snice-treemap.d.ts +49 -0
- package/dist/components/treemap/snice-treemap.js +455 -0
- package/dist/components/treemap/snice-treemap.js.map +1 -0
- package/dist/components/treemap/snice-treemap.types.d.ts +42 -0
- package/dist/components/virtual-scroller/snice-virtual-scroller.d.ts +5 -0
- package/dist/components/virtual-scroller/snice-virtual-scroller.js +47 -16
- package/dist/components/virtual-scroller/snice-virtual-scroller.js.map +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.cjs.map +1 -1
- package/dist/index.esm.js +1 -1
- package/dist/index.esm.js.map +1 -1
- package/dist/index.iife.js +1 -1
- package/dist/index.iife.js.map +1 -1
- package/dist/symbols.cjs +1 -1
- package/dist/symbols.esm.js +1 -1
- package/dist/transitions.cjs +1 -1
- package/dist/transitions.esm.js +1 -1
- package/docs/ai/components/camera-annotate.md +82 -0
- package/docs/ai/components/candlestick.md +79 -0
- package/docs/ai/components/funnel.md +86 -0
- package/docs/ai/components/network-graph.md +87 -0
- package/docs/ai/components/sankey.md +63 -0
- package/docs/ai/components/time-range-picker.md +78 -0
- package/docs/ai/components/treemap.md +78 -0
- package/docs/components/camera-annotate.md +186 -0
- package/docs/components/candlestick.md +196 -0
- package/docs/components/funnel.md +191 -0
- package/docs/components/network-graph.md +215 -0
- package/docs/components/sankey.md +201 -0
- package/docs/components/time-range-picker.md +213 -0
- package/docs/components/treemap.md +198 -0
- package/package.json +1 -1
|
@@ -0,0 +1,717 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* snice v4.8.0
|
|
3
|
+
* Imperative TypeScript framework for building vanilla web components with decorators, differential rendering, routing, and controllers. No virtual DOM, no build complexity.
|
|
4
|
+
* (c) 2024
|
|
5
|
+
* Released under the MIT License.
|
|
6
|
+
*/
|
|
7
|
+
if(typeof globalThis.Snice==="undefined"){console.warn("[snice] snice-runtime.min.js must be loaded before snice-candlestick.min.js");}
|
|
8
|
+
var SniceCandlestick = (function (exports, snice) {
|
|
9
|
+
'use strict';
|
|
10
|
+
|
|
11
|
+
/******************************************************************************
|
|
12
|
+
Copyright (c) Microsoft Corporation.
|
|
13
|
+
|
|
14
|
+
Permission to use, copy, modify, and/or distribute this software for any
|
|
15
|
+
purpose with or without fee is hereby granted.
|
|
16
|
+
|
|
17
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
18
|
+
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
19
|
+
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
20
|
+
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
21
|
+
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
22
|
+
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
23
|
+
PERFORMANCE OF THIS SOFTWARE.
|
|
24
|
+
***************************************************************************** */
|
|
25
|
+
/* global Reflect, Promise, SuppressedError, Symbol, Iterator */
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
function __esDecorate(ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
|
|
29
|
+
function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
|
|
30
|
+
var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
|
|
31
|
+
var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
|
|
32
|
+
var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
|
|
33
|
+
var _, done = false;
|
|
34
|
+
for (var i = decorators.length - 1; i >= 0; i--) {
|
|
35
|
+
var context = {};
|
|
36
|
+
for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
|
|
37
|
+
for (var p in contextIn.access) context.access[p] = contextIn.access[p];
|
|
38
|
+
context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
|
|
39
|
+
var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
|
|
40
|
+
if (kind === "accessor") {
|
|
41
|
+
if (result === void 0) continue;
|
|
42
|
+
if (result === null || typeof result !== "object") throw new TypeError("Object expected");
|
|
43
|
+
if (_ = accept(result.get)) descriptor.get = _;
|
|
44
|
+
if (_ = accept(result.set)) descriptor.set = _;
|
|
45
|
+
if (_ = accept(result.init)) initializers.unshift(_);
|
|
46
|
+
}
|
|
47
|
+
else if (_ = accept(result)) {
|
|
48
|
+
if (kind === "field") initializers.unshift(_);
|
|
49
|
+
else descriptor[key] = _;
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
if (target) Object.defineProperty(target, contextIn.name, descriptor);
|
|
53
|
+
done = true;
|
|
54
|
+
}
|
|
55
|
+
function __runInitializers(thisArg, initializers, value) {
|
|
56
|
+
var useValue = arguments.length > 2;
|
|
57
|
+
for (var i = 0; i < initializers.length; i++) {
|
|
58
|
+
value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
|
|
59
|
+
}
|
|
60
|
+
return useValue ? value : void 0;
|
|
61
|
+
}
|
|
62
|
+
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
63
|
+
var e = new Error(message);
|
|
64
|
+
return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
var cssContent = ":host{display:block;font-family:var(--snice-font-family, -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif);contain:layout style paint;width:100%;--candlestick-bg:var(--snice-color-background, rgb(255 255 255));--candlestick-text:var(--snice-color-text, rgb(23 23 23));--candlestick-text-secondary:var(--snice-color-text-secondary, rgb(82 82 82));--candlestick-border:var(--snice-color-border, rgb(226 226 226));--candlestick-grid:var(--snice-color-border, rgb(226 226 226));--candlestick-bullish:var(--snice-candlestick-bullish, rgb(22 163 74));--candlestick-bearish:var(--snice-candlestick-bearish, rgb(220 38 38))}.candlestick{position:relative;background:var(--candlestick-bg);overflow:hidden;user-select:none}.candlestick__svg{display:block;width:100%;height:100%}.candlestick__grid-line{stroke:var(--candlestick-grid);stroke-width:1px;stroke-dasharray:2 4;opacity:.5}.candlestick__axis-label{fill:var(--candlestick-text-secondary);font-size:.6875rem;font-family:inherit}.candlestick__axis-label--x{text-anchor:middle;dominant-baseline:hanging}.candlestick__axis-label--y{text-anchor:end;dominant-baseline:central}.candlestick__body{cursor:pointer;transition:opacity var(--snice-transition-fast, 150ms) ease}.candlestick__body:hover{opacity:.8}.candlestick__wick{stroke-width:1px;pointer-events:none}.candlestick__volume{opacity:.3}.candlestick__crosshair-h,.candlestick__crosshair-v{stroke:var(--candlestick-text-secondary);stroke-width:1px;stroke-dasharray:4 3;pointer-events:none;opacity:.6}.candlestick__crosshair-label{fill:var(--candlestick-text);font-size:.625rem;font-family:inherit;pointer-events:none}.candlestick__crosshair-label-bg{fill:var(--candlestick-bg);stroke:var(--candlestick-border);stroke-width:1px;pointer-events:none}.candlestick__tooltip{position:absolute;background:var(--candlestick-bg);border:1px solid var(--candlestick-border);border-radius:4px;padding:var(--snice-spacing-xs,.5rem);font-size:.75rem;color:var(--candlestick-text);pointer-events:none;z-index:10;box-shadow:var(--snice-shadow-md,0 4px 6px -1px rgb(0 0 0 / .1),0 2px 4px -2px rgb(0 0 0 / .1));white-space:nowrap;opacity:0;transition:opacity var(--snice-transition-fast, 150ms) ease}.candlestick__tooltip--visible{opacity:1}.candlestick__tooltip-row{display:flex;justify-content:space-between;gap:var(--snice-spacing-sm,.75rem);line-height:var(--snice-line-height-normal, 1.5)}.candlestick__tooltip-label{color:var(--candlestick-text-secondary)}.candlestick__tooltip-value{font-weight:var(--snice-font-weight-semibold,600)}.candlestick__tooltip-value--bullish{color:var(--candlestick-bullish)}.candlestick__tooltip-value--bearish{color:var(--candlestick-bearish)}.candlestick__body--animated,.candlestick__wick--animated{animation:.4s ease-out both candlestick-appear}.candlestick__volume--animated{animation:.4s ease-out both volume-appear}@keyframes candlestick-appear{from{opacity:0;transform:scaleY(0)}to{opacity:1;transform:scaleY(1)}}@keyframes volume-appear{from{opacity:0}to{opacity:.3}}";
|
|
68
|
+
|
|
69
|
+
const PADDING = { top: 16, right: 64, bottom: 32, left: 8 };
|
|
70
|
+
const VOLUME_HEIGHT_RATIO = 0.2;
|
|
71
|
+
const MIN_CANDLE_WIDTH = 3;
|
|
72
|
+
const MAX_CANDLE_WIDTH = 24;
|
|
73
|
+
let SniceCandlestick = (() => {
|
|
74
|
+
let _classDecorators = [snice.element('snice-candlestick')];
|
|
75
|
+
let _classDescriptor;
|
|
76
|
+
let _classExtraInitializers = [];
|
|
77
|
+
let _classThis;
|
|
78
|
+
let _classSuper = HTMLElement;
|
|
79
|
+
let _instanceExtraInitializers = [];
|
|
80
|
+
let _data_decorators;
|
|
81
|
+
let _data_initializers = [];
|
|
82
|
+
let _data_extraInitializers = [];
|
|
83
|
+
let _showVolume_decorators;
|
|
84
|
+
let _showVolume_initializers = [];
|
|
85
|
+
let _showVolume_extraInitializers = [];
|
|
86
|
+
let _showGrid_decorators;
|
|
87
|
+
let _showGrid_initializers = [];
|
|
88
|
+
let _showGrid_extraInitializers = [];
|
|
89
|
+
let _showCrosshair_decorators;
|
|
90
|
+
let _showCrosshair_initializers = [];
|
|
91
|
+
let _showCrosshair_extraInitializers = [];
|
|
92
|
+
let _bullishColor_decorators;
|
|
93
|
+
let _bullishColor_initializers = [];
|
|
94
|
+
let _bullishColor_extraInitializers = [];
|
|
95
|
+
let _bearishColor_decorators;
|
|
96
|
+
let _bearishColor_initializers = [];
|
|
97
|
+
let _bearishColor_extraInitializers = [];
|
|
98
|
+
let _timeFormat_decorators;
|
|
99
|
+
let _timeFormat_initializers = [];
|
|
100
|
+
let _timeFormat_extraInitializers = [];
|
|
101
|
+
let _yAxisFormat_decorators;
|
|
102
|
+
let _yAxisFormat_initializers = [];
|
|
103
|
+
let _yAxisFormat_extraInitializers = [];
|
|
104
|
+
let _zoomEnabled_decorators;
|
|
105
|
+
let _zoomEnabled_initializers = [];
|
|
106
|
+
let _zoomEnabled_extraInitializers = [];
|
|
107
|
+
let _animation_decorators;
|
|
108
|
+
let _animation_initializers = [];
|
|
109
|
+
let _animation_extraInitializers = [];
|
|
110
|
+
let _containerEl_decorators;
|
|
111
|
+
let _containerEl_initializers = [];
|
|
112
|
+
let _containerEl_extraInitializers = [];
|
|
113
|
+
let _svgEl_decorators;
|
|
114
|
+
let _svgEl_initializers = [];
|
|
115
|
+
let _svgEl_extraInitializers = [];
|
|
116
|
+
let _chartContentEl_decorators;
|
|
117
|
+
let _chartContentEl_initializers = [];
|
|
118
|
+
let _chartContentEl_extraInitializers = [];
|
|
119
|
+
let _crosshairGroupEl_decorators;
|
|
120
|
+
let _crosshairGroupEl_initializers = [];
|
|
121
|
+
let _crosshairGroupEl_extraInitializers = [];
|
|
122
|
+
let _tooltipEl_decorators;
|
|
123
|
+
let _tooltipEl_initializers = [];
|
|
124
|
+
let _tooltipEl_extraInitializers = [];
|
|
125
|
+
let _emitCandleClick_decorators;
|
|
126
|
+
let _emitCandleHover_decorators;
|
|
127
|
+
let _emitCrosshairMove_decorators;
|
|
128
|
+
let _init_decorators;
|
|
129
|
+
let _cleanup_decorators;
|
|
130
|
+
let _onDataChange_decorators;
|
|
131
|
+
let _onDisplayChange_decorators;
|
|
132
|
+
let _renderContent_decorators;
|
|
133
|
+
let _componentStyles_decorators;
|
|
134
|
+
(class extends _classSuper {
|
|
135
|
+
static { _classThis = this; }
|
|
136
|
+
constructor() {
|
|
137
|
+
super(...arguments);
|
|
138
|
+
this.data = (__runInitializers(this, _instanceExtraInitializers), __runInitializers(this, _data_initializers, []));
|
|
139
|
+
this.showVolume = (__runInitializers(this, _data_extraInitializers), __runInitializers(this, _showVolume_initializers, false));
|
|
140
|
+
this.showGrid = (__runInitializers(this, _showVolume_extraInitializers), __runInitializers(this, _showGrid_initializers, true));
|
|
141
|
+
this.showCrosshair = (__runInitializers(this, _showGrid_extraInitializers), __runInitializers(this, _showCrosshair_initializers, true));
|
|
142
|
+
this.bullishColor = (__runInitializers(this, _showCrosshair_extraInitializers), __runInitializers(this, _bullishColor_initializers, ''));
|
|
143
|
+
this.bearishColor = (__runInitializers(this, _bullishColor_extraInitializers), __runInitializers(this, _bearishColor_initializers, ''));
|
|
144
|
+
this.timeFormat = (__runInitializers(this, _bearishColor_extraInitializers), __runInitializers(this, _timeFormat_initializers, 'auto'));
|
|
145
|
+
this.yAxisFormat = (__runInitializers(this, _timeFormat_extraInitializers), __runInitializers(this, _yAxisFormat_initializers, 'number'));
|
|
146
|
+
this.zoomEnabled = (__runInitializers(this, _yAxisFormat_extraInitializers), __runInitializers(this, _zoomEnabled_initializers, true));
|
|
147
|
+
this.animation = (__runInitializers(this, _zoomEnabled_extraInitializers), __runInitializers(this, _animation_initializers, true));
|
|
148
|
+
this.containerEl = (__runInitializers(this, _animation_extraInitializers), __runInitializers(this, _containerEl_initializers, void 0));
|
|
149
|
+
this.svgEl = (__runInitializers(this, _containerEl_extraInitializers), __runInitializers(this, _svgEl_initializers, void 0));
|
|
150
|
+
this.chartContentEl = (__runInitializers(this, _svgEl_extraInitializers), __runInitializers(this, _chartContentEl_initializers, void 0));
|
|
151
|
+
this.crosshairGroupEl = (__runInitializers(this, _chartContentEl_extraInitializers), __runInitializers(this, _crosshairGroupEl_initializers, void 0));
|
|
152
|
+
this.tooltipEl = (__runInitializers(this, _crosshairGroupEl_extraInitializers), __runInitializers(this, _tooltipEl_initializers, void 0));
|
|
153
|
+
// Internal state — plain fields, no @property
|
|
154
|
+
this.viewStart = (__runInitializers(this, _tooltipEl_extraInitializers), 0);
|
|
155
|
+
this.viewEnd = 0;
|
|
156
|
+
this.mouseX = -1;
|
|
157
|
+
this.mouseY = -1;
|
|
158
|
+
this.isDragging = false;
|
|
159
|
+
this.dragStartX = 0;
|
|
160
|
+
this.dragStartViewStart = 0;
|
|
161
|
+
this.dragStartViewEnd = 0;
|
|
162
|
+
this.resizeObserver = null;
|
|
163
|
+
this.svgWidth = 600;
|
|
164
|
+
this.svgHeight = 400;
|
|
165
|
+
this.lastDataLength = 0;
|
|
166
|
+
this.cachedData = [];
|
|
167
|
+
this.rafId = 0;
|
|
168
|
+
this.animateNext = true;
|
|
169
|
+
this.handleMouseMove = (e) => {
|
|
170
|
+
const svg = this.svgEl;
|
|
171
|
+
if (!svg)
|
|
172
|
+
return;
|
|
173
|
+
const ctm = svg.getScreenCTM();
|
|
174
|
+
if (ctm) {
|
|
175
|
+
const pt = new DOMPoint(e.clientX, e.clientY).matrixTransform(ctm.inverse());
|
|
176
|
+
this.mouseX = pt.x;
|
|
177
|
+
this.mouseY = pt.y;
|
|
178
|
+
}
|
|
179
|
+
if (this.isDragging && this.zoomEnabled) {
|
|
180
|
+
const dx = e.clientX - this.dragStartX;
|
|
181
|
+
const area = this.chartArea;
|
|
182
|
+
const viewSize = this.dragStartViewEnd - this.dragStartViewStart;
|
|
183
|
+
const candlesPerPx = viewSize / area.width;
|
|
184
|
+
const shift = Math.round(-dx * candlesPerPx);
|
|
185
|
+
let newStart = this.dragStartViewStart + shift;
|
|
186
|
+
let newEnd = this.dragStartViewEnd + shift;
|
|
187
|
+
if (newStart < 0) {
|
|
188
|
+
newStart = 0;
|
|
189
|
+
newEnd = viewSize;
|
|
190
|
+
}
|
|
191
|
+
if (newEnd > this.cachedData.length) {
|
|
192
|
+
newEnd = this.cachedData.length;
|
|
193
|
+
newStart = this.cachedData.length - viewSize;
|
|
194
|
+
}
|
|
195
|
+
const vs = Math.max(0, newStart);
|
|
196
|
+
const ve = Math.min(this.cachedData.length, newEnd);
|
|
197
|
+
if (vs !== this.viewStart || ve !== this.viewEnd) {
|
|
198
|
+
this.viewStart = vs;
|
|
199
|
+
this.viewEnd = ve;
|
|
200
|
+
this.rebuildChart();
|
|
201
|
+
return;
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
if (this.showCrosshair) {
|
|
205
|
+
const idx = this.xToIndex(this.mouseX);
|
|
206
|
+
const candle = this.visibleData[idx];
|
|
207
|
+
if (candle) {
|
|
208
|
+
const price = this.yToPrice(this.mouseY);
|
|
209
|
+
this.emitCrosshairMove(price, this.formatDate(candle.date), this.mouseX, this.mouseY);
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
// Only update crosshair + tooltip via direct DOM manipulation — no re-render
|
|
213
|
+
if (this.rafId)
|
|
214
|
+
cancelAnimationFrame(this.rafId);
|
|
215
|
+
this.rafId = requestAnimationFrame(() => {
|
|
216
|
+
this.updateCrosshairDOM();
|
|
217
|
+
this.updateTooltipDOM();
|
|
218
|
+
});
|
|
219
|
+
};
|
|
220
|
+
this.handleMouseLeave = () => {
|
|
221
|
+
this.mouseX = -1;
|
|
222
|
+
this.mouseY = -1;
|
|
223
|
+
this.isDragging = false;
|
|
224
|
+
this.updateCrosshairDOM();
|
|
225
|
+
this.updateTooltipDOM();
|
|
226
|
+
};
|
|
227
|
+
this.handleMouseDown = (e) => {
|
|
228
|
+
if (!this.zoomEnabled)
|
|
229
|
+
return;
|
|
230
|
+
this.isDragging = true;
|
|
231
|
+
this.dragStartX = e.clientX;
|
|
232
|
+
this.dragStartViewStart = this.viewStart;
|
|
233
|
+
this.dragStartViewEnd = this.viewEnd;
|
|
234
|
+
};
|
|
235
|
+
this.handleMouseUp = () => {
|
|
236
|
+
this.isDragging = false;
|
|
237
|
+
};
|
|
238
|
+
this.handleWheel = (e) => {
|
|
239
|
+
if (!this.zoomEnabled)
|
|
240
|
+
return;
|
|
241
|
+
e.preventDefault();
|
|
242
|
+
const viewSize = this.viewEnd - this.viewStart;
|
|
243
|
+
const zoomFactor = e.deltaY > 0 ? 1.1 : 0.9;
|
|
244
|
+
let newSize = Math.round(viewSize * zoomFactor);
|
|
245
|
+
newSize = Math.max(10, Math.min(this.cachedData.length, newSize));
|
|
246
|
+
const area = this.chartArea;
|
|
247
|
+
const mouseRatio = (this.mouseX - area.x) / area.width;
|
|
248
|
+
const center = this.viewStart + viewSize * mouseRatio;
|
|
249
|
+
let newStart = Math.round(center - newSize * mouseRatio);
|
|
250
|
+
let newEnd = newStart + newSize;
|
|
251
|
+
if (newStart < 0) {
|
|
252
|
+
newStart = 0;
|
|
253
|
+
newEnd = newSize;
|
|
254
|
+
}
|
|
255
|
+
if (newEnd > this.cachedData.length) {
|
|
256
|
+
newEnd = this.cachedData.length;
|
|
257
|
+
newStart = this.cachedData.length - newSize;
|
|
258
|
+
}
|
|
259
|
+
this.viewStart = Math.max(0, newStart);
|
|
260
|
+
this.viewEnd = Math.min(this.cachedData.length, newEnd);
|
|
261
|
+
this.rebuildChart();
|
|
262
|
+
};
|
|
263
|
+
}
|
|
264
|
+
static {
|
|
265
|
+
const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
|
|
266
|
+
_data_decorators = [snice.property({ type: Array, attribute: false })];
|
|
267
|
+
_showVolume_decorators = [snice.property({ type: Boolean })];
|
|
268
|
+
_showGrid_decorators = [snice.property({ type: Boolean })];
|
|
269
|
+
_showCrosshair_decorators = [snice.property({ type: Boolean })];
|
|
270
|
+
_bullishColor_decorators = [snice.property()];
|
|
271
|
+
_bearishColor_decorators = [snice.property()];
|
|
272
|
+
_timeFormat_decorators = [snice.property()];
|
|
273
|
+
_yAxisFormat_decorators = [snice.property()];
|
|
274
|
+
_zoomEnabled_decorators = [snice.property({ type: Boolean })];
|
|
275
|
+
_animation_decorators = [snice.property({ type: Boolean })];
|
|
276
|
+
_containerEl_decorators = [snice.query('.candlestick')];
|
|
277
|
+
_svgEl_decorators = [snice.query('.candlestick__svg')];
|
|
278
|
+
_chartContentEl_decorators = [snice.query('.candlestick__chart-content')];
|
|
279
|
+
_crosshairGroupEl_decorators = [snice.query('.candlestick__crosshair-group')];
|
|
280
|
+
_tooltipEl_decorators = [snice.query('.candlestick__tooltip')];
|
|
281
|
+
_emitCandleClick_decorators = [snice.dispatch('candle-click', { bubbles: true, composed: true })];
|
|
282
|
+
_emitCandleHover_decorators = [snice.dispatch('candle-hover', { bubbles: true, composed: true })];
|
|
283
|
+
_emitCrosshairMove_decorators = [snice.dispatch('crosshair-move', { bubbles: true, composed: true })];
|
|
284
|
+
_init_decorators = [snice.ready()];
|
|
285
|
+
_cleanup_decorators = [snice.dispose()];
|
|
286
|
+
_onDataChange_decorators = [snice.watch('data')];
|
|
287
|
+
_onDisplayChange_decorators = [snice.watch('showVolume', 'showGrid', 'bullishColor', 'bearishColor', 'timeFormat', 'yAxisFormat', 'animation')];
|
|
288
|
+
_renderContent_decorators = [snice.render({ once: true })];
|
|
289
|
+
_componentStyles_decorators = [snice.styles()];
|
|
290
|
+
__esDecorate(this, null, _emitCandleClick_decorators, { kind: "method", name: "emitCandleClick", static: false, private: false, access: { has: obj => "emitCandleClick" in obj, get: obj => obj.emitCandleClick }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
291
|
+
__esDecorate(this, null, _emitCandleHover_decorators, { kind: "method", name: "emitCandleHover", static: false, private: false, access: { has: obj => "emitCandleHover" in obj, get: obj => obj.emitCandleHover }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
292
|
+
__esDecorate(this, null, _emitCrosshairMove_decorators, { kind: "method", name: "emitCrosshairMove", static: false, private: false, access: { has: obj => "emitCrosshairMove" in obj, get: obj => obj.emitCrosshairMove }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
293
|
+
__esDecorate(this, null, _init_decorators, { kind: "method", name: "init", static: false, private: false, access: { has: obj => "init" in obj, get: obj => obj.init }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
294
|
+
__esDecorate(this, null, _cleanup_decorators, { kind: "method", name: "cleanup", static: false, private: false, access: { has: obj => "cleanup" in obj, get: obj => obj.cleanup }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
295
|
+
__esDecorate(this, null, _onDataChange_decorators, { kind: "method", name: "onDataChange", static: false, private: false, access: { has: obj => "onDataChange" in obj, get: obj => obj.onDataChange }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
296
|
+
__esDecorate(this, null, _onDisplayChange_decorators, { kind: "method", name: "onDisplayChange", static: false, private: false, access: { has: obj => "onDisplayChange" in obj, get: obj => obj.onDisplayChange }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
297
|
+
__esDecorate(this, null, _renderContent_decorators, { kind: "method", name: "renderContent", static: false, private: false, access: { has: obj => "renderContent" in obj, get: obj => obj.renderContent }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
298
|
+
__esDecorate(this, null, _componentStyles_decorators, { kind: "method", name: "componentStyles", static: false, private: false, access: { has: obj => "componentStyles" in obj, get: obj => obj.componentStyles }, metadata: _metadata }, null, _instanceExtraInitializers);
|
|
299
|
+
__esDecorate(null, null, _data_decorators, { kind: "field", name: "data", static: false, private: false, access: { has: obj => "data" in obj, get: obj => obj.data, set: (obj, value) => { obj.data = value; } }, metadata: _metadata }, _data_initializers, _data_extraInitializers);
|
|
300
|
+
__esDecorate(null, null, _showVolume_decorators, { kind: "field", name: "showVolume", static: false, private: false, access: { has: obj => "showVolume" in obj, get: obj => obj.showVolume, set: (obj, value) => { obj.showVolume = value; } }, metadata: _metadata }, _showVolume_initializers, _showVolume_extraInitializers);
|
|
301
|
+
__esDecorate(null, null, _showGrid_decorators, { kind: "field", name: "showGrid", static: false, private: false, access: { has: obj => "showGrid" in obj, get: obj => obj.showGrid, set: (obj, value) => { obj.showGrid = value; } }, metadata: _metadata }, _showGrid_initializers, _showGrid_extraInitializers);
|
|
302
|
+
__esDecorate(null, null, _showCrosshair_decorators, { kind: "field", name: "showCrosshair", static: false, private: false, access: { has: obj => "showCrosshair" in obj, get: obj => obj.showCrosshair, set: (obj, value) => { obj.showCrosshair = value; } }, metadata: _metadata }, _showCrosshair_initializers, _showCrosshair_extraInitializers);
|
|
303
|
+
__esDecorate(null, null, _bullishColor_decorators, { kind: "field", name: "bullishColor", static: false, private: false, access: { has: obj => "bullishColor" in obj, get: obj => obj.bullishColor, set: (obj, value) => { obj.bullishColor = value; } }, metadata: _metadata }, _bullishColor_initializers, _bullishColor_extraInitializers);
|
|
304
|
+
__esDecorate(null, null, _bearishColor_decorators, { kind: "field", name: "bearishColor", static: false, private: false, access: { has: obj => "bearishColor" in obj, get: obj => obj.bearishColor, set: (obj, value) => { obj.bearishColor = value; } }, metadata: _metadata }, _bearishColor_initializers, _bearishColor_extraInitializers);
|
|
305
|
+
__esDecorate(null, null, _timeFormat_decorators, { kind: "field", name: "timeFormat", static: false, private: false, access: { has: obj => "timeFormat" in obj, get: obj => obj.timeFormat, set: (obj, value) => { obj.timeFormat = value; } }, metadata: _metadata }, _timeFormat_initializers, _timeFormat_extraInitializers);
|
|
306
|
+
__esDecorate(null, null, _yAxisFormat_decorators, { kind: "field", name: "yAxisFormat", static: false, private: false, access: { has: obj => "yAxisFormat" in obj, get: obj => obj.yAxisFormat, set: (obj, value) => { obj.yAxisFormat = value; } }, metadata: _metadata }, _yAxisFormat_initializers, _yAxisFormat_extraInitializers);
|
|
307
|
+
__esDecorate(null, null, _zoomEnabled_decorators, { kind: "field", name: "zoomEnabled", static: false, private: false, access: { has: obj => "zoomEnabled" in obj, get: obj => obj.zoomEnabled, set: (obj, value) => { obj.zoomEnabled = value; } }, metadata: _metadata }, _zoomEnabled_initializers, _zoomEnabled_extraInitializers);
|
|
308
|
+
__esDecorate(null, null, _animation_decorators, { kind: "field", name: "animation", static: false, private: false, access: { has: obj => "animation" in obj, get: obj => obj.animation, set: (obj, value) => { obj.animation = value; } }, metadata: _metadata }, _animation_initializers, _animation_extraInitializers);
|
|
309
|
+
__esDecorate(null, null, _containerEl_decorators, { kind: "field", name: "containerEl", static: false, private: false, access: { has: obj => "containerEl" in obj, get: obj => obj.containerEl, set: (obj, value) => { obj.containerEl = value; } }, metadata: _metadata }, _containerEl_initializers, _containerEl_extraInitializers);
|
|
310
|
+
__esDecorate(null, null, _svgEl_decorators, { kind: "field", name: "svgEl", static: false, private: false, access: { has: obj => "svgEl" in obj, get: obj => obj.svgEl, set: (obj, value) => { obj.svgEl = value; } }, metadata: _metadata }, _svgEl_initializers, _svgEl_extraInitializers);
|
|
311
|
+
__esDecorate(null, null, _chartContentEl_decorators, { kind: "field", name: "chartContentEl", static: false, private: false, access: { has: obj => "chartContentEl" in obj, get: obj => obj.chartContentEl, set: (obj, value) => { obj.chartContentEl = value; } }, metadata: _metadata }, _chartContentEl_initializers, _chartContentEl_extraInitializers);
|
|
312
|
+
__esDecorate(null, null, _crosshairGroupEl_decorators, { kind: "field", name: "crosshairGroupEl", static: false, private: false, access: { has: obj => "crosshairGroupEl" in obj, get: obj => obj.crosshairGroupEl, set: (obj, value) => { obj.crosshairGroupEl = value; } }, metadata: _metadata }, _crosshairGroupEl_initializers, _crosshairGroupEl_extraInitializers);
|
|
313
|
+
__esDecorate(null, null, _tooltipEl_decorators, { kind: "field", name: "tooltipEl", static: false, private: false, access: { has: obj => "tooltipEl" in obj, get: obj => obj.tooltipEl, set: (obj, value) => { obj.tooltipEl = value; } }, metadata: _metadata }, _tooltipEl_initializers, _tooltipEl_extraInitializers);
|
|
314
|
+
__esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
|
|
315
|
+
_classThis = _classDescriptor.value;
|
|
316
|
+
if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
|
|
317
|
+
__runInitializers(_classThis, _classExtraInitializers);
|
|
318
|
+
}
|
|
319
|
+
emitCandleClick(candle, index) {
|
|
320
|
+
return { candle, index };
|
|
321
|
+
}
|
|
322
|
+
emitCandleHover(candle, index) {
|
|
323
|
+
return { candle, index };
|
|
324
|
+
}
|
|
325
|
+
emitCrosshairMove(price, date, x, y) {
|
|
326
|
+
return { price, date, x, y };
|
|
327
|
+
}
|
|
328
|
+
init() {
|
|
329
|
+
this.cachedData = this.data;
|
|
330
|
+
this.viewEnd = this.data.length;
|
|
331
|
+
this.viewStart = Math.max(0, this.viewEnd - 80);
|
|
332
|
+
this.resizeObserver = new ResizeObserver(() => {
|
|
333
|
+
this.measureSize();
|
|
334
|
+
this.rebuildChart();
|
|
335
|
+
});
|
|
336
|
+
if (this.containerEl) {
|
|
337
|
+
this.resizeObserver.observe(this.containerEl);
|
|
338
|
+
}
|
|
339
|
+
this.measureSize();
|
|
340
|
+
this.rebuildChart();
|
|
341
|
+
}
|
|
342
|
+
cleanup() {
|
|
343
|
+
this.resizeObserver?.disconnect();
|
|
344
|
+
if (this.rafId)
|
|
345
|
+
cancelAnimationFrame(this.rafId);
|
|
346
|
+
}
|
|
347
|
+
onDataChange() {
|
|
348
|
+
this.cachedData = this.data;
|
|
349
|
+
const dataLen = this.cachedData.length;
|
|
350
|
+
if (dataLen > 0 && dataLen !== this.lastDataLength) {
|
|
351
|
+
this.lastDataLength = dataLen;
|
|
352
|
+
this.viewEnd = dataLen;
|
|
353
|
+
this.viewStart = Math.max(0, dataLen - 80);
|
|
354
|
+
}
|
|
355
|
+
this.animateNext = true;
|
|
356
|
+
this.rebuildChart();
|
|
357
|
+
}
|
|
358
|
+
onDisplayChange() {
|
|
359
|
+
this.rebuildChart();
|
|
360
|
+
}
|
|
361
|
+
measureSize() {
|
|
362
|
+
if (!this.containerEl)
|
|
363
|
+
return;
|
|
364
|
+
const rect = this.containerEl.getBoundingClientRect();
|
|
365
|
+
if (rect.width > 0)
|
|
366
|
+
this.svgWidth = rect.width;
|
|
367
|
+
if (rect.height > 0)
|
|
368
|
+
this.svgHeight = rect.height;
|
|
369
|
+
}
|
|
370
|
+
get visibleData() {
|
|
371
|
+
return this.cachedData.slice(this.viewStart, this.viewEnd);
|
|
372
|
+
}
|
|
373
|
+
get chartArea() {
|
|
374
|
+
const volumeSpace = this.showVolume ? this.svgHeight * VOLUME_HEIGHT_RATIO : 0;
|
|
375
|
+
return {
|
|
376
|
+
x: PADDING.left,
|
|
377
|
+
y: PADDING.top,
|
|
378
|
+
width: this.svgWidth - PADDING.left - PADDING.right,
|
|
379
|
+
height: this.svgHeight - PADDING.top - PADDING.bottom - volumeSpace,
|
|
380
|
+
volumeY: this.svgHeight - PADDING.bottom - volumeSpace,
|
|
381
|
+
volumeHeight: volumeSpace
|
|
382
|
+
};
|
|
383
|
+
}
|
|
384
|
+
get priceRange() {
|
|
385
|
+
const visible = this.visibleData;
|
|
386
|
+
if (visible.length === 0)
|
|
387
|
+
return { min: 0, max: 100 };
|
|
388
|
+
let min = Infinity;
|
|
389
|
+
let max = -Infinity;
|
|
390
|
+
for (const d of visible) {
|
|
391
|
+
if (d.low < min)
|
|
392
|
+
min = d.low;
|
|
393
|
+
if (d.high > max)
|
|
394
|
+
max = d.high;
|
|
395
|
+
}
|
|
396
|
+
const padding = (max - min) * 0.05 || 1;
|
|
397
|
+
return { min: min - padding, max: max + padding };
|
|
398
|
+
}
|
|
399
|
+
get volumeMax() {
|
|
400
|
+
const visible = this.visibleData;
|
|
401
|
+
if (visible.length === 0)
|
|
402
|
+
return 1;
|
|
403
|
+
return Math.max(...visible.map(d => d.volume || 0)) || 1;
|
|
404
|
+
}
|
|
405
|
+
get candleWidth() {
|
|
406
|
+
const area = this.chartArea;
|
|
407
|
+
const count = this.visibleData.length || 1;
|
|
408
|
+
const totalWidth = area.width / count;
|
|
409
|
+
const bodyWidth = totalWidth * 0.7;
|
|
410
|
+
return Math.max(MIN_CANDLE_WIDTH, Math.min(MAX_CANDLE_WIDTH, bodyWidth));
|
|
411
|
+
}
|
|
412
|
+
priceToY(price) {
|
|
413
|
+
const { min, max } = this.priceRange;
|
|
414
|
+
const area = this.chartArea;
|
|
415
|
+
const ratio = (price - min) / (max - min);
|
|
416
|
+
return area.y + area.height * (1 - ratio);
|
|
417
|
+
}
|
|
418
|
+
yToPrice(y) {
|
|
419
|
+
const { min, max } = this.priceRange;
|
|
420
|
+
const area = this.chartArea;
|
|
421
|
+
const ratio = 1 - (y - area.y) / area.height;
|
|
422
|
+
return min + ratio * (max - min);
|
|
423
|
+
}
|
|
424
|
+
indexToX(index) {
|
|
425
|
+
const area = this.chartArea;
|
|
426
|
+
const count = this.visibleData.length || 1;
|
|
427
|
+
const step = area.width / count;
|
|
428
|
+
return area.x + step * index + step / 2;
|
|
429
|
+
}
|
|
430
|
+
xToIndex(x) {
|
|
431
|
+
const area = this.chartArea;
|
|
432
|
+
const count = this.visibleData.length || 1;
|
|
433
|
+
const step = area.width / count;
|
|
434
|
+
const idx = Math.floor((x - area.x) / step);
|
|
435
|
+
return Math.max(0, Math.min(count - 1, idx));
|
|
436
|
+
}
|
|
437
|
+
formatPrice(price) {
|
|
438
|
+
switch (this.yAxisFormat) {
|
|
439
|
+
case 'currency':
|
|
440
|
+
return price.toLocaleString(undefined, { minimumFractionDigits: 2, maximumFractionDigits: 2 });
|
|
441
|
+
case 'percent':
|
|
442
|
+
return price.toFixed(2) + '%';
|
|
443
|
+
default:
|
|
444
|
+
return price >= 1000 ? price.toLocaleString(undefined, { maximumFractionDigits: 2 }) : price.toFixed(2);
|
|
445
|
+
}
|
|
446
|
+
}
|
|
447
|
+
formatDate(dateVal) {
|
|
448
|
+
const d = dateVal instanceof Date ? dateVal : new Date(dateVal);
|
|
449
|
+
if (isNaN(d.getTime()))
|
|
450
|
+
return String(dateVal);
|
|
451
|
+
const fmt = this.timeFormat;
|
|
452
|
+
if (fmt === 'date')
|
|
453
|
+
return d.toLocaleDateString(undefined, { month: 'short', day: 'numeric' });
|
|
454
|
+
if (fmt === 'time')
|
|
455
|
+
return d.toLocaleTimeString(undefined, { hour: '2-digit', minute: '2-digit' });
|
|
456
|
+
if (fmt === 'datetime')
|
|
457
|
+
return d.toLocaleString(undefined, { month: 'short', day: 'numeric', hour: '2-digit', minute: '2-digit' });
|
|
458
|
+
if (fmt === 'month')
|
|
459
|
+
return d.toLocaleDateString(undefined, { month: 'short', year: '2-digit' });
|
|
460
|
+
if (fmt === 'year')
|
|
461
|
+
return d.getFullYear().toString();
|
|
462
|
+
// auto
|
|
463
|
+
return d.toLocaleDateString(undefined, { month: 'short', day: 'numeric' });
|
|
464
|
+
}
|
|
465
|
+
/** Rebuild the static chart SVG (candles, grid, axes, volume). Does NOT include crosshair. */
|
|
466
|
+
rebuildChart() {
|
|
467
|
+
if (!this.chartContentEl || !this.svgEl) {
|
|
468
|
+
requestAnimationFrame(() => this.rebuildChart());
|
|
469
|
+
return;
|
|
470
|
+
}
|
|
471
|
+
const visible = this.visibleData;
|
|
472
|
+
let svg = '';
|
|
473
|
+
if (visible.length > 0) {
|
|
474
|
+
svg += this.buildGridLines();
|
|
475
|
+
svg += this.buildYAxis();
|
|
476
|
+
svg += this.buildXAxis();
|
|
477
|
+
svg += this.buildVolumeBars();
|
|
478
|
+
svg += this.buildCandles();
|
|
479
|
+
}
|
|
480
|
+
this.chartContentEl.innerHTML = svg;
|
|
481
|
+
// Update SVG viewBox
|
|
482
|
+
this.svgEl.setAttribute('viewBox', `0 0 ${this.svgWidth} ${this.svgHeight}`);
|
|
483
|
+
this.svgEl.setAttribute('aria-label', `Candlestick chart with ${this.cachedData.length} data points`);
|
|
484
|
+
// Update container height
|
|
485
|
+
if (this.containerEl) {
|
|
486
|
+
this.containerEl.style.height = `${this.svgHeight}px`;
|
|
487
|
+
}
|
|
488
|
+
// Consume animation flag after building candles
|
|
489
|
+
this.animateNext = false;
|
|
490
|
+
// Update crosshair after chart rebuild
|
|
491
|
+
this.updateCrosshairDOM();
|
|
492
|
+
this.updateTooltipDOM();
|
|
493
|
+
}
|
|
494
|
+
resetZoom() {
|
|
495
|
+
this.viewStart = 0;
|
|
496
|
+
this.viewEnd = this.cachedData.length;
|
|
497
|
+
this.rebuildChart();
|
|
498
|
+
}
|
|
499
|
+
zoomTo(startIndex, endIndex) {
|
|
500
|
+
this.viewStart = Math.max(0, startIndex);
|
|
501
|
+
this.viewEnd = Math.min(this.cachedData.length, endIndex);
|
|
502
|
+
this.rebuildChart();
|
|
503
|
+
}
|
|
504
|
+
/** Update crosshair overlay via direct DOM manipulation — no re-render needed */
|
|
505
|
+
updateCrosshairDOM() {
|
|
506
|
+
const group = this.crosshairGroupEl;
|
|
507
|
+
if (!group)
|
|
508
|
+
return;
|
|
509
|
+
if (!this.showCrosshair || this.mouseX < 0 || this.mouseY < 0) {
|
|
510
|
+
group.innerHTML = '';
|
|
511
|
+
return;
|
|
512
|
+
}
|
|
513
|
+
const area = this.chartArea;
|
|
514
|
+
const totalChartBottom = area.y + area.height + area.volumeHeight;
|
|
515
|
+
const isInChart = this.mouseX >= area.x && this.mouseX <= area.x + area.width
|
|
516
|
+
&& this.mouseY >= area.y && this.mouseY <= totalChartBottom;
|
|
517
|
+
if (!isInChart) {
|
|
518
|
+
group.innerHTML = '';
|
|
519
|
+
return;
|
|
520
|
+
}
|
|
521
|
+
const price = this.yToPrice(this.mouseY);
|
|
522
|
+
const idx = this.xToIndex(this.mouseX);
|
|
523
|
+
const candle = this.visibleData[idx];
|
|
524
|
+
const snapX = this.indexToX(idx);
|
|
525
|
+
let parts = '';
|
|
526
|
+
// Horizontal line
|
|
527
|
+
parts += `<line class="candlestick__crosshair-h" x1="${area.x}" y1="${this.mouseY}" x2="${area.x + area.width}" y2="${this.mouseY}" />`;
|
|
528
|
+
// Vertical line
|
|
529
|
+
parts += `<line class="candlestick__crosshair-v" x1="${snapX}" y1="${area.y}" x2="${snapX}" y2="${totalChartBottom}" />`;
|
|
530
|
+
// Price label
|
|
531
|
+
const priceLabel = this.formatPrice(price);
|
|
532
|
+
const labelX = this.svgWidth - PADDING.right + 4;
|
|
533
|
+
parts += `<rect class="candlestick__crosshair-label-bg" x="${labelX}" y="${this.mouseY - 9}" width="${PADDING.right - 8}" height="18" rx="2" />`;
|
|
534
|
+
parts += `<text class="candlestick__crosshair-label" x="${labelX + 4}" y="${this.mouseY + 4}">${priceLabel}</text>`;
|
|
535
|
+
// Date label
|
|
536
|
+
if (candle) {
|
|
537
|
+
const dateLabel = this.formatDate(candle.date);
|
|
538
|
+
const dateLabelY = totalChartBottom + 4;
|
|
539
|
+
parts += `<rect class="candlestick__crosshair-label-bg" x="${snapX - 36}" y="${dateLabelY}" width="72" height="18" rx="2" />`;
|
|
540
|
+
parts += `<text class="candlestick__crosshair-label" x="${snapX}" y="${dateLabelY + 13}" text-anchor="middle">${dateLabel}</text>`;
|
|
541
|
+
}
|
|
542
|
+
group.innerHTML = parts;
|
|
543
|
+
}
|
|
544
|
+
/** Update tooltip via direct DOM manipulation — no re-render needed */
|
|
545
|
+
updateTooltipDOM() {
|
|
546
|
+
const tooltip = this.tooltipEl;
|
|
547
|
+
if (!tooltip)
|
|
548
|
+
return;
|
|
549
|
+
const tooltipCandle = this.getTooltipCandle();
|
|
550
|
+
const hasTooltip = tooltipCandle !== null;
|
|
551
|
+
if (!hasTooltip) {
|
|
552
|
+
tooltip.classList.remove('candlestick__tooltip--visible');
|
|
553
|
+
return;
|
|
554
|
+
}
|
|
555
|
+
const isBullish = tooltipCandle.close >= tooltipCandle.open;
|
|
556
|
+
const showVolumeInTooltip = this.showVolume && tooltipCandle.volume !== undefined;
|
|
557
|
+
const tooltipIdx = this.xToIndex(this.mouseX);
|
|
558
|
+
const tooltipX = this.indexToX(tooltipIdx);
|
|
559
|
+
const tooltipLeft = tooltipX + this.candleWidth + 12;
|
|
560
|
+
const tooltipFlip = tooltipLeft + 160 > this.svgWidth;
|
|
561
|
+
const tooltipFinalLeft = tooltipFlip ? tooltipX - this.candleWidth - 170 : tooltipLeft;
|
|
562
|
+
tooltip.style.left = `${Math.max(0, tooltipFinalLeft)}px`;
|
|
563
|
+
tooltip.style.top = `${PADDING.top}px`;
|
|
564
|
+
tooltip.classList.add('candlestick__tooltip--visible');
|
|
565
|
+
let rows = '';
|
|
566
|
+
rows += `<div class="candlestick__tooltip-row"><span class="candlestick__tooltip-label">Date</span><span class="candlestick__tooltip-value">${this.formatDate(tooltipCandle.date)}</span></div>`;
|
|
567
|
+
rows += `<div class="candlestick__tooltip-row"><span class="candlestick__tooltip-label">Open</span><span class="candlestick__tooltip-value">${this.formatPrice(tooltipCandle.open)}</span></div>`;
|
|
568
|
+
rows += `<div class="candlestick__tooltip-row"><span class="candlestick__tooltip-label">High</span><span class="candlestick__tooltip-value">${this.formatPrice(tooltipCandle.high)}</span></div>`;
|
|
569
|
+
rows += `<div class="candlestick__tooltip-row"><span class="candlestick__tooltip-label">Low</span><span class="candlestick__tooltip-value">${this.formatPrice(tooltipCandle.low)}</span></div>`;
|
|
570
|
+
const closeClass = isBullish ? 'candlestick__tooltip-value--bullish' : 'candlestick__tooltip-value--bearish';
|
|
571
|
+
rows += `<div class="candlestick__tooltip-row"><span class="candlestick__tooltip-label">Close</span><span class="candlestick__tooltip-value ${closeClass}">${this.formatPrice(tooltipCandle.close)}</span></div>`;
|
|
572
|
+
if (showVolumeInTooltip) {
|
|
573
|
+
rows += `<div class="candlestick__tooltip-row"><span class="candlestick__tooltip-label">Volume</span><span class="candlestick__tooltip-value">${tooltipCandle.volume?.toLocaleString() || '0'}</span></div>`;
|
|
574
|
+
}
|
|
575
|
+
tooltip.innerHTML = rows;
|
|
576
|
+
}
|
|
577
|
+
buildGridLines() {
|
|
578
|
+
if (!this.showGrid)
|
|
579
|
+
return '';
|
|
580
|
+
const area = this.chartArea;
|
|
581
|
+
const { min, max } = this.priceRange;
|
|
582
|
+
const ticks = 6;
|
|
583
|
+
const step = (max - min) / ticks;
|
|
584
|
+
let lines = '';
|
|
585
|
+
for (let i = 0; i <= ticks; i++) {
|
|
586
|
+
const price = min + step * i;
|
|
587
|
+
const y = this.priceToY(price);
|
|
588
|
+
lines += `<line class="candlestick__grid-line" x1="${area.x}" y1="${y}" x2="${area.x + area.width}" y2="${y}" />`;
|
|
589
|
+
}
|
|
590
|
+
return lines;
|
|
591
|
+
}
|
|
592
|
+
buildYAxis() {
|
|
593
|
+
const { min, max } = this.priceRange;
|
|
594
|
+
const ticks = 6;
|
|
595
|
+
const step = (max - min) / ticks;
|
|
596
|
+
let labels = '';
|
|
597
|
+
const labelX = this.svgWidth - PADDING.right + 8;
|
|
598
|
+
for (let i = 0; i <= ticks; i++) {
|
|
599
|
+
const price = min + step * i;
|
|
600
|
+
const y = this.priceToY(price);
|
|
601
|
+
labels += `<text class="candlestick__axis-label candlestick__axis-label--y" x="${labelX}" y="${y}">${this.formatPrice(price)}</text>`;
|
|
602
|
+
}
|
|
603
|
+
return labels;
|
|
604
|
+
}
|
|
605
|
+
buildXAxis() {
|
|
606
|
+
const visible = this.visibleData;
|
|
607
|
+
if (visible.length === 0)
|
|
608
|
+
return '';
|
|
609
|
+
const area = this.chartArea;
|
|
610
|
+
const labelY = area.y + area.height + area.volumeHeight + 16;
|
|
611
|
+
const maxLabels = Math.floor(area.width / 80);
|
|
612
|
+
const step = Math.max(1, Math.ceil(visible.length / maxLabels));
|
|
613
|
+
let labels = '';
|
|
614
|
+
for (let i = 0; i < visible.length; i += step) {
|
|
615
|
+
const x = this.indexToX(i);
|
|
616
|
+
labels += `<text class="candlestick__axis-label candlestick__axis-label--x" x="${x}" y="${labelY}">${this.formatDate(visible[i].date)}</text>`;
|
|
617
|
+
}
|
|
618
|
+
return labels;
|
|
619
|
+
}
|
|
620
|
+
buildCandles() {
|
|
621
|
+
const visible = this.visibleData;
|
|
622
|
+
if (visible.length === 0)
|
|
623
|
+
return '';
|
|
624
|
+
const cw = this.candleWidth;
|
|
625
|
+
const halfCw = cw / 2;
|
|
626
|
+
let parts = '';
|
|
627
|
+
for (let i = 0; i < visible.length; i++) {
|
|
628
|
+
const candle = visible[i];
|
|
629
|
+
const isBullish = candle.close >= candle.open;
|
|
630
|
+
const color = isBullish
|
|
631
|
+
? (this.bullishColor || 'var(--candlestick-bullish)')
|
|
632
|
+
: (this.bearishColor || 'var(--candlestick-bearish)');
|
|
633
|
+
const x = this.indexToX(i);
|
|
634
|
+
const highY = this.priceToY(candle.high);
|
|
635
|
+
const lowY = this.priceToY(candle.low);
|
|
636
|
+
const openY = this.priceToY(candle.open);
|
|
637
|
+
const closeY = this.priceToY(candle.close);
|
|
638
|
+
const bodyTop = Math.min(openY, closeY);
|
|
639
|
+
const bodyHeight = Math.max(1, Math.abs(closeY - openY));
|
|
640
|
+
const shouldAnimate = this.animation && this.animateNext;
|
|
641
|
+
const animDelay = shouldAnimate ? `animation-delay: ${i * 8}ms;` : '';
|
|
642
|
+
const wickAnimClass = shouldAnimate ? ' candlestick__wick--animated' : '';
|
|
643
|
+
const bodyAnimClass = shouldAnimate ? ' candlestick__body--animated' : '';
|
|
644
|
+
// Wick (high to low)
|
|
645
|
+
parts += `<line class="candlestick__wick${wickAnimClass}" x1="${x}" y1="${highY}" x2="${x}" y2="${lowY}" stroke="${color}" style="${animDelay}" />`;
|
|
646
|
+
// Body (open to close)
|
|
647
|
+
parts += `<rect class="candlestick__body${bodyAnimClass}" x="${x - halfCw}" y="${bodyTop}" width="${cw}" height="${bodyHeight}" fill="${color}" stroke="${color}" stroke-width="1" rx="1" style="${animDelay}" data-candle-index="${i}" />`;
|
|
648
|
+
}
|
|
649
|
+
return parts;
|
|
650
|
+
}
|
|
651
|
+
buildVolumeBars() {
|
|
652
|
+
if (!this.showVolume)
|
|
653
|
+
return '';
|
|
654
|
+
const visible = this.visibleData;
|
|
655
|
+
if (visible.length === 0)
|
|
656
|
+
return '';
|
|
657
|
+
const area = this.chartArea;
|
|
658
|
+
const volMax = this.volumeMax;
|
|
659
|
+
const cw = this.candleWidth;
|
|
660
|
+
const halfCw = cw / 2;
|
|
661
|
+
let parts = '';
|
|
662
|
+
for (let i = 0; i < visible.length; i++) {
|
|
663
|
+
const candle = visible[i];
|
|
664
|
+
const vol = candle.volume || 0;
|
|
665
|
+
const isBullish = candle.close >= candle.open;
|
|
666
|
+
const color = isBullish
|
|
667
|
+
? (this.bullishColor || 'var(--candlestick-bullish)')
|
|
668
|
+
: (this.bearishColor || 'var(--candlestick-bearish)');
|
|
669
|
+
const x = this.indexToX(i);
|
|
670
|
+
const barHeight = (vol / volMax) * area.volumeHeight;
|
|
671
|
+
const barY = area.volumeY + area.volumeHeight - barHeight;
|
|
672
|
+
const shouldAnimate = this.animation && this.animateNext;
|
|
673
|
+
const animDelay = shouldAnimate ? `animation-delay: ${i * 8}ms;` : '';
|
|
674
|
+
const animClass = shouldAnimate ? ' candlestick__volume--animated' : '';
|
|
675
|
+
parts += `<rect class="candlestick__volume${animClass}" x="${x - halfCw}" y="${barY}" width="${cw}" height="${barHeight}" fill="${color}" style="${animDelay}" />`;
|
|
676
|
+
}
|
|
677
|
+
return parts;
|
|
678
|
+
}
|
|
679
|
+
getTooltipCandle() {
|
|
680
|
+
if (this.mouseX < 0)
|
|
681
|
+
return null;
|
|
682
|
+
const area = this.chartArea;
|
|
683
|
+
if (this.mouseX < area.x || this.mouseX > area.x + area.width)
|
|
684
|
+
return null;
|
|
685
|
+
const idx = this.xToIndex(this.mouseX);
|
|
686
|
+
return this.visibleData[idx] || null;
|
|
687
|
+
}
|
|
688
|
+
renderContent() {
|
|
689
|
+
return snice.html /*html*/ `
|
|
690
|
+
<div class="candlestick"
|
|
691
|
+
style="height: ${this.svgHeight}px;"
|
|
692
|
+
@mousemove=${this.handleMouseMove}
|
|
693
|
+
@mouseleave=${this.handleMouseLeave}
|
|
694
|
+
@mousedown=${this.handleMouseDown}
|
|
695
|
+
@mouseup=${this.handleMouseUp}
|
|
696
|
+
@wheel=${this.handleWheel}>
|
|
697
|
+
<svg class="candlestick__svg" viewBox="0 0 ${this.svgWidth} ${this.svgHeight}" preserveAspectRatio="none" role="img" aria-label="Candlestick chart with ${this.data.length} data points">
|
|
698
|
+
<g class="candlestick__chart-content"></g>
|
|
699
|
+
<g class="candlestick__crosshair-group"></g>
|
|
700
|
+
</svg>
|
|
701
|
+
<div class="candlestick__tooltip"></div>
|
|
702
|
+
</div>
|
|
703
|
+
`;
|
|
704
|
+
}
|
|
705
|
+
componentStyles() {
|
|
706
|
+
return snice.css /*css*/ `${cssContent}`;
|
|
707
|
+
}
|
|
708
|
+
});
|
|
709
|
+
return _classThis;
|
|
710
|
+
})();
|
|
711
|
+
|
|
712
|
+
exports.SniceCandlestick = SniceCandlestick;
|
|
713
|
+
|
|
714
|
+
return exports;
|
|
715
|
+
|
|
716
|
+
})({}, Snice);
|
|
717
|
+
//# sourceMappingURL=snice-candlestick.js.map
|