@pipsend/charts 2.3.4 → 2.3.10
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 +49 -35
- package/dist/pipsend-charts.production.mjs +2 -2
- package/dist/pipsend-charts.standalone.development.js +49 -35
- package/dist/pipsend-charts.standalone.development.mjs +49 -35
- package/dist/pipsend-charts.standalone.production.js +2 -2
- package/dist/pipsend-charts.standalone.production.mjs +2 -2
- package/dist/typings.d.ts +27 -0
- package/package.json +1 -83
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/*!
|
|
2
2
|
* @license
|
|
3
|
-
* Pipsend Charts v2.3.
|
|
3
|
+
* Pipsend Charts v2.3.10
|
|
4
4
|
* Copyright (c) 2026 Pipsend
|
|
5
5
|
* Licensed under MIT License
|
|
6
6
|
* Built on TradingView Lightweight Charts™ (Apache 2.0)
|
|
@@ -2486,14 +2486,8 @@
|
|
|
2486
2486
|
return this._private__styleGetter(this._private__findBar, this._private__series._internal_options(), barIndex, precomputedBars);
|
|
2487
2487
|
}
|
|
2488
2488
|
/**
|
|
2489
|
-
* Like `barStyle`, but
|
|
2490
|
-
*
|
|
2491
|
-
*
|
|
2492
|
-
* Recolouring walks items that were laid out against the data as it was. A
|
|
2493
|
-
* bar that has since disappeared is not an error there: the view is about
|
|
2494
|
-
* to be rebuilt from the new data anyway. Letting it throw took down
|
|
2495
|
-
* whatever asked for the repaint — including `setData`, which left the
|
|
2496
|
-
* series without its data and the pane empty until the page was reloaded.
|
|
2489
|
+
* Like `barStyle`, but null instead of throwing when the bar is gone, which
|
|
2490
|
+
* a recolour of items laid out against older data can hit.
|
|
2497
2491
|
*/
|
|
2498
2492
|
_internal_barStyleOrNull(barIndex, precomputedBars) {
|
|
2499
2493
|
if (precomputedBars === undefined && this._private__series._internal_bars()._internal_valueAt(barIndex) === null) {
|
|
@@ -2895,7 +2889,10 @@
|
|
|
2895
2889
|
commonRendererData._internal_additionalPaddingTop = additionalPadding;
|
|
2896
2890
|
commonRendererData._internal_additionalPaddingBottom = additionalPadding;
|
|
2897
2891
|
commonRendererData._internal_coordinate = data._internal_coordinate;
|
|
2898
|
-
|
|
2892
|
+
// Re-runs at draw time, after the axis has moved the label clear of overlaps.
|
|
2893
|
+
if (data._internal_fixedCoordinate !== undefined) {
|
|
2894
|
+
commonRendererData._internal_fixedCoordinate = data._internal_fixedCoordinate;
|
|
2895
|
+
}
|
|
2899
2896
|
axisRendererData._internal_text = data._internal_text;
|
|
2900
2897
|
axisRendererData._internal_visible = data._internal_visible;
|
|
2901
2898
|
axisRendererData._internal_tickVisible = data._internal_tickVisible;
|
|
@@ -3772,7 +3769,6 @@
|
|
|
3772
3769
|
}
|
|
3773
3770
|
}
|
|
3774
3771
|
|
|
3775
|
-
const TICK_DENSITY = 2.5;
|
|
3776
3772
|
class PriceTickMarkBuilder {
|
|
3777
3773
|
constructor(priceScale, base, coordinateToLogicalFunc, logicalToCoordinateFunc) {
|
|
3778
3774
|
this._private__marks = [];
|
|
@@ -3833,7 +3829,7 @@
|
|
|
3833
3829
|
return this._private__priceScale._internal_fontSize();
|
|
3834
3830
|
}
|
|
3835
3831
|
_private__tickMarkHeight() {
|
|
3836
|
-
return Math.ceil(this._private__fontHeight() *
|
|
3832
|
+
return Math.max(1, Math.ceil(this._private__fontHeight() * this._private__priceScale._internal_options().tickMarkSpacing));
|
|
3837
3833
|
}
|
|
3838
3834
|
_private__updateMarks(firstValue, span, high, low, minCoord, maxCoord) {
|
|
3839
3835
|
const marks = this._private__marks;
|
|
@@ -3998,6 +3994,9 @@
|
|
|
3998
3994
|
this._private__invalidateInternalHeightCache();
|
|
3999
3995
|
this._private__marksCache = null;
|
|
4000
3996
|
}
|
|
3997
|
+
if (options.tickMarkSpacing !== undefined) {
|
|
3998
|
+
this._private__marksCache = null;
|
|
3999
|
+
}
|
|
4001
4000
|
}
|
|
4002
4001
|
_internal_isAutoScale() {
|
|
4003
4002
|
return this._private__options.autoScale;
|
|
@@ -5175,6 +5174,9 @@
|
|
|
5175
5174
|
this._private__uniformDistribution = val;
|
|
5176
5175
|
this._private__cache = null;
|
|
5177
5176
|
}
|
|
5177
|
+
_internal_invalidate() {
|
|
5178
|
+
this._private__cache = null;
|
|
5179
|
+
}
|
|
5178
5180
|
_internal_setTimeScalePoints(newPoints, firstChangedPointIndex) {
|
|
5179
5181
|
this._private__removeMarksSinceIndex(firstChangedPointIndex);
|
|
5180
5182
|
this._private__cache = null;
|
|
@@ -5193,7 +5195,7 @@
|
|
|
5193
5195
|
});
|
|
5194
5196
|
}
|
|
5195
5197
|
}
|
|
5196
|
-
_internal_build(spacing, maxWidth, checkIndicesForData, indicesWithDataMap, indicesWithDataId) {
|
|
5198
|
+
_internal_build(spacing, maxWidth, checkIndicesForData, indicesWithDataMap, indicesWithDataId, allows = () => true) {
|
|
5197
5199
|
const maxIndexesPerMark = Math.ceil(maxWidth / spacing);
|
|
5198
5200
|
if (this._private__cache === null ||
|
|
5199
5201
|
this._private__cache._internal_maxIndexesPerMark !== maxIndexesPerMark ||
|
|
@@ -5202,7 +5204,7 @@
|
|
|
5202
5204
|
this._private__cache = {
|
|
5203
5205
|
_internal_indicesWithDataId: indicesWithDataId,
|
|
5204
5206
|
_internal_checkIndicesForData: checkIndicesForData,
|
|
5205
|
-
_internal_marks: this._private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap),
|
|
5207
|
+
_internal_marks: this._private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap, allows),
|
|
5206
5208
|
_internal_maxIndexesPerMark: maxIndexesPerMark,
|
|
5207
5209
|
};
|
|
5208
5210
|
}
|
|
@@ -5226,7 +5228,7 @@
|
|
|
5226
5228
|
this._private__marksByWeight.delete(weight);
|
|
5227
5229
|
}
|
|
5228
5230
|
}
|
|
5229
|
-
_private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap) {
|
|
5231
|
+
_private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap, allows) {
|
|
5230
5232
|
let marks = [];
|
|
5231
5233
|
const canBeIncluded = (mark) => !checkIndicesForData || indicesWithDataMap.has(mark.index);
|
|
5232
5234
|
for (const weight of Array.from(this._private__marksByWeight.keys()).sort((a, b) => b - a)) {
|
|
@@ -5244,6 +5246,11 @@
|
|
|
5244
5246
|
let leftIndex = -Infinity;
|
|
5245
5247
|
for (let i = 0; i < currentWeightLength; i++) {
|
|
5246
5248
|
const mark = currentWeight[i];
|
|
5249
|
+
// Skipped before the fit check: a rejected mark must not count as one
|
|
5250
|
+
// that did not fit, which with uniform distribution drops its whole weight.
|
|
5251
|
+
if (!allows(mark, maxIndexesPerMark)) {
|
|
5252
|
+
continue;
|
|
5253
|
+
}
|
|
5247
5254
|
const currentIndex = mark.index;
|
|
5248
5255
|
// Determine indexes with which current index will be compared
|
|
5249
5256
|
// All marks to the right is moved to new array
|
|
@@ -5550,7 +5557,7 @@
|
|
|
5550
5557
|
const visibleBars = ensureNotNull(this._internal_visibleStrictRange());
|
|
5551
5558
|
const firstBar = Math.max(visibleBars._internal_left(), visibleBars._internal_left() - indexPerLabel);
|
|
5552
5559
|
const lastBar = Math.max(visibleBars._internal_right(), visibleBars._internal_right() - indexPerLabel);
|
|
5553
|
-
const items = this._private__tickMarks._internal_build(spacing, maxLabelWidth, this._private__options.ignoreWhitespaceIndices, this._private__indicesWithData, this._private__indicesWithDataUpdateId);
|
|
5560
|
+
const items = this._private__tickMarks._internal_build(spacing, maxLabelWidth, this._private__options.ignoreWhitespaceIndices, this._private__indicesWithData, this._private__indicesWithDataUpdateId, (mark, barsPerMark) => this._private__horzScaleBehavior.allowsTickMark?.(mark, barsPerMark) ?? true);
|
|
5554
5561
|
// according to indexPerLabel value this value means "earliest index which _might be_ used as the second label on time scale"
|
|
5555
5562
|
const earliestIndexOfSecondLabel = this._private__firstIndex() + indexPerLabel;
|
|
5556
5563
|
// according to indexPerLabel value this value means "earliest index which _might be_ used as the second last label on time scale"
|
|
@@ -5928,6 +5935,7 @@
|
|
|
5928
5935
|
_private__invalidateTickMarks() {
|
|
5929
5936
|
this._private__resetTimeMarksCache();
|
|
5930
5937
|
this._private__formattedByWeight.clear();
|
|
5938
|
+
this._private__tickMarks._internal_invalidate();
|
|
5931
5939
|
}
|
|
5932
5940
|
_private__updateDateTimeFormatter() {
|
|
5933
5941
|
this._private__horzScaleBehavior.updateFormatter(this._private__localizationOptions);
|
|
@@ -7042,6 +7050,14 @@
|
|
|
7042
7050
|
const tp = item;
|
|
7043
7051
|
return this._private__dateTimeFormatter._internal_format(new Date(tp._internal_timestamp * 1000));
|
|
7044
7052
|
}
|
|
7053
|
+
allowsTickMark(tickMark, barsPerMark) {
|
|
7054
|
+
const filter = this._private__options.timeScale.tickMarkFilter;
|
|
7055
|
+
if (filter === undefined) {
|
|
7056
|
+
return true;
|
|
7057
|
+
}
|
|
7058
|
+
const tickMarkType = weightToTickMarkType(tickMark.weight, this._private__options.timeScale.timeVisible, this._private__options.timeScale.secondsVisible);
|
|
7059
|
+
return filter(tickMark.originalTime, tickMarkType, barsPerMark);
|
|
7060
|
+
}
|
|
7045
7061
|
formatTickmark(tickMark, localizationOptions) {
|
|
7046
7062
|
const tickMarkType = weightToTickMarkType(tickMark.weight, this._private__options.timeScale.timeVisible, this._private__options.timeScale.secondsVisible);
|
|
7047
7063
|
const options = this._private__options.timeScale;
|
|
@@ -11446,9 +11462,6 @@
|
|
|
11446
11462
|
_internal__updateOptions() {
|
|
11447
11463
|
const colorer = this._internal__series._internal_barColorer();
|
|
11448
11464
|
this._internal__items = this._internal__items.map((item) => {
|
|
11449
|
-
// An item whose bar is gone keeps the colour it had. Throwing here
|
|
11450
|
-
// took down whatever asked for the repaint — `setData` among them,
|
|
11451
|
-
// which left the series without its data and the pane empty.
|
|
11452
11465
|
const style = colorer._internal_barStyleOrNull(item._internal_time);
|
|
11453
11466
|
return style === null ? item : { ...item, ...style };
|
|
11454
11467
|
});
|
|
@@ -11751,6 +11764,7 @@
|
|
|
11751
11764
|
},
|
|
11752
11765
|
minimumWidth: 0,
|
|
11753
11766
|
ensureEdgeTickMarksVisible: false,
|
|
11767
|
+
tickMarkSpacing: 2.5,
|
|
11754
11768
|
};
|
|
11755
11769
|
|
|
11756
11770
|
const timeScaleOptionsDefaults = {
|
|
@@ -12846,8 +12860,6 @@
|
|
|
12846
12860
|
const colorer = this._internal__series._internal_barColorer();
|
|
12847
12861
|
this._internal__items = this._internal__series._internal_bars()._internal_rows().map((row) => {
|
|
12848
12862
|
const value = row._internal_value[3 /* PlotRowValueIndex.Close */];
|
|
12849
|
-
// The row travels with the point: without it the colorer looks it up
|
|
12850
|
-
// again by index, and that lookup could fail and take the repaint down.
|
|
12851
12863
|
return this._internal__createRawItem(row._internal_index, value, colorer, row);
|
|
12852
12864
|
});
|
|
12853
12865
|
}
|
|
@@ -12870,10 +12882,10 @@
|
|
|
12870
12882
|
if (point) {
|
|
12871
12883
|
const style = styleGetter(renderingScope, point);
|
|
12872
12884
|
if (style !== prevStyle) {
|
|
12873
|
-
context.beginPath();
|
|
12874
12885
|
if (prevStyle !== null) {
|
|
12875
12886
|
context.fill();
|
|
12876
12887
|
}
|
|
12888
|
+
context.beginPath();
|
|
12877
12889
|
context.fillStyle = style;
|
|
12878
12890
|
prevStyle = style;
|
|
12879
12891
|
}
|
|
@@ -13812,9 +13824,6 @@
|
|
|
13812
13824
|
}
|
|
13813
13825
|
_internal__fillRawPoints() {
|
|
13814
13826
|
const colorer = this._internal__series._internal_barColorer();
|
|
13815
|
-
// The row goes to the colorer as it is. Asking for the style by index
|
|
13816
|
-
// alone made it look the row up again, and that second lookup could come
|
|
13817
|
-
// back empty and throw, taking the whole repaint down with it.
|
|
13818
13827
|
this._internal__items = this._internal__series._internal_bars()._internal_rows().map((row) => this._internal__createRawItem(row._internal_index, row, colorer));
|
|
13819
13828
|
}
|
|
13820
13829
|
}
|
|
@@ -17885,7 +17894,7 @@
|
|
|
17885
17894
|
hideSource: options.hideSource ?? true,
|
|
17886
17895
|
};
|
|
17887
17896
|
const sourceOptions = series.options();
|
|
17888
|
-
// Same price scale and
|
|
17897
|
+
// Same price scale, formatting and axis labels as the source: the candles are a
|
|
17889
17898
|
// restatement of that series, not a second instrument, so they must not
|
|
17890
17899
|
// autoscale on their own axis or round to a different precision.
|
|
17891
17900
|
const haSeries = chart.addSeries(candlestickSeries, {
|
|
@@ -17899,6 +17908,8 @@
|
|
|
17899
17908
|
wickDownColor: resolved.wickDownColor,
|
|
17900
17909
|
priceScaleId: sourceOptions.priceScaleId,
|
|
17901
17910
|
priceFormat: sourceOptions.priceFormat,
|
|
17911
|
+
lastValueVisible: sourceOptions.lastValueVisible,
|
|
17912
|
+
priceLineVisible: sourceOptions.priceLineVisible,
|
|
17902
17913
|
}, resolved.paneIndex);
|
|
17903
17914
|
let restoreSourcePaint = null;
|
|
17904
17915
|
const blankSource = (blank) => {
|
|
@@ -18100,12 +18111,14 @@
|
|
|
18100
18111
|
const macdSeries = chart.addSeries(lineSeries, {
|
|
18101
18112
|
color: resolved.colorMACD,
|
|
18102
18113
|
}, paneIndex);
|
|
18114
|
+
// An index past the last pane opens a new one, so the rest follow MACD to where it landed.
|
|
18115
|
+
const macdPane = paneIndexOf(chart, macdSeries, paneIndex);
|
|
18103
18116
|
const signalSeries = chart.addSeries(lineSeries, {
|
|
18104
18117
|
color: resolved.colorSignal,
|
|
18105
|
-
},
|
|
18118
|
+
}, macdPane);
|
|
18106
18119
|
const histogramSeries$1 = chart.addSeries(histogramSeries, {
|
|
18107
18120
|
color: resolved.colorHistogramUp,
|
|
18108
|
-
},
|
|
18121
|
+
}, macdPane);
|
|
18109
18122
|
// Calculate EMA
|
|
18110
18123
|
const calculateEMA = (prices, period) => {
|
|
18111
18124
|
const ema = [];
|
|
@@ -18237,13 +18250,13 @@
|
|
|
18237
18250
|
// Stochastic is bounded to 0-100; pinning it keeps the pane readable
|
|
18238
18251
|
autoscaleInfoProvider: boundedScale,
|
|
18239
18252
|
}, paneIndex);
|
|
18253
|
+
// An index past the last pane opens a new one, so %D follows %K to where it landed.
|
|
18254
|
+
const scalePane = paneIndexOf(chart, kSeries, paneIndex);
|
|
18240
18255
|
// Create %D line (slow - signal)
|
|
18241
18256
|
const dSeries = chart.addSeries(lineSeries, {
|
|
18242
18257
|
color: resolved.colorD,
|
|
18243
18258
|
autoscaleInfoProvider: boundedScale,
|
|
18244
|
-
},
|
|
18245
|
-
// The pane the series landed in, which is not always the one asked for.
|
|
18246
|
-
const scalePane = paneIndexOf(chart, kSeries, paneIndex);
|
|
18259
|
+
}, scalePane);
|
|
18247
18260
|
chart.priceScale(kSeries.options().priceScaleId ?? 'right', scalePane).applyOptions({
|
|
18248
18261
|
scaleMargins: {
|
|
18249
18262
|
top: 0.1,
|
|
@@ -18585,15 +18598,16 @@
|
|
|
18585
18598
|
color: resolved.colorADX,
|
|
18586
18599
|
autoscaleInfoProvider: boundedScale,
|
|
18587
18600
|
}, paneIndex);
|
|
18601
|
+
// An index past the last pane opens a new one, so the DI lines follow ADX to where it landed.
|
|
18602
|
+
const scalePane = paneIndexOf(chart, adxSeries, paneIndex);
|
|
18588
18603
|
const plusSeries = chart.addSeries(lineSeries, {
|
|
18589
18604
|
color: resolved.colorPlusDI,
|
|
18590
18605
|
autoscaleInfoProvider: boundedScale,
|
|
18591
|
-
},
|
|
18606
|
+
}, scalePane);
|
|
18592
18607
|
const minusSeries = chart.addSeries(lineSeries, {
|
|
18593
18608
|
color: resolved.colorMinusDI,
|
|
18594
18609
|
autoscaleInfoProvider: boundedScale,
|
|
18595
|
-
},
|
|
18596
|
-
const scalePane = paneIndexOf(chart, adxSeries, paneIndex);
|
|
18610
|
+
}, scalePane);
|
|
18597
18611
|
chart.priceScale(adxSeries.options().priceScaleId ?? 'right', scalePane).applyOptions({
|
|
18598
18612
|
scaleMargins: {
|
|
18599
18613
|
top: 0.1,
|
|
@@ -31006,7 +31020,7 @@
|
|
|
31006
31020
|
* Returns the current version as a string. For example `'1.0.0'`.
|
|
31007
31021
|
*/
|
|
31008
31022
|
function version() {
|
|
31009
|
-
return "2.3.
|
|
31023
|
+
return "2.3.10";
|
|
31010
31024
|
}
|
|
31011
31025
|
|
|
31012
31026
|
var PipsendChartsModule = /*#__PURE__*/Object.freeze({
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/*!
|
|
2
2
|
* @license
|
|
3
|
-
* Pipsend Charts v2.3.
|
|
3
|
+
* Pipsend Charts v2.3.10
|
|
4
4
|
* Copyright (c) 2026 Pipsend
|
|
5
5
|
* Licensed under MIT License
|
|
6
6
|
* Built on TradingView Lightweight Charts™ (Apache 2.0)
|
|
@@ -2483,14 +2483,8 @@ class SeriesBarColorer {
|
|
|
2483
2483
|
return this._private__styleGetter(this._private__findBar, this._private__series._internal_options(), barIndex, precomputedBars);
|
|
2484
2484
|
}
|
|
2485
2485
|
/**
|
|
2486
|
-
* Like `barStyle`, but
|
|
2487
|
-
*
|
|
2488
|
-
*
|
|
2489
|
-
* Recolouring walks items that were laid out against the data as it was. A
|
|
2490
|
-
* bar that has since disappeared is not an error there: the view is about
|
|
2491
|
-
* to be rebuilt from the new data anyway. Letting it throw took down
|
|
2492
|
-
* whatever asked for the repaint — including `setData`, which left the
|
|
2493
|
-
* series without its data and the pane empty until the page was reloaded.
|
|
2486
|
+
* Like `barStyle`, but null instead of throwing when the bar is gone, which
|
|
2487
|
+
* a recolour of items laid out against older data can hit.
|
|
2494
2488
|
*/
|
|
2495
2489
|
_internal_barStyleOrNull(barIndex, precomputedBars) {
|
|
2496
2490
|
if (precomputedBars === undefined && this._private__series._internal_bars()._internal_valueAt(barIndex) === null) {
|
|
@@ -2892,7 +2886,10 @@ class SeriesPrimitivePriceAxisViewWrapper extends PriceAxisView {
|
|
|
2892
2886
|
commonRendererData._internal_additionalPaddingTop = additionalPadding;
|
|
2893
2887
|
commonRendererData._internal_additionalPaddingBottom = additionalPadding;
|
|
2894
2888
|
commonRendererData._internal_coordinate = data._internal_coordinate;
|
|
2895
|
-
|
|
2889
|
+
// Re-runs at draw time, after the axis has moved the label clear of overlaps.
|
|
2890
|
+
if (data._internal_fixedCoordinate !== undefined) {
|
|
2891
|
+
commonRendererData._internal_fixedCoordinate = data._internal_fixedCoordinate;
|
|
2892
|
+
}
|
|
2896
2893
|
axisRendererData._internal_text = data._internal_text;
|
|
2897
2894
|
axisRendererData._internal_visible = data._internal_visible;
|
|
2898
2895
|
axisRendererData._internal_tickVisible = data._internal_tickVisible;
|
|
@@ -3769,7 +3766,6 @@ class PriceTickSpanCalculator {
|
|
|
3769
3766
|
}
|
|
3770
3767
|
}
|
|
3771
3768
|
|
|
3772
|
-
const TICK_DENSITY = 2.5;
|
|
3773
3769
|
class PriceTickMarkBuilder {
|
|
3774
3770
|
constructor(priceScale, base, coordinateToLogicalFunc, logicalToCoordinateFunc) {
|
|
3775
3771
|
this._private__marks = [];
|
|
@@ -3830,7 +3826,7 @@ class PriceTickMarkBuilder {
|
|
|
3830
3826
|
return this._private__priceScale._internal_fontSize();
|
|
3831
3827
|
}
|
|
3832
3828
|
_private__tickMarkHeight() {
|
|
3833
|
-
return Math.ceil(this._private__fontHeight() *
|
|
3829
|
+
return Math.max(1, Math.ceil(this._private__fontHeight() * this._private__priceScale._internal_options().tickMarkSpacing));
|
|
3834
3830
|
}
|
|
3835
3831
|
_private__updateMarks(firstValue, span, high, low, minCoord, maxCoord) {
|
|
3836
3832
|
const marks = this._private__marks;
|
|
@@ -3995,6 +3991,9 @@ class PriceScale {
|
|
|
3995
3991
|
this._private__invalidateInternalHeightCache();
|
|
3996
3992
|
this._private__marksCache = null;
|
|
3997
3993
|
}
|
|
3994
|
+
if (options.tickMarkSpacing !== undefined) {
|
|
3995
|
+
this._private__marksCache = null;
|
|
3996
|
+
}
|
|
3998
3997
|
}
|
|
3999
3998
|
_internal_isAutoScale() {
|
|
4000
3999
|
return this._private__options.autoScale;
|
|
@@ -5172,6 +5171,9 @@ class TickMarks {
|
|
|
5172
5171
|
this._private__uniformDistribution = val;
|
|
5173
5172
|
this._private__cache = null;
|
|
5174
5173
|
}
|
|
5174
|
+
_internal_invalidate() {
|
|
5175
|
+
this._private__cache = null;
|
|
5176
|
+
}
|
|
5175
5177
|
_internal_setTimeScalePoints(newPoints, firstChangedPointIndex) {
|
|
5176
5178
|
this._private__removeMarksSinceIndex(firstChangedPointIndex);
|
|
5177
5179
|
this._private__cache = null;
|
|
@@ -5190,7 +5192,7 @@ class TickMarks {
|
|
|
5190
5192
|
});
|
|
5191
5193
|
}
|
|
5192
5194
|
}
|
|
5193
|
-
_internal_build(spacing, maxWidth, checkIndicesForData, indicesWithDataMap, indicesWithDataId) {
|
|
5195
|
+
_internal_build(spacing, maxWidth, checkIndicesForData, indicesWithDataMap, indicesWithDataId, allows = () => true) {
|
|
5194
5196
|
const maxIndexesPerMark = Math.ceil(maxWidth / spacing);
|
|
5195
5197
|
if (this._private__cache === null ||
|
|
5196
5198
|
this._private__cache._internal_maxIndexesPerMark !== maxIndexesPerMark ||
|
|
@@ -5199,7 +5201,7 @@ class TickMarks {
|
|
|
5199
5201
|
this._private__cache = {
|
|
5200
5202
|
_internal_indicesWithDataId: indicesWithDataId,
|
|
5201
5203
|
_internal_checkIndicesForData: checkIndicesForData,
|
|
5202
|
-
_internal_marks: this._private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap),
|
|
5204
|
+
_internal_marks: this._private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap, allows),
|
|
5203
5205
|
_internal_maxIndexesPerMark: maxIndexesPerMark,
|
|
5204
5206
|
};
|
|
5205
5207
|
}
|
|
@@ -5223,7 +5225,7 @@ class TickMarks {
|
|
|
5223
5225
|
this._private__marksByWeight.delete(weight);
|
|
5224
5226
|
}
|
|
5225
5227
|
}
|
|
5226
|
-
_private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap) {
|
|
5228
|
+
_private__buildMarksImpl(maxIndexesPerMark, checkIndicesForData, indicesWithDataMap, allows) {
|
|
5227
5229
|
let marks = [];
|
|
5228
5230
|
const canBeIncluded = (mark) => !checkIndicesForData || indicesWithDataMap.has(mark.index);
|
|
5229
5231
|
for (const weight of Array.from(this._private__marksByWeight.keys()).sort((a, b) => b - a)) {
|
|
@@ -5241,6 +5243,11 @@ class TickMarks {
|
|
|
5241
5243
|
let leftIndex = -Infinity;
|
|
5242
5244
|
for (let i = 0; i < currentWeightLength; i++) {
|
|
5243
5245
|
const mark = currentWeight[i];
|
|
5246
|
+
// Skipped before the fit check: a rejected mark must not count as one
|
|
5247
|
+
// that did not fit, which with uniform distribution drops its whole weight.
|
|
5248
|
+
if (!allows(mark, maxIndexesPerMark)) {
|
|
5249
|
+
continue;
|
|
5250
|
+
}
|
|
5244
5251
|
const currentIndex = mark.index;
|
|
5245
5252
|
// Determine indexes with which current index will be compared
|
|
5246
5253
|
// All marks to the right is moved to new array
|
|
@@ -5547,7 +5554,7 @@ class TimeScale {
|
|
|
5547
5554
|
const visibleBars = ensureNotNull(this._internal_visibleStrictRange());
|
|
5548
5555
|
const firstBar = Math.max(visibleBars._internal_left(), visibleBars._internal_left() - indexPerLabel);
|
|
5549
5556
|
const lastBar = Math.max(visibleBars._internal_right(), visibleBars._internal_right() - indexPerLabel);
|
|
5550
|
-
const items = this._private__tickMarks._internal_build(spacing, maxLabelWidth, this._private__options.ignoreWhitespaceIndices, this._private__indicesWithData, this._private__indicesWithDataUpdateId);
|
|
5557
|
+
const items = this._private__tickMarks._internal_build(spacing, maxLabelWidth, this._private__options.ignoreWhitespaceIndices, this._private__indicesWithData, this._private__indicesWithDataUpdateId, (mark, barsPerMark) => this._private__horzScaleBehavior.allowsTickMark?.(mark, barsPerMark) ?? true);
|
|
5551
5558
|
// according to indexPerLabel value this value means "earliest index which _might be_ used as the second label on time scale"
|
|
5552
5559
|
const earliestIndexOfSecondLabel = this._private__firstIndex() + indexPerLabel;
|
|
5553
5560
|
// according to indexPerLabel value this value means "earliest index which _might be_ used as the second last label on time scale"
|
|
@@ -5925,6 +5932,7 @@ class TimeScale {
|
|
|
5925
5932
|
_private__invalidateTickMarks() {
|
|
5926
5933
|
this._private__resetTimeMarksCache();
|
|
5927
5934
|
this._private__formattedByWeight.clear();
|
|
5935
|
+
this._private__tickMarks._internal_invalidate();
|
|
5928
5936
|
}
|
|
5929
5937
|
_private__updateDateTimeFormatter() {
|
|
5930
5938
|
this._private__horzScaleBehavior.updateFormatter(this._private__localizationOptions);
|
|
@@ -7039,6 +7047,14 @@ class HorzScaleBehaviorTime {
|
|
|
7039
7047
|
const tp = item;
|
|
7040
7048
|
return this._private__dateTimeFormatter._internal_format(new Date(tp._internal_timestamp * 1000));
|
|
7041
7049
|
}
|
|
7050
|
+
allowsTickMark(tickMark, barsPerMark) {
|
|
7051
|
+
const filter = this._private__options.timeScale.tickMarkFilter;
|
|
7052
|
+
if (filter === undefined) {
|
|
7053
|
+
return true;
|
|
7054
|
+
}
|
|
7055
|
+
const tickMarkType = weightToTickMarkType(tickMark.weight, this._private__options.timeScale.timeVisible, this._private__options.timeScale.secondsVisible);
|
|
7056
|
+
return filter(tickMark.originalTime, tickMarkType, barsPerMark);
|
|
7057
|
+
}
|
|
7042
7058
|
formatTickmark(tickMark, localizationOptions) {
|
|
7043
7059
|
const tickMarkType = weightToTickMarkType(tickMark.weight, this._private__options.timeScale.timeVisible, this._private__options.timeScale.secondsVisible);
|
|
7044
7060
|
const options = this._private__options.timeScale;
|
|
@@ -11443,9 +11459,6 @@ class SeriesPaneViewBase {
|
|
|
11443
11459
|
_internal__updateOptions() {
|
|
11444
11460
|
const colorer = this._internal__series._internal_barColorer();
|
|
11445
11461
|
this._internal__items = this._internal__items.map((item) => {
|
|
11446
|
-
// An item whose bar is gone keeps the colour it had. Throwing here
|
|
11447
|
-
// took down whatever asked for the repaint — `setData` among them,
|
|
11448
|
-
// which left the series without its data and the pane empty.
|
|
11449
11462
|
const style = colorer._internal_barStyleOrNull(item._internal_time);
|
|
11450
11463
|
return style === null ? item : { ...item, ...style };
|
|
11451
11464
|
});
|
|
@@ -11748,6 +11761,7 @@ const priceScaleOptionsDefaults = {
|
|
|
11748
11761
|
},
|
|
11749
11762
|
minimumWidth: 0,
|
|
11750
11763
|
ensureEdgeTickMarksVisible: false,
|
|
11764
|
+
tickMarkSpacing: 2.5,
|
|
11751
11765
|
};
|
|
11752
11766
|
|
|
11753
11767
|
const timeScaleOptionsDefaults = {
|
|
@@ -12843,8 +12857,6 @@ class LinePaneViewBase extends SeriesPaneViewBase {
|
|
|
12843
12857
|
const colorer = this._internal__series._internal_barColorer();
|
|
12844
12858
|
this._internal__items = this._internal__series._internal_bars()._internal_rows().map((row) => {
|
|
12845
12859
|
const value = row._internal_value[3 /* PlotRowValueIndex.Close */];
|
|
12846
|
-
// The row travels with the point: without it the colorer looks it up
|
|
12847
|
-
// again by index, and that lookup could fail and take the repaint down.
|
|
12848
12860
|
return this._internal__createRawItem(row._internal_index, value, colorer, row);
|
|
12849
12861
|
});
|
|
12850
12862
|
}
|
|
@@ -12867,10 +12879,10 @@ styleGetter) {
|
|
|
12867
12879
|
if (point) {
|
|
12868
12880
|
const style = styleGetter(renderingScope, point);
|
|
12869
12881
|
if (style !== prevStyle) {
|
|
12870
|
-
context.beginPath();
|
|
12871
12882
|
if (prevStyle !== null) {
|
|
12872
12883
|
context.fill();
|
|
12873
12884
|
}
|
|
12885
|
+
context.beginPath();
|
|
12874
12886
|
context.fillStyle = style;
|
|
12875
12887
|
prevStyle = style;
|
|
12876
12888
|
}
|
|
@@ -13809,9 +13821,6 @@ class BarsPaneViewBase extends SeriesPaneViewBase {
|
|
|
13809
13821
|
}
|
|
13810
13822
|
_internal__fillRawPoints() {
|
|
13811
13823
|
const colorer = this._internal__series._internal_barColorer();
|
|
13812
|
-
// The row goes to the colorer as it is. Asking for the style by index
|
|
13813
|
-
// alone made it look the row up again, and that second lookup could come
|
|
13814
|
-
// back empty and throw, taking the whole repaint down with it.
|
|
13815
13824
|
this._internal__items = this._internal__series._internal_bars()._internal_rows().map((row) => this._internal__createRawItem(row._internal_index, row, colorer));
|
|
13816
13825
|
}
|
|
13817
13826
|
}
|
|
@@ -17882,7 +17891,7 @@ function applyHeikinAshi(series, chart, options = {}) {
|
|
|
17882
17891
|
hideSource: options.hideSource ?? true,
|
|
17883
17892
|
};
|
|
17884
17893
|
const sourceOptions = series.options();
|
|
17885
|
-
// Same price scale and
|
|
17894
|
+
// Same price scale, formatting and axis labels as the source: the candles are a
|
|
17886
17895
|
// restatement of that series, not a second instrument, so they must not
|
|
17887
17896
|
// autoscale on their own axis or round to a different precision.
|
|
17888
17897
|
const haSeries = chart.addSeries(candlestickSeries, {
|
|
@@ -17896,6 +17905,8 @@ function applyHeikinAshi(series, chart, options = {}) {
|
|
|
17896
17905
|
wickDownColor: resolved.wickDownColor,
|
|
17897
17906
|
priceScaleId: sourceOptions.priceScaleId,
|
|
17898
17907
|
priceFormat: sourceOptions.priceFormat,
|
|
17908
|
+
lastValueVisible: sourceOptions.lastValueVisible,
|
|
17909
|
+
priceLineVisible: sourceOptions.priceLineVisible,
|
|
17899
17910
|
}, resolved.paneIndex);
|
|
17900
17911
|
let restoreSourcePaint = null;
|
|
17901
17912
|
const blankSource = (blank) => {
|
|
@@ -18097,12 +18108,14 @@ function applyMACD(series, chart, options = {}) {
|
|
|
18097
18108
|
const macdSeries = chart.addSeries(lineSeries, {
|
|
18098
18109
|
color: resolved.colorMACD,
|
|
18099
18110
|
}, paneIndex);
|
|
18111
|
+
// An index past the last pane opens a new one, so the rest follow MACD to where it landed.
|
|
18112
|
+
const macdPane = paneIndexOf(chart, macdSeries, paneIndex);
|
|
18100
18113
|
const signalSeries = chart.addSeries(lineSeries, {
|
|
18101
18114
|
color: resolved.colorSignal,
|
|
18102
|
-
},
|
|
18115
|
+
}, macdPane);
|
|
18103
18116
|
const histogramSeries$1 = chart.addSeries(histogramSeries, {
|
|
18104
18117
|
color: resolved.colorHistogramUp,
|
|
18105
|
-
},
|
|
18118
|
+
}, macdPane);
|
|
18106
18119
|
// Calculate EMA
|
|
18107
18120
|
const calculateEMA = (prices, period) => {
|
|
18108
18121
|
const ema = [];
|
|
@@ -18234,13 +18247,13 @@ function applyStochastic(series, chart, options = {}) {
|
|
|
18234
18247
|
// Stochastic is bounded to 0-100; pinning it keeps the pane readable
|
|
18235
18248
|
autoscaleInfoProvider: boundedScale,
|
|
18236
18249
|
}, paneIndex);
|
|
18250
|
+
// An index past the last pane opens a new one, so %D follows %K to where it landed.
|
|
18251
|
+
const scalePane = paneIndexOf(chart, kSeries, paneIndex);
|
|
18237
18252
|
// Create %D line (slow - signal)
|
|
18238
18253
|
const dSeries = chart.addSeries(lineSeries, {
|
|
18239
18254
|
color: resolved.colorD,
|
|
18240
18255
|
autoscaleInfoProvider: boundedScale,
|
|
18241
|
-
},
|
|
18242
|
-
// The pane the series landed in, which is not always the one asked for.
|
|
18243
|
-
const scalePane = paneIndexOf(chart, kSeries, paneIndex);
|
|
18256
|
+
}, scalePane);
|
|
18244
18257
|
chart.priceScale(kSeries.options().priceScaleId ?? 'right', scalePane).applyOptions({
|
|
18245
18258
|
scaleMargins: {
|
|
18246
18259
|
top: 0.1,
|
|
@@ -18582,15 +18595,16 @@ function applyADX(series, chart, options = {}) {
|
|
|
18582
18595
|
color: resolved.colorADX,
|
|
18583
18596
|
autoscaleInfoProvider: boundedScale,
|
|
18584
18597
|
}, paneIndex);
|
|
18598
|
+
// An index past the last pane opens a new one, so the DI lines follow ADX to where it landed.
|
|
18599
|
+
const scalePane = paneIndexOf(chart, adxSeries, paneIndex);
|
|
18585
18600
|
const plusSeries = chart.addSeries(lineSeries, {
|
|
18586
18601
|
color: resolved.colorPlusDI,
|
|
18587
18602
|
autoscaleInfoProvider: boundedScale,
|
|
18588
|
-
},
|
|
18603
|
+
}, scalePane);
|
|
18589
18604
|
const minusSeries = chart.addSeries(lineSeries, {
|
|
18590
18605
|
color: resolved.colorMinusDI,
|
|
18591
18606
|
autoscaleInfoProvider: boundedScale,
|
|
18592
|
-
},
|
|
18593
|
-
const scalePane = paneIndexOf(chart, adxSeries, paneIndex);
|
|
18607
|
+
}, scalePane);
|
|
18594
18608
|
chart.priceScale(adxSeries.options().priceScaleId ?? 'right', scalePane).applyOptions({
|
|
18595
18609
|
scaleMargins: {
|
|
18596
18610
|
top: 0.1,
|
|
@@ -31003,7 +31017,7 @@ const customSeriesDefaultOptions = {
|
|
|
31003
31017
|
* Returns the current version as a string. For example `'1.0.0'`.
|
|
31004
31018
|
*/
|
|
31005
31019
|
function version() {
|
|
31006
|
-
return "2.3.
|
|
31020
|
+
return "2.3.10";
|
|
31007
31021
|
}
|
|
31008
31022
|
|
|
31009
31023
|
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 };
|