@pipsend/charts 2.3.10 → 2.3.11
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/dist/pipsend-charts.development.mjs +124 -12
- package/dist/pipsend-charts.production.mjs +2 -2
- package/dist/pipsend-charts.standalone.development.js +124 -12
- package/dist/pipsend-charts.standalone.development.mjs +124 -12
- package/dist/pipsend-charts.standalone.production.js +2 -2
- package/dist/pipsend-charts.standalone.production.mjs +2 -2
- package/dist/typings.d.ts +19 -8
- package/package.json +83 -1
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/*!
|
|
2
2
|
* @license
|
|
3
|
-
* Pipsend Charts v2.3.
|
|
3
|
+
* Pipsend Charts v2.3.11
|
|
4
4
|
* Copyright (c) 2026 Pipsend
|
|
5
5
|
* Licensed under MIT License
|
|
6
6
|
* Built on TradingView Lightweight Charts™ (Apache 2.0)
|
|
@@ -19723,6 +19723,8 @@
|
|
|
19723
19723
|
this._private__pointerId = null;
|
|
19724
19724
|
this._private__pressOrigin = null;
|
|
19725
19725
|
this._private__pressedLine = null;
|
|
19726
|
+
/** Whether the gesture in flight came from a finger rather than a mouse. */
|
|
19727
|
+
this._private__pressWasTouch = false;
|
|
19726
19728
|
/** Distance from the pointer to the dragged line when the press landed. */
|
|
19727
19729
|
this._private__grabOffset = 0;
|
|
19728
19730
|
/** Latest pointer position in pane coordinates, or null when off the panes. */
|
|
@@ -19787,8 +19789,18 @@
|
|
|
19787
19789
|
this._private__applyCursor();
|
|
19788
19790
|
}
|
|
19789
19791
|
_private__onPointerDown(event) {
|
|
19790
|
-
|
|
19792
|
+
// Hover belongs to the mouse. Touch leaves whatever the last press marked
|
|
19793
|
+
// still marked, so trusting it here grabbed that line again wherever the
|
|
19794
|
+
// next tap landed: every press resolves itself instead.
|
|
19795
|
+
this._private__pressWasTouch = event.pointerType !== 'mouse';
|
|
19796
|
+
let line = this._private__pressWasTouch || this._private__hoveredId === null
|
|
19797
|
+
? null
|
|
19798
|
+
: this._private__lines.get(this._private__hoveredId) ?? null;
|
|
19799
|
+
if (line === null) {
|
|
19800
|
+
line = this._private__resolveHitAt(event);
|
|
19801
|
+
}
|
|
19791
19802
|
if (!line) {
|
|
19803
|
+
this._private__clearTouchHover();
|
|
19792
19804
|
return;
|
|
19793
19805
|
}
|
|
19794
19806
|
this._private__pressOrigin = { _internal_x: event.clientX, _internal_y: event.clientY };
|
|
@@ -19827,6 +19839,7 @@
|
|
|
19827
19839
|
}
|
|
19828
19840
|
_private__onPointerUp(event) {
|
|
19829
19841
|
const dragged = this._private__dragging;
|
|
19842
|
+
const wasTouch = this._private__pressWasTouch;
|
|
19830
19843
|
const pressed = this._private__pressedLine;
|
|
19831
19844
|
const origin = this._private__pressOrigin;
|
|
19832
19845
|
this._private__releasePointer();
|
|
@@ -19848,12 +19861,24 @@
|
|
|
19848
19861
|
dragged.click();
|
|
19849
19862
|
}
|
|
19850
19863
|
}
|
|
19864
|
+
this._private__clearTouchHover(wasTouch);
|
|
19851
19865
|
this._private__applyCursor();
|
|
19852
19866
|
return;
|
|
19853
19867
|
}
|
|
19854
19868
|
if (pressed !== null && !moved && pressed.isClickable()) {
|
|
19855
19869
|
pressed.click();
|
|
19856
19870
|
}
|
|
19871
|
+
this._private__clearTouchHover(wasTouch);
|
|
19872
|
+
}
|
|
19873
|
+
/** A finger leaves nothing hovered behind it, the way lifting a mouse does. */
|
|
19874
|
+
_private__clearTouchHover(wasTouch = this._private__pressWasTouch) {
|
|
19875
|
+
if (!wasTouch || this._private__hoveredId === null) {
|
|
19876
|
+
return;
|
|
19877
|
+
}
|
|
19878
|
+
const line = this._private__lines.get(this._private__hoveredId) ?? null;
|
|
19879
|
+
this._private__setHovered(null);
|
|
19880
|
+
this._private__setHoveredPart(line, null);
|
|
19881
|
+
this._private__applyCursor();
|
|
19857
19882
|
}
|
|
19858
19883
|
/**
|
|
19859
19884
|
* Abort an in-flight gesture: the line goes back to where it was and no
|
|
@@ -19899,9 +19924,38 @@
|
|
|
19899
19924
|
return paneY === null ? null : line.priceAt(paneY - this._private__grabOffset);
|
|
19900
19925
|
}
|
|
19901
19926
|
/** The pointer's position inside the line's pane, in pane coordinates. */
|
|
19902
|
-
|
|
19927
|
+
/**
|
|
19928
|
+
* The hovered id comes from the crosshair, which touch never moves before it
|
|
19929
|
+
* presses, so the press resolves the target itself.
|
|
19930
|
+
*/
|
|
19931
|
+
_private__resolveHitAt(event) {
|
|
19932
|
+
for (const line of this._private__lines.values()) {
|
|
19933
|
+
if (!line.hitTestAt) {
|
|
19934
|
+
continue;
|
|
19935
|
+
}
|
|
19936
|
+
const paneElement = this._private__paneElementOf(line);
|
|
19937
|
+
if (paneElement === null) {
|
|
19938
|
+
continue;
|
|
19939
|
+
}
|
|
19940
|
+
const rect = paneElement.getBoundingClientRect();
|
|
19941
|
+
// A fingertip is far coarser than a pointer, so its targets are widened.
|
|
19942
|
+
const slop = event.pointerType === 'mouse' ? 0 : 12 /* Constants.TouchSlopPx */;
|
|
19943
|
+
const hit = this._private__splitHit(line.hitTestAt(event.clientX - rect.left, event.clientY - rect.top, slop));
|
|
19944
|
+
if (hit === null) {
|
|
19945
|
+
continue;
|
|
19946
|
+
}
|
|
19947
|
+
this._private__setHovered(line.id());
|
|
19948
|
+
this._private__setHoveredPart(line, hit._internal_part);
|
|
19949
|
+
return line;
|
|
19950
|
+
}
|
|
19951
|
+
return null;
|
|
19952
|
+
}
|
|
19953
|
+
_private__paneElementOf(line) {
|
|
19903
19954
|
const pane = this._private__chart.panes()[line.paneIndex()];
|
|
19904
|
-
|
|
19955
|
+
return pane ? pane.getHTMLElement() : null;
|
|
19956
|
+
}
|
|
19957
|
+
_private__paneY(line, event) {
|
|
19958
|
+
const paneElement = this._private__paneElementOf(line);
|
|
19905
19959
|
if (paneElement) {
|
|
19906
19960
|
return event.clientY - paneElement.getBoundingClientRect().top;
|
|
19907
19961
|
}
|
|
@@ -20018,6 +20072,7 @@
|
|
|
20018
20072
|
* line. Hit testing comes from the engine — the line's id travels as the price
|
|
20019
20073
|
* line's `externalId` — so the hit area matches what is drawn.
|
|
20020
20074
|
*/
|
|
20075
|
+
const HIT_TOLERANCE_PX$1 = 8;
|
|
20021
20076
|
class DraggablePriceLine {
|
|
20022
20077
|
constructor(chart, series, options) {
|
|
20023
20078
|
this._private__priceLine = null;
|
|
@@ -20070,6 +20125,14 @@
|
|
|
20070
20125
|
color: hovered ? this._private__options.hoverColor : this._private__originalColor,
|
|
20071
20126
|
});
|
|
20072
20127
|
}
|
|
20128
|
+
/**
|
|
20129
|
+
* The engine draws this one, so there is no pane view to ask: a press within
|
|
20130
|
+
* the line's own grab strip counts as a hit.
|
|
20131
|
+
*/
|
|
20132
|
+
hitTestAt(x, y, slop = 0) {
|
|
20133
|
+
const coord = this._private__series.priceToCoordinate(this._private__options.price);
|
|
20134
|
+
return coord !== null && Math.abs(y - coord) <= HIT_TOLERANCE_PX$1 + slop ? this._private__id : null;
|
|
20135
|
+
}
|
|
20073
20136
|
priceAt(paneY) {
|
|
20074
20137
|
const price = this._private__series.coordinateToPrice(paneY);
|
|
20075
20138
|
return price === null ? null : price;
|
|
@@ -20612,22 +20675,27 @@
|
|
|
20612
20675
|
_internal_setData(data) {
|
|
20613
20676
|
this._private__data = data;
|
|
20614
20677
|
}
|
|
20615
|
-
|
|
20678
|
+
/**
|
|
20679
|
+
* `slop` widens every target by the same amount, for input coarser than a
|
|
20680
|
+
* mouse pointer.
|
|
20681
|
+
*/
|
|
20682
|
+
_internal_hitTest(x, y, slop = 0) {
|
|
20616
20683
|
// The close button sits on top of the label, which sits on top of the
|
|
20617
20684
|
// line, so the narrowest target is tested first.
|
|
20618
20685
|
for (const layout of this._private__layouts) {
|
|
20619
|
-
if (layout._internal_closable && x >= layout._internal_closeLeft && x <= layout._internal_closeRight &&
|
|
20620
|
-
Math.abs(y - layout._internal_labelY) <= layout._internal_height / 2) {
|
|
20686
|
+
if (layout._internal_closable && x >= layout._internal_closeLeft - slop && x <= layout._internal_closeRight + slop &&
|
|
20687
|
+
Math.abs(y - layout._internal_labelY) <= layout._internal_height / 2 + slop) {
|
|
20621
20688
|
return { _internal_level: layout._internal_level, _internal_part: 'close' };
|
|
20622
20689
|
}
|
|
20623
20690
|
}
|
|
20624
20691
|
for (const layout of this._private__layouts) {
|
|
20625
|
-
if (x >= layout._internal_pillLeft && x <= layout._internal_pillRight
|
|
20692
|
+
if (x >= layout._internal_pillLeft - slop && x <= layout._internal_pillRight + slop &&
|
|
20693
|
+
Math.abs(y - layout._internal_labelY) <= layout._internal_height / 2 + slop) {
|
|
20626
20694
|
return { _internal_level: layout._internal_level, _internal_part: 'body' };
|
|
20627
20695
|
}
|
|
20628
20696
|
}
|
|
20629
20697
|
for (const layout of this._private__layouts) {
|
|
20630
|
-
if (Math.abs(y - layout._internal_y) <= 8 /* Constants.LineHitTolerance */) {
|
|
20698
|
+
if (Math.abs(y - layout._internal_y) <= 8 /* Constants.LineHitTolerance */ + slop) {
|
|
20631
20699
|
return { _internal_level: layout._internal_level, _internal_part: 'line' };
|
|
20632
20700
|
}
|
|
20633
20701
|
}
|
|
@@ -20864,8 +20932,8 @@
|
|
|
20864
20932
|
zOrder() {
|
|
20865
20933
|
return 'top';
|
|
20866
20934
|
}
|
|
20867
|
-
_internal_hitTest(x, y) {
|
|
20868
|
-
return this._private__data === null ? null : this._private__renderer._internal_hitTest(x, y);
|
|
20935
|
+
_internal_hitTest(x, y, slop = 0) {
|
|
20936
|
+
return this._private__data === null ? null : this._private__renderer._internal_hitTest(x, y, slop);
|
|
20869
20937
|
}
|
|
20870
20938
|
}
|
|
20871
20939
|
|
|
@@ -21016,6 +21084,13 @@
|
|
|
21016
21084
|
* of jumping to sit under it — which matters most when the label has been
|
|
21017
21085
|
* fanned away from its own line.
|
|
21018
21086
|
*/
|
|
21087
|
+
hitTestAt(x, y, slop = 0) {
|
|
21088
|
+
const hit = this._private__paneView._internal_hitTest(x, y, slop);
|
|
21089
|
+
if (hit === null) {
|
|
21090
|
+
return null;
|
|
21091
|
+
}
|
|
21092
|
+
return this._private__levelOptions(hit._internal_level) === null ? null : `${this._private__id}#${hit._internal_level}:${hit._internal_part}`;
|
|
21093
|
+
}
|
|
21019
21094
|
dragAnchorY() {
|
|
21020
21095
|
if (this._private__dragLevel === null) {
|
|
21021
21096
|
return null;
|
|
@@ -30086,6 +30161,7 @@
|
|
|
30086
30161
|
this._private__mouseMoveHandler = null;
|
|
30087
30162
|
this._private__pointerDownHandler = null;
|
|
30088
30163
|
this._private__pointerUpHandler = null;
|
|
30164
|
+
this._private__pointerMoveHandler = null;
|
|
30089
30165
|
this._private__pointerCancelHandler = null;
|
|
30090
30166
|
this._private__lostCaptureHandler = null;
|
|
30091
30167
|
this._private__windowPointerUpHandler = null;
|
|
@@ -30660,10 +30736,12 @@
|
|
|
30660
30736
|
if (chartElement) {
|
|
30661
30737
|
this._private__pointerDownHandler = (event) => this._private__handlePointerDown(event);
|
|
30662
30738
|
this._private__pointerUpHandler = (event) => this._private__handlePointerUp(event);
|
|
30739
|
+
this._private__pointerMoveHandler = (event) => this._private__handlePointerMove(event);
|
|
30663
30740
|
this._private__pointerCancelHandler = (event) => this._private__handlePointerUp(event);
|
|
30664
30741
|
this._private__lostCaptureHandler = (event) => this._private__handleLostPointerCapture(event);
|
|
30665
30742
|
chartElement.addEventListener('pointerdown', this._private__pointerDownHandler);
|
|
30666
30743
|
chartElement.addEventListener('pointerup', this._private__pointerUpHandler);
|
|
30744
|
+
chartElement.addEventListener('pointermove', this._private__pointerMoveHandler);
|
|
30667
30745
|
chartElement.addEventListener('pointercancel', this._private__pointerCancelHandler);
|
|
30668
30746
|
chartElement.addEventListener('lostpointercapture', this._private__lostCaptureHandler);
|
|
30669
30747
|
}
|
|
@@ -30698,6 +30776,10 @@
|
|
|
30698
30776
|
chartElement.removeEventListener('pointerup', this._private__pointerUpHandler);
|
|
30699
30777
|
this._private__pointerUpHandler = null;
|
|
30700
30778
|
}
|
|
30779
|
+
if (this._private__pointerMoveHandler) {
|
|
30780
|
+
chartElement.removeEventListener('pointermove', this._private__pointerMoveHandler);
|
|
30781
|
+
this._private__pointerMoveHandler = null;
|
|
30782
|
+
}
|
|
30701
30783
|
if (this._private__pointerCancelHandler) {
|
|
30702
30784
|
chartElement.removeEventListener('pointercancel', this._private__pointerCancelHandler);
|
|
30703
30785
|
this._private__pointerCancelHandler = null;
|
|
@@ -30847,6 +30929,36 @@
|
|
|
30847
30929
|
// mouse events, and those are what drive the crosshair the drag reads.
|
|
30848
30930
|
this._private__disableChartInteractions();
|
|
30849
30931
|
}
|
|
30932
|
+
/**
|
|
30933
|
+
* The drag reads the crosshair, which touch never moves: its move handler
|
|
30934
|
+
* only tries to pan, and the drag has just turned panning off. So touch is
|
|
30935
|
+
* driven straight from the pointer instead.
|
|
30936
|
+
*/
|
|
30937
|
+
_private__handlePointerMove(event) {
|
|
30938
|
+
if (!this._private__isDragging || this._private__draggedToolId === null || event.pointerType === 'mouse') {
|
|
30939
|
+
return;
|
|
30940
|
+
}
|
|
30941
|
+
if (this._private__pointerId !== null && event.pointerId !== this._private__pointerId) {
|
|
30942
|
+
return;
|
|
30943
|
+
}
|
|
30944
|
+
const tool = this._private__tools.get(this._private__draggedToolId);
|
|
30945
|
+
if (!tool) {
|
|
30946
|
+
return;
|
|
30947
|
+
}
|
|
30948
|
+
const paneElement = this._private__paneElementOf(tool);
|
|
30949
|
+
if (paneElement === null) {
|
|
30950
|
+
return;
|
|
30951
|
+
}
|
|
30952
|
+
const rect = paneElement.getBoundingClientRect();
|
|
30953
|
+
const series = tool.series();
|
|
30954
|
+
const price = series.coordinateToPrice((event.clientY - rect.top));
|
|
30955
|
+
const time = timeFromCoordinate(this._private__chart, series, event.clientX - rect.left);
|
|
30956
|
+
if (price === null || time === null) {
|
|
30957
|
+
return;
|
|
30958
|
+
}
|
|
30959
|
+
tool.updateDrag(time, price);
|
|
30960
|
+
event.preventDefault();
|
|
30961
|
+
}
|
|
30850
30962
|
_private__handlePointerUp(event) {
|
|
30851
30963
|
if (!this._private__isDragging || this._private__draggedToolId === null) {
|
|
30852
30964
|
return;
|
|
@@ -31020,7 +31132,7 @@
|
|
|
31020
31132
|
* Returns the current version as a string. For example `'1.0.0'`.
|
|
31021
31133
|
*/
|
|
31022
31134
|
function version() {
|
|
31023
|
-
return "2.3.
|
|
31135
|
+
return "2.3.11";
|
|
31024
31136
|
}
|
|
31025
31137
|
|
|
31026
31138
|
var PipsendChartsModule = /*#__PURE__*/Object.freeze({
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/*!
|
|
2
2
|
* @license
|
|
3
|
-
* Pipsend Charts v2.3.
|
|
3
|
+
* Pipsend Charts v2.3.11
|
|
4
4
|
* Copyright (c) 2026 Pipsend
|
|
5
5
|
* Licensed under MIT License
|
|
6
6
|
* Built on TradingView Lightweight Charts™ (Apache 2.0)
|
|
@@ -19720,6 +19720,8 @@ class TradingLineController {
|
|
|
19720
19720
|
this._private__pointerId = null;
|
|
19721
19721
|
this._private__pressOrigin = null;
|
|
19722
19722
|
this._private__pressedLine = null;
|
|
19723
|
+
/** Whether the gesture in flight came from a finger rather than a mouse. */
|
|
19724
|
+
this._private__pressWasTouch = false;
|
|
19723
19725
|
/** Distance from the pointer to the dragged line when the press landed. */
|
|
19724
19726
|
this._private__grabOffset = 0;
|
|
19725
19727
|
/** Latest pointer position in pane coordinates, or null when off the panes. */
|
|
@@ -19784,8 +19786,18 @@ class TradingLineController {
|
|
|
19784
19786
|
this._private__applyCursor();
|
|
19785
19787
|
}
|
|
19786
19788
|
_private__onPointerDown(event) {
|
|
19787
|
-
|
|
19789
|
+
// Hover belongs to the mouse. Touch leaves whatever the last press marked
|
|
19790
|
+
// still marked, so trusting it here grabbed that line again wherever the
|
|
19791
|
+
// next tap landed: every press resolves itself instead.
|
|
19792
|
+
this._private__pressWasTouch = event.pointerType !== 'mouse';
|
|
19793
|
+
let line = this._private__pressWasTouch || this._private__hoveredId === null
|
|
19794
|
+
? null
|
|
19795
|
+
: this._private__lines.get(this._private__hoveredId) ?? null;
|
|
19796
|
+
if (line === null) {
|
|
19797
|
+
line = this._private__resolveHitAt(event);
|
|
19798
|
+
}
|
|
19788
19799
|
if (!line) {
|
|
19800
|
+
this._private__clearTouchHover();
|
|
19789
19801
|
return;
|
|
19790
19802
|
}
|
|
19791
19803
|
this._private__pressOrigin = { _internal_x: event.clientX, _internal_y: event.clientY };
|
|
@@ -19824,6 +19836,7 @@ class TradingLineController {
|
|
|
19824
19836
|
}
|
|
19825
19837
|
_private__onPointerUp(event) {
|
|
19826
19838
|
const dragged = this._private__dragging;
|
|
19839
|
+
const wasTouch = this._private__pressWasTouch;
|
|
19827
19840
|
const pressed = this._private__pressedLine;
|
|
19828
19841
|
const origin = this._private__pressOrigin;
|
|
19829
19842
|
this._private__releasePointer();
|
|
@@ -19845,12 +19858,24 @@ class TradingLineController {
|
|
|
19845
19858
|
dragged.click();
|
|
19846
19859
|
}
|
|
19847
19860
|
}
|
|
19861
|
+
this._private__clearTouchHover(wasTouch);
|
|
19848
19862
|
this._private__applyCursor();
|
|
19849
19863
|
return;
|
|
19850
19864
|
}
|
|
19851
19865
|
if (pressed !== null && !moved && pressed.isClickable()) {
|
|
19852
19866
|
pressed.click();
|
|
19853
19867
|
}
|
|
19868
|
+
this._private__clearTouchHover(wasTouch);
|
|
19869
|
+
}
|
|
19870
|
+
/** A finger leaves nothing hovered behind it, the way lifting a mouse does. */
|
|
19871
|
+
_private__clearTouchHover(wasTouch = this._private__pressWasTouch) {
|
|
19872
|
+
if (!wasTouch || this._private__hoveredId === null) {
|
|
19873
|
+
return;
|
|
19874
|
+
}
|
|
19875
|
+
const line = this._private__lines.get(this._private__hoveredId) ?? null;
|
|
19876
|
+
this._private__setHovered(null);
|
|
19877
|
+
this._private__setHoveredPart(line, null);
|
|
19878
|
+
this._private__applyCursor();
|
|
19854
19879
|
}
|
|
19855
19880
|
/**
|
|
19856
19881
|
* Abort an in-flight gesture: the line goes back to where it was and no
|
|
@@ -19896,9 +19921,38 @@ class TradingLineController {
|
|
|
19896
19921
|
return paneY === null ? null : line.priceAt(paneY - this._private__grabOffset);
|
|
19897
19922
|
}
|
|
19898
19923
|
/** The pointer's position inside the line's pane, in pane coordinates. */
|
|
19899
|
-
|
|
19924
|
+
/**
|
|
19925
|
+
* The hovered id comes from the crosshair, which touch never moves before it
|
|
19926
|
+
* presses, so the press resolves the target itself.
|
|
19927
|
+
*/
|
|
19928
|
+
_private__resolveHitAt(event) {
|
|
19929
|
+
for (const line of this._private__lines.values()) {
|
|
19930
|
+
if (!line.hitTestAt) {
|
|
19931
|
+
continue;
|
|
19932
|
+
}
|
|
19933
|
+
const paneElement = this._private__paneElementOf(line);
|
|
19934
|
+
if (paneElement === null) {
|
|
19935
|
+
continue;
|
|
19936
|
+
}
|
|
19937
|
+
const rect = paneElement.getBoundingClientRect();
|
|
19938
|
+
// A fingertip is far coarser than a pointer, so its targets are widened.
|
|
19939
|
+
const slop = event.pointerType === 'mouse' ? 0 : 12 /* Constants.TouchSlopPx */;
|
|
19940
|
+
const hit = this._private__splitHit(line.hitTestAt(event.clientX - rect.left, event.clientY - rect.top, slop));
|
|
19941
|
+
if (hit === null) {
|
|
19942
|
+
continue;
|
|
19943
|
+
}
|
|
19944
|
+
this._private__setHovered(line.id());
|
|
19945
|
+
this._private__setHoveredPart(line, hit._internal_part);
|
|
19946
|
+
return line;
|
|
19947
|
+
}
|
|
19948
|
+
return null;
|
|
19949
|
+
}
|
|
19950
|
+
_private__paneElementOf(line) {
|
|
19900
19951
|
const pane = this._private__chart.panes()[line.paneIndex()];
|
|
19901
|
-
|
|
19952
|
+
return pane ? pane.getHTMLElement() : null;
|
|
19953
|
+
}
|
|
19954
|
+
_private__paneY(line, event) {
|
|
19955
|
+
const paneElement = this._private__paneElementOf(line);
|
|
19902
19956
|
if (paneElement) {
|
|
19903
19957
|
return event.clientY - paneElement.getBoundingClientRect().top;
|
|
19904
19958
|
}
|
|
@@ -20015,6 +20069,7 @@ let nextLineId = 0;
|
|
|
20015
20069
|
* line. Hit testing comes from the engine — the line's id travels as the price
|
|
20016
20070
|
* line's `externalId` — so the hit area matches what is drawn.
|
|
20017
20071
|
*/
|
|
20072
|
+
const HIT_TOLERANCE_PX$1 = 8;
|
|
20018
20073
|
class DraggablePriceLine {
|
|
20019
20074
|
constructor(chart, series, options) {
|
|
20020
20075
|
this._private__priceLine = null;
|
|
@@ -20067,6 +20122,14 @@ class DraggablePriceLine {
|
|
|
20067
20122
|
color: hovered ? this._private__options.hoverColor : this._private__originalColor,
|
|
20068
20123
|
});
|
|
20069
20124
|
}
|
|
20125
|
+
/**
|
|
20126
|
+
* The engine draws this one, so there is no pane view to ask: a press within
|
|
20127
|
+
* the line's own grab strip counts as a hit.
|
|
20128
|
+
*/
|
|
20129
|
+
hitTestAt(x, y, slop = 0) {
|
|
20130
|
+
const coord = this._private__series.priceToCoordinate(this._private__options.price);
|
|
20131
|
+
return coord !== null && Math.abs(y - coord) <= HIT_TOLERANCE_PX$1 + slop ? this._private__id : null;
|
|
20132
|
+
}
|
|
20070
20133
|
priceAt(paneY) {
|
|
20071
20134
|
const price = this._private__series.coordinateToPrice(paneY);
|
|
20072
20135
|
return price === null ? null : price;
|
|
@@ -20609,22 +20672,27 @@ class PositionLineRenderer {
|
|
|
20609
20672
|
_internal_setData(data) {
|
|
20610
20673
|
this._private__data = data;
|
|
20611
20674
|
}
|
|
20612
|
-
|
|
20675
|
+
/**
|
|
20676
|
+
* `slop` widens every target by the same amount, for input coarser than a
|
|
20677
|
+
* mouse pointer.
|
|
20678
|
+
*/
|
|
20679
|
+
_internal_hitTest(x, y, slop = 0) {
|
|
20613
20680
|
// The close button sits on top of the label, which sits on top of the
|
|
20614
20681
|
// line, so the narrowest target is tested first.
|
|
20615
20682
|
for (const layout of this._private__layouts) {
|
|
20616
|
-
if (layout._internal_closable && x >= layout._internal_closeLeft && x <= layout._internal_closeRight &&
|
|
20617
|
-
Math.abs(y - layout._internal_labelY) <= layout._internal_height / 2) {
|
|
20683
|
+
if (layout._internal_closable && x >= layout._internal_closeLeft - slop && x <= layout._internal_closeRight + slop &&
|
|
20684
|
+
Math.abs(y - layout._internal_labelY) <= layout._internal_height / 2 + slop) {
|
|
20618
20685
|
return { _internal_level: layout._internal_level, _internal_part: 'close' };
|
|
20619
20686
|
}
|
|
20620
20687
|
}
|
|
20621
20688
|
for (const layout of this._private__layouts) {
|
|
20622
|
-
if (x >= layout._internal_pillLeft && x <= layout._internal_pillRight
|
|
20689
|
+
if (x >= layout._internal_pillLeft - slop && x <= layout._internal_pillRight + slop &&
|
|
20690
|
+
Math.abs(y - layout._internal_labelY) <= layout._internal_height / 2 + slop) {
|
|
20623
20691
|
return { _internal_level: layout._internal_level, _internal_part: 'body' };
|
|
20624
20692
|
}
|
|
20625
20693
|
}
|
|
20626
20694
|
for (const layout of this._private__layouts) {
|
|
20627
|
-
if (Math.abs(y - layout._internal_y) <= 8 /* Constants.LineHitTolerance */) {
|
|
20695
|
+
if (Math.abs(y - layout._internal_y) <= 8 /* Constants.LineHitTolerance */ + slop) {
|
|
20628
20696
|
return { _internal_level: layout._internal_level, _internal_part: 'line' };
|
|
20629
20697
|
}
|
|
20630
20698
|
}
|
|
@@ -20861,8 +20929,8 @@ class PositionLinePaneView {
|
|
|
20861
20929
|
zOrder() {
|
|
20862
20930
|
return 'top';
|
|
20863
20931
|
}
|
|
20864
|
-
_internal_hitTest(x, y) {
|
|
20865
|
-
return this._private__data === null ? null : this._private__renderer._internal_hitTest(x, y);
|
|
20932
|
+
_internal_hitTest(x, y, slop = 0) {
|
|
20933
|
+
return this._private__data === null ? null : this._private__renderer._internal_hitTest(x, y, slop);
|
|
20866
20934
|
}
|
|
20867
20935
|
}
|
|
20868
20936
|
|
|
@@ -21013,6 +21081,13 @@ class PositionLine {
|
|
|
21013
21081
|
* of jumping to sit under it — which matters most when the label has been
|
|
21014
21082
|
* fanned away from its own line.
|
|
21015
21083
|
*/
|
|
21084
|
+
hitTestAt(x, y, slop = 0) {
|
|
21085
|
+
const hit = this._private__paneView._internal_hitTest(x, y, slop);
|
|
21086
|
+
if (hit === null) {
|
|
21087
|
+
return null;
|
|
21088
|
+
}
|
|
21089
|
+
return this._private__levelOptions(hit._internal_level) === null ? null : `${this._private__id}#${hit._internal_level}:${hit._internal_part}`;
|
|
21090
|
+
}
|
|
21016
21091
|
dragAnchorY() {
|
|
21017
21092
|
if (this._private__dragLevel === null) {
|
|
21018
21093
|
return null;
|
|
@@ -30083,6 +30158,7 @@ class DrawingToolsManager {
|
|
|
30083
30158
|
this._private__mouseMoveHandler = null;
|
|
30084
30159
|
this._private__pointerDownHandler = null;
|
|
30085
30160
|
this._private__pointerUpHandler = null;
|
|
30161
|
+
this._private__pointerMoveHandler = null;
|
|
30086
30162
|
this._private__pointerCancelHandler = null;
|
|
30087
30163
|
this._private__lostCaptureHandler = null;
|
|
30088
30164
|
this._private__windowPointerUpHandler = null;
|
|
@@ -30657,10 +30733,12 @@ class DrawingToolsManager {
|
|
|
30657
30733
|
if (chartElement) {
|
|
30658
30734
|
this._private__pointerDownHandler = (event) => this._private__handlePointerDown(event);
|
|
30659
30735
|
this._private__pointerUpHandler = (event) => this._private__handlePointerUp(event);
|
|
30736
|
+
this._private__pointerMoveHandler = (event) => this._private__handlePointerMove(event);
|
|
30660
30737
|
this._private__pointerCancelHandler = (event) => this._private__handlePointerUp(event);
|
|
30661
30738
|
this._private__lostCaptureHandler = (event) => this._private__handleLostPointerCapture(event);
|
|
30662
30739
|
chartElement.addEventListener('pointerdown', this._private__pointerDownHandler);
|
|
30663
30740
|
chartElement.addEventListener('pointerup', this._private__pointerUpHandler);
|
|
30741
|
+
chartElement.addEventListener('pointermove', this._private__pointerMoveHandler);
|
|
30664
30742
|
chartElement.addEventListener('pointercancel', this._private__pointerCancelHandler);
|
|
30665
30743
|
chartElement.addEventListener('lostpointercapture', this._private__lostCaptureHandler);
|
|
30666
30744
|
}
|
|
@@ -30695,6 +30773,10 @@ class DrawingToolsManager {
|
|
|
30695
30773
|
chartElement.removeEventListener('pointerup', this._private__pointerUpHandler);
|
|
30696
30774
|
this._private__pointerUpHandler = null;
|
|
30697
30775
|
}
|
|
30776
|
+
if (this._private__pointerMoveHandler) {
|
|
30777
|
+
chartElement.removeEventListener('pointermove', this._private__pointerMoveHandler);
|
|
30778
|
+
this._private__pointerMoveHandler = null;
|
|
30779
|
+
}
|
|
30698
30780
|
if (this._private__pointerCancelHandler) {
|
|
30699
30781
|
chartElement.removeEventListener('pointercancel', this._private__pointerCancelHandler);
|
|
30700
30782
|
this._private__pointerCancelHandler = null;
|
|
@@ -30844,6 +30926,36 @@ class DrawingToolsManager {
|
|
|
30844
30926
|
// mouse events, and those are what drive the crosshair the drag reads.
|
|
30845
30927
|
this._private__disableChartInteractions();
|
|
30846
30928
|
}
|
|
30929
|
+
/**
|
|
30930
|
+
* The drag reads the crosshair, which touch never moves: its move handler
|
|
30931
|
+
* only tries to pan, and the drag has just turned panning off. So touch is
|
|
30932
|
+
* driven straight from the pointer instead.
|
|
30933
|
+
*/
|
|
30934
|
+
_private__handlePointerMove(event) {
|
|
30935
|
+
if (!this._private__isDragging || this._private__draggedToolId === null || event.pointerType === 'mouse') {
|
|
30936
|
+
return;
|
|
30937
|
+
}
|
|
30938
|
+
if (this._private__pointerId !== null && event.pointerId !== this._private__pointerId) {
|
|
30939
|
+
return;
|
|
30940
|
+
}
|
|
30941
|
+
const tool = this._private__tools.get(this._private__draggedToolId);
|
|
30942
|
+
if (!tool) {
|
|
30943
|
+
return;
|
|
30944
|
+
}
|
|
30945
|
+
const paneElement = this._private__paneElementOf(tool);
|
|
30946
|
+
if (paneElement === null) {
|
|
30947
|
+
return;
|
|
30948
|
+
}
|
|
30949
|
+
const rect = paneElement.getBoundingClientRect();
|
|
30950
|
+
const series = tool.series();
|
|
30951
|
+
const price = series.coordinateToPrice((event.clientY - rect.top));
|
|
30952
|
+
const time = timeFromCoordinate(this._private__chart, series, event.clientX - rect.left);
|
|
30953
|
+
if (price === null || time === null) {
|
|
30954
|
+
return;
|
|
30955
|
+
}
|
|
30956
|
+
tool.updateDrag(time, price);
|
|
30957
|
+
event.preventDefault();
|
|
30958
|
+
}
|
|
30847
30959
|
_private__handlePointerUp(event) {
|
|
30848
30960
|
if (!this._private__isDragging || this._private__draggedToolId === null) {
|
|
30849
30961
|
return;
|
|
@@ -31017,7 +31129,7 @@ const customSeriesDefaultOptions = {
|
|
|
31017
31129
|
* Returns the current version as a string. For example `'1.0.0'`.
|
|
31018
31130
|
*/
|
|
31019
31131
|
function version() {
|
|
31020
|
-
return "2.3.
|
|
31132
|
+
return "2.3.11";
|
|
31021
31133
|
}
|
|
31022
31134
|
|
|
31023
31135
|
export { areaSeries as AreaSeries, ArrowTool, barSeries as BarSeries, baselineSeries as BaselineSeries, BrushTool, candlestickSeries as CandlestickSeries, CircleTool, ColorType, CrossLineTool, CrosshairMode, DEFAULT_SESSIONS, DraggablePriceLine, DrawingToolsManager, EXTENDED_FIBONACCI_RATIOS, FibonacciCalculator, FibonacciExtensionTool, FibonacciFanTool, FibonacciTool, GanttTool, histogramSeries as HistogramSeries, HorizontalLineTool, InteractiveLineManager, LastPriceAnimationMode, lineSeries as LineSeries, LineStyle, LineType, MismatchDirection, ParallelChannelTool, PitchforkTool, PolygonTool, PositionCalculator, PositionLine, PositionMarkersManager, PositionTool, PriceLineSource, PriceScaleMode, RectangleTool, RulerCalculator, RulerTool, STANDARD_FIBONACCI_RATIOS, TextTool, TickMarkType, TrackingModeExitMode, TradingSessionsIndicator, TrendLineTool, VerticalLineTool, VolumeProfileIndicator, applyADX, applyATR, applyBollingerBands, applyCCI, applyDonchianChannels, applyEMA, applyHeikinAshi, applyIchimoku, applyKeltnerChannels, applyMACD, applyMFI, applyOBV, applyParabolicSAR, applyPivotPoints, applyRSI, applySMA, applyStochastic, applySuperTrend, applyVWAP, applyVolume, applyWMA, applyWilliamsR, calculateHeikinAshi, calculatePipConfig, coordinateFromTime, createArrowTool, createBrushTool, createChart, createChartEx, createCircleTool, createCrossLineTool, createFibonacciExtensionTool, createFibonacciFanTool, createFibonacciTool, createGanttTool, createHorizontalLineTool, createImageWatermark, createInteractiveLineManager, createOptionsChart, createParallelChannelTool, createPitchforkTool, createPolygonTool, createPositionLine, createPositionMarkers, createPositionTool, createRectangleTool, createRulerTool, createSeriesMarkers, createTextTool, createTextWatermark, createTradingLine, createTradingSessionsIndicator, createTrendLineTool, createUpDownMarkers, createVerticalLineTool, createVolumeProfileIndicator, createYieldCurveChart, customSeriesDefaultOptions, defaultHorzScaleBehavior, getPipConfig, hideSeriesPaint, isBusinessDay, isUTCTimestamp, setSeriesVolumes, setVolumeProfileData, timeFromCoordinate, version };
|