You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

86 lines
13 KiB

2 years ago
  1. /*
  2. Map plugin v0.1 for Highcharts
  3. (c) 2011-2013 Torstein Hønsi
  4. License: www.highcharts.com/license
  5. */
  6. (function (g) {
  7. function x(a, b, c) { for (var d = 4, e = []; d--;)e[d] = Math.round(b.rgba[d] + (a.rgba[d] - b.rgba[d]) * (1 - c)); return "rgba(" + e.join(",") + ")" } var r = g.Axis, y = g.Chart, s = g.Point, z = g.Pointer, l = g.each, v = g.extend, p = g.merge, n = g.pick, A = g.numberFormat, B = g.getOptions(), k = g.seriesTypes, q = B.plotOptions, t = g.wrap, u = g.Color, w = function () { }; B.mapNavigation = {
  8. buttonOptions: { align: "right", verticalAlign: "bottom", x: 0, width: 18, height: 18, style: { fontSize: "15px", fontWeight: "bold", textAlign: "center" } }, buttons: {
  9. zoomIn: {
  10. onclick: function () { this.mapZoom(0.5) },
  11. text: "+", y: -32
  12. }, zoomOut: { onclick: function () { this.mapZoom(2) }, text: "-", y: 0 }
  13. }
  14. }; g.splitPath = function (a) { var b, a = a.replace(/([A-Za-z])/g, " $1 "), a = a.replace(/^\s*/, "").replace(/\s*$/, ""), a = a.split(/[ ,]+/); for (b = 0; b < a.length; b++)/[a-zA-Z]/.test(a[b]) || (a[b] = parseFloat(a[b])); return a }; g.maps = {}; t(r.prototype, "getSeriesExtremes", function (a) {
  15. var b = this.isXAxis, c, d, e = []; l(this.series, function (a, b) { if (a.useMapGeometry) e[b] = a.xData, a.xData = [] }); a.call(this); c = n(this.dataMin, Number.MAX_VALUE); d = n(this.dataMax,
  16. Number.MIN_VALUE); l(this.series, function (a, i) { if (a.useMapGeometry) c = Math.min(c, a[b ? "minX" : "minY"]), d = Math.max(d, a[b ? "maxX" : "maxY"]), a.xData = e[i] }); this.dataMin = c; this.dataMax = d
  17. }); t(r.prototype, "setAxisTranslation", function (a) {
  18. var b = this.chart, c = b.plotWidth / b.plotHeight, d = this.isXAxis, e = b.xAxis[0]; a.call(this); if (b.options.chart.type === "map" && !d && e.transA !== void 0) this.transA = e.transA = Math.min(this.transA, e.transA), a = (e.max - e.min) / (this.max - this.min), e = a > c ? this : e, c = (e.max - e.min) * e.transA, e.minPixelPadding =
  19. (e.len - c) / 2
  20. }); t(y.prototype, "render", function (a) { var b = this, c = b.options.mapNavigation; a.call(b); b.renderMapNavigation(); c.zoomOnDoubleClick && g.addEvent(b.container, "dblclick", function (a) { b.pointer.onContainerDblClick(a) }); c.zoomOnMouseWheel && g.addEvent(b.container, document.onmousewheel === void 0 ? "DOMMouseScroll" : "mousewheel", function (a) { b.pointer.onContainerMouseWheel(a) }) }); v(z.prototype, {
  21. onContainerDblClick: function (a) {
  22. var b = this.chart, a = this.normalize(a); b.isInsidePlot(a.chartX - b.plotLeft, a.chartY -
  23. b.plotTop) && b.mapZoom(0.5, b.xAxis[0].toValue(a.chartX), b.yAxis[0].toValue(a.chartY))
  24. }, onContainerMouseWheel: function (a) { var b = this.chart, c, a = this.normalize(a); c = a.detail || -(a.wheelDelta / 120); b.isInsidePlot(a.chartX - b.plotLeft, a.chartY - b.plotTop) && b.mapZoom(c > 0 ? 2 : 0.5, b.xAxis[0].toValue(a.chartX), b.yAxis[0].toValue(a.chartY)) }
  25. }); t(z.prototype, "init", function (a, b, c) { a.call(this, b, c); if (c.mapNavigation.enableTouchZoom) this.pinchX = this.pinchHor = this.pinchY = this.pinchVert = !0 }); v(y.prototype, {
  26. renderMapNavigation: function () {
  27. var a =
  28. this, b = this.options.mapNavigation, c = b.buttons, d, e, f, i = function () { this.handler.call(a) }; if (b.enableButtons) for (d in c) if (c.hasOwnProperty(d)) f = p(b.buttonOptions, c[d]), e = a.renderer.button(f.text, 0, 0, i).attr({ width: f.width, height: f.height }).css(f.style).add(), e.handler = f.onclick, e.align(v(f, { width: e.width, height: e.height }), null, "spacingBox")
  29. }, fitToBox: function (a, b) {
  30. l([["x", "width"], ["y", "height"]], function (c) {
  31. var d = c[0], c = c[1]; a[d] + a[c] > b[d] + b[c] && (a[c] > b[c] ? (a[c] = b[c], a[d] = b[d]) : a[d] = b[d] + b[c] - a[c]);
  32. a[c] > b[c] && (a[c] = b[c]); a[d] < b[d] && (a[d] = b[d])
  33. }); return a
  34. }, mapZoom: function (a, b, c) {
  35. if (!this.isMapZooming) {
  36. var d = this, e = d.xAxis[0], f = e.max - e.min, i = n(b, e.min + f / 2), b = f * a, f = d.yAxis[0], h = f.max - f.min, c = n(c, f.min + h / 2); a *= h; i -= b / 2; h = c - a / 2; c = n(d.options.chart.animation, !0); b = d.fitToBox({ x: i, y: h, width: b, height: a }, { x: e.dataMin, y: f.dataMin, width: e.dataMax - e.dataMin, height: f.dataMax - f.dataMin }); e.setExtremes(b.x, b.x + b.width, !1); f.setExtremes(b.y, b.y + b.height, !1); if (e = c ? c.duration || 500 : 0) d.isMapZooming = !0, setTimeout(function () {
  37. d.isMapZooming =
  38. !1
  39. }, e); d.redraw()
  40. }
  41. }
  42. }); q.map = p(q.scatter, { animation: !1, nullColor: "#F8F8F8", borderColor: "silver", borderWidth: 1, marker: null, stickyTracking: !1, dataLabels: { verticalAlign: "middle" }, turboThreshold: 0, tooltip: { followPointer: !0, pointFormat: "{point.name}: {point.y}<br/>" }, states: { normal: { animation: !0 } } }); r = g.extendClass(s, {
  43. applyOptions: function (a, b) { var c = s.prototype.applyOptions.call(this, a, b); if (c.path && typeof c.path === "string") c.path = c.options.path = g.splitPath(c.path); return c }, onMouseOver: function () {
  44. clearTimeout(this.colorInterval);
  45. s.prototype.onMouseOver.call(this)
  46. }, onMouseOut: function () { var a = this, b = +new Date, c = u(a.options.color), d = u(a.pointAttr.hover.fill), e = a.series.options.states.normal.animation, f = e && (e.duration || 500); if (f && c.rgba.length === 4 && d.rgba.length === 4) delete a.pointAttr[""].fill, clearTimeout(a.colorInterval), a.colorInterval = setInterval(function () { var e = (new Date - b) / f, h = a.graphic; e > 1 && (e = 1); h && h.attr("fill", x(d, c, e)); e >= 1 && clearTimeout(a.colorInterval) }, 13); s.prototype.onMouseOut.call(a) }
  47. }); k.map = g.extendClass(k.scatter,
  48. {
  49. type: "map", pointAttrToOptions: { stroke: "borderColor", "stroke-width": "borderWidth", fill: "color" }, colorKey: "y", pointClass: r, trackerGroups: ["group", "markerGroup", "dataLabelsGroup"], getSymbol: w, supportsDrilldown: !0, getExtremesFromAll: !0, useMapGeometry: !0, init: function (a) {
  50. var b = this, c = a.options.legend.valueDecimals, d = [], e, f, i, h, j, o, m; o = a.options.legend.layout === "horizontal"; g.Series.prototype.init.apply(this, arguments); j = b.options.colorRange; if (h = b.options.valueRanges) l(h, function (a) {
  51. f = a.from; i = a.to; e =
  52. ""; f === void 0 ? e = "< " : i === void 0 && (e = "> "); f !== void 0 && (e += A(f, c)); f !== void 0 && i !== void 0 && (e += " - "); i !== void 0 && (e += A(i, c)); d.push(g.extend({ chart: b.chart, name: e, options: {}, drawLegendSymbol: k.area.prototype.drawLegendSymbol, visible: !0, setState: function () { }, setVisible: function () { } }, a))
  53. }), b.legendItems = d; else if (j) f = j.from, i = j.to, h = j.fromLabel, j = j.toLabel, m = o ? [0, 0, 1, 0] : [0, 1, 0, 0], o || (o = h, h = j, j = o), o = { linearGradient: { x1: m[0], y1: m[1], x2: m[2], y2: m[3] }, stops: [[0, f], [1, i]] }, d = [{
  54. chart: b.chart, options: {}, fromLabel: h,
  55. toLabel: j, color: o, drawLegendSymbol: this.drawLegendSymbolGradient, visible: !0, setState: function () { }, setVisible: function () { }
  56. }], b.legendItems = d
  57. }, drawLegendSymbol: k.area.prototype.drawLegendSymbol, drawLegendSymbolGradient: function (a, b) {
  58. var c = a.options.symbolPadding, d = n(a.options.padding, 8), e, f, i = this.chart.renderer.fontMetrics(a.options.itemStyle.fontSize).h, h = a.options.layout === "horizontal", j; j = n(a.options.rectangleLength, 200); h ? (e = -(c / 2), f = 0) : (e = -j + a.baseline - c / 2, f = d + i); b.fromText = this.chart.renderer.text(b.fromLabel,
  59. f, e).attr({ zIndex: 2 }).add(b.legendGroup); f = b.fromText.getBBox(); b.legendSymbol = this.chart.renderer.rect(h ? f.x + f.width + c : f.x - i - c, f.y, h ? j : i, h ? i : j, 2).attr({ zIndex: 1 }).add(b.legendGroup); j = b.legendSymbol.getBBox(); b.toText = this.chart.renderer.text(b.toLabel, j.x + j.width + c, h ? e : j.y + j.height - c).attr({ zIndex: 2 }).add(b.legendGroup); e = b.toText.getBBox(); h ? (a.offsetWidth = f.width + j.width + e.width + c * 2 + d, a.itemY = i + d) : (a.offsetWidth = Math.max(f.width, e.width) + c + j.width + d, a.itemY = j.height + d, a.itemX = c)
  60. }, getBox: function (a) {
  61. var b =
  62. Number.MIN_VALUE, c = Number.MAX_VALUE, d = Number.MIN_VALUE, e = Number.MAX_VALUE; l(a || this.options.data, function (a) { for (var i = a.path, h = i.length, j = !1, g = Number.MIN_VALUE, m = Number.MAX_VALUE, k = Number.MIN_VALUE, l = Number.MAX_VALUE; h--;)typeof i[h] === "number" && !isNaN(i[h]) && (j ? (g = Math.max(g, i[h]), m = Math.min(m, i[h])) : (k = Math.max(k, i[h]), l = Math.min(l, i[h])), j = !j); a._maxX = g; a._minX = m; a._maxY = k; a._minY = l; b = Math.max(b, g); c = Math.min(c, m); d = Math.max(d, k); e = Math.min(e, l) }); this.minY = e; this.maxY = d; this.minX = c; this.maxX =
  63. b
  64. }, translatePath: function (a) { var b = !1, c = this.xAxis, d = this.yAxis, e, a = [].concat(a); for (e = a.length; e--;)typeof a[e] === "number" && (a[e] = b ? Math.round(c.translate(a[e])) : Math.round(d.len - d.translate(a[e])), b = !b); return a }, setData: function () { g.Series.prototype.setData.apply(this, arguments); this.getBox() }, translate: function () {
  65. var a = this, b = Number.MAX_VALUE, c = Number.MIN_VALUE; a.generatePoints(); l(a.data, function (d) {
  66. d.shapeType = "path"; d.shapeArgs = { d: a.translatePath(d.path) }; if (typeof d.y === "number") if (d.y > c) c =
  67. d.y; else if (d.y < b) b = d.y
  68. }); a.translateColors(b, c)
  69. }, translateColors: function (a, b) { var c = this.options, d = c.valueRanges, e = c.colorRange, f = this.colorKey, i, h; e && (i = u(e.from), h = u(e.to)); l(this.data, function (g) { var k = g[f], m, l, n; if (d) for (n = d.length; n--;) { if (m = d[n], i = m.from, h = m.to, (i === void 0 || k >= i) && (h === void 0 || k <= h)) { l = m.color; break } } else e && k !== void 0 && (m = 1 - (b - k) / (b - a), l = k === null ? c.nullColor : x(i, h, m)); if (l) g.color = null, g.options.color = l }) }, drawGraph: w, drawDataLabels: w, drawPoints: function () {
  70. var a = this.xAxis,
  71. b = this.yAxis, c = this.colorKey; l(this.data, function (a) { a.plotY = 1; if (a[c] === null) a[c] = 0, a.isNull = !0 }); k.column.prototype.drawPoints.apply(this); l(this.data, function (d) { var e = d.dataLabels, f = a.toPixels(d._minX, !0), g = a.toPixels(d._maxX, !0), h = b.toPixels(d._minY, !0), j = b.toPixels(d._maxY, !0); d.plotX = Math.round(f + (g - f) * n(e && e.anchorX, 0.5)); d.plotY = Math.round(h + (j - h) * n(e && e.anchorY, 0.5)); d.isNull && (d[c] = null) }); g.Series.prototype.drawDataLabels.call(this)
  72. }, animateDrilldown: function (a) {
  73. var b = this.chart.plotBox,
  74. c = this.chart.drilldownLevels[this.chart.drilldownLevels.length - 1], d = c.bBox, e = this.chart.options.drilldown.animation; if (!a) a = Math.min(d.width / b.width, d.height / b.height), c.shapeArgs = { scaleX: a, scaleY: a, translateX: d.x, translateY: d.y }, l(this.points, function (a) { a.graphic.attr(c.shapeArgs).animate({ scaleX: 1, scaleY: 1, translateX: 0, translateY: 0 }, e) }), delete this.animate
  75. }, animateDrillupFrom: function (a) { k.column.prototype.animateDrillupFrom.call(this, a) }, animateDrillupTo: function (a) {
  76. k.column.prototype.animateDrillupTo.call(this,
  77. a)
  78. }
  79. }); q.mapline = p(q.map, { lineWidth: 1, backgroundColor: "none" }); k.mapline = g.extendClass(k.map, { type: "mapline", pointAttrToOptions: { stroke: "color", "stroke-width": "lineWidth", fill: "backgroundColor" }, drawLegendSymbol: k.line.prototype.drawLegendSymbol }); q.mappoint = p(q.scatter, { dataLabels: { enabled: !0, format: "{point.name}", color: "black", style: { textShadow: "0 0 5px white" } } }); k.mappoint = g.extendClass(k.scatter, { type: "mappoint" }); g.Map = function (a, b) {
  80. var c = {
  81. endOnTick: !1, gridLineWidth: 0, labels: { enabled: !1 }, lineWidth: 0,
  82. minPadding: 0, maxPadding: 0, startOnTick: !1, tickWidth: 0, title: null
  83. }, d; d = a.series; a.series = null; a = p({ chart: { type: "map", panning: "xy" }, xAxis: c, yAxis: p(c, { reversed: !0 }) }, a, { chart: { inverted: !1 } }); a.series = d; return new g.Chart(a, b)
  84. }
  85. })(Highcharts);