612 lines
21 KiB
JavaScript
612 lines
21 KiB
JavaScript
/* *
|
|
*
|
|
* (c) 2010-2021 Torstein Honsi
|
|
*
|
|
* License: www.highcharts.com/license
|
|
*
|
|
* !!!!!!! SOURCE GETS TRANSPILED BY TYPESCRIPT. EDIT TS FILE ONLY. !!!!!!!
|
|
*
|
|
* */
|
|
'use strict';
|
|
var __extends = (this && this.__extends) || (function () {
|
|
var extendStatics = function (d, b) {
|
|
extendStatics = Object.setPrototypeOf ||
|
|
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
|
|
function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };
|
|
return extendStatics(d, b);
|
|
};
|
|
return function (d, b) {
|
|
if (typeof b !== "function" && b !== null)
|
|
throw new TypeError("Class extends value " + String(b) + " is not a constructor or null");
|
|
extendStatics(d, b);
|
|
function __() { this.constructor = d; }
|
|
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
|
|
};
|
|
})();
|
|
import FlagsPoint from './FlagsPoint.js';
|
|
import H from '../../Core/Globals.js';
|
|
var noop = H.noop;
|
|
import OnSeriesComposition from '../OnSeriesComposition.js';
|
|
import R from '../../Core/Renderer/RendererUtilities.js';
|
|
var distribute = R.distribute;
|
|
import SeriesRegistry from '../../Core/Series/SeriesRegistry.js';
|
|
var Series = SeriesRegistry.series, ColumnSeries = SeriesRegistry.seriesTypes.column;
|
|
import SVGElement from '../../Core/Renderer/SVG/SVGElement.js';
|
|
import U from '../../Core/Utilities.js';
|
|
var addEvent = U.addEvent, defined = U.defined, extend = U.extend, merge = U.merge, objectEach = U.objectEach, wrap = U.wrap;
|
|
import './FlagsSymbols.js';
|
|
/* *
|
|
*
|
|
* Classes
|
|
*
|
|
* */
|
|
/**
|
|
* The Flags series.
|
|
*
|
|
* @private
|
|
* @class
|
|
* @name Highcharts.seriesTypes.flags
|
|
*
|
|
* @augments Highcharts.Series
|
|
*/
|
|
var FlagsSeries = /** @class */ (function (_super) {
|
|
__extends(FlagsSeries, _super);
|
|
function FlagsSeries() {
|
|
/* *
|
|
*
|
|
* Static Properties
|
|
*
|
|
* */
|
|
var _this = _super !== null && _super.apply(this, arguments) || this;
|
|
/* *
|
|
*
|
|
* Properties
|
|
*
|
|
* */
|
|
_this.data = void 0;
|
|
_this.options = void 0;
|
|
_this.points = void 0;
|
|
return _this;
|
|
/* eslint-enable valid-jsdoc */
|
|
}
|
|
/* *
|
|
*
|
|
* Functions
|
|
*
|
|
* */
|
|
/* eslint-disable valid-jsdoc */
|
|
/**
|
|
* Disable animation, but keep clipping (#8546).
|
|
* @private
|
|
*/
|
|
FlagsSeries.prototype.animate = function (init) {
|
|
if (init) {
|
|
this.setClip();
|
|
}
|
|
};
|
|
/**
|
|
* Draw the markers.
|
|
* @private
|
|
*/
|
|
FlagsSeries.prototype.drawPoints = function () {
|
|
var series = this, points = series.points, chart = series.chart, renderer = chart.renderer, plotX, plotY, inverted = chart.inverted, options = series.options, optionsY = options.y, shape, i, point, graphic, stackIndex, anchorY, attribs, outsideRight, yAxis = series.yAxis, boxesMap = {}, boxes = [], centered;
|
|
i = points.length;
|
|
while (i--) {
|
|
point = points[i];
|
|
outsideRight =
|
|
(inverted ? point.plotY : point.plotX) >
|
|
series.xAxis.len;
|
|
plotX = point.plotX;
|
|
stackIndex = point.stackIndex;
|
|
shape = point.options.shape || options.shape;
|
|
plotY = point.plotY;
|
|
if (typeof plotY !== 'undefined') {
|
|
plotY = point.plotY + optionsY -
|
|
(typeof stackIndex !== 'undefined' &&
|
|
(stackIndex * options.stackDistance));
|
|
}
|
|
// skip connectors for higher level stacked points
|
|
point.anchorX = stackIndex ? void 0 : point.plotX;
|
|
anchorY = stackIndex ? void 0 : point.plotY;
|
|
centered = shape !== 'flag';
|
|
graphic = point.graphic;
|
|
// Only draw the point if y is defined and the flag is within
|
|
// the visible area
|
|
if (typeof plotY !== 'undefined' &&
|
|
plotX >= 0 &&
|
|
!outsideRight) {
|
|
// #15384
|
|
if (graphic && point.hasNewShapeType()) {
|
|
graphic = graphic.destroy();
|
|
}
|
|
// Create the flag
|
|
if (!graphic) {
|
|
graphic = point.graphic = renderer.label('', null, null, shape, null, null, options.useHTML)
|
|
.addClass('highcharts-point')
|
|
.add(series.markerGroup);
|
|
// Add reference to the point for tracker (#6303)
|
|
if (point.graphic.div) {
|
|
point.graphic.div.point = point;
|
|
}
|
|
graphic.isNew = true;
|
|
}
|
|
graphic.attr({
|
|
align: centered ? 'center' : 'left',
|
|
width: options.width,
|
|
height: options.height,
|
|
'text-align': options.textAlign
|
|
});
|
|
if (!chart.styledMode) {
|
|
graphic
|
|
.attr(series.pointAttribs(point))
|
|
.css(merge(options.style, point.style))
|
|
.shadow(options.shadow);
|
|
}
|
|
if (plotX > 0) { // #3119
|
|
plotX -= graphic.strokeWidth() % 2; // #4285
|
|
}
|
|
// Plant the flag
|
|
attribs = {
|
|
y: plotY,
|
|
anchorY: anchorY
|
|
};
|
|
if (options.allowOverlapX) {
|
|
attribs.x = plotX;
|
|
attribs.anchorX = point.anchorX;
|
|
}
|
|
graphic.attr({
|
|
text: point.options.title || options.title || 'A'
|
|
})[graphic.isNew ? 'attr' : 'animate'](attribs);
|
|
// Rig for the distribute function
|
|
if (!options.allowOverlapX) {
|
|
if (!boxesMap[point.plotX]) {
|
|
boxesMap[point.plotX] = {
|
|
align: centered ? 0.5 : 0,
|
|
size: graphic.width,
|
|
target: plotX,
|
|
anchorX: plotX
|
|
};
|
|
}
|
|
else {
|
|
boxesMap[point.plotX].size = Math.max(boxesMap[point.plotX].size, graphic.width);
|
|
}
|
|
}
|
|
// Set the tooltip anchor position
|
|
point.tooltipPos = [
|
|
plotX,
|
|
plotY + yAxis.pos - chart.plotTop
|
|
]; // #6327
|
|
}
|
|
else if (graphic) {
|
|
point.graphic = graphic.destroy();
|
|
}
|
|
}
|
|
// Handle X-dimension overlapping
|
|
if (!options.allowOverlapX) {
|
|
var maxDistance_1 = 100;
|
|
objectEach(boxesMap, function (box) {
|
|
box.plotX = box.anchorX;
|
|
boxes.push(box);
|
|
maxDistance_1 = Math.max(box.size, maxDistance_1);
|
|
});
|
|
// If necessary (for overlapping or long labels) distribute it
|
|
// depending on the label width or a hardcoded value, #16041.
|
|
distribute(boxes, inverted ? yAxis.len : this.xAxis.len, maxDistance_1);
|
|
points.forEach(function (point) {
|
|
var plotX = point.plotX, graphic = point.graphic, box = graphic && boxesMap[plotX];
|
|
if (box && graphic) {
|
|
// Hide flag when its box position is not specified
|
|
// (#8573, #9299)
|
|
if (!defined(box.pos)) {
|
|
graphic.hide().isNew = true;
|
|
}
|
|
else {
|
|
graphic[graphic.isNew ? 'attr' : 'animate']({
|
|
x: box.pos + (box.align || 0) * box.size,
|
|
anchorX: point.anchorX
|
|
}).show().isNew = false;
|
|
}
|
|
}
|
|
});
|
|
}
|
|
// Can be a mix of SVG and HTML and we need events for both (#6303)
|
|
if (options.useHTML) {
|
|
wrap(series.markerGroup, 'on', function (proceed) {
|
|
return SVGElement.prototype.on.apply(
|
|
// for HTML
|
|
// eslint-disable-next-line no-invalid-this
|
|
proceed.apply(this, [].slice.call(arguments, 1)),
|
|
// and for SVG
|
|
[].slice.call(arguments, 1));
|
|
});
|
|
}
|
|
};
|
|
/**
|
|
* Extend the column trackers with listeners to expand and contract
|
|
* stacks.
|
|
* @private
|
|
*/
|
|
FlagsSeries.prototype.drawTracker = function () {
|
|
var series = this, points = series.points;
|
|
_super.prototype.drawTracker.call(this);
|
|
/* *
|
|
* Bring each stacked flag up on mouse over, this allows readability
|
|
* of vertically stacked elements as well as tight points on the x
|
|
* axis. #1924.
|
|
*/
|
|
points.forEach(function (point) {
|
|
var graphic = point.graphic;
|
|
if (graphic) {
|
|
if (point.unbindMouseOver) {
|
|
point.unbindMouseOver();
|
|
}
|
|
point.unbindMouseOver = addEvent(graphic.element, 'mouseover', function () {
|
|
// Raise this point
|
|
if (point.stackIndex > 0 &&
|
|
!point.raised) {
|
|
point._y = graphic.y;
|
|
graphic.attr({
|
|
y: point._y - 8
|
|
});
|
|
point.raised = true;
|
|
}
|
|
// Revert other raised points
|
|
points.forEach(function (otherPoint) {
|
|
if (otherPoint !== point &&
|
|
otherPoint.raised &&
|
|
otherPoint.graphic) {
|
|
otherPoint.graphic.attr({
|
|
y: otherPoint._y
|
|
});
|
|
otherPoint.raised = false;
|
|
}
|
|
});
|
|
});
|
|
}
|
|
});
|
|
};
|
|
/**
|
|
* Get presentational attributes
|
|
* @private
|
|
*/
|
|
FlagsSeries.prototype.pointAttribs = function (point, state) {
|
|
var options = this.options, color = (point && point.color) || this.color, lineColor = options.lineColor, lineWidth = (point && point.lineWidth), fill = (point && point.fillColor) || options.fillColor;
|
|
if (state) {
|
|
fill = options.states[state].fillColor;
|
|
lineColor = options.states[state].lineColor;
|
|
lineWidth = options.states[state].lineWidth;
|
|
}
|
|
return {
|
|
fill: fill || color,
|
|
stroke: lineColor || color,
|
|
'stroke-width': lineWidth || options.lineWidth || 0
|
|
};
|
|
};
|
|
/**
|
|
* @private
|
|
*/
|
|
FlagsSeries.prototype.setClip = function () {
|
|
Series.prototype.setClip.apply(this, arguments);
|
|
if (this.options.clip !== false &&
|
|
this.sharedClipKey &&
|
|
this.markerGroup) {
|
|
this.markerGroup.clip(this.chart.sharedClips[this.sharedClipKey]);
|
|
}
|
|
};
|
|
/**
|
|
* Flags are used to mark events in stock charts. They can be added on the
|
|
* timeline, or attached to a specific series.
|
|
*
|
|
* @sample stock/demo/flags-general/
|
|
* Flags on a line series
|
|
*
|
|
* @extends plotOptions.column
|
|
* @excluding animation, borderColor, borderRadius, borderWidth,
|
|
* colorByPoint, dataGrouping, pointPadding, pointWidth,
|
|
* turboThreshold
|
|
* @product highstock
|
|
* @optionparent plotOptions.flags
|
|
*/
|
|
FlagsSeries.defaultOptions = merge(ColumnSeries.defaultOptions, {
|
|
/**
|
|
* In case the flag is placed on a series, on what point key to place
|
|
* it. Line and columns have one key, `y`. In range or OHLC-type series,
|
|
* however, the flag can optionally be placed on the `open`, `high`,
|
|
* `low` or `close` key.
|
|
*
|
|
* @sample {highstock} stock/plotoptions/flags-onkey/
|
|
* Range series, flag on high
|
|
*
|
|
* @type {string}
|
|
* @default y
|
|
* @since 4.2.2
|
|
* @product highstock
|
|
* @validvalue ["y", "open", "high", "low", "close"]
|
|
* @apioption plotOptions.flags.onKey
|
|
*/
|
|
/**
|
|
* The id of the series that the flags should be drawn on. If no id
|
|
* is given, the flags are drawn on the x axis.
|
|
*
|
|
* @sample {highstock} stock/plotoptions/flags/
|
|
* Flags on series and on x axis
|
|
*
|
|
* @type {string}
|
|
* @product highstock
|
|
* @apioption plotOptions.flags.onSeries
|
|
*/
|
|
pointRange: 0,
|
|
/**
|
|
* Whether the flags are allowed to overlap sideways. If `false`, the
|
|
* flags are moved sideways using an algorithm that seeks to place every
|
|
* flag as close as possible to its original position.
|
|
*
|
|
* @sample {highstock} stock/plotoptions/flags-allowoverlapx
|
|
* Allow sideways overlap
|
|
*
|
|
* @since 6.0.4
|
|
*/
|
|
allowOverlapX: false,
|
|
/**
|
|
* The shape of the marker. Can be one of "flag", "circlepin",
|
|
* "squarepin", or an image of the format `url(/path-to-image.jpg)`.
|
|
* Individual shapes can also be set for each point.
|
|
*
|
|
* @sample {highstock} stock/plotoptions/flags/
|
|
* Different shapes
|
|
*
|
|
* @type {Highcharts.FlagsShapeValue}
|
|
* @product highstock
|
|
*/
|
|
shape: 'flag',
|
|
/**
|
|
* When multiple flags in the same series fall on the same value, this
|
|
* number determines the vertical offset between them.
|
|
*
|
|
* @sample {highstock} stock/plotoptions/flags-stackdistance/
|
|
* A greater stack distance
|
|
*
|
|
* @product highstock
|
|
*/
|
|
stackDistance: 12,
|
|
/**
|
|
* Text alignment for the text inside the flag.
|
|
*
|
|
* @since 5.0.0
|
|
* @product highstock
|
|
* @validvalue ["left", "center", "right"]
|
|
*/
|
|
textAlign: 'center',
|
|
/**
|
|
* Specific tooltip options for flag series. Flag series tooltips are
|
|
* different from most other types in that a flag doesn't have a data
|
|
* value, so the tooltip rather displays the `text` option for each
|
|
* point.
|
|
*
|
|
* @extends plotOptions.series.tooltip
|
|
* @excluding changeDecimals, valueDecimals, valuePrefix, valueSuffix
|
|
* @product highstock
|
|
*/
|
|
tooltip: {
|
|
pointFormat: '{point.text}'
|
|
},
|
|
threshold: null,
|
|
/**
|
|
* The text to display on each flag. This can be defined on series
|
|
* level, or individually for each point. Defaults to `"A"`.
|
|
*
|
|
* @type {string}
|
|
* @default A
|
|
* @product highstock
|
|
* @apioption plotOptions.flags.title
|
|
*/
|
|
/**
|
|
* The y position of the top left corner of the flag relative to either
|
|
* the series (if onSeries is defined), or the x axis. Defaults to
|
|
* `-30`.
|
|
*
|
|
* @product highstock
|
|
*/
|
|
y: -30,
|
|
/**
|
|
* Whether to use HTML to render the flag texts. Using HTML allows for
|
|
* advanced formatting, images and reliable bi-directional text
|
|
* rendering. Note that exported images won't respect the HTML, and that
|
|
* HTML won't respect Z-index settings.
|
|
*
|
|
* @type {boolean}
|
|
* @default false
|
|
* @since 1.3
|
|
* @product highstock
|
|
* @apioption plotOptions.flags.useHTML
|
|
*/
|
|
/**
|
|
* Fixed width of the flag's shape. By default, width is autocalculated
|
|
* according to the flag's title.
|
|
*
|
|
* @sample {highstock} stock/demo/flags-shapes/
|
|
* Flags with fixed width
|
|
*
|
|
* @type {number}
|
|
* @product highstock
|
|
* @apioption plotOptions.flags.width
|
|
*/
|
|
/**
|
|
* Fixed height of the flag's shape. By default, height is
|
|
* autocalculated according to the flag's title.
|
|
*
|
|
* @type {number}
|
|
* @product highstock
|
|
* @apioption plotOptions.flags.height
|
|
*/
|
|
/**
|
|
* The fill color for the flags.
|
|
*
|
|
* @type {Highcharts.ColorString|Highcharts.GradientColorObject|Highcharts.PatternObject}
|
|
* @product highstock
|
|
*/
|
|
fillColor: "#ffffff" /* Palette.backgroundColor */,
|
|
/**
|
|
* The color of the line/border of the flag.
|
|
*
|
|
* In styled mode, the stroke is set in the
|
|
* `.highcharts-flag-series.highcharts-point` rule.
|
|
*
|
|
* @type {Highcharts.ColorString|Highcharts.GradientColorObject|Highcharts.PatternObject}
|
|
* @default #000000
|
|
* @product highstock
|
|
* @apioption plotOptions.flags.lineColor
|
|
*/
|
|
/**
|
|
* The pixel width of the flag's line/border.
|
|
*
|
|
* @product highstock
|
|
*/
|
|
lineWidth: 1,
|
|
states: {
|
|
/**
|
|
* @extends plotOptions.column.states.hover
|
|
* @product highstock
|
|
*/
|
|
hover: {
|
|
/**
|
|
* The color of the line/border of the flag.
|
|
*
|
|
* @type {Highcharts.ColorString|Highcharts.GradientColorObject|Highcharts.PatternObject}
|
|
* @product highstock
|
|
*/
|
|
lineColor: "#000000" /* Palette.neutralColor100 */,
|
|
/**
|
|
* The fill or background color of the flag.
|
|
*
|
|
* @type {Highcharts.ColorString|Highcharts.GradientColorObject|Highcharts.PatternObject}
|
|
* @product highstock
|
|
*/
|
|
fillColor: "#ccd6eb" /* Palette.highlightColor20 */
|
|
}
|
|
},
|
|
/**
|
|
* The text styles of the flag.
|
|
*
|
|
* In styled mode, the styles are set in the
|
|
* `.highcharts-flag-series .highcharts-point` rule.
|
|
*
|
|
* @type {Highcharts.CSSObject}
|
|
* @default {"fontSize": "11px", "fontWeight": "bold"}
|
|
* @product highstock
|
|
*/
|
|
style: {
|
|
/** @ignore-option */
|
|
fontSize: '11px',
|
|
/** @ignore-option */
|
|
fontWeight: 'bold'
|
|
}
|
|
});
|
|
return FlagsSeries;
|
|
}(ColumnSeries));
|
|
OnSeriesComposition.compose(FlagsSeries);
|
|
extend(FlagsSeries.prototype, {
|
|
allowDG: false,
|
|
forceCrop: true,
|
|
invertible: false,
|
|
noSharedTooltip: true,
|
|
pointClass: FlagsPoint,
|
|
sorted: false,
|
|
takeOrdinalPosition: false,
|
|
trackerGroups: ['markerGroup'],
|
|
buildKDTree: noop,
|
|
/**
|
|
* Inherit the initialization from base Series.
|
|
* @private
|
|
*/
|
|
init: Series.prototype.init,
|
|
/**
|
|
* Don't invert the flag marker group (#4960).
|
|
* @private
|
|
*/
|
|
invertGroups: noop
|
|
});
|
|
SeriesRegistry.registerSeriesType('flags', FlagsSeries);
|
|
/* *
|
|
*
|
|
* Default Export
|
|
*
|
|
* */
|
|
export default FlagsSeries;
|
|
/* *
|
|
*
|
|
* API Declarations
|
|
*
|
|
* */
|
|
/**
|
|
* @typedef {"circlepin"|"flag"|"squarepin"} Highcharts.FlagsShapeValue
|
|
*/
|
|
''; // detach doclets above
|
|
/* *
|
|
*
|
|
* API Option
|
|
*
|
|
* */
|
|
/**
|
|
* A `flags` series. If the [type](#series.flags.type) option is not
|
|
* specified, it is inherited from [chart.type](#chart.type).
|
|
*
|
|
* @extends series,plotOptions.flags
|
|
* @excluding animation, borderColor, borderRadius, borderWidth, colorByPoint,
|
|
* connectNulls, dashStyle, dataGrouping, dataParser, dataURL,
|
|
* gapSize, gapUnit, linecap, lineWidth, marker, pointPadding,
|
|
* pointWidth, step, turboThreshold, useOhlcData
|
|
* @product highstock
|
|
* @apioption series.flags
|
|
*/
|
|
/**
|
|
* An array of data points for the series. For the `flags` series type,
|
|
* points can be given in the following ways:
|
|
*
|
|
* 1. An array of objects with named values. The following snippet shows only a
|
|
* few settings, see the complete options set below. If the total number of
|
|
* data points exceeds the series'
|
|
* [turboThreshold](#series.flags.turboThreshold), this option is not
|
|
* available.
|
|
* ```js
|
|
* data: [{
|
|
* x: 1,
|
|
* title: "A",
|
|
* text: "First event"
|
|
* }, {
|
|
* x: 1,
|
|
* title: "B",
|
|
* text: "Second event"
|
|
* }]
|
|
* ```
|
|
*
|
|
* @type {Array<*>}
|
|
* @extends series.line.data
|
|
* @excluding dataLabels, marker, name, y
|
|
* @product highstock
|
|
* @apioption series.flags.data
|
|
*/
|
|
/**
|
|
* The fill color of an individual flag. By default it inherits from
|
|
* the series color.
|
|
*
|
|
* @type {Highcharts.ColorString|Highcharts.GradientColorObject|Highcharts.PatternObject}
|
|
* @product highstock
|
|
* @apioption series.flags.data.fillColor
|
|
*/
|
|
/**
|
|
* The longer text to be shown in the flag's tooltip.
|
|
*
|
|
* @type {string}
|
|
* @product highstock
|
|
* @apioption series.flags.data.text
|
|
*/
|
|
/**
|
|
* The short text to be shown on the flag.
|
|
*
|
|
* @type {string}
|
|
* @product highstock
|
|
* @apioption series.flags.data.title
|
|
*/
|
|
''; // adds doclets above to transpiled file
|