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.
87 lines
13 KiB
87 lines
13 KiB
/*
|
|
Map plugin v0.1 for Highcharts
|
|
|
|
(c) 2011-2013 Torstein Hønsi
|
|
|
|
License: www.highcharts.com/license
|
|
*/
|
|
(function (g) {
|
|
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 = {
|
|
buttonOptions: { align: "right", verticalAlign: "bottom", x: 0, width: 18, height: 18, style: { fontSize: "15px", fontWeight: "bold", textAlign: "center" } }, buttons: {
|
|
zoomIn: {
|
|
onclick: function () { this.mapZoom(0.5) },
|
|
text: "+", y: -32
|
|
}, zoomOut: { onclick: function () { this.mapZoom(2) }, text: "-", y: 0 }
|
|
}
|
|
}; 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) {
|
|
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,
|
|
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
|
|
}); t(r.prototype, "setAxisTranslation", function (a) {
|
|
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 =
|
|
(e.len - c) / 2
|
|
}); 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, {
|
|
onContainerDblClick: function (a) {
|
|
var b = this.chart, a = this.normalize(a); b.isInsidePlot(a.chartX - b.plotLeft, a.chartY -
|
|
b.plotTop) && b.mapZoom(0.5, b.xAxis[0].toValue(a.chartX), b.yAxis[0].toValue(a.chartY))
|
|
}, 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)) }
|
|
}); 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, {
|
|
renderMapNavigation: function () {
|
|
var a =
|
|
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")
|
|
}, fitToBox: function (a, b) {
|
|
l([["x", "width"], ["y", "height"]], function (c) {
|
|
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]);
|
|
a[c] > b[c] && (a[c] = b[c]); a[d] < b[d] && (a[d] = b[d])
|
|
}); return a
|
|
}, mapZoom: function (a, b, c) {
|
|
if (!this.isMapZooming) {
|
|
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 () {
|
|
d.isMapZooming =
|
|
!1
|
|
}, e); d.redraw()
|
|
}
|
|
}
|
|
}); 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, {
|
|
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 () {
|
|
clearTimeout(this.colorInterval);
|
|
s.prototype.onMouseOver.call(this)
|
|
}, 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) }
|
|
}); k.map = g.extendClass(k.scatter,
|
|
{
|
|
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) {
|
|
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) {
|
|
f = a.from; i = a.to; e =
|
|
""; 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))
|
|
}), 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 = [{
|
|
chart: b.chart, options: {}, fromLabel: h,
|
|
toLabel: j, color: o, drawLegendSymbol: this.drawLegendSymbolGradient, visible: !0, setState: function () { }, setVisible: function () { }
|
|
}], b.legendItems = d
|
|
}, drawLegendSymbol: k.area.prototype.drawLegendSymbol, drawLegendSymbolGradient: function (a, b) {
|
|
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,
|
|
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)
|
|
}, getBox: function (a) {
|
|
var b =
|
|
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 =
|
|
b
|
|
}, 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 () {
|
|
var a = this, b = Number.MAX_VALUE, c = Number.MIN_VALUE; a.generatePoints(); l(a.data, function (d) {
|
|
d.shapeType = "path"; d.shapeArgs = { d: a.translatePath(d.path) }; if (typeof d.y === "number") if (d.y > c) c =
|
|
d.y; else if (d.y < b) b = d.y
|
|
}); a.translateColors(b, c)
|
|
}, 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 () {
|
|
var a = this.xAxis,
|
|
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)
|
|
}, animateDrilldown: function (a) {
|
|
var b = this.chart.plotBox,
|
|
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
|
|
}, animateDrillupFrom: function (a) { k.column.prototype.animateDrillupFrom.call(this, a) }, animateDrillupTo: function (a) {
|
|
k.column.prototype.animateDrillupTo.call(this,
|
|
a)
|
|
}
|
|
}); 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) {
|
|
var c = {
|
|
endOnTick: !1, gridLineWidth: 0, labels: { enabled: !1 }, lineWidth: 0,
|
|
minPadding: 0, maxPadding: 0, startOnTick: !1, tickWidth: 0, title: null
|
|
}, 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)
|
|
}
|
|
})(Highcharts);
|