+
diff --git a/activity_dashboard_mngmnt/static/src/css/style.scss b/activity_dashboard_mngmnt/static/src/css/style.scss
index d861d3e66..438998397 100644
--- a/activity_dashboard_mngmnt/static/src/css/style.scss
+++ b/activity_dashboard_mngmnt/static/src/css/style.scss
@@ -12,6 +12,7 @@
padding: 1.7rem 1.5rem 1.5rem 1.5rem;
margin: 1rem auto;
height: 100px;
+ cursor: pointer;
}
.activity-dashboard-card__icon-container {
height: 50px;
diff --git a/activity_dashboard_mngmnt/static/src/js/activity_dashboard.js b/activity_dashboard_mngmnt/static/src/js/activity_dashboard.js
index ecf7375fb..07d7b5b46 100644
--- a/activity_dashboard_mngmnt/static/src/js/activity_dashboard.js
+++ b/activity_dashboard_mngmnt/static/src/js/activity_dashboard.js
@@ -51,27 +51,30 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
len_cancel: result.len_cancel
}));
});
-// this.$('.table_view').html(QWeb.render('ManageActivity'));
self.results = ''
self._rpc({
model: 'mail.activity',
method : 'search_read',
- domain: [["state", "=", 'done'], ["active", "=", false]],
+ domain: [["state", "=", 'done']],
+ context: { active_test: false },
}).then(function(done_activity){
self._rpc({
model: 'mail.activity',
method : 'search_read',
domain: [["state", "=", 'planned']],
+ context: { active_test: false },
}).then(function(planned_activity){
self._rpc({
model: 'mail.activity',
method : 'search_read',
domain: [["state", "=", 'today']],
+ context: { active_test: false },
}).then(function(today_activity){
self._rpc({
model: 'mail.activity',
method : 'search_read',
domain: [["state", "=", 'overdue']],
+ context: { active_test: false },
}).then(function(overdue_activity){
self.$('.table_view_activity').html(QWeb.render('ActivityTable', {
done_activity: done_activity,
@@ -85,14 +88,14 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
});
},
click_view: function(e){
- var id = e.target.value
+ var id = e.target.value;
this.do_action({
type: 'ir.actions.act_window',
name: 'All Activity',
res_model: 'mail.activity',
- domain: [['id', '=', id]],
- views: [[false, 'list'], [false, 'form']],
- view_mode: 'list,form',
+ res_id: parseInt(id),
+ views: [[false, 'form']],
+ view_mode: 'form',
target: 'current'
});
},
@@ -108,13 +111,14 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
type: 'ir.actions.act_window',
name: 'Activity Origin',
res_model: result.model,
- domain: [['id', '=', result.res_id]],
- views: [[false, 'list'], [false, 'form']],
- view_mode: 'list,form',
+ res_id: result.res_id,
+ views: [[false, 'form']],
+ view_mode: 'form',
target: 'current'
});
});
},
+
all_activity: function(e) {
var self = this;
e.stopPropagation();
@@ -126,11 +130,11 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
type: 'ir.actions.act_window',
name: 'All Activity',
res_model: 'mail.activity',
- // res_id: [1],
domain: [],
views: [[false, 'list'], [false, 'form']],
view_mode: 'list',
- target: 'current'
+ target: 'current',
+ context: { active_test: false },
});
},
@@ -148,7 +152,8 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
domain: [['state', '=', 'planned']],
views: [[false, 'list'], [false, 'form']],
view_mode: 'list',
- target: 'current'
+ target: 'current',
+ context: { active_test: false },
});
},
@@ -163,10 +168,11 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
type: 'ir.actions.act_window',
name: 'Completed Activity',
res_model: 'mail.activity',
- domain: [['state', '=', 'done'], ['active', '=', false]],
+ domain: [['state', '=', 'done']],
views: [[false, 'list'], [false, 'form']],
view_mode: 'list',
- target: 'current'
+ target: 'current',
+ context: { active_test: false },
});
},
@@ -182,7 +188,8 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
domain: [['state', '=', 'today']],
views: [[false, 'list'], [false, 'form']],
view_mode: 'list',
- target: 'current'
+ target: 'current',
+ context: { active_test: false },
});
},
@@ -200,7 +207,8 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
domain: [['state', '=', 'overdue']],
views: [[false, 'list'], [false, 'form']],
view_mode: 'list',
- target: 'current'
+ target: 'current',
+ context: { active_test: false },
});
},
@@ -219,7 +227,8 @@ odoo.define('activity_dashboard_mngmnt.activity_dashboard', function (require) {
domain: [['state', '=', 'cancel']],
views: [[false, 'list'], [false, 'form']],
view_mode: 'list',
- target: 'current'
+ target: 'current',
+ context: { active_test: false },
});
},
diff --git a/activity_dashboard_mngmnt/static/src/js/lib/Chart.bundle.js b/activity_dashboard_mngmnt/static/src/js/lib/Chart.bundle.js
deleted file mode 100644
index 33a955afe..000000000
--- a/activity_dashboard_mngmnt/static/src/js/lib/Chart.bundle.js
+++ /dev/null
@@ -1,19288 +0,0 @@
-/*!
- * Chart.js v2.8.0
- * https://www.chartjs.org
- * (c) 2019 Chart.js Contributors
- * Released under the MIT License
- */
-(function (global, factory) {
-typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
-typeof define === 'function' && define.amd ? define(factory) :
-(global.Chart = factory());
-}(this, (function () { 'use strict';
-
-/* MIT license */
-
-var conversions = {
- rgb2hsl: rgb2hsl,
- rgb2hsv: rgb2hsv,
- rgb2hwb: rgb2hwb,
- rgb2cmyk: rgb2cmyk,
- rgb2keyword: rgb2keyword,
- rgb2xyz: rgb2xyz,
- rgb2lab: rgb2lab,
- rgb2lch: rgb2lch,
-
- hsl2rgb: hsl2rgb,
- hsl2hsv: hsl2hsv,
- hsl2hwb: hsl2hwb,
- hsl2cmyk: hsl2cmyk,
- hsl2keyword: hsl2keyword,
-
- hsv2rgb: hsv2rgb,
- hsv2hsl: hsv2hsl,
- hsv2hwb: hsv2hwb,
- hsv2cmyk: hsv2cmyk,
- hsv2keyword: hsv2keyword,
-
- hwb2rgb: hwb2rgb,
- hwb2hsl: hwb2hsl,
- hwb2hsv: hwb2hsv,
- hwb2cmyk: hwb2cmyk,
- hwb2keyword: hwb2keyword,
-
- cmyk2rgb: cmyk2rgb,
- cmyk2hsl: cmyk2hsl,
- cmyk2hsv: cmyk2hsv,
- cmyk2hwb: cmyk2hwb,
- cmyk2keyword: cmyk2keyword,
-
- keyword2rgb: keyword2rgb,
- keyword2hsl: keyword2hsl,
- keyword2hsv: keyword2hsv,
- keyword2hwb: keyword2hwb,
- keyword2cmyk: keyword2cmyk,
- keyword2lab: keyword2lab,
- keyword2xyz: keyword2xyz,
-
- xyz2rgb: xyz2rgb,
- xyz2lab: xyz2lab,
- xyz2lch: xyz2lch,
-
- lab2xyz: lab2xyz,
- lab2rgb: lab2rgb,
- lab2lch: lab2lch,
-
- lch2lab: lch2lab,
- lch2xyz: lch2xyz,
- lch2rgb: lch2rgb
-};
-
-
-function rgb2hsl(rgb) {
- var r = rgb[0]/255,
- g = rgb[1]/255,
- b = rgb[2]/255,
- min = Math.min(r, g, b),
- max = Math.max(r, g, b),
- delta = max - min,
- h, s, l;
-
- if (max == min)
- h = 0;
- else if (r == max)
- h = (g - b) / delta;
- else if (g == max)
- h = 2 + (b - r) / delta;
- else if (b == max)
- h = 4 + (r - g)/ delta;
-
- h = Math.min(h * 60, 360);
-
- if (h < 0)
- h += 360;
-
- l = (min + max) / 2;
-
- if (max == min)
- s = 0;
- else if (l <= 0.5)
- s = delta / (max + min);
- else
- s = delta / (2 - max - min);
-
- return [h, s * 100, l * 100];
-}
-
-function rgb2hsv(rgb) {
- var r = rgb[0],
- g = rgb[1],
- b = rgb[2],
- min = Math.min(r, g, b),
- max = Math.max(r, g, b),
- delta = max - min,
- h, s, v;
-
- if (max == 0)
- s = 0;
- else
- s = (delta/max * 1000)/10;
-
- if (max == min)
- h = 0;
- else if (r == max)
- h = (g - b) / delta;
- else if (g == max)
- h = 2 + (b - r) / delta;
- else if (b == max)
- h = 4 + (r - g) / delta;
-
- h = Math.min(h * 60, 360);
-
- if (h < 0)
- h += 360;
-
- v = ((max / 255) * 1000) / 10;
-
- return [h, s, v];
-}
-
-function rgb2hwb(rgb) {
- var r = rgb[0],
- g = rgb[1],
- b = rgb[2],
- h = rgb2hsl(rgb)[0],
- w = 1/255 * Math.min(r, Math.min(g, b)),
- b = 1 - 1/255 * Math.max(r, Math.max(g, b));
-
- return [h, w * 100, b * 100];
-}
-
-function rgb2cmyk(rgb) {
- var r = rgb[0] / 255,
- g = rgb[1] / 255,
- b = rgb[2] / 255,
- c, m, y, k;
-
- k = Math.min(1 - r, 1 - g, 1 - b);
- c = (1 - r - k) / (1 - k) || 0;
- m = (1 - g - k) / (1 - k) || 0;
- y = (1 - b - k) / (1 - k) || 0;
- return [c * 100, m * 100, y * 100, k * 100];
-}
-
-function rgb2keyword(rgb) {
- return reverseKeywords[JSON.stringify(rgb)];
-}
-
-function rgb2xyz(rgb) {
- var r = rgb[0] / 255,
- g = rgb[1] / 255,
- b = rgb[2] / 255;
-
- // assume sRGB
- r = r > 0.04045 ? Math.pow(((r + 0.055) / 1.055), 2.4) : (r / 12.92);
- g = g > 0.04045 ? Math.pow(((g + 0.055) / 1.055), 2.4) : (g / 12.92);
- b = b > 0.04045 ? Math.pow(((b + 0.055) / 1.055), 2.4) : (b / 12.92);
-
- var x = (r * 0.4124) + (g * 0.3576) + (b * 0.1805);
- var y = (r * 0.2126) + (g * 0.7152) + (b * 0.0722);
- var z = (r * 0.0193) + (g * 0.1192) + (b * 0.9505);
-
- return [x * 100, y *100, z * 100];
-}
-
-function rgb2lab(rgb) {
- var xyz = rgb2xyz(rgb),
- x = xyz[0],
- y = xyz[1],
- z = xyz[2],
- l, a, b;
-
- x /= 95.047;
- y /= 100;
- z /= 108.883;
-
- x = x > 0.008856 ? Math.pow(x, 1/3) : (7.787 * x) + (16 / 116);
- y = y > 0.008856 ? Math.pow(y, 1/3) : (7.787 * y) + (16 / 116);
- z = z > 0.008856 ? Math.pow(z, 1/3) : (7.787 * z) + (16 / 116);
-
- l = (116 * y) - 16;
- a = 500 * (x - y);
- b = 200 * (y - z);
-
- return [l, a, b];
-}
-
-function rgb2lch(args) {
- return lab2lch(rgb2lab(args));
-}
-
-function hsl2rgb(hsl) {
- var h = hsl[0] / 360,
- s = hsl[1] / 100,
- l = hsl[2] / 100,
- t1, t2, t3, rgb, val;
-
- if (s == 0) {
- val = l * 255;
- return [val, val, val];
- }
-
- if (l < 0.5)
- t2 = l * (1 + s);
- else
- t2 = l + s - l * s;
- t1 = 2 * l - t2;
-
- rgb = [0, 0, 0];
- for (var i = 0; i < 3; i++) {
- t3 = h + 1 / 3 * - (i - 1);
- t3 < 0 && t3++;
- t3 > 1 && t3--;
-
- if (6 * t3 < 1)
- val = t1 + (t2 - t1) * 6 * t3;
- else if (2 * t3 < 1)
- val = t2;
- else if (3 * t3 < 2)
- val = t1 + (t2 - t1) * (2 / 3 - t3) * 6;
- else
- val = t1;
-
- rgb[i] = val * 255;
- }
-
- return rgb;
-}
-
-function hsl2hsv(hsl) {
- var h = hsl[0],
- s = hsl[1] / 100,
- l = hsl[2] / 100,
- sv, v;
-
- if(l === 0) {
- // no need to do calc on black
- // also avoids divide by 0 error
- return [0, 0, 0];
- }
-
- l *= 2;
- s *= (l <= 1) ? l : 2 - l;
- v = (l + s) / 2;
- sv = (2 * s) / (l + s);
- return [h, sv * 100, v * 100];
-}
-
-function hsl2hwb(args) {
- return rgb2hwb(hsl2rgb(args));
-}
-
-function hsl2cmyk(args) {
- return rgb2cmyk(hsl2rgb(args));
-}
-
-function hsl2keyword(args) {
- return rgb2keyword(hsl2rgb(args));
-}
-
-
-function hsv2rgb(hsv) {
- var h = hsv[0] / 60,
- s = hsv[1] / 100,
- v = hsv[2] / 100,
- hi = Math.floor(h) % 6;
-
- var f = h - Math.floor(h),
- p = 255 * v * (1 - s),
- q = 255 * v * (1 - (s * f)),
- t = 255 * v * (1 - (s * (1 - f))),
- v = 255 * v;
-
- switch(hi) {
- case 0:
- return [v, t, p];
- case 1:
- return [q, v, p];
- case 2:
- return [p, v, t];
- case 3:
- return [p, q, v];
- case 4:
- return [t, p, v];
- case 5:
- return [v, p, q];
- }
-}
-
-function hsv2hsl(hsv) {
- var h = hsv[0],
- s = hsv[1] / 100,
- v = hsv[2] / 100,
- sl, l;
-
- l = (2 - s) * v;
- sl = s * v;
- sl /= (l <= 1) ? l : 2 - l;
- sl = sl || 0;
- l /= 2;
- return [h, sl * 100, l * 100];
-}
-
-function hsv2hwb(args) {
- return rgb2hwb(hsv2rgb(args))
-}
-
-function hsv2cmyk(args) {
- return rgb2cmyk(hsv2rgb(args));
-}
-
-function hsv2keyword(args) {
- return rgb2keyword(hsv2rgb(args));
-}
-
-// http://dev.w3.org/csswg/css-color/#hwb-to-rgb
-function hwb2rgb(hwb) {
- var h = hwb[0] / 360,
- wh = hwb[1] / 100,
- bl = hwb[2] / 100,
- ratio = wh + bl,
- i, v, f, n;
-
- // wh + bl cant be > 1
- if (ratio > 1) {
- wh /= ratio;
- bl /= ratio;
- }
-
- i = Math.floor(6 * h);
- v = 1 - bl;
- f = 6 * h - i;
- if ((i & 0x01) != 0) {
- f = 1 - f;
- }
- n = wh + f * (v - wh); // linear interpolation
-
- switch (i) {
- default:
- case 6:
- case 0: r = v; g = n; b = wh; break;
- case 1: r = n; g = v; b = wh; break;
- case 2: r = wh; g = v; b = n; break;
- case 3: r = wh; g = n; b = v; break;
- case 4: r = n; g = wh; b = v; break;
- case 5: r = v; g = wh; b = n; break;
- }
-
- return [r * 255, g * 255, b * 255];
-}
-
-function hwb2hsl(args) {
- return rgb2hsl(hwb2rgb(args));
-}
-
-function hwb2hsv(args) {
- return rgb2hsv(hwb2rgb(args));
-}
-
-function hwb2cmyk(args) {
- return rgb2cmyk(hwb2rgb(args));
-}
-
-function hwb2keyword(args) {
- return rgb2keyword(hwb2rgb(args));
-}
-
-function cmyk2rgb(cmyk) {
- var c = cmyk[0] / 100,
- m = cmyk[1] / 100,
- y = cmyk[2] / 100,
- k = cmyk[3] / 100,
- r, g, b;
-
- r = 1 - Math.min(1, c * (1 - k) + k);
- g = 1 - Math.min(1, m * (1 - k) + k);
- b = 1 - Math.min(1, y * (1 - k) + k);
- return [r * 255, g * 255, b * 255];
-}
-
-function cmyk2hsl(args) {
- return rgb2hsl(cmyk2rgb(args));
-}
-
-function cmyk2hsv(args) {
- return rgb2hsv(cmyk2rgb(args));
-}
-
-function cmyk2hwb(args) {
- return rgb2hwb(cmyk2rgb(args));
-}
-
-function cmyk2keyword(args) {
- return rgb2keyword(cmyk2rgb(args));
-}
-
-
-function xyz2rgb(xyz) {
- var x = xyz[0] / 100,
- y = xyz[1] / 100,
- z = xyz[2] / 100,
- r, g, b;
-
- r = (x * 3.2406) + (y * -1.5372) + (z * -0.4986);
- g = (x * -0.9689) + (y * 1.8758) + (z * 0.0415);
- b = (x * 0.0557) + (y * -0.2040) + (z * 1.0570);
-
- // assume sRGB
- r = r > 0.0031308 ? ((1.055 * Math.pow(r, 1.0 / 2.4)) - 0.055)
- : r = (r * 12.92);
-
- g = g > 0.0031308 ? ((1.055 * Math.pow(g, 1.0 / 2.4)) - 0.055)
- : g = (g * 12.92);
-
- b = b > 0.0031308 ? ((1.055 * Math.pow(b, 1.0 / 2.4)) - 0.055)
- : b = (b * 12.92);
-
- r = Math.min(Math.max(0, r), 1);
- g = Math.min(Math.max(0, g), 1);
- b = Math.min(Math.max(0, b), 1);
-
- return [r * 255, g * 255, b * 255];
-}
-
-function xyz2lab(xyz) {
- var x = xyz[0],
- y = xyz[1],
- z = xyz[2],
- l, a, b;
-
- x /= 95.047;
- y /= 100;
- z /= 108.883;
-
- x = x > 0.008856 ? Math.pow(x, 1/3) : (7.787 * x) + (16 / 116);
- y = y > 0.008856 ? Math.pow(y, 1/3) : (7.787 * y) + (16 / 116);
- z = z > 0.008856 ? Math.pow(z, 1/3) : (7.787 * z) + (16 / 116);
-
- l = (116 * y) - 16;
- a = 500 * (x - y);
- b = 200 * (y - z);
-
- return [l, a, b];
-}
-
-function xyz2lch(args) {
- return lab2lch(xyz2lab(args));
-}
-
-function lab2xyz(lab) {
- var l = lab[0],
- a = lab[1],
- b = lab[2],
- x, y, z, y2;
-
- if (l <= 8) {
- y = (l * 100) / 903.3;
- y2 = (7.787 * (y / 100)) + (16 / 116);
- } else {
- y = 100 * Math.pow((l + 16) / 116, 3);
- y2 = Math.pow(y / 100, 1/3);
- }
-
- x = x / 95.047 <= 0.008856 ? x = (95.047 * ((a / 500) + y2 - (16 / 116))) / 7.787 : 95.047 * Math.pow((a / 500) + y2, 3);
-
- z = z / 108.883 <= 0.008859 ? z = (108.883 * (y2 - (b / 200) - (16 / 116))) / 7.787 : 108.883 * Math.pow(y2 - (b / 200), 3);
-
- return [x, y, z];
-}
-
-function lab2lch(lab) {
- var l = lab[0],
- a = lab[1],
- b = lab[2],
- hr, h, c;
-
- hr = Math.atan2(b, a);
- h = hr * 360 / 2 / Math.PI;
- if (h < 0) {
- h += 360;
- }
- c = Math.sqrt(a * a + b * b);
- return [l, c, h];
-}
-
-function lab2rgb(args) {
- return xyz2rgb(lab2xyz(args));
-}
-
-function lch2lab(lch) {
- var l = lch[0],
- c = lch[1],
- h = lch[2],
- a, b, hr;
-
- hr = h / 360 * 2 * Math.PI;
- a = c * Math.cos(hr);
- b = c * Math.sin(hr);
- return [l, a, b];
-}
-
-function lch2xyz(args) {
- return lab2xyz(lch2lab(args));
-}
-
-function lch2rgb(args) {
- return lab2rgb(lch2lab(args));
-}
-
-function keyword2rgb(keyword) {
- return cssKeywords[keyword];
-}
-
-function keyword2hsl(args) {
- return rgb2hsl(keyword2rgb(args));
-}
-
-function keyword2hsv(args) {
- return rgb2hsv(keyword2rgb(args));
-}
-
-function keyword2hwb(args) {
- return rgb2hwb(keyword2rgb(args));
-}
-
-function keyword2cmyk(args) {
- return rgb2cmyk(keyword2rgb(args));
-}
-
-function keyword2lab(args) {
- return rgb2lab(keyword2rgb(args));
-}
-
-function keyword2xyz(args) {
- return rgb2xyz(keyword2rgb(args));
-}
-
-var cssKeywords = {
- aliceblue: [240,248,255],
- antiquewhite: [250,235,215],
- aqua: [0,255,255],
- aquamarine: [127,255,212],
- azure: [240,255,255],
- beige: [245,245,220],
- bisque: [255,228,196],
- black: [0,0,0],
- blanchedalmond: [255,235,205],
- blue: [0,0,255],
- blueviolet: [138,43,226],
- brown: [165,42,42],
- burlywood: [222,184,135],
- cadetblue: [95,158,160],
- chartreuse: [127,255,0],
- chocolate: [210,105,30],
- coral: [255,127,80],
- cornflowerblue: [100,149,237],
- cornsilk: [255,248,220],
- crimson: [220,20,60],
- cyan: [0,255,255],
- darkblue: [0,0,139],
- darkcyan: [0,139,139],
- darkgoldenrod: [184,134,11],
- darkgray: [169,169,169],
- darkgreen: [0,100,0],
- darkgrey: [169,169,169],
- darkkhaki: [189,183,107],
- darkmagenta: [139,0,139],
- darkolivegreen: [85,107,47],
- darkorange: [255,140,0],
- darkorchid: [153,50,204],
- darkred: [139,0,0],
- darksalmon: [233,150,122],
- darkseagreen: [143,188,143],
- darkslateblue: [72,61,139],
- darkslategray: [47,79,79],
- darkslategrey: [47,79,79],
- darkturquoise: [0,206,209],
- darkviolet: [148,0,211],
- deeppink: [255,20,147],
- deepskyblue: [0,191,255],
- dimgray: [105,105,105],
- dimgrey: [105,105,105],
- dodgerblue: [30,144,255],
- firebrick: [178,34,34],
- floralwhite: [255,250,240],
- forestgreen: [34,139,34],
- fuchsia: [255,0,255],
- gainsboro: [220,220,220],
- ghostwhite: [248,248,255],
- gold: [255,215,0],
- goldenrod: [218,165,32],
- gray: [128,128,128],
- green: [0,128,0],
- greenyellow: [173,255,47],
- grey: [128,128,128],
- honeydew: [240,255,240],
- hotpink: [255,105,180],
- indianred: [205,92,92],
- indigo: [75,0,130],
- ivory: [255,255,240],
- khaki: [240,230,140],
- lavender: [230,230,250],
- lavenderblush: [255,240,245],
- lawngreen: [124,252,0],
- lemonchiffon: [255,250,205],
- lightblue: [173,216,230],
- lightcoral: [240,128,128],
- lightcyan: [224,255,255],
- lightgoldenrodyellow: [250,250,210],
- lightgray: [211,211,211],
- lightgreen: [144,238,144],
- lightgrey: [211,211,211],
- lightpink: [255,182,193],
- lightsalmon: [255,160,122],
- lightseagreen: [32,178,170],
- lightskyblue: [135,206,250],
- lightslategray: [119,136,153],
- lightslategrey: [119,136,153],
- lightsteelblue: [176,196,222],
- lightyellow: [255,255,224],
- lime: [0,255,0],
- limegreen: [50,205,50],
- linen: [250,240,230],
- magenta: [255,0,255],
- maroon: [128,0,0],
- mediumaquamarine: [102,205,170],
- mediumblue: [0,0,205],
- mediumorchid: [186,85,211],
- mediumpurple: [147,112,219],
- mediumseagreen: [60,179,113],
- mediumslateblue: [123,104,238],
- mediumspringgreen: [0,250,154],
- mediumturquoise: [72,209,204],
- mediumvioletred: [199,21,133],
- midnightblue: [25,25,112],
- mintcream: [245,255,250],
- mistyrose: [255,228,225],
- moccasin: [255,228,181],
- navajowhite: [255,222,173],
- navy: [0,0,128],
- oldlace: [253,245,230],
- olive: [128,128,0],
- olivedrab: [107,142,35],
- orange: [255,165,0],
- orangered: [255,69,0],
- orchid: [218,112,214],
- palegoldenrod: [238,232,170],
- palegreen: [152,251,152],
- paleturquoise: [175,238,238],
- palevioletred: [219,112,147],
- papayawhip: [255,239,213],
- peachpuff: [255,218,185],
- peru: [205,133,63],
- pink: [255,192,203],
- plum: [221,160,221],
- powderblue: [176,224,230],
- purple: [128,0,128],
- rebeccapurple: [102, 51, 153],
- red: [255,0,0],
- rosybrown: [188,143,143],
- royalblue: [65,105,225],
- saddlebrown: [139,69,19],
- salmon: [250,128,114],
- sandybrown: [244,164,96],
- seagreen: [46,139,87],
- seashell: [255,245,238],
- sienna: [160,82,45],
- silver: [192,192,192],
- skyblue: [135,206,235],
- slateblue: [106,90,205],
- slategray: [112,128,144],
- slategrey: [112,128,144],
- snow: [255,250,250],
- springgreen: [0,255,127],
- steelblue: [70,130,180],
- tan: [210,180,140],
- teal: [0,128,128],
- thistle: [216,191,216],
- tomato: [255,99,71],
- turquoise: [64,224,208],
- violet: [238,130,238],
- wheat: [245,222,179],
- white: [255,255,255],
- whitesmoke: [245,245,245],
- yellow: [255,255,0],
- yellowgreen: [154,205,50]
-};
-
-var reverseKeywords = {};
-for (var key in cssKeywords) {
- reverseKeywords[JSON.stringify(cssKeywords[key])] = key;
-}
-
-var convert = function() {
- return new Converter();
-};
-
-for (var func in conversions) {
- // export Raw versions
- convert[func + "Raw"] = (function(func) {
- // accept array or plain args
- return function(arg) {
- if (typeof arg == "number")
- arg = Array.prototype.slice.call(arguments);
- return conversions[func](arg);
- }
- })(func);
-
- var pair = /(\w+)2(\w+)/.exec(func),
- from = pair[1],
- to = pair[2];
-
- // export rgb2hsl and ["rgb"]["hsl"]
- convert[from] = convert[from] || {};
-
- convert[from][to] = convert[func] = (function(func) {
- return function(arg) {
- if (typeof arg == "number")
- arg = Array.prototype.slice.call(arguments);
-
- var val = conversions[func](arg);
- if (typeof val == "string" || val === undefined)
- return val; // keyword
-
- for (var i = 0; i < val.length; i++)
- val[i] = Math.round(val[i]);
- return val;
- }
- })(func);
-}
-
-
-/* Converter does lazy conversion and caching */
-var Converter = function() {
- this.convs = {};
-};
-
-/* Either get the values for a space or
- set the values for a space, depending on args */
-Converter.prototype.routeSpace = function(space, args) {
- var values = args[0];
- if (values === undefined) {
- // color.rgb()
- return this.getValues(space);
- }
- // color.rgb(10, 10, 10)
- if (typeof values == "number") {
- values = Array.prototype.slice.call(args);
- }
-
- return this.setValues(space, values);
-};
-
-/* Set the values for a space, invalidating cache */
-Converter.prototype.setValues = function(space, values) {
- this.space = space;
- this.convs = {};
- this.convs[space] = values;
- return this;
-};
-
-/* Get the values for a space. If there's already
- a conversion for the space, fetch it, otherwise
- compute it */
-Converter.prototype.getValues = function(space) {
- var vals = this.convs[space];
- if (!vals) {
- var fspace = this.space,
- from = this.convs[fspace];
- vals = convert[fspace][space](from);
-
- this.convs[space] = vals;
- }
- return vals;
-};
-
-["rgb", "hsl", "hsv", "cmyk", "keyword"].forEach(function(space) {
- Converter.prototype[space] = function(vals) {
- return this.routeSpace(space, arguments);
- };
-});
-
-var colorConvert = convert;
-
-var colorName = {
- "aliceblue": [240, 248, 255],
- "antiquewhite": [250, 235, 215],
- "aqua": [0, 255, 255],
- "aquamarine": [127, 255, 212],
- "azure": [240, 255, 255],
- "beige": [245, 245, 220],
- "bisque": [255, 228, 196],
- "black": [0, 0, 0],
- "blanchedalmond": [255, 235, 205],
- "blue": [0, 0, 255],
- "blueviolet": [138, 43, 226],
- "brown": [165, 42, 42],
- "burlywood": [222, 184, 135],
- "cadetblue": [95, 158, 160],
- "chartreuse": [127, 255, 0],
- "chocolate": [210, 105, 30],
- "coral": [255, 127, 80],
- "cornflowerblue": [100, 149, 237],
- "cornsilk": [255, 248, 220],
- "crimson": [220, 20, 60],
- "cyan": [0, 255, 255],
- "darkblue": [0, 0, 139],
- "darkcyan": [0, 139, 139],
- "darkgoldenrod": [184, 134, 11],
- "darkgray": [169, 169, 169],
- "darkgreen": [0, 100, 0],
- "darkgrey": [169, 169, 169],
- "darkkhaki": [189, 183, 107],
- "darkmagenta": [139, 0, 139],
- "darkolivegreen": [85, 107, 47],
- "darkorange": [255, 140, 0],
- "darkorchid": [153, 50, 204],
- "darkred": [139, 0, 0],
- "darksalmon": [233, 150, 122],
- "darkseagreen": [143, 188, 143],
- "darkslateblue": [72, 61, 139],
- "darkslategray": [47, 79, 79],
- "darkslategrey": [47, 79, 79],
- "darkturquoise": [0, 206, 209],
- "darkviolet": [148, 0, 211],
- "deeppink": [255, 20, 147],
- "deepskyblue": [0, 191, 255],
- "dimgray": [105, 105, 105],
- "dimgrey": [105, 105, 105],
- "dodgerblue": [30, 144, 255],
- "firebrick": [178, 34, 34],
- "floralwhite": [255, 250, 240],
- "forestgreen": [34, 139, 34],
- "fuchsia": [255, 0, 255],
- "gainsboro": [220, 220, 220],
- "ghostwhite": [248, 248, 255],
- "gold": [255, 215, 0],
- "goldenrod": [218, 165, 32],
- "gray": [128, 128, 128],
- "green": [0, 128, 0],
- "greenyellow": [173, 255, 47],
- "grey": [128, 128, 128],
- "honeydew": [240, 255, 240],
- "hotpink": [255, 105, 180],
- "indianred": [205, 92, 92],
- "indigo": [75, 0, 130],
- "ivory": [255, 255, 240],
- "khaki": [240, 230, 140],
- "lavender": [230, 230, 250],
- "lavenderblush": [255, 240, 245],
- "lawngreen": [124, 252, 0],
- "lemonchiffon": [255, 250, 205],
- "lightblue": [173, 216, 230],
- "lightcoral": [240, 128, 128],
- "lightcyan": [224, 255, 255],
- "lightgoldenrodyellow": [250, 250, 210],
- "lightgray": [211, 211, 211],
- "lightgreen": [144, 238, 144],
- "lightgrey": [211, 211, 211],
- "lightpink": [255, 182, 193],
- "lightsalmon": [255, 160, 122],
- "lightseagreen": [32, 178, 170],
- "lightskyblue": [135, 206, 250],
- "lightslategray": [119, 136, 153],
- "lightslategrey": [119, 136, 153],
- "lightsteelblue": [176, 196, 222],
- "lightyellow": [255, 255, 224],
- "lime": [0, 255, 0],
- "limegreen": [50, 205, 50],
- "linen": [250, 240, 230],
- "magenta": [255, 0, 255],
- "maroon": [128, 0, 0],
- "mediumaquamarine": [102, 205, 170],
- "mediumblue": [0, 0, 205],
- "mediumorchid": [186, 85, 211],
- "mediumpurple": [147, 112, 219],
- "mediumseagreen": [60, 179, 113],
- "mediumslateblue": [123, 104, 238],
- "mediumspringgreen": [0, 250, 154],
- "mediumturquoise": [72, 209, 204],
- "mediumvioletred": [199, 21, 133],
- "midnightblue": [25, 25, 112],
- "mintcream": [245, 255, 250],
- "mistyrose": [255, 228, 225],
- "moccasin": [255, 228, 181],
- "navajowhite": [255, 222, 173],
- "navy": [0, 0, 128],
- "oldlace": [253, 245, 230],
- "olive": [128, 128, 0],
- "olivedrab": [107, 142, 35],
- "orange": [255, 165, 0],
- "orangered": [255, 69, 0],
- "orchid": [218, 112, 214],
- "palegoldenrod": [238, 232, 170],
- "palegreen": [152, 251, 152],
- "paleturquoise": [175, 238, 238],
- "palevioletred": [219, 112, 147],
- "papayawhip": [255, 239, 213],
- "peachpuff": [255, 218, 185],
- "peru": [205, 133, 63],
- "pink": [255, 192, 203],
- "plum": [221, 160, 221],
- "powderblue": [176, 224, 230],
- "purple": [128, 0, 128],
- "rebeccapurple": [102, 51, 153],
- "red": [255, 0, 0],
- "rosybrown": [188, 143, 143],
- "royalblue": [65, 105, 225],
- "saddlebrown": [139, 69, 19],
- "salmon": [250, 128, 114],
- "sandybrown": [244, 164, 96],
- "seagreen": [46, 139, 87],
- "seashell": [255, 245, 238],
- "sienna": [160, 82, 45],
- "silver": [192, 192, 192],
- "skyblue": [135, 206, 235],
- "slateblue": [106, 90, 205],
- "slategray": [112, 128, 144],
- "slategrey": [112, 128, 144],
- "snow": [255, 250, 250],
- "springgreen": [0, 255, 127],
- "steelblue": [70, 130, 180],
- "tan": [210, 180, 140],
- "teal": [0, 128, 128],
- "thistle": [216, 191, 216],
- "tomato": [255, 99, 71],
- "turquoise": [64, 224, 208],
- "violet": [238, 130, 238],
- "wheat": [245, 222, 179],
- "white": [255, 255, 255],
- "whitesmoke": [245, 245, 245],
- "yellow": [255, 255, 0],
- "yellowgreen": [154, 205, 50]
-};
-
-/* MIT license */
-
-
-var colorString = {
- getRgba: getRgba,
- getHsla: getHsla,
- getRgb: getRgb,
- getHsl: getHsl,
- getHwb: getHwb,
- getAlpha: getAlpha,
-
- hexString: hexString,
- rgbString: rgbString,
- rgbaString: rgbaString,
- percentString: percentString,
- percentaString: percentaString,
- hslString: hslString,
- hslaString: hslaString,
- hwbString: hwbString,
- keyword: keyword
-};
-
-function getRgba(string) {
- if (!string) {
- return;
- }
- var abbr = /^#([a-fA-F0-9]{3,4})$/i,
- hex = /^#([a-fA-F0-9]{6}([a-fA-F0-9]{2})?)$/i,
- rgba = /^rgba?\(\s*([+-]?\d+)\s*,\s*([+-]?\d+)\s*,\s*([+-]?\d+)\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)$/i,
- per = /^rgba?\(\s*([+-]?[\d\.]+)\%\s*,\s*([+-]?[\d\.]+)\%\s*,\s*([+-]?[\d\.]+)\%\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)$/i,
- keyword = /(\w+)/;
-
- var rgb = [0, 0, 0],
- a = 1,
- match = string.match(abbr),
- hexAlpha = "";
- if (match) {
- match = match[1];
- hexAlpha = match[3];
- for (var i = 0; i < rgb.length; i++) {
- rgb[i] = parseInt(match[i] + match[i], 16);
- }
- if (hexAlpha) {
- a = Math.round((parseInt(hexAlpha + hexAlpha, 16) / 255) * 100) / 100;
- }
- }
- else if (match = string.match(hex)) {
- hexAlpha = match[2];
- match = match[1];
- for (var i = 0; i < rgb.length; i++) {
- rgb[i] = parseInt(match.slice(i * 2, i * 2 + 2), 16);
- }
- if (hexAlpha) {
- a = Math.round((parseInt(hexAlpha, 16) / 255) * 100) / 100;
- }
- }
- else if (match = string.match(rgba)) {
- for (var i = 0; i < rgb.length; i++) {
- rgb[i] = parseInt(match[i + 1]);
- }
- a = parseFloat(match[4]);
- }
- else if (match = string.match(per)) {
- for (var i = 0; i < rgb.length; i++) {
- rgb[i] = Math.round(parseFloat(match[i + 1]) * 2.55);
- }
- a = parseFloat(match[4]);
- }
- else if (match = string.match(keyword)) {
- if (match[1] == "transparent") {
- return [0, 0, 0, 0];
- }
- rgb = colorName[match[1]];
- if (!rgb) {
- return;
- }
- }
-
- for (var i = 0; i < rgb.length; i++) {
- rgb[i] = scale(rgb[i], 0, 255);
- }
- if (!a && a != 0) {
- a = 1;
- }
- else {
- a = scale(a, 0, 1);
- }
- rgb[3] = a;
- return rgb;
-}
-
-function getHsla(string) {
- if (!string) {
- return;
- }
- var hsl = /^hsla?\(\s*([+-]?\d+)(?:deg)?\s*,\s*([+-]?[\d\.]+)%\s*,\s*([+-]?[\d\.]+)%\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)/;
- var match = string.match(hsl);
- if (match) {
- var alpha = parseFloat(match[4]);
- var h = scale(parseInt(match[1]), 0, 360),
- s = scale(parseFloat(match[2]), 0, 100),
- l = scale(parseFloat(match[3]), 0, 100),
- a = scale(isNaN(alpha) ? 1 : alpha, 0, 1);
- return [h, s, l, a];
- }
-}
-
-function getHwb(string) {
- if (!string) {
- return;
- }
- var hwb = /^hwb\(\s*([+-]?\d+)(?:deg)?\s*,\s*([+-]?[\d\.]+)%\s*,\s*([+-]?[\d\.]+)%\s*(?:,\s*([+-]?[\d\.]+)\s*)?\)/;
- var match = string.match(hwb);
- if (match) {
- var alpha = parseFloat(match[4]);
- var h = scale(parseInt(match[1]), 0, 360),
- w = scale(parseFloat(match[2]), 0, 100),
- b = scale(parseFloat(match[3]), 0, 100),
- a = scale(isNaN(alpha) ? 1 : alpha, 0, 1);
- return [h, w, b, a];
- }
-}
-
-function getRgb(string) {
- var rgba = getRgba(string);
- return rgba && rgba.slice(0, 3);
-}
-
-function getHsl(string) {
- var hsla = getHsla(string);
- return hsla && hsla.slice(0, 3);
-}
-
-function getAlpha(string) {
- var vals = getRgba(string);
- if (vals) {
- return vals[3];
- }
- else if (vals = getHsla(string)) {
- return vals[3];
- }
- else if (vals = getHwb(string)) {
- return vals[3];
- }
-}
-
-// generators
-function hexString(rgba, a) {
- var a = (a !== undefined && rgba.length === 3) ? a : rgba[3];
- return "#" + hexDouble(rgba[0])
- + hexDouble(rgba[1])
- + hexDouble(rgba[2])
- + (
- (a >= 0 && a < 1)
- ? hexDouble(Math.round(a * 255))
- : ""
- );
-}
-
-function rgbString(rgba, alpha) {
- if (alpha < 1 || (rgba[3] && rgba[3] < 1)) {
- return rgbaString(rgba, alpha);
- }
- return "rgb(" + rgba[0] + ", " + rgba[1] + ", " + rgba[2] + ")";
-}
-
-function rgbaString(rgba, alpha) {
- if (alpha === undefined) {
- alpha = (rgba[3] !== undefined ? rgba[3] : 1);
- }
- return "rgba(" + rgba[0] + ", " + rgba[1] + ", " + rgba[2]
- + ", " + alpha + ")";
-}
-
-function percentString(rgba, alpha) {
- if (alpha < 1 || (rgba[3] && rgba[3] < 1)) {
- return percentaString(rgba, alpha);
- }
- var r = Math.round(rgba[0]/255 * 100),
- g = Math.round(rgba[1]/255 * 100),
- b = Math.round(rgba[2]/255 * 100);
-
- return "rgb(" + r + "%, " + g + "%, " + b + "%)";
-}
-
-function percentaString(rgba, alpha) {
- var r = Math.round(rgba[0]/255 * 100),
- g = Math.round(rgba[1]/255 * 100),
- b = Math.round(rgba[2]/255 * 100);
- return "rgba(" + r + "%, " + g + "%, " + b + "%, " + (alpha || rgba[3] || 1) + ")";
-}
-
-function hslString(hsla, alpha) {
- if (alpha < 1 || (hsla[3] && hsla[3] < 1)) {
- return hslaString(hsla, alpha);
- }
- return "hsl(" + hsla[0] + ", " + hsla[1] + "%, " + hsla[2] + "%)";
-}
-
-function hslaString(hsla, alpha) {
- if (alpha === undefined) {
- alpha = (hsla[3] !== undefined ? hsla[3] : 1);
- }
- return "hsla(" + hsla[0] + ", " + hsla[1] + "%, " + hsla[2] + "%, "
- + alpha + ")";
-}
-
-// hwb is a bit different than rgb(a) & hsl(a) since there is no alpha specific syntax
-// (hwb have alpha optional & 1 is default value)
-function hwbString(hwb, alpha) {
- if (alpha === undefined) {
- alpha = (hwb[3] !== undefined ? hwb[3] : 1);
- }
- return "hwb(" + hwb[0] + ", " + hwb[1] + "%, " + hwb[2] + "%"
- + (alpha !== undefined && alpha !== 1 ? ", " + alpha : "") + ")";
-}
-
-function keyword(rgb) {
- return reverseNames[rgb.slice(0, 3)];
-}
-
-// helpers
-function scale(num, min, max) {
- return Math.min(Math.max(min, num), max);
-}
-
-function hexDouble(num) {
- var str = num.toString(16).toUpperCase();
- return (str.length < 2) ? "0" + str : str;
-}
-
-
-//create a list of reverse color names
-var reverseNames = {};
-for (var name in colorName) {
- reverseNames[colorName[name]] = name;
-}
-
-/* MIT license */
-
-
-
-var Color = function (obj) {
- if (obj instanceof Color) {
- return obj;
- }
- if (!(this instanceof Color)) {
- return new Color(obj);
- }
-
- this.valid = false;
- this.values = {
- rgb: [0, 0, 0],
- hsl: [0, 0, 0],
- hsv: [0, 0, 0],
- hwb: [0, 0, 0],
- cmyk: [0, 0, 0, 0],
- alpha: 1
- };
-
- // parse Color() argument
- var vals;
- if (typeof obj === 'string') {
- vals = colorString.getRgba(obj);
- if (vals) {
- this.setValues('rgb', vals);
- } else if (vals = colorString.getHsla(obj)) {
- this.setValues('hsl', vals);
- } else if (vals = colorString.getHwb(obj)) {
- this.setValues('hwb', vals);
- }
- } else if (typeof obj === 'object') {
- vals = obj;
- if (vals.r !== undefined || vals.red !== undefined) {
- this.setValues('rgb', vals);
- } else if (vals.l !== undefined || vals.lightness !== undefined) {
- this.setValues('hsl', vals);
- } else if (vals.v !== undefined || vals.value !== undefined) {
- this.setValues('hsv', vals);
- } else if (vals.w !== undefined || vals.whiteness !== undefined) {
- this.setValues('hwb', vals);
- } else if (vals.c !== undefined || vals.cyan !== undefined) {
- this.setValues('cmyk', vals);
- }
- }
-};
-
-Color.prototype = {
- isValid: function () {
- return this.valid;
- },
- rgb: function () {
- return this.setSpace('rgb', arguments);
- },
- hsl: function () {
- return this.setSpace('hsl', arguments);
- },
- hsv: function () {
- return this.setSpace('hsv', arguments);
- },
- hwb: function () {
- return this.setSpace('hwb', arguments);
- },
- cmyk: function () {
- return this.setSpace('cmyk', arguments);
- },
-
- rgbArray: function () {
- return this.values.rgb;
- },
- hslArray: function () {
- return this.values.hsl;
- },
- hsvArray: function () {
- return this.values.hsv;
- },
- hwbArray: function () {
- var values = this.values;
- if (values.alpha !== 1) {
- return values.hwb.concat([values.alpha]);
- }
- return values.hwb;
- },
- cmykArray: function () {
- return this.values.cmyk;
- },
- rgbaArray: function () {
- var values = this.values;
- return values.rgb.concat([values.alpha]);
- },
- hslaArray: function () {
- var values = this.values;
- return values.hsl.concat([values.alpha]);
- },
- alpha: function (val) {
- if (val === undefined) {
- return this.values.alpha;
- }
- this.setValues('alpha', val);
- return this;
- },
-
- red: function (val) {
- return this.setChannel('rgb', 0, val);
- },
- green: function (val) {
- return this.setChannel('rgb', 1, val);
- },
- blue: function (val) {
- return this.setChannel('rgb', 2, val);
- },
- hue: function (val) {
- if (val) {
- val %= 360;
- val = val < 0 ? 360 + val : val;
- }
- return this.setChannel('hsl', 0, val);
- },
- saturation: function (val) {
- return this.setChannel('hsl', 1, val);
- },
- lightness: function (val) {
- return this.setChannel('hsl', 2, val);
- },
- saturationv: function (val) {
- return this.setChannel('hsv', 1, val);
- },
- whiteness: function (val) {
- return this.setChannel('hwb', 1, val);
- },
- blackness: function (val) {
- return this.setChannel('hwb', 2, val);
- },
- value: function (val) {
- return this.setChannel('hsv', 2, val);
- },
- cyan: function (val) {
- return this.setChannel('cmyk', 0, val);
- },
- magenta: function (val) {
- return this.setChannel('cmyk', 1, val);
- },
- yellow: function (val) {
- return this.setChannel('cmyk', 2, val);
- },
- black: function (val) {
- return this.setChannel('cmyk', 3, val);
- },
-
- hexString: function () {
- return colorString.hexString(this.values.rgb);
- },
- rgbString: function () {
- return colorString.rgbString(this.values.rgb, this.values.alpha);
- },
- rgbaString: function () {
- return colorString.rgbaString(this.values.rgb, this.values.alpha);
- },
- percentString: function () {
- return colorString.percentString(this.values.rgb, this.values.alpha);
- },
- hslString: function () {
- return colorString.hslString(this.values.hsl, this.values.alpha);
- },
- hslaString: function () {
- return colorString.hslaString(this.values.hsl, this.values.alpha);
- },
- hwbString: function () {
- return colorString.hwbString(this.values.hwb, this.values.alpha);
- },
- keyword: function () {
- return colorString.keyword(this.values.rgb, this.values.alpha);
- },
-
- rgbNumber: function () {
- var rgb = this.values.rgb;
- return (rgb[0] << 16) | (rgb[1] << 8) | rgb[2];
- },
-
- luminosity: function () {
- // http://www.w3.org/TR/WCAG20/#relativeluminancedef
- var rgb = this.values.rgb;
- var lum = [];
- for (var i = 0; i < rgb.length; i++) {
- var chan = rgb[i] / 255;
- lum[i] = (chan <= 0.03928) ? chan / 12.92 : Math.pow(((chan + 0.055) / 1.055), 2.4);
- }
- return 0.2126 * lum[0] + 0.7152 * lum[1] + 0.0722 * lum[2];
- },
-
- contrast: function (color2) {
- // http://www.w3.org/TR/WCAG20/#contrast-ratiodef
- var lum1 = this.luminosity();
- var lum2 = color2.luminosity();
- if (lum1 > lum2) {
- return (lum1 + 0.05) / (lum2 + 0.05);
- }
- return (lum2 + 0.05) / (lum1 + 0.05);
- },
-
- level: function (color2) {
- var contrastRatio = this.contrast(color2);
- if (contrastRatio >= 7.1) {
- return 'AAA';
- }
-
- return (contrastRatio >= 4.5) ? 'AA' : '';
- },
-
- dark: function () {
- // YIQ equation from http://24ways.org/2010/calculating-color-contrast
- var rgb = this.values.rgb;
- var yiq = (rgb[0] * 299 + rgb[1] * 587 + rgb[2] * 114) / 1000;
- return yiq < 128;
- },
-
- light: function () {
- return !this.dark();
- },
-
- negate: function () {
- var rgb = [];
- for (var i = 0; i < 3; i++) {
- rgb[i] = 255 - this.values.rgb[i];
- }
- this.setValues('rgb', rgb);
- return this;
- },
-
- lighten: function (ratio) {
- var hsl = this.values.hsl;
- hsl[2] += hsl[2] * ratio;
- this.setValues('hsl', hsl);
- return this;
- },
-
- darken: function (ratio) {
- var hsl = this.values.hsl;
- hsl[2] -= hsl[2] * ratio;
- this.setValues('hsl', hsl);
- return this;
- },
-
- saturate: function (ratio) {
- var hsl = this.values.hsl;
- hsl[1] += hsl[1] * ratio;
- this.setValues('hsl', hsl);
- return this;
- },
-
- desaturate: function (ratio) {
- var hsl = this.values.hsl;
- hsl[1] -= hsl[1] * ratio;
- this.setValues('hsl', hsl);
- return this;
- },
-
- whiten: function (ratio) {
- var hwb = this.values.hwb;
- hwb[1] += hwb[1] * ratio;
- this.setValues('hwb', hwb);
- return this;
- },
-
- blacken: function (ratio) {
- var hwb = this.values.hwb;
- hwb[2] += hwb[2] * ratio;
- this.setValues('hwb', hwb);
- return this;
- },
-
- greyscale: function () {
- var rgb = this.values.rgb;
- // http://en.wikipedia.org/wiki/Grayscale#Converting_color_to_grayscale
- var val = rgb[0] * 0.3 + rgb[1] * 0.59 + rgb[2] * 0.11;
- this.setValues('rgb', [val, val, val]);
- return this;
- },
-
- clearer: function (ratio) {
- var alpha = this.values.alpha;
- this.setValues('alpha', alpha - (alpha * ratio));
- return this;
- },
-
- opaquer: function (ratio) {
- var alpha = this.values.alpha;
- this.setValues('alpha', alpha + (alpha * ratio));
- return this;
- },
-
- rotate: function (degrees) {
- var hsl = this.values.hsl;
- var hue = (hsl[0] + degrees) % 360;
- hsl[0] = hue < 0 ? 360 + hue : hue;
- this.setValues('hsl', hsl);
- return this;
- },
-
- /**
- * Ported from sass implementation in C
- * https://github.com/sass/libsass/blob/0e6b4a2850092356aa3ece07c6b249f0221caced/functions.cpp#L209
- */
- mix: function (mixinColor, weight) {
- var color1 = this;
- var color2 = mixinColor;
- var p = weight === undefined ? 0.5 : weight;
-
- var w = 2 * p - 1;
- var a = color1.alpha() - color2.alpha();
-
- var w1 = (((w * a === -1) ? w : (w + a) / (1 + w * a)) + 1) / 2.0;
- var w2 = 1 - w1;
-
- return this
- .rgb(
- w1 * color1.red() + w2 * color2.red(),
- w1 * color1.green() + w2 * color2.green(),
- w1 * color1.blue() + w2 * color2.blue()
- )
- .alpha(color1.alpha() * p + color2.alpha() * (1 - p));
- },
-
- toJSON: function () {
- return this.rgb();
- },
-
- clone: function () {
- // NOTE(SB): using node-clone creates a dependency to Buffer when using browserify,
- // making the final build way to big to embed in Chart.js. So let's do it manually,
- // assuming that values to clone are 1 dimension arrays containing only numbers,
- // except 'alpha' which is a number.
- var result = new Color();
- var source = this.values;
- var target = result.values;
- var value, type;
-
- for (var prop in source) {
- if (source.hasOwnProperty(prop)) {
- value = source[prop];
- type = ({}).toString.call(value);
- if (type === '[object Array]') {
- target[prop] = value.slice(0);
- } else if (type === '[object Number]') {
- target[prop] = value;
- } else {
- console.error('unexpected color value:', value);
- }
- }
- }
-
- return result;
- }
-};
-
-Color.prototype.spaces = {
- rgb: ['red', 'green', 'blue'],
- hsl: ['hue', 'saturation', 'lightness'],
- hsv: ['hue', 'saturation', 'value'],
- hwb: ['hue', 'whiteness', 'blackness'],
- cmyk: ['cyan', 'magenta', 'yellow', 'black']
-};
-
-Color.prototype.maxes = {
- rgb: [255, 255, 255],
- hsl: [360, 100, 100],
- hsv: [360, 100, 100],
- hwb: [360, 100, 100],
- cmyk: [100, 100, 100, 100]
-};
-
-Color.prototype.getValues = function (space) {
- var values = this.values;
- var vals = {};
-
- for (var i = 0; i < space.length; i++) {
- vals[space.charAt(i)] = values[space][i];
- }
-
- if (values.alpha !== 1) {
- vals.a = values.alpha;
- }
-
- // {r: 255, g: 255, b: 255, a: 0.4}
- return vals;
-};
-
-Color.prototype.setValues = function (space, vals) {
- var values = this.values;
- var spaces = this.spaces;
- var maxes = this.maxes;
- var alpha = 1;
- var i;
-
- this.valid = true;
-
- if (space === 'alpha') {
- alpha = vals;
- } else if (vals.length) {
- // [10, 10, 10]
- values[space] = vals.slice(0, space.length);
- alpha = vals[space.length];
- } else if (vals[space.charAt(0)] !== undefined) {
- // {r: 10, g: 10, b: 10}
- for (i = 0; i < space.length; i++) {
- values[space][i] = vals[space.charAt(i)];
- }
-
- alpha = vals.a;
- } else if (vals[spaces[space][0]] !== undefined) {
- // {red: 10, green: 10, blue: 10}
- var chans = spaces[space];
-
- for (i = 0; i < space.length; i++) {
- values[space][i] = vals[chans[i]];
- }
-
- alpha = vals.alpha;
- }
-
- values.alpha = Math.max(0, Math.min(1, (alpha === undefined ? values.alpha : alpha)));
-
- if (space === 'alpha') {
- return false;
- }
-
- var capped;
-
- // cap values of the space prior converting all values
- for (i = 0; i < space.length; i++) {
- capped = Math.max(0, Math.min(maxes[space][i], values[space][i]));
- values[space][i] = Math.round(capped);
- }
-
- // convert to all the other color spaces
- for (var sname in spaces) {
- if (sname !== space) {
- values[sname] = colorConvert[space][sname](values[space]);
- }
- }
-
- return true;
-};
-
-Color.prototype.setSpace = function (space, args) {
- var vals = args[0];
-
- if (vals === undefined) {
- // color.rgb()
- return this.getValues(space);
- }
-
- // color.rgb(10, 10, 10)
- if (typeof vals === 'number') {
- vals = Array.prototype.slice.call(args);
- }
-
- this.setValues(space, vals);
- return this;
-};
-
-Color.prototype.setChannel = function (space, index, val) {
- var svalues = this.values[space];
- if (val === undefined) {
- // color.red()
- return svalues[index];
- } else if (val === svalues[index]) {
- // color.red(color.red())
- return this;
- }
-
- // color.red(100)
- svalues[index] = val;
- this.setValues(space, svalues);
-
- return this;
-};
-
-if (typeof window !== 'undefined') {
- window.Color = Color;
-}
-
-var chartjsColor = Color;
-
-/**
- * @namespace Chart.helpers
- */
-var helpers = {
- /**
- * An empty function that can be used, for example, for optional callback.
- */
- noop: function() {},
-
- /**
- * Returns a unique id, sequentially generated from a global variable.
- * @returns {number}
- * @function
- */
- uid: (function() {
- var id = 0;
- return function() {
- return id++;
- };
- }()),
-
- /**
- * Returns true if `value` is neither null nor undefined, else returns false.
- * @param {*} value - The value to test.
- * @returns {boolean}
- * @since 2.7.0
- */
- isNullOrUndef: function(value) {
- return value === null || typeof value === 'undefined';
- },
-
- /**
- * Returns true if `value` is an array (including typed arrays), else returns false.
- * @param {*} value - The value to test.
- * @returns {boolean}
- * @function
- */
- isArray: function(value) {
- if (Array.isArray && Array.isArray(value)) {
- return true;
- }
- var type = Object.prototype.toString.call(value);
- if (type.substr(0, 7) === '[object' && type.substr(-6) === 'Array]') {
- return true;
- }
- return false;
- },
-
- /**
- * Returns true if `value` is an object (excluding null), else returns false.
- * @param {*} value - The value to test.
- * @returns {boolean}
- * @since 2.7.0
- */
- isObject: function(value) {
- return value !== null && Object.prototype.toString.call(value) === '[object Object]';
- },
-
- /**
- * Returns true if `value` is a finite number, else returns false
- * @param {*} value - The value to test.
- * @returns {boolean}
- */
- isFinite: function(value) {
- return (typeof value === 'number' || value instanceof Number) && isFinite(value);
- },
-
- /**
- * Returns `value` if defined, else returns `defaultValue`.
- * @param {*} value - The value to return if defined.
- * @param {*} defaultValue - The value to return if `value` is undefined.
- * @returns {*}
- */
- valueOrDefault: function(value, defaultValue) {
- return typeof value === 'undefined' ? defaultValue : value;
- },
-
- /**
- * Returns value at the given `index` in array if defined, else returns `defaultValue`.
- * @param {Array} value - The array to lookup for value at `index`.
- * @param {number} index - The index in `value` to lookup for value.
- * @param {*} defaultValue - The value to return if `value[index]` is undefined.
- * @returns {*}
- */
- valueAtIndexOrDefault: function(value, index, defaultValue) {
- return helpers.valueOrDefault(helpers.isArray(value) ? value[index] : value, defaultValue);
- },
-
- /**
- * Calls `fn` with the given `args` in the scope defined by `thisArg` and returns the
- * value returned by `fn`. If `fn` is not a function, this method returns undefined.
- * @param {function} fn - The function to call.
- * @param {Array|undefined|null} args - The arguments with which `fn` should be called.
- * @param {object} [thisArg] - The value of `this` provided for the call to `fn`.
- * @returns {*}
- */
- callback: function(fn, args, thisArg) {
- if (fn && typeof fn.call === 'function') {
- return fn.apply(thisArg, args);
- }
- },
-
- /**
- * Note(SB) for performance sake, this method should only be used when loopable type
- * is unknown or in none intensive code (not called often and small loopable). Else
- * it's preferable to use a regular for() loop and save extra function calls.
- * @param {object|Array} loopable - The object or array to be iterated.
- * @param {function} fn - The function to call for each item.
- * @param {object} [thisArg] - The value of `this` provided for the call to `fn`.
- * @param {boolean} [reverse] - If true, iterates backward on the loopable.
- */
- each: function(loopable, fn, thisArg, reverse) {
- var i, len, keys;
- if (helpers.isArray(loopable)) {
- len = loopable.length;
- if (reverse) {
- for (i = len - 1; i >= 0; i--) {
- fn.call(thisArg, loopable[i], i);
- }
- } else {
- for (i = 0; i < len; i++) {
- fn.call(thisArg, loopable[i], i);
- }
- }
- } else if (helpers.isObject(loopable)) {
- keys = Object.keys(loopable);
- len = keys.length;
- for (i = 0; i < len; i++) {
- fn.call(thisArg, loopable[keys[i]], keys[i]);
- }
- }
- },
-
- /**
- * Returns true if the `a0` and `a1` arrays have the same content, else returns false.
- * @see https://stackoverflow.com/a/14853974
- * @param {Array} a0 - The array to compare
- * @param {Array} a1 - The array to compare
- * @returns {boolean}
- */
- arrayEquals: function(a0, a1) {
- var i, ilen, v0, v1;
-
- if (!a0 || !a1 || a0.length !== a1.length) {
- return false;
- }
-
- for (i = 0, ilen = a0.length; i < ilen; ++i) {
- v0 = a0[i];
- v1 = a1[i];
-
- if (v0 instanceof Array && v1 instanceof Array) {
- if (!helpers.arrayEquals(v0, v1)) {
- return false;
- }
- } else if (v0 !== v1) {
- // NOTE: two different object instances will never be equal: {x:20} != {x:20}
- return false;
- }
- }
-
- return true;
- },
-
- /**
- * Returns a deep copy of `source` without keeping references on objects and arrays.
- * @param {*} source - The value to clone.
- * @returns {*}
- */
- clone: function(source) {
- if (helpers.isArray(source)) {
- return source.map(helpers.clone);
- }
-
- if (helpers.isObject(source)) {
- var target = {};
- var keys = Object.keys(source);
- var klen = keys.length;
- var k = 0;
-
- for (; k < klen; ++k) {
- target[keys[k]] = helpers.clone(source[keys[k]]);
- }
-
- return target;
- }
-
- return source;
- },
-
- /**
- * The default merger when Chart.helpers.merge is called without merger option.
- * Note(SB): also used by mergeConfig and mergeScaleConfig as fallback.
- * @private
- */
- _merger: function(key, target, source, options) {
- var tval = target[key];
- var sval = source[key];
-
- if (helpers.isObject(tval) && helpers.isObject(sval)) {
- helpers.merge(tval, sval, options);
- } else {
- target[key] = helpers.clone(sval);
- }
- },
-
- /**
- * Merges source[key] in target[key] only if target[key] is undefined.
- * @private
- */
- _mergerIf: function(key, target, source) {
- var tval = target[key];
- var sval = source[key];
-
- if (helpers.isObject(tval) && helpers.isObject(sval)) {
- helpers.mergeIf(tval, sval);
- } else if (!target.hasOwnProperty(key)) {
- target[key] = helpers.clone(sval);
- }
- },
-
- /**
- * Recursively deep copies `source` properties into `target` with the given `options`.
- * IMPORTANT: `target` is not cloned and will be updated with `source` properties.
- * @param {object} target - The target object in which all sources are merged into.
- * @param {object|object[]} source - Object(s) to merge into `target`.
- * @param {object} [options] - Merging options:
- * @param {function} [options.merger] - The merge method (key, target, source, options)
- * @returns {object} The `target` object.
- */
- merge: function(target, source, options) {
- var sources = helpers.isArray(source) ? source : [source];
- var ilen = sources.length;
- var merge, i, keys, klen, k;
-
- if (!helpers.isObject(target)) {
- return target;
- }
-
- options = options || {};
- merge = options.merger || helpers._merger;
-
- for (i = 0; i < ilen; ++i) {
- source = sources[i];
- if (!helpers.isObject(source)) {
- continue;
- }
-
- keys = Object.keys(source);
- for (k = 0, klen = keys.length; k < klen; ++k) {
- merge(keys[k], target, source, options);
- }
- }
-
- return target;
- },
-
- /**
- * Recursively deep copies `source` properties into `target` *only* if not defined in target.
- * IMPORTANT: `target` is not cloned and will be updated with `source` properties.
- * @param {object} target - The target object in which all sources are merged into.
- * @param {object|object[]} source - Object(s) to merge into `target`.
- * @returns {object} The `target` object.
- */
- mergeIf: function(target, source) {
- return helpers.merge(target, source, {merger: helpers._mergerIf});
- },
-
- /**
- * Applies the contents of two or more objects together into the first object.
- * @param {object} target - The target object in which all objects are merged into.
- * @param {object} arg1 - Object containing additional properties to merge in target.
- * @param {object} argN - Additional objects containing properties to merge in target.
- * @returns {object} The `target` object.
- */
- extend: function(target) {
- var setFn = function(value, key) {
- target[key] = value;
- };
- for (var i = 1, ilen = arguments.length; i < ilen; ++i) {
- helpers.each(arguments[i], setFn);
- }
- return target;
- },
-
- /**
- * Basic javascript inheritance based on the model created in Backbone.js
- */
- inherits: function(extensions) {
- var me = this;
- var ChartElement = (extensions && extensions.hasOwnProperty('constructor')) ? extensions.constructor : function() {
- return me.apply(this, arguments);
- };
-
- var Surrogate = function() {
- this.constructor = ChartElement;
- };
-
- Surrogate.prototype = me.prototype;
- ChartElement.prototype = new Surrogate();
- ChartElement.extend = helpers.inherits;
-
- if (extensions) {
- helpers.extend(ChartElement.prototype, extensions);
- }
-
- ChartElement.__super__ = me.prototype;
- return ChartElement;
- }
-};
-
-var helpers_core = helpers;
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, use Chart.helpers.callback instead.
- * @function Chart.helpers.callCallback
- * @deprecated since version 2.6.0
- * @todo remove at version 3
- * @private
- */
-helpers.callCallback = helpers.callback;
-
-/**
- * Provided for backward compatibility, use Array.prototype.indexOf instead.
- * Array.prototype.indexOf compatibility: Chrome, Opera, Safari, FF1.5+, IE9+
- * @function Chart.helpers.indexOf
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers.indexOf = function(array, item, fromIndex) {
- return Array.prototype.indexOf.call(array, item, fromIndex);
-};
-
-/**
- * Provided for backward compatibility, use Chart.helpers.valueOrDefault instead.
- * @function Chart.helpers.getValueOrDefault
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers.getValueOrDefault = helpers.valueOrDefault;
-
-/**
- * Provided for backward compatibility, use Chart.helpers.valueAtIndexOrDefault instead.
- * @function Chart.helpers.getValueAtIndexOrDefault
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers.getValueAtIndexOrDefault = helpers.valueAtIndexOrDefault;
-
-/**
- * Easing functions adapted from Robert Penner's easing equations.
- * @namespace Chart.helpers.easingEffects
- * @see http://www.robertpenner.com/easing/
- */
-var effects = {
- linear: function(t) {
- return t;
- },
-
- easeInQuad: function(t) {
- return t * t;
- },
-
- easeOutQuad: function(t) {
- return -t * (t - 2);
- },
-
- easeInOutQuad: function(t) {
- if ((t /= 0.5) < 1) {
- return 0.5 * t * t;
- }
- return -0.5 * ((--t) * (t - 2) - 1);
- },
-
- easeInCubic: function(t) {
- return t * t * t;
- },
-
- easeOutCubic: function(t) {
- return (t = t - 1) * t * t + 1;
- },
-
- easeInOutCubic: function(t) {
- if ((t /= 0.5) < 1) {
- return 0.5 * t * t * t;
- }
- return 0.5 * ((t -= 2) * t * t + 2);
- },
-
- easeInQuart: function(t) {
- return t * t * t * t;
- },
-
- easeOutQuart: function(t) {
- return -((t = t - 1) * t * t * t - 1);
- },
-
- easeInOutQuart: function(t) {
- if ((t /= 0.5) < 1) {
- return 0.5 * t * t * t * t;
- }
- return -0.5 * ((t -= 2) * t * t * t - 2);
- },
-
- easeInQuint: function(t) {
- return t * t * t * t * t;
- },
-
- easeOutQuint: function(t) {
- return (t = t - 1) * t * t * t * t + 1;
- },
-
- easeInOutQuint: function(t) {
- if ((t /= 0.5) < 1) {
- return 0.5 * t * t * t * t * t;
- }
- return 0.5 * ((t -= 2) * t * t * t * t + 2);
- },
-
- easeInSine: function(t) {
- return -Math.cos(t * (Math.PI / 2)) + 1;
- },
-
- easeOutSine: function(t) {
- return Math.sin(t * (Math.PI / 2));
- },
-
- easeInOutSine: function(t) {
- return -0.5 * (Math.cos(Math.PI * t) - 1);
- },
-
- easeInExpo: function(t) {
- return (t === 0) ? 0 : Math.pow(2, 10 * (t - 1));
- },
-
- easeOutExpo: function(t) {
- return (t === 1) ? 1 : -Math.pow(2, -10 * t) + 1;
- },
-
- easeInOutExpo: function(t) {
- if (t === 0) {
- return 0;
- }
- if (t === 1) {
- return 1;
- }
- if ((t /= 0.5) < 1) {
- return 0.5 * Math.pow(2, 10 * (t - 1));
- }
- return 0.5 * (-Math.pow(2, -10 * --t) + 2);
- },
-
- easeInCirc: function(t) {
- if (t >= 1) {
- return t;
- }
- return -(Math.sqrt(1 - t * t) - 1);
- },
-
- easeOutCirc: function(t) {
- return Math.sqrt(1 - (t = t - 1) * t);
- },
-
- easeInOutCirc: function(t) {
- if ((t /= 0.5) < 1) {
- return -0.5 * (Math.sqrt(1 - t * t) - 1);
- }
- return 0.5 * (Math.sqrt(1 - (t -= 2) * t) + 1);
- },
-
- easeInElastic: function(t) {
- var s = 1.70158;
- var p = 0;
- var a = 1;
- if (t === 0) {
- return 0;
- }
- if (t === 1) {
- return 1;
- }
- if (!p) {
- p = 0.3;
- }
- if (a < 1) {
- a = 1;
- s = p / 4;
- } else {
- s = p / (2 * Math.PI) * Math.asin(1 / a);
- }
- return -(a * Math.pow(2, 10 * (t -= 1)) * Math.sin((t - s) * (2 * Math.PI) / p));
- },
-
- easeOutElastic: function(t) {
- var s = 1.70158;
- var p = 0;
- var a = 1;
- if (t === 0) {
- return 0;
- }
- if (t === 1) {
- return 1;
- }
- if (!p) {
- p = 0.3;
- }
- if (a < 1) {
- a = 1;
- s = p / 4;
- } else {
- s = p / (2 * Math.PI) * Math.asin(1 / a);
- }
- return a * Math.pow(2, -10 * t) * Math.sin((t - s) * (2 * Math.PI) / p) + 1;
- },
-
- easeInOutElastic: function(t) {
- var s = 1.70158;
- var p = 0;
- var a = 1;
- if (t === 0) {
- return 0;
- }
- if ((t /= 0.5) === 2) {
- return 1;
- }
- if (!p) {
- p = 0.45;
- }
- if (a < 1) {
- a = 1;
- s = p / 4;
- } else {
- s = p / (2 * Math.PI) * Math.asin(1 / a);
- }
- if (t < 1) {
- return -0.5 * (a * Math.pow(2, 10 * (t -= 1)) * Math.sin((t - s) * (2 * Math.PI) / p));
- }
- return a * Math.pow(2, -10 * (t -= 1)) * Math.sin((t - s) * (2 * Math.PI) / p) * 0.5 + 1;
- },
- easeInBack: function(t) {
- var s = 1.70158;
- return t * t * ((s + 1) * t - s);
- },
-
- easeOutBack: function(t) {
- var s = 1.70158;
- return (t = t - 1) * t * ((s + 1) * t + s) + 1;
- },
-
- easeInOutBack: function(t) {
- var s = 1.70158;
- if ((t /= 0.5) < 1) {
- return 0.5 * (t * t * (((s *= (1.525)) + 1) * t - s));
- }
- return 0.5 * ((t -= 2) * t * (((s *= (1.525)) + 1) * t + s) + 2);
- },
-
- easeInBounce: function(t) {
- return 1 - effects.easeOutBounce(1 - t);
- },
-
- easeOutBounce: function(t) {
- if (t < (1 / 2.75)) {
- return 7.5625 * t * t;
- }
- if (t < (2 / 2.75)) {
- return 7.5625 * (t -= (1.5 / 2.75)) * t + 0.75;
- }
- if (t < (2.5 / 2.75)) {
- return 7.5625 * (t -= (2.25 / 2.75)) * t + 0.9375;
- }
- return 7.5625 * (t -= (2.625 / 2.75)) * t + 0.984375;
- },
-
- easeInOutBounce: function(t) {
- if (t < 0.5) {
- return effects.easeInBounce(t * 2) * 0.5;
- }
- return effects.easeOutBounce(t * 2 - 1) * 0.5 + 0.5;
- }
-};
-
-var helpers_easing = {
- effects: effects
-};
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, use Chart.helpers.easing.effects instead.
- * @function Chart.helpers.easingEffects
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers_core.easingEffects = effects;
-
-var PI = Math.PI;
-var RAD_PER_DEG = PI / 180;
-var DOUBLE_PI = PI * 2;
-var HALF_PI = PI / 2;
-var QUARTER_PI = PI / 4;
-var TWO_THIRDS_PI = PI * 2 / 3;
-
-/**
- * @namespace Chart.helpers.canvas
- */
-var exports$1 = {
- /**
- * Clears the entire canvas associated to the given `chart`.
- * @param {Chart} chart - The chart for which to clear the canvas.
- */
- clear: function(chart) {
- chart.ctx.clearRect(0, 0, chart.width, chart.height);
- },
-
- /**
- * Creates a "path" for a rectangle with rounded corners at position (x, y) with a
- * given size (width, height) and the same `radius` for all corners.
- * @param {CanvasRenderingContext2D} ctx - The canvas 2D Context.
- * @param {number} x - The x axis of the coordinate for the rectangle starting point.
- * @param {number} y - The y axis of the coordinate for the rectangle starting point.
- * @param {number} width - The rectangle's width.
- * @param {number} height - The rectangle's height.
- * @param {number} radius - The rounded amount (in pixels) for the four corners.
- * @todo handle `radius` as top-left, top-right, bottom-right, bottom-left array/object?
- */
- roundedRect: function(ctx, x, y, width, height, radius) {
- if (radius) {
- var r = Math.min(radius, height / 2, width / 2);
- var left = x + r;
- var top = y + r;
- var right = x + width - r;
- var bottom = y + height - r;
-
- ctx.moveTo(x, top);
- if (left < right && top < bottom) {
- ctx.arc(left, top, r, -PI, -HALF_PI);
- ctx.arc(right, top, r, -HALF_PI, 0);
- ctx.arc(right, bottom, r, 0, HALF_PI);
- ctx.arc(left, bottom, r, HALF_PI, PI);
- } else if (left < right) {
- ctx.moveTo(left, y);
- ctx.arc(right, top, r, -HALF_PI, HALF_PI);
- ctx.arc(left, top, r, HALF_PI, PI + HALF_PI);
- } else if (top < bottom) {
- ctx.arc(left, top, r, -PI, 0);
- ctx.arc(left, bottom, r, 0, PI);
- } else {
- ctx.arc(left, top, r, -PI, PI);
- }
- ctx.closePath();
- ctx.moveTo(x, y);
- } else {
- ctx.rect(x, y, width, height);
- }
- },
-
- drawPoint: function(ctx, style, radius, x, y, rotation) {
- var type, xOffset, yOffset, size, cornerRadius;
- var rad = (rotation || 0) * RAD_PER_DEG;
-
- if (style && typeof style === 'object') {
- type = style.toString();
- if (type === '[object HTMLImageElement]' || type === '[object HTMLCanvasElement]') {
- ctx.drawImage(style, x - style.width / 2, y - style.height / 2, style.width, style.height);
- return;
- }
- }
-
- if (isNaN(radius) || radius <= 0) {
- return;
- }
-
- ctx.beginPath();
-
- switch (style) {
- // Default includes circle
- default:
- ctx.arc(x, y, radius, 0, DOUBLE_PI);
- ctx.closePath();
- break;
- case 'triangle':
- ctx.moveTo(x + Math.sin(rad) * radius, y - Math.cos(rad) * radius);
- rad += TWO_THIRDS_PI;
- ctx.lineTo(x + Math.sin(rad) * radius, y - Math.cos(rad) * radius);
- rad += TWO_THIRDS_PI;
- ctx.lineTo(x + Math.sin(rad) * radius, y - Math.cos(rad) * radius);
- ctx.closePath();
- break;
- case 'rectRounded':
- // NOTE: the rounded rect implementation changed to use `arc` instead of
- // `quadraticCurveTo` since it generates better results when rect is
- // almost a circle. 0.516 (instead of 0.5) produces results with visually
- // closer proportion to the previous impl and it is inscribed in the
- // circle with `radius`. For more details, see the following PRs:
- // https://github.com/chartjs/Chart.js/issues/5597
- // https://github.com/chartjs/Chart.js/issues/5858
- cornerRadius = radius * 0.516;
- size = radius - cornerRadius;
- xOffset = Math.cos(rad + QUARTER_PI) * size;
- yOffset = Math.sin(rad + QUARTER_PI) * size;
- ctx.arc(x - xOffset, y - yOffset, cornerRadius, rad - PI, rad - HALF_PI);
- ctx.arc(x + yOffset, y - xOffset, cornerRadius, rad - HALF_PI, rad);
- ctx.arc(x + xOffset, y + yOffset, cornerRadius, rad, rad + HALF_PI);
- ctx.arc(x - yOffset, y + xOffset, cornerRadius, rad + HALF_PI, rad + PI);
- ctx.closePath();
- break;
- case 'rect':
- if (!rotation) {
- size = Math.SQRT1_2 * radius;
- ctx.rect(x - size, y - size, 2 * size, 2 * size);
- break;
- }
- rad += QUARTER_PI;
- /* falls through */
- case 'rectRot':
- xOffset = Math.cos(rad) * radius;
- yOffset = Math.sin(rad) * radius;
- ctx.moveTo(x - xOffset, y - yOffset);
- ctx.lineTo(x + yOffset, y - xOffset);
- ctx.lineTo(x + xOffset, y + yOffset);
- ctx.lineTo(x - yOffset, y + xOffset);
- ctx.closePath();
- break;
- case 'crossRot':
- rad += QUARTER_PI;
- /* falls through */
- case 'cross':
- xOffset = Math.cos(rad) * radius;
- yOffset = Math.sin(rad) * radius;
- ctx.moveTo(x - xOffset, y - yOffset);
- ctx.lineTo(x + xOffset, y + yOffset);
- ctx.moveTo(x + yOffset, y - xOffset);
- ctx.lineTo(x - yOffset, y + xOffset);
- break;
- case 'star':
- xOffset = Math.cos(rad) * radius;
- yOffset = Math.sin(rad) * radius;
- ctx.moveTo(x - xOffset, y - yOffset);
- ctx.lineTo(x + xOffset, y + yOffset);
- ctx.moveTo(x + yOffset, y - xOffset);
- ctx.lineTo(x - yOffset, y + xOffset);
- rad += QUARTER_PI;
- xOffset = Math.cos(rad) * radius;
- yOffset = Math.sin(rad) * radius;
- ctx.moveTo(x - xOffset, y - yOffset);
- ctx.lineTo(x + xOffset, y + yOffset);
- ctx.moveTo(x + yOffset, y - xOffset);
- ctx.lineTo(x - yOffset, y + xOffset);
- break;
- case 'line':
- xOffset = Math.cos(rad) * radius;
- yOffset = Math.sin(rad) * radius;
- ctx.moveTo(x - xOffset, y - yOffset);
- ctx.lineTo(x + xOffset, y + yOffset);
- break;
- case 'dash':
- ctx.moveTo(x, y);
- ctx.lineTo(x + Math.cos(rad) * radius, y + Math.sin(rad) * radius);
- break;
- }
-
- ctx.fill();
- ctx.stroke();
- },
-
- /**
- * Returns true if the point is inside the rectangle
- * @param {object} point - The point to test
- * @param {object} area - The rectangle
- * @returns {boolean}
- * @private
- */
- _isPointInArea: function(point, area) {
- var epsilon = 1e-6; // 1e-6 is margin in pixels for accumulated error.
-
- return point.x > area.left - epsilon && point.x < area.right + epsilon &&
- point.y > area.top - epsilon && point.y < area.bottom + epsilon;
- },
-
- clipArea: function(ctx, area) {
- ctx.save();
- ctx.beginPath();
- ctx.rect(area.left, area.top, area.right - area.left, area.bottom - area.top);
- ctx.clip();
- },
-
- unclipArea: function(ctx) {
- ctx.restore();
- },
-
- lineTo: function(ctx, previous, target, flip) {
- var stepped = target.steppedLine;
- if (stepped) {
- if (stepped === 'middle') {
- var midpoint = (previous.x + target.x) / 2.0;
- ctx.lineTo(midpoint, flip ? target.y : previous.y);
- ctx.lineTo(midpoint, flip ? previous.y : target.y);
- } else if ((stepped === 'after' && !flip) || (stepped !== 'after' && flip)) {
- ctx.lineTo(previous.x, target.y);
- } else {
- ctx.lineTo(target.x, previous.y);
- }
- ctx.lineTo(target.x, target.y);
- return;
- }
-
- if (!target.tension) {
- ctx.lineTo(target.x, target.y);
- return;
- }
-
- ctx.bezierCurveTo(
- flip ? previous.controlPointPreviousX : previous.controlPointNextX,
- flip ? previous.controlPointPreviousY : previous.controlPointNextY,
- flip ? target.controlPointNextX : target.controlPointPreviousX,
- flip ? target.controlPointNextY : target.controlPointPreviousY,
- target.x,
- target.y);
- }
-};
-
-var helpers_canvas = exports$1;
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, use Chart.helpers.canvas.clear instead.
- * @namespace Chart.helpers.clear
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers_core.clear = exports$1.clear;
-
-/**
- * Provided for backward compatibility, use Chart.helpers.canvas.roundedRect instead.
- * @namespace Chart.helpers.drawRoundedRectangle
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers_core.drawRoundedRectangle = function(ctx) {
- ctx.beginPath();
- exports$1.roundedRect.apply(exports$1, arguments);
-};
-
-var defaults = {
- /**
- * @private
- */
- _set: function(scope, values) {
- return helpers_core.merge(this[scope] || (this[scope] = {}), values);
- }
-};
-
-defaults._set('global', {
- defaultColor: 'rgba(0,0,0,0.1)',
- defaultFontColor: '#666',
- defaultFontFamily: "'Helvetica Neue', 'Helvetica', 'Arial', sans-serif",
- defaultFontSize: 12,
- defaultFontStyle: 'normal',
- defaultLineHeight: 1.2,
- showLines: true
-});
-
-var core_defaults = defaults;
-
-var valueOrDefault = helpers_core.valueOrDefault;
-
-/**
- * Converts the given font object into a CSS font string.
- * @param {object} font - A font object.
- * @return {string} The CSS font string. See https://developer.mozilla.org/en-US/docs/Web/CSS/font
- * @private
- */
-function toFontString(font) {
- if (!font || helpers_core.isNullOrUndef(font.size) || helpers_core.isNullOrUndef(font.family)) {
- return null;
- }
-
- return (font.style ? font.style + ' ' : '')
- + (font.weight ? font.weight + ' ' : '')
- + font.size + 'px '
- + font.family;
-}
-
-/**
- * @alias Chart.helpers.options
- * @namespace
- */
-var helpers_options = {
- /**
- * Converts the given line height `value` in pixels for a specific font `size`.
- * @param {number|string} value - The lineHeight to parse (eg. 1.6, '14px', '75%', '1.6em').
- * @param {number} size - The font size (in pixels) used to resolve relative `value`.
- * @returns {number} The effective line height in pixels (size * 1.2 if value is invalid).
- * @see https://developer.mozilla.org/en-US/docs/Web/CSS/line-height
- * @since 2.7.0
- */
- toLineHeight: function(value, size) {
- var matches = ('' + value).match(/^(normal|(\d+(?:\.\d+)?)(px|em|%)?)$/);
- if (!matches || matches[1] === 'normal') {
- return size * 1.2;
- }
-
- value = +matches[2];
-
- switch (matches[3]) {
- case 'px':
- return value;
- case '%':
- value /= 100;
- break;
- default:
- break;
- }
-
- return size * value;
- },
-
- /**
- * Converts the given value into a padding object with pre-computed width/height.
- * @param {number|object} value - If a number, set the value to all TRBL component,
- * else, if and object, use defined properties and sets undefined ones to 0.
- * @returns {object} The padding values (top, right, bottom, left, width, height)
- * @since 2.7.0
- */
- toPadding: function(value) {
- var t, r, b, l;
-
- if (helpers_core.isObject(value)) {
- t = +value.top || 0;
- r = +value.right || 0;
- b = +value.bottom || 0;
- l = +value.left || 0;
- } else {
- t = r = b = l = +value || 0;
- }
-
- return {
- top: t,
- right: r,
- bottom: b,
- left: l,
- height: t + b,
- width: l + r
- };
- },
-
- /**
- * Parses font options and returns the font object.
- * @param {object} options - A object that contains font options to be parsed.
- * @return {object} The font object.
- * @todo Support font.* options and renamed to toFont().
- * @private
- */
- _parseFont: function(options) {
- var globalDefaults = core_defaults.global;
- var size = valueOrDefault(options.fontSize, globalDefaults.defaultFontSize);
- var font = {
- family: valueOrDefault(options.fontFamily, globalDefaults.defaultFontFamily),
- lineHeight: helpers_core.options.toLineHeight(valueOrDefault(options.lineHeight, globalDefaults.defaultLineHeight), size),
- size: size,
- style: valueOrDefault(options.fontStyle, globalDefaults.defaultFontStyle),
- weight: null,
- string: ''
- };
-
- font.string = toFontString(font);
- return font;
- },
-
- /**
- * Evaluates the given `inputs` sequentially and returns the first defined value.
- * @param {Array} inputs - An array of values, falling back to the last value.
- * @param {object} [context] - If defined and the current value is a function, the value
- * is called with `context` as first argument and the result becomes the new input.
- * @param {number} [index] - If defined and the current value is an array, the value
- * at `index` become the new input.
- * @since 2.7.0
- */
- resolve: function(inputs, context, index) {
- var i, ilen, value;
-
- for (i = 0, ilen = inputs.length; i < ilen; ++i) {
- value = inputs[i];
- if (value === undefined) {
- continue;
- }
- if (context !== undefined && typeof value === 'function') {
- value = value(context);
- }
- if (index !== undefined && helpers_core.isArray(value)) {
- value = value[index];
- }
- if (value !== undefined) {
- return value;
- }
- }
- }
-};
-
-var helpers$1 = helpers_core;
-var easing = helpers_easing;
-var canvas = helpers_canvas;
-var options = helpers_options;
-helpers$1.easing = easing;
-helpers$1.canvas = canvas;
-helpers$1.options = options;
-
-function interpolate(start, view, model, ease) {
- var keys = Object.keys(model);
- var i, ilen, key, actual, origin, target, type, c0, c1;
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
-
- target = model[key];
-
- // if a value is added to the model after pivot() has been called, the view
- // doesn't contain it, so let's initialize the view to the target value.
- if (!view.hasOwnProperty(key)) {
- view[key] = target;
- }
-
- actual = view[key];
-
- if (actual === target || key[0] === '_') {
- continue;
- }
-
- if (!start.hasOwnProperty(key)) {
- start[key] = actual;
- }
-
- origin = start[key];
-
- type = typeof target;
-
- if (type === typeof origin) {
- if (type === 'string') {
- c0 = chartjsColor(origin);
- if (c0.valid) {
- c1 = chartjsColor(target);
- if (c1.valid) {
- view[key] = c1.mix(c0, ease).rgbString();
- continue;
- }
- }
- } else if (helpers$1.isFinite(origin) && helpers$1.isFinite(target)) {
- view[key] = origin + (target - origin) * ease;
- continue;
- }
- }
-
- view[key] = target;
- }
-}
-
-var Element = function(configuration) {
- helpers$1.extend(this, configuration);
- this.initialize.apply(this, arguments);
-};
-
-helpers$1.extend(Element.prototype, {
-
- initialize: function() {
- this.hidden = false;
- },
-
- pivot: function() {
- var me = this;
- if (!me._view) {
- me._view = helpers$1.clone(me._model);
- }
- me._start = {};
- return me;
- },
-
- transition: function(ease) {
- var me = this;
- var model = me._model;
- var start = me._start;
- var view = me._view;
-
- // No animation -> No Transition
- if (!model || ease === 1) {
- me._view = model;
- me._start = null;
- return me;
- }
-
- if (!view) {
- view = me._view = {};
- }
-
- if (!start) {
- start = me._start = {};
- }
-
- interpolate(start, view, model, ease);
-
- return me;
- },
-
- tooltipPosition: function() {
- return {
- x: this._model.x,
- y: this._model.y
- };
- },
-
- hasValue: function() {
- return helpers$1.isNumber(this._model.x) && helpers$1.isNumber(this._model.y);
- }
-});
-
-Element.extend = helpers$1.inherits;
-
-var core_element = Element;
-
-var exports$2 = core_element.extend({
- chart: null, // the animation associated chart instance
- currentStep: 0, // the current animation step
- numSteps: 60, // default number of steps
- easing: '', // the easing to use for this animation
- render: null, // render function used by the animation service
-
- onAnimationProgress: null, // user specified callback to fire on each step of the animation
- onAnimationComplete: null, // user specified callback to fire when the animation finishes
-});
-
-var core_animation = exports$2;
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, use Chart.Animation instead
- * @prop Chart.Animation#animationObject
- * @deprecated since version 2.6.0
- * @todo remove at version 3
- */
-Object.defineProperty(exports$2.prototype, 'animationObject', {
- get: function() {
- return this;
- }
-});
-
-/**
- * Provided for backward compatibility, use Chart.Animation#chart instead
- * @prop Chart.Animation#chartInstance
- * @deprecated since version 2.6.0
- * @todo remove at version 3
- */
-Object.defineProperty(exports$2.prototype, 'chartInstance', {
- get: function() {
- return this.chart;
- },
- set: function(value) {
- this.chart = value;
- }
-});
-
-core_defaults._set('global', {
- animation: {
- duration: 1000,
- easing: 'easeOutQuart',
- onProgress: helpers$1.noop,
- onComplete: helpers$1.noop
- }
-});
-
-var core_animations = {
- animations: [],
- request: null,
-
- /**
- * @param {Chart} chart - The chart to animate.
- * @param {Chart.Animation} animation - The animation that we will animate.
- * @param {number} duration - The animation duration in ms.
- * @param {boolean} lazy - if true, the chart is not marked as animating to enable more responsive interactions
- */
- addAnimation: function(chart, animation, duration, lazy) {
- var animations = this.animations;
- var i, ilen;
-
- animation.chart = chart;
- animation.startTime = Date.now();
- animation.duration = duration;
-
- if (!lazy) {
- chart.animating = true;
- }
-
- for (i = 0, ilen = animations.length; i < ilen; ++i) {
- if (animations[i].chart === chart) {
- animations[i] = animation;
- return;
- }
- }
-
- animations.push(animation);
-
- // If there are no animations queued, manually kickstart a digest, for lack of a better word
- if (animations.length === 1) {
- this.requestAnimationFrame();
- }
- },
-
- cancelAnimation: function(chart) {
- var index = helpers$1.findIndex(this.animations, function(animation) {
- return animation.chart === chart;
- });
-
- if (index !== -1) {
- this.animations.splice(index, 1);
- chart.animating = false;
- }
- },
-
- requestAnimationFrame: function() {
- var me = this;
- if (me.request === null) {
- // Skip animation frame requests until the active one is executed.
- // This can happen when processing mouse events, e.g. 'mousemove'
- // and 'mouseout' events will trigger multiple renders.
- me.request = helpers$1.requestAnimFrame.call(window, function() {
- me.request = null;
- me.startDigest();
- });
- }
- },
-
- /**
- * @private
- */
- startDigest: function() {
- var me = this;
-
- me.advance();
-
- // Do we have more stuff to animate?
- if (me.animations.length > 0) {
- me.requestAnimationFrame();
- }
- },
-
- /**
- * @private
- */
- advance: function() {
- var animations = this.animations;
- var animation, chart, numSteps, nextStep;
- var i = 0;
-
- // 1 animation per chart, so we are looping charts here
- while (i < animations.length) {
- animation = animations[i];
- chart = animation.chart;
- numSteps = animation.numSteps;
-
- // Make sure that currentStep starts at 1
- // https://github.com/chartjs/Chart.js/issues/6104
- nextStep = Math.floor((Date.now() - animation.startTime) / animation.duration * numSteps) + 1;
- animation.currentStep = Math.min(nextStep, numSteps);
-
- helpers$1.callback(animation.render, [chart, animation], chart);
- helpers$1.callback(animation.onAnimationProgress, [animation], chart);
-
- if (animation.currentStep >= numSteps) {
- helpers$1.callback(animation.onAnimationComplete, [animation], chart);
- chart.animating = false;
- animations.splice(i, 1);
- } else {
- ++i;
- }
- }
- }
-};
-
-var resolve = helpers$1.options.resolve;
-
-var arrayEvents = ['push', 'pop', 'shift', 'splice', 'unshift'];
-
-/**
- * Hooks the array methods that add or remove values ('push', pop', 'shift', 'splice',
- * 'unshift') and notify the listener AFTER the array has been altered. Listeners are
- * called on the 'onData*' callbacks (e.g. onDataPush, etc.) with same arguments.
- */
-function listenArrayEvents(array, listener) {
- if (array._chartjs) {
- array._chartjs.listeners.push(listener);
- return;
- }
-
- Object.defineProperty(array, '_chartjs', {
- configurable: true,
- enumerable: false,
- value: {
- listeners: [listener]
- }
- });
-
- arrayEvents.forEach(function(key) {
- var method = 'onData' + key.charAt(0).toUpperCase() + key.slice(1);
- var base = array[key];
-
- Object.defineProperty(array, key, {
- configurable: true,
- enumerable: false,
- value: function() {
- var args = Array.prototype.slice.call(arguments);
- var res = base.apply(this, args);
-
- helpers$1.each(array._chartjs.listeners, function(object) {
- if (typeof object[method] === 'function') {
- object[method].apply(object, args);
- }
- });
-
- return res;
- }
- });
- });
-}
-
-/**
- * Removes the given array event listener and cleanup extra attached properties (such as
- * the _chartjs stub and overridden methods) if array doesn't have any more listeners.
- */
-function unlistenArrayEvents(array, listener) {
- var stub = array._chartjs;
- if (!stub) {
- return;
- }
-
- var listeners = stub.listeners;
- var index = listeners.indexOf(listener);
- if (index !== -1) {
- listeners.splice(index, 1);
- }
-
- if (listeners.length > 0) {
- return;
- }
-
- arrayEvents.forEach(function(key) {
- delete array[key];
- });
-
- delete array._chartjs;
-}
-
-// Base class for all dataset controllers (line, bar, etc)
-var DatasetController = function(chart, datasetIndex) {
- this.initialize(chart, datasetIndex);
-};
-
-helpers$1.extend(DatasetController.prototype, {
-
- /**
- * Element type used to generate a meta dataset (e.g. Chart.element.Line).
- * @type {Chart.core.element}
- */
- datasetElementType: null,
-
- /**
- * Element type used to generate a meta data (e.g. Chart.element.Point).
- * @type {Chart.core.element}
- */
- dataElementType: null,
-
- initialize: function(chart, datasetIndex) {
- var me = this;
- me.chart = chart;
- me.index = datasetIndex;
- me.linkScales();
- me.addElements();
- },
-
- updateIndex: function(datasetIndex) {
- this.index = datasetIndex;
- },
-
- linkScales: function() {
- var me = this;
- var meta = me.getMeta();
- var dataset = me.getDataset();
-
- if (meta.xAxisID === null || !(meta.xAxisID in me.chart.scales)) {
- meta.xAxisID = dataset.xAxisID || me.chart.options.scales.xAxes[0].id;
- }
- if (meta.yAxisID === null || !(meta.yAxisID in me.chart.scales)) {
- meta.yAxisID = dataset.yAxisID || me.chart.options.scales.yAxes[0].id;
- }
- },
-
- getDataset: function() {
- return this.chart.data.datasets[this.index];
- },
-
- getMeta: function() {
- return this.chart.getDatasetMeta(this.index);
- },
-
- getScaleForId: function(scaleID) {
- return this.chart.scales[scaleID];
- },
-
- /**
- * @private
- */
- _getValueScaleId: function() {
- return this.getMeta().yAxisID;
- },
-
- /**
- * @private
- */
- _getIndexScaleId: function() {
- return this.getMeta().xAxisID;
- },
-
- /**
- * @private
- */
- _getValueScale: function() {
- return this.getScaleForId(this._getValueScaleId());
- },
-
- /**
- * @private
- */
- _getIndexScale: function() {
- return this.getScaleForId(this._getIndexScaleId());
- },
-
- reset: function() {
- this.update(true);
- },
-
- /**
- * @private
- */
- destroy: function() {
- if (this._data) {
- unlistenArrayEvents(this._data, this);
- }
- },
-
- createMetaDataset: function() {
- var me = this;
- var type = me.datasetElementType;
- return type && new type({
- _chart: me.chart,
- _datasetIndex: me.index
- });
- },
-
- createMetaData: function(index) {
- var me = this;
- var type = me.dataElementType;
- return type && new type({
- _chart: me.chart,
- _datasetIndex: me.index,
- _index: index
- });
- },
-
- addElements: function() {
- var me = this;
- var meta = me.getMeta();
- var data = me.getDataset().data || [];
- var metaData = meta.data;
- var i, ilen;
-
- for (i = 0, ilen = data.length; i < ilen; ++i) {
- metaData[i] = metaData[i] || me.createMetaData(i);
- }
-
- meta.dataset = meta.dataset || me.createMetaDataset();
- },
-
- addElementAndReset: function(index) {
- var element = this.createMetaData(index);
- this.getMeta().data.splice(index, 0, element);
- this.updateElement(element, index, true);
- },
-
- buildOrUpdateElements: function() {
- var me = this;
- var dataset = me.getDataset();
- var data = dataset.data || (dataset.data = []);
-
- // In order to correctly handle data addition/deletion animation (an thus simulate
- // real-time charts), we need to monitor these data modifications and synchronize
- // the internal meta data accordingly.
- if (me._data !== data) {
- if (me._data) {
- // This case happens when the user replaced the data array instance.
- unlistenArrayEvents(me._data, me);
- }
-
- if (data && Object.isExtensible(data)) {
- listenArrayEvents(data, me);
- }
- me._data = data;
- }
-
- // Re-sync meta data in case the user replaced the data array or if we missed
- // any updates and so make sure that we handle number of datapoints changing.
- me.resyncElements();
- },
-
- update: helpers$1.noop,
-
- transition: function(easingValue) {
- var meta = this.getMeta();
- var elements = meta.data || [];
- var ilen = elements.length;
- var i = 0;
-
- for (; i < ilen; ++i) {
- elements[i].transition(easingValue);
- }
-
- if (meta.dataset) {
- meta.dataset.transition(easingValue);
- }
- },
-
- draw: function() {
- var meta = this.getMeta();
- var elements = meta.data || [];
- var ilen = elements.length;
- var i = 0;
-
- if (meta.dataset) {
- meta.dataset.draw();
- }
-
- for (; i < ilen; ++i) {
- elements[i].draw();
- }
- },
-
- removeHoverStyle: function(element) {
- helpers$1.merge(element._model, element.$previousStyle || {});
- delete element.$previousStyle;
- },
-
- setHoverStyle: function(element) {
- var dataset = this.chart.data.datasets[element._datasetIndex];
- var index = element._index;
- var custom = element.custom || {};
- var model = element._model;
- var getHoverColor = helpers$1.getHoverColor;
-
- element.$previousStyle = {
- backgroundColor: model.backgroundColor,
- borderColor: model.borderColor,
- borderWidth: model.borderWidth
- };
-
- model.backgroundColor = resolve([custom.hoverBackgroundColor, dataset.hoverBackgroundColor, getHoverColor(model.backgroundColor)], undefined, index);
- model.borderColor = resolve([custom.hoverBorderColor, dataset.hoverBorderColor, getHoverColor(model.borderColor)], undefined, index);
- model.borderWidth = resolve([custom.hoverBorderWidth, dataset.hoverBorderWidth, model.borderWidth], undefined, index);
- },
-
- /**
- * @private
- */
- resyncElements: function() {
- var me = this;
- var meta = me.getMeta();
- var data = me.getDataset().data;
- var numMeta = meta.data.length;
- var numData = data.length;
-
- if (numData < numMeta) {
- meta.data.splice(numData, numMeta - numData);
- } else if (numData > numMeta) {
- me.insertElements(numMeta, numData - numMeta);
- }
- },
-
- /**
- * @private
- */
- insertElements: function(start, count) {
- for (var i = 0; i < count; ++i) {
- this.addElementAndReset(start + i);
- }
- },
-
- /**
- * @private
- */
- onDataPush: function() {
- var count = arguments.length;
- this.insertElements(this.getDataset().data.length - count, count);
- },
-
- /**
- * @private
- */
- onDataPop: function() {
- this.getMeta().data.pop();
- },
-
- /**
- * @private
- */
- onDataShift: function() {
- this.getMeta().data.shift();
- },
-
- /**
- * @private
- */
- onDataSplice: function(start, count) {
- this.getMeta().data.splice(start, count);
- this.insertElements(start, arguments.length - 2);
- },
-
- /**
- * @private
- */
- onDataUnshift: function() {
- this.insertElements(0, arguments.length);
- }
-});
-
-DatasetController.extend = helpers$1.inherits;
-
-var core_datasetController = DatasetController;
-
-core_defaults._set('global', {
- elements: {
- arc: {
- backgroundColor: core_defaults.global.defaultColor,
- borderColor: '#fff',
- borderWidth: 2,
- borderAlign: 'center'
- }
- }
-});
-
-var element_arc = core_element.extend({
- inLabelRange: function(mouseX) {
- var vm = this._view;
-
- if (vm) {
- return (Math.pow(mouseX - vm.x, 2) < Math.pow(vm.radius + vm.hoverRadius, 2));
- }
- return false;
- },
-
- inRange: function(chartX, chartY) {
- var vm = this._view;
-
- if (vm) {
- var pointRelativePosition = helpers$1.getAngleFromPoint(vm, {x: chartX, y: chartY});
- var angle = pointRelativePosition.angle;
- var distance = pointRelativePosition.distance;
-
- // Sanitise angle range
- var startAngle = vm.startAngle;
- var endAngle = vm.endAngle;
- while (endAngle < startAngle) {
- endAngle += 2.0 * Math.PI;
- }
- while (angle > endAngle) {
- angle -= 2.0 * Math.PI;
- }
- while (angle < startAngle) {
- angle += 2.0 * Math.PI;
- }
-
- // Check if within the range of the open/close angle
- var betweenAngles = (angle >= startAngle && angle <= endAngle);
- var withinRadius = (distance >= vm.innerRadius && distance <= vm.outerRadius);
-
- return (betweenAngles && withinRadius);
- }
- return false;
- },
-
- getCenterPoint: function() {
- var vm = this._view;
- var halfAngle = (vm.startAngle + vm.endAngle) / 2;
- var halfRadius = (vm.innerRadius + vm.outerRadius) / 2;
- return {
- x: vm.x + Math.cos(halfAngle) * halfRadius,
- y: vm.y + Math.sin(halfAngle) * halfRadius
- };
- },
-
- getArea: function() {
- var vm = this._view;
- return Math.PI * ((vm.endAngle - vm.startAngle) / (2 * Math.PI)) * (Math.pow(vm.outerRadius, 2) - Math.pow(vm.innerRadius, 2));
- },
-
- tooltipPosition: function() {
- var vm = this._view;
- var centreAngle = vm.startAngle + ((vm.endAngle - vm.startAngle) / 2);
- var rangeFromCentre = (vm.outerRadius - vm.innerRadius) / 2 + vm.innerRadius;
-
- return {
- x: vm.x + (Math.cos(centreAngle) * rangeFromCentre),
- y: vm.y + (Math.sin(centreAngle) * rangeFromCentre)
- };
- },
-
- draw: function() {
- var ctx = this._chart.ctx;
- var vm = this._view;
- var sA = vm.startAngle;
- var eA = vm.endAngle;
- var pixelMargin = (vm.borderAlign === 'inner') ? 0.33 : 0;
- var angleMargin;
-
- ctx.save();
-
- ctx.beginPath();
- ctx.arc(vm.x, vm.y, Math.max(vm.outerRadius - pixelMargin, 0), sA, eA);
- ctx.arc(vm.x, vm.y, vm.innerRadius, eA, sA, true);
- ctx.closePath();
-
- ctx.fillStyle = vm.backgroundColor;
- ctx.fill();
-
- if (vm.borderWidth) {
- if (vm.borderAlign === 'inner') {
- // Draw an inner border by cliping the arc and drawing a double-width border
- // Enlarge the clipping arc by 0.33 pixels to eliminate glitches between borders
- ctx.beginPath();
- angleMargin = pixelMargin / vm.outerRadius;
- ctx.arc(vm.x, vm.y, vm.outerRadius, sA - angleMargin, eA + angleMargin);
- if (vm.innerRadius > pixelMargin) {
- angleMargin = pixelMargin / vm.innerRadius;
- ctx.arc(vm.x, vm.y, vm.innerRadius - pixelMargin, eA + angleMargin, sA - angleMargin, true);
- } else {
- ctx.arc(vm.x, vm.y, pixelMargin, eA + Math.PI / 2, sA - Math.PI / 2);
- }
- ctx.closePath();
- ctx.clip();
-
- ctx.beginPath();
- ctx.arc(vm.x, vm.y, vm.outerRadius, sA, eA);
- ctx.arc(vm.x, vm.y, vm.innerRadius, eA, sA, true);
- ctx.closePath();
-
- ctx.lineWidth = vm.borderWidth * 2;
- ctx.lineJoin = 'round';
- } else {
- ctx.lineWidth = vm.borderWidth;
- ctx.lineJoin = 'bevel';
- }
-
- ctx.strokeStyle = vm.borderColor;
- ctx.stroke();
- }
-
- ctx.restore();
- }
-});
-
-var valueOrDefault$1 = helpers$1.valueOrDefault;
-
-var defaultColor = core_defaults.global.defaultColor;
-
-core_defaults._set('global', {
- elements: {
- line: {
- tension: 0.4,
- backgroundColor: defaultColor,
- borderWidth: 3,
- borderColor: defaultColor,
- borderCapStyle: 'butt',
- borderDash: [],
- borderDashOffset: 0.0,
- borderJoinStyle: 'miter',
- capBezierPoints: true,
- fill: true, // do we fill in the area between the line and its base axis
- }
- }
-});
-
-var element_line = core_element.extend({
- draw: function() {
- var me = this;
- var vm = me._view;
- var ctx = me._chart.ctx;
- var spanGaps = vm.spanGaps;
- var points = me._children.slice(); // clone array
- var globalDefaults = core_defaults.global;
- var globalOptionLineElements = globalDefaults.elements.line;
- var lastDrawnIndex = -1;
- var index, current, previous, currentVM;
-
- // If we are looping, adding the first point again
- if (me._loop && points.length) {
- points.push(points[0]);
- }
-
- ctx.save();
-
- // Stroke Line Options
- ctx.lineCap = vm.borderCapStyle || globalOptionLineElements.borderCapStyle;
-
- // IE 9 and 10 do not support line dash
- if (ctx.setLineDash) {
- ctx.setLineDash(vm.borderDash || globalOptionLineElements.borderDash);
- }
-
- ctx.lineDashOffset = valueOrDefault$1(vm.borderDashOffset, globalOptionLineElements.borderDashOffset);
- ctx.lineJoin = vm.borderJoinStyle || globalOptionLineElements.borderJoinStyle;
- ctx.lineWidth = valueOrDefault$1(vm.borderWidth, globalOptionLineElements.borderWidth);
- ctx.strokeStyle = vm.borderColor || globalDefaults.defaultColor;
-
- // Stroke Line
- ctx.beginPath();
- lastDrawnIndex = -1;
-
- for (index = 0; index < points.length; ++index) {
- current = points[index];
- previous = helpers$1.previousItem(points, index);
- currentVM = current._view;
-
- // First point moves to it's starting position no matter what
- if (index === 0) {
- if (!currentVM.skip) {
- ctx.moveTo(currentVM.x, currentVM.y);
- lastDrawnIndex = index;
- }
- } else {
- previous = lastDrawnIndex === -1 ? previous : points[lastDrawnIndex];
-
- if (!currentVM.skip) {
- if ((lastDrawnIndex !== (index - 1) && !spanGaps) || lastDrawnIndex === -1) {
- // There was a gap and this is the first point after the gap
- ctx.moveTo(currentVM.x, currentVM.y);
- } else {
- // Line to next point
- helpers$1.canvas.lineTo(ctx, previous._view, current._view);
- }
- lastDrawnIndex = index;
- }
- }
- }
-
- ctx.stroke();
- ctx.restore();
- }
-});
-
-var valueOrDefault$2 = helpers$1.valueOrDefault;
-
-var defaultColor$1 = core_defaults.global.defaultColor;
-
-core_defaults._set('global', {
- elements: {
- point: {
- radius: 3,
- pointStyle: 'circle',
- backgroundColor: defaultColor$1,
- borderColor: defaultColor$1,
- borderWidth: 1,
- // Hover
- hitRadius: 1,
- hoverRadius: 4,
- hoverBorderWidth: 1
- }
- }
-});
-
-function xRange(mouseX) {
- var vm = this._view;
- return vm ? (Math.abs(mouseX - vm.x) < vm.radius + vm.hitRadius) : false;
-}
-
-function yRange(mouseY) {
- var vm = this._view;
- return vm ? (Math.abs(mouseY - vm.y) < vm.radius + vm.hitRadius) : false;
-}
-
-var element_point = core_element.extend({
- inRange: function(mouseX, mouseY) {
- var vm = this._view;
- return vm ? ((Math.pow(mouseX - vm.x, 2) + Math.pow(mouseY - vm.y, 2)) < Math.pow(vm.hitRadius + vm.radius, 2)) : false;
- },
-
- inLabelRange: xRange,
- inXRange: xRange,
- inYRange: yRange,
-
- getCenterPoint: function() {
- var vm = this._view;
- return {
- x: vm.x,
- y: vm.y
- };
- },
-
- getArea: function() {
- return Math.PI * Math.pow(this._view.radius, 2);
- },
-
- tooltipPosition: function() {
- var vm = this._view;
- return {
- x: vm.x,
- y: vm.y,
- padding: vm.radius + vm.borderWidth
- };
- },
-
- draw: function(chartArea) {
- var vm = this._view;
- var ctx = this._chart.ctx;
- var pointStyle = vm.pointStyle;
- var rotation = vm.rotation;
- var radius = vm.radius;
- var x = vm.x;
- var y = vm.y;
- var globalDefaults = core_defaults.global;
- var defaultColor = globalDefaults.defaultColor; // eslint-disable-line no-shadow
-
- if (vm.skip) {
- return;
- }
-
- // Clipping for Points.
- if (chartArea === undefined || helpers$1.canvas._isPointInArea(vm, chartArea)) {
- ctx.strokeStyle = vm.borderColor || defaultColor;
- ctx.lineWidth = valueOrDefault$2(vm.borderWidth, globalDefaults.elements.point.borderWidth);
- ctx.fillStyle = vm.backgroundColor || defaultColor;
- helpers$1.canvas.drawPoint(ctx, pointStyle, radius, x, y, rotation);
- }
- }
-});
-
-var defaultColor$2 = core_defaults.global.defaultColor;
-
-core_defaults._set('global', {
- elements: {
- rectangle: {
- backgroundColor: defaultColor$2,
- borderColor: defaultColor$2,
- borderSkipped: 'bottom',
- borderWidth: 0
- }
- }
-});
-
-function isVertical(vm) {
- return vm && vm.width !== undefined;
-}
-
-/**
- * Helper function to get the bounds of the bar regardless of the orientation
- * @param bar {Chart.Element.Rectangle} the bar
- * @return {Bounds} bounds of the bar
- * @private
- */
-function getBarBounds(vm) {
- var x1, x2, y1, y2, half;
-
- if (isVertical(vm)) {
- half = vm.width / 2;
- x1 = vm.x - half;
- x2 = vm.x + half;
- y1 = Math.min(vm.y, vm.base);
- y2 = Math.max(vm.y, vm.base);
- } else {
- half = vm.height / 2;
- x1 = Math.min(vm.x, vm.base);
- x2 = Math.max(vm.x, vm.base);
- y1 = vm.y - half;
- y2 = vm.y + half;
- }
-
- return {
- left: x1,
- top: y1,
- right: x2,
- bottom: y2
- };
-}
-
-function swap(orig, v1, v2) {
- return orig === v1 ? v2 : orig === v2 ? v1 : orig;
-}
-
-function parseBorderSkipped(vm) {
- var edge = vm.borderSkipped;
- var res = {};
-
- if (!edge) {
- return res;
- }
-
- if (vm.horizontal) {
- if (vm.base > vm.x) {
- edge = swap(edge, 'left', 'right');
- }
- } else if (vm.base < vm.y) {
- edge = swap(edge, 'bottom', 'top');
- }
-
- res[edge] = true;
- return res;
-}
-
-function parseBorderWidth(vm, maxW, maxH) {
- var value = vm.borderWidth;
- var skip = parseBorderSkipped(vm);
- var t, r, b, l;
-
- if (helpers$1.isObject(value)) {
- t = +value.top || 0;
- r = +value.right || 0;
- b = +value.bottom || 0;
- l = +value.left || 0;
- } else {
- t = r = b = l = +value || 0;
- }
-
- return {
- t: skip.top || (t < 0) ? 0 : t > maxH ? maxH : t,
- r: skip.right || (r < 0) ? 0 : r > maxW ? maxW : r,
- b: skip.bottom || (b < 0) ? 0 : b > maxH ? maxH : b,
- l: skip.left || (l < 0) ? 0 : l > maxW ? maxW : l
- };
-}
-
-function boundingRects(vm) {
- var bounds = getBarBounds(vm);
- var width = bounds.right - bounds.left;
- var height = bounds.bottom - bounds.top;
- var border = parseBorderWidth(vm, width / 2, height / 2);
-
- return {
- outer: {
- x: bounds.left,
- y: bounds.top,
- w: width,
- h: height
- },
- inner: {
- x: bounds.left + border.l,
- y: bounds.top + border.t,
- w: width - border.l - border.r,
- h: height - border.t - border.b
- }
- };
-}
-
-function inRange(vm, x, y) {
- var skipX = x === null;
- var skipY = y === null;
- var bounds = !vm || (skipX && skipY) ? false : getBarBounds(vm);
-
- return bounds
- && (skipX || x >= bounds.left && x <= bounds.right)
- && (skipY || y >= bounds.top && y <= bounds.bottom);
-}
-
-var element_rectangle = core_element.extend({
- draw: function() {
- var ctx = this._chart.ctx;
- var vm = this._view;
- var rects = boundingRects(vm);
- var outer = rects.outer;
- var inner = rects.inner;
-
- ctx.fillStyle = vm.backgroundColor;
- ctx.fillRect(outer.x, outer.y, outer.w, outer.h);
-
- if (outer.w === inner.w && outer.h === inner.h) {
- return;
- }
-
- ctx.save();
- ctx.beginPath();
- ctx.rect(outer.x, outer.y, outer.w, outer.h);
- ctx.clip();
- ctx.fillStyle = vm.borderColor;
- ctx.rect(inner.x, inner.y, inner.w, inner.h);
- ctx.fill('evenodd');
- ctx.restore();
- },
-
- height: function() {
- var vm = this._view;
- return vm.base - vm.y;
- },
-
- inRange: function(mouseX, mouseY) {
- return inRange(this._view, mouseX, mouseY);
- },
-
- inLabelRange: function(mouseX, mouseY) {
- var vm = this._view;
- return isVertical(vm)
- ? inRange(vm, mouseX, null)
- : inRange(vm, null, mouseY);
- },
-
- inXRange: function(mouseX) {
- return inRange(this._view, mouseX, null);
- },
-
- inYRange: function(mouseY) {
- return inRange(this._view, null, mouseY);
- },
-
- getCenterPoint: function() {
- var vm = this._view;
- var x, y;
- if (isVertical(vm)) {
- x = vm.x;
- y = (vm.y + vm.base) / 2;
- } else {
- x = (vm.x + vm.base) / 2;
- y = vm.y;
- }
-
- return {x: x, y: y};
- },
-
- getArea: function() {
- var vm = this._view;
-
- return isVertical(vm)
- ? vm.width * Math.abs(vm.y - vm.base)
- : vm.height * Math.abs(vm.x - vm.base);
- },
-
- tooltipPosition: function() {
- var vm = this._view;
- return {
- x: vm.x,
- y: vm.y
- };
- }
-});
-
-var elements = {};
-var Arc = element_arc;
-var Line = element_line;
-var Point = element_point;
-var Rectangle = element_rectangle;
-elements.Arc = Arc;
-elements.Line = Line;
-elements.Point = Point;
-elements.Rectangle = Rectangle;
-
-var resolve$1 = helpers$1.options.resolve;
-
-core_defaults._set('bar', {
- hover: {
- mode: 'label'
- },
-
- scales: {
- xAxes: [{
- type: 'category',
- categoryPercentage: 0.8,
- barPercentage: 0.9,
- offset: true,
- gridLines: {
- offsetGridLines: true
- }
- }],
-
- yAxes: [{
- type: 'linear'
- }]
- }
-});
-
-/**
- * Computes the "optimal" sample size to maintain bars equally sized while preventing overlap.
- * @private
- */
-function computeMinSampleSize(scale, pixels) {
- var min = scale.isHorizontal() ? scale.width : scale.height;
- var ticks = scale.getTicks();
- var prev, curr, i, ilen;
-
- for (i = 1, ilen = pixels.length; i < ilen; ++i) {
- min = Math.min(min, Math.abs(pixels[i] - pixels[i - 1]));
- }
-
- for (i = 0, ilen = ticks.length; i < ilen; ++i) {
- curr = scale.getPixelForTick(i);
- min = i > 0 ? Math.min(min, curr - prev) : min;
- prev = curr;
- }
-
- return min;
-}
-
-/**
- * Computes an "ideal" category based on the absolute bar thickness or, if undefined or null,
- * uses the smallest interval (see computeMinSampleSize) that prevents bar overlapping. This
- * mode currently always generates bars equally sized (until we introduce scriptable options?).
- * @private
- */
-function computeFitCategoryTraits(index, ruler, options) {
- var thickness = options.barThickness;
- var count = ruler.stackCount;
- var curr = ruler.pixels[index];
- var size, ratio;
-
- if (helpers$1.isNullOrUndef(thickness)) {
- size = ruler.min * options.categoryPercentage;
- ratio = options.barPercentage;
- } else {
- // When bar thickness is enforced, category and bar percentages are ignored.
- // Note(SB): we could add support for relative bar thickness (e.g. barThickness: '50%')
- // and deprecate barPercentage since this value is ignored when thickness is absolute.
- size = thickness * count;
- ratio = 1;
- }
-
- return {
- chunk: size / count,
- ratio: ratio,
- start: curr - (size / 2)
- };
-}
-
-/**
- * Computes an "optimal" category that globally arranges bars side by side (no gap when
- * percentage options are 1), based on the previous and following categories. This mode
- * generates bars with different widths when data are not evenly spaced.
- * @private
- */
-function computeFlexCategoryTraits(index, ruler, options) {
- var pixels = ruler.pixels;
- var curr = pixels[index];
- var prev = index > 0 ? pixels[index - 1] : null;
- var next = index < pixels.length - 1 ? pixels[index + 1] : null;
- var percent = options.categoryPercentage;
- var start, size;
-
- if (prev === null) {
- // first data: its size is double based on the next point or,
- // if it's also the last data, we use the scale size.
- prev = curr - (next === null ? ruler.end - ruler.start : next - curr);
- }
-
- if (next === null) {
- // last data: its size is also double based on the previous point.
- next = curr + curr - prev;
- }
-
- start = curr - (curr - Math.min(prev, next)) / 2 * percent;
- size = Math.abs(next - prev) / 2 * percent;
-
- return {
- chunk: size / ruler.stackCount,
- ratio: options.barPercentage,
- start: start
- };
-}
-
-var controller_bar = core_datasetController.extend({
-
- dataElementType: elements.Rectangle,
-
- initialize: function() {
- var me = this;
- var meta;
-
- core_datasetController.prototype.initialize.apply(me, arguments);
-
- meta = me.getMeta();
- meta.stack = me.getDataset().stack;
- meta.bar = true;
- },
-
- update: function(reset) {
- var me = this;
- var rects = me.getMeta().data;
- var i, ilen;
-
- me._ruler = me.getRuler();
-
- for (i = 0, ilen = rects.length; i < ilen; ++i) {
- me.updateElement(rects[i], i, reset);
- }
- },
-
- updateElement: function(rectangle, index, reset) {
- var me = this;
- var meta = me.getMeta();
- var dataset = me.getDataset();
- var options = me._resolveElementOptions(rectangle, index);
-
- rectangle._xScale = me.getScaleForId(meta.xAxisID);
- rectangle._yScale = me.getScaleForId(meta.yAxisID);
- rectangle._datasetIndex = me.index;
- rectangle._index = index;
- rectangle._model = {
- backgroundColor: options.backgroundColor,
- borderColor: options.borderColor,
- borderSkipped: options.borderSkipped,
- borderWidth: options.borderWidth,
- datasetLabel: dataset.label,
- label: me.chart.data.labels[index]
- };
-
- me._updateElementGeometry(rectangle, index, reset);
-
- rectangle.pivot();
- },
-
- /**
- * @private
- */
- _updateElementGeometry: function(rectangle, index, reset) {
- var me = this;
- var model = rectangle._model;
- var vscale = me._getValueScale();
- var base = vscale.getBasePixel();
- var horizontal = vscale.isHorizontal();
- var ruler = me._ruler || me.getRuler();
- var vpixels = me.calculateBarValuePixels(me.index, index);
- var ipixels = me.calculateBarIndexPixels(me.index, index, ruler);
-
- model.horizontal = horizontal;
- model.base = reset ? base : vpixels.base;
- model.x = horizontal ? reset ? base : vpixels.head : ipixels.center;
- model.y = horizontal ? ipixels.center : reset ? base : vpixels.head;
- model.height = horizontal ? ipixels.size : undefined;
- model.width = horizontal ? undefined : ipixels.size;
- },
-
- /**
- * Returns the stacks based on groups and bar visibility.
- * @param {number} [last] - The dataset index
- * @returns {string[]} The list of stack IDs
- * @private
- */
- _getStacks: function(last) {
- var me = this;
- var chart = me.chart;
- var scale = me._getIndexScale();
- var stacked = scale.options.stacked;
- var ilen = last === undefined ? chart.data.datasets.length : last + 1;
- var stacks = [];
- var i, meta;
-
- for (i = 0; i < ilen; ++i) {
- meta = chart.getDatasetMeta(i);
- if (meta.bar && chart.isDatasetVisible(i) &&
- (stacked === false ||
- (stacked === true && stacks.indexOf(meta.stack) === -1) ||
- (stacked === undefined && (meta.stack === undefined || stacks.indexOf(meta.stack) === -1)))) {
- stacks.push(meta.stack);
- }
- }
-
- return stacks;
- },
-
- /**
- * Returns the effective number of stacks based on groups and bar visibility.
- * @private
- */
- getStackCount: function() {
- return this._getStacks().length;
- },
-
- /**
- * Returns the stack index for the given dataset based on groups and bar visibility.
- * @param {number} [datasetIndex] - The dataset index
- * @param {string} [name] - The stack name to find
- * @returns {number} The stack index
- * @private
- */
- getStackIndex: function(datasetIndex, name) {
- var stacks = this._getStacks(datasetIndex);
- var index = (name !== undefined)
- ? stacks.indexOf(name)
- : -1; // indexOf returns -1 if element is not present
-
- return (index === -1)
- ? stacks.length - 1
- : index;
- },
-
- /**
- * @private
- */
- getRuler: function() {
- var me = this;
- var scale = me._getIndexScale();
- var stackCount = me.getStackCount();
- var datasetIndex = me.index;
- var isHorizontal = scale.isHorizontal();
- var start = isHorizontal ? scale.left : scale.top;
- var end = start + (isHorizontal ? scale.width : scale.height);
- var pixels = [];
- var i, ilen, min;
-
- for (i = 0, ilen = me.getMeta().data.length; i < ilen; ++i) {
- pixels.push(scale.getPixelForValue(null, i, datasetIndex));
- }
-
- min = helpers$1.isNullOrUndef(scale.options.barThickness)
- ? computeMinSampleSize(scale, pixels)
- : -1;
-
- return {
- min: min,
- pixels: pixels,
- start: start,
- end: end,
- stackCount: stackCount,
- scale: scale
- };
- },
-
- /**
- * Note: pixel values are not clamped to the scale area.
- * @private
- */
- calculateBarValuePixels: function(datasetIndex, index) {
- var me = this;
- var chart = me.chart;
- var meta = me.getMeta();
- var scale = me._getValueScale();
- var isHorizontal = scale.isHorizontal();
- var datasets = chart.data.datasets;
- var value = +scale.getRightValue(datasets[datasetIndex].data[index]);
- var minBarLength = scale.options.minBarLength;
- var stacked = scale.options.stacked;
- var stack = meta.stack;
- var start = 0;
- var i, imeta, ivalue, base, head, size;
-
- if (stacked || (stacked === undefined && stack !== undefined)) {
- for (i = 0; i < datasetIndex; ++i) {
- imeta = chart.getDatasetMeta(i);
-
- if (imeta.bar &&
- imeta.stack === stack &&
- imeta.controller._getValueScaleId() === scale.id &&
- chart.isDatasetVisible(i)) {
-
- ivalue = +scale.getRightValue(datasets[i].data[index]);
- if ((value < 0 && ivalue < 0) || (value >= 0 && ivalue > 0)) {
- start += ivalue;
- }
- }
- }
- }
-
- base = scale.getPixelForValue(start);
- head = scale.getPixelForValue(start + value);
- size = head - base;
-
- if (minBarLength !== undefined && Math.abs(size) < minBarLength) {
- size = minBarLength;
- if (value >= 0 && !isHorizontal || value < 0 && isHorizontal) {
- head = base - minBarLength;
- } else {
- head = base + minBarLength;
- }
- }
-
- return {
- size: size,
- base: base,
- head: head,
- center: head + size / 2
- };
- },
-
- /**
- * @private
- */
- calculateBarIndexPixels: function(datasetIndex, index, ruler) {
- var me = this;
- var options = ruler.scale.options;
- var range = options.barThickness === 'flex'
- ? computeFlexCategoryTraits(index, ruler, options)
- : computeFitCategoryTraits(index, ruler, options);
-
- var stackIndex = me.getStackIndex(datasetIndex, me.getMeta().stack);
- var center = range.start + (range.chunk * stackIndex) + (range.chunk / 2);
- var size = Math.min(
- helpers$1.valueOrDefault(options.maxBarThickness, Infinity),
- range.chunk * range.ratio);
-
- return {
- base: center - size / 2,
- head: center + size / 2,
- center: center,
- size: size
- };
- },
-
- draw: function() {
- var me = this;
- var chart = me.chart;
- var scale = me._getValueScale();
- var rects = me.getMeta().data;
- var dataset = me.getDataset();
- var ilen = rects.length;
- var i = 0;
-
- helpers$1.canvas.clipArea(chart.ctx, chart.chartArea);
-
- for (; i < ilen; ++i) {
- if (!isNaN(scale.getRightValue(dataset.data[i]))) {
- rects[i].draw();
- }
- }
-
- helpers$1.canvas.unclipArea(chart.ctx);
- },
-
- /**
- * @private
- */
- _resolveElementOptions: function(rectangle, index) {
- var me = this;
- var chart = me.chart;
- var datasets = chart.data.datasets;
- var dataset = datasets[me.index];
- var custom = rectangle.custom || {};
- var options = chart.options.elements.rectangle;
- var values = {};
- var i, ilen, key;
-
- // Scriptable options
- var context = {
- chart: chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- var keys = [
- 'backgroundColor',
- 'borderColor',
- 'borderSkipped',
- 'borderWidth'
- ];
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$1([
- custom[key],
- dataset[key],
- options[key]
- ], context, index);
- }
-
- return values;
- }
-});
-
-var valueOrDefault$3 = helpers$1.valueOrDefault;
-var resolve$2 = helpers$1.options.resolve;
-
-core_defaults._set('bubble', {
- hover: {
- mode: 'single'
- },
-
- scales: {
- xAxes: [{
- type: 'linear', // bubble should probably use a linear scale by default
- position: 'bottom',
- id: 'x-axis-0' // need an ID so datasets can reference the scale
- }],
- yAxes: [{
- type: 'linear',
- position: 'left',
- id: 'y-axis-0'
- }]
- },
-
- tooltips: {
- callbacks: {
- title: function() {
- // Title doesn't make sense for scatter since we format the data as a point
- return '';
- },
- label: function(item, data) {
- var datasetLabel = data.datasets[item.datasetIndex].label || '';
- var dataPoint = data.datasets[item.datasetIndex].data[item.index];
- return datasetLabel + ': (' + item.xLabel + ', ' + item.yLabel + ', ' + dataPoint.r + ')';
- }
- }
- }
-});
-
-var controller_bubble = core_datasetController.extend({
- /**
- * @protected
- */
- dataElementType: elements.Point,
-
- /**
- * @protected
- */
- update: function(reset) {
- var me = this;
- var meta = me.getMeta();
- var points = meta.data;
-
- // Update Points
- helpers$1.each(points, function(point, index) {
- me.updateElement(point, index, reset);
- });
- },
-
- /**
- * @protected
- */
- updateElement: function(point, index, reset) {
- var me = this;
- var meta = me.getMeta();
- var custom = point.custom || {};
- var xScale = me.getScaleForId(meta.xAxisID);
- var yScale = me.getScaleForId(meta.yAxisID);
- var options = me._resolveElementOptions(point, index);
- var data = me.getDataset().data[index];
- var dsIndex = me.index;
-
- var x = reset ? xScale.getPixelForDecimal(0.5) : xScale.getPixelForValue(typeof data === 'object' ? data : NaN, index, dsIndex);
- var y = reset ? yScale.getBasePixel() : yScale.getPixelForValue(data, index, dsIndex);
-
- point._xScale = xScale;
- point._yScale = yScale;
- point._options = options;
- point._datasetIndex = dsIndex;
- point._index = index;
- point._model = {
- backgroundColor: options.backgroundColor,
- borderColor: options.borderColor,
- borderWidth: options.borderWidth,
- hitRadius: options.hitRadius,
- pointStyle: options.pointStyle,
- rotation: options.rotation,
- radius: reset ? 0 : options.radius,
- skip: custom.skip || isNaN(x) || isNaN(y),
- x: x,
- y: y,
- };
-
- point.pivot();
- },
-
- /**
- * @protected
- */
- setHoverStyle: function(point) {
- var model = point._model;
- var options = point._options;
- var getHoverColor = helpers$1.getHoverColor;
-
- point.$previousStyle = {
- backgroundColor: model.backgroundColor,
- borderColor: model.borderColor,
- borderWidth: model.borderWidth,
- radius: model.radius
- };
-
- model.backgroundColor = valueOrDefault$3(options.hoverBackgroundColor, getHoverColor(options.backgroundColor));
- model.borderColor = valueOrDefault$3(options.hoverBorderColor, getHoverColor(options.borderColor));
- model.borderWidth = valueOrDefault$3(options.hoverBorderWidth, options.borderWidth);
- model.radius = options.radius + options.hoverRadius;
- },
-
- /**
- * @private
- */
- _resolveElementOptions: function(point, index) {
- var me = this;
- var chart = me.chart;
- var datasets = chart.data.datasets;
- var dataset = datasets[me.index];
- var custom = point.custom || {};
- var options = chart.options.elements.point;
- var data = dataset.data[index];
- var values = {};
- var i, ilen, key;
-
- // Scriptable options
- var context = {
- chart: chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- var keys = [
- 'backgroundColor',
- 'borderColor',
- 'borderWidth',
- 'hoverBackgroundColor',
- 'hoverBorderColor',
- 'hoverBorderWidth',
- 'hoverRadius',
- 'hitRadius',
- 'pointStyle',
- 'rotation'
- ];
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$2([
- custom[key],
- dataset[key],
- options[key]
- ], context, index);
- }
-
- // Custom radius resolution
- values.radius = resolve$2([
- custom.radius,
- data ? data.r : undefined,
- dataset.radius,
- options.radius
- ], context, index);
-
- return values;
- }
-});
-
-var resolve$3 = helpers$1.options.resolve;
-var valueOrDefault$4 = helpers$1.valueOrDefault;
-
-core_defaults._set('doughnut', {
- animation: {
- // Boolean - Whether we animate the rotation of the Doughnut
- animateRotate: true,
- // Boolean - Whether we animate scaling the Doughnut from the centre
- animateScale: false
- },
- hover: {
- mode: 'single'
- },
- legendCallback: function(chart) {
- var text = [];
- text.push('
');
-
- var data = chart.data;
- var datasets = data.datasets;
- var labels = data.labels;
-
- if (datasets.length) {
- for (var i = 0; i < datasets[0].data.length; ++i) {
- text.push(' ');
- if (labels[i]) {
- text.push(labels[i]);
- }
- text.push(' ');
- }
- }
-
- text.push(' ');
- return text.join('');
- },
- legend: {
- labels: {
- generateLabels: function(chart) {
- var data = chart.data;
- if (data.labels.length && data.datasets.length) {
- return data.labels.map(function(label, i) {
- var meta = chart.getDatasetMeta(0);
- var ds = data.datasets[0];
- var arc = meta.data[i];
- var custom = arc && arc.custom || {};
- var arcOpts = chart.options.elements.arc;
- var fill = resolve$3([custom.backgroundColor, ds.backgroundColor, arcOpts.backgroundColor], undefined, i);
- var stroke = resolve$3([custom.borderColor, ds.borderColor, arcOpts.borderColor], undefined, i);
- var bw = resolve$3([custom.borderWidth, ds.borderWidth, arcOpts.borderWidth], undefined, i);
-
- return {
- text: label,
- fillStyle: fill,
- strokeStyle: stroke,
- lineWidth: bw,
- hidden: isNaN(ds.data[i]) || meta.data[i].hidden,
-
- // Extra data used for toggling the correct item
- index: i
- };
- });
- }
- return [];
- }
- },
-
- onClick: function(e, legendItem) {
- var index = legendItem.index;
- var chart = this.chart;
- var i, ilen, meta;
-
- for (i = 0, ilen = (chart.data.datasets || []).length; i < ilen; ++i) {
- meta = chart.getDatasetMeta(i);
- // toggle visibility of index if exists
- if (meta.data[index]) {
- meta.data[index].hidden = !meta.data[index].hidden;
- }
- }
-
- chart.update();
- }
- },
-
- // The percentage of the chart that we cut out of the middle.
- cutoutPercentage: 50,
-
- // The rotation of the chart, where the first data arc begins.
- rotation: Math.PI * -0.5,
-
- // The total circumference of the chart.
- circumference: Math.PI * 2.0,
-
- // Need to override these to give a nice default
- tooltips: {
- callbacks: {
- title: function() {
- return '';
- },
- label: function(tooltipItem, data) {
- var dataLabel = data.labels[tooltipItem.index];
- var value = ': ' + data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index];
-
- if (helpers$1.isArray(dataLabel)) {
- // show value on first line of multiline label
- // need to clone because we are changing the value
- dataLabel = dataLabel.slice();
- dataLabel[0] += value;
- } else {
- dataLabel += value;
- }
-
- return dataLabel;
- }
- }
- }
-});
-
-var controller_doughnut = core_datasetController.extend({
-
- dataElementType: elements.Arc,
-
- linkScales: helpers$1.noop,
-
- // Get index of the dataset in relation to the visible datasets. This allows determining the inner and outer radius correctly
- getRingIndex: function(datasetIndex) {
- var ringIndex = 0;
-
- for (var j = 0; j < datasetIndex; ++j) {
- if (this.chart.isDatasetVisible(j)) {
- ++ringIndex;
- }
- }
-
- return ringIndex;
- },
-
- update: function(reset) {
- var me = this;
- var chart = me.chart;
- var chartArea = chart.chartArea;
- var opts = chart.options;
- var availableWidth = chartArea.right - chartArea.left;
- var availableHeight = chartArea.bottom - chartArea.top;
- var minSize = Math.min(availableWidth, availableHeight);
- var offset = {x: 0, y: 0};
- var meta = me.getMeta();
- var arcs = meta.data;
- var cutoutPercentage = opts.cutoutPercentage;
- var circumference = opts.circumference;
- var chartWeight = me._getRingWeight(me.index);
- var i, ilen;
-
- // If the chart's circumference isn't a full circle, calculate minSize as a ratio of the width/height of the arc
- if (circumference < Math.PI * 2.0) {
- var startAngle = opts.rotation % (Math.PI * 2.0);
- startAngle += Math.PI * 2.0 * (startAngle >= Math.PI ? -1 : startAngle < -Math.PI ? 1 : 0);
- var endAngle = startAngle + circumference;
- var start = {x: Math.cos(startAngle), y: Math.sin(startAngle)};
- var end = {x: Math.cos(endAngle), y: Math.sin(endAngle)};
- var contains0 = (startAngle <= 0 && endAngle >= 0) || (startAngle <= Math.PI * 2.0 && Math.PI * 2.0 <= endAngle);
- var contains90 = (startAngle <= Math.PI * 0.5 && Math.PI * 0.5 <= endAngle) || (startAngle <= Math.PI * 2.5 && Math.PI * 2.5 <= endAngle);
- var contains180 = (startAngle <= -Math.PI && -Math.PI <= endAngle) || (startAngle <= Math.PI && Math.PI <= endAngle);
- var contains270 = (startAngle <= -Math.PI * 0.5 && -Math.PI * 0.5 <= endAngle) || (startAngle <= Math.PI * 1.5 && Math.PI * 1.5 <= endAngle);
- var cutout = cutoutPercentage / 100.0;
- var min = {x: contains180 ? -1 : Math.min(start.x * (start.x < 0 ? 1 : cutout), end.x * (end.x < 0 ? 1 : cutout)), y: contains270 ? -1 : Math.min(start.y * (start.y < 0 ? 1 : cutout), end.y * (end.y < 0 ? 1 : cutout))};
- var max = {x: contains0 ? 1 : Math.max(start.x * (start.x > 0 ? 1 : cutout), end.x * (end.x > 0 ? 1 : cutout)), y: contains90 ? 1 : Math.max(start.y * (start.y > 0 ? 1 : cutout), end.y * (end.y > 0 ? 1 : cutout))};
- var size = {width: (max.x - min.x) * 0.5, height: (max.y - min.y) * 0.5};
- minSize = Math.min(availableWidth / size.width, availableHeight / size.height);
- offset = {x: (max.x + min.x) * -0.5, y: (max.y + min.y) * -0.5};
- }
-
- for (i = 0, ilen = arcs.length; i < ilen; ++i) {
- arcs[i]._options = me._resolveElementOptions(arcs[i], i);
- }
-
- chart.borderWidth = me.getMaxBorderWidth();
- chart.outerRadius = Math.max((minSize - chart.borderWidth) / 2, 0);
- chart.innerRadius = Math.max(cutoutPercentage ? (chart.outerRadius / 100) * (cutoutPercentage) : 0, 0);
- chart.radiusLength = (chart.outerRadius - chart.innerRadius) / (me._getVisibleDatasetWeightTotal() || 1);
- chart.offsetX = offset.x * chart.outerRadius;
- chart.offsetY = offset.y * chart.outerRadius;
-
- meta.total = me.calculateTotal();
-
- me.outerRadius = chart.outerRadius - chart.radiusLength * me._getRingWeightOffset(me.index);
- me.innerRadius = Math.max(me.outerRadius - chart.radiusLength * chartWeight, 0);
-
- for (i = 0, ilen = arcs.length; i < ilen; ++i) {
- me.updateElement(arcs[i], i, reset);
- }
- },
-
- updateElement: function(arc, index, reset) {
- var me = this;
- var chart = me.chart;
- var chartArea = chart.chartArea;
- var opts = chart.options;
- var animationOpts = opts.animation;
- var centerX = (chartArea.left + chartArea.right) / 2;
- var centerY = (chartArea.top + chartArea.bottom) / 2;
- var startAngle = opts.rotation; // non reset case handled later
- var endAngle = opts.rotation; // non reset case handled later
- var dataset = me.getDataset();
- var circumference = reset && animationOpts.animateRotate ? 0 : arc.hidden ? 0 : me.calculateCircumference(dataset.data[index]) * (opts.circumference / (2.0 * Math.PI));
- var innerRadius = reset && animationOpts.animateScale ? 0 : me.innerRadius;
- var outerRadius = reset && animationOpts.animateScale ? 0 : me.outerRadius;
- var options = arc._options || {};
-
- helpers$1.extend(arc, {
- // Utility
- _datasetIndex: me.index,
- _index: index,
-
- // Desired view properties
- _model: {
- backgroundColor: options.backgroundColor,
- borderColor: options.borderColor,
- borderWidth: options.borderWidth,
- borderAlign: options.borderAlign,
- x: centerX + chart.offsetX,
- y: centerY + chart.offsetY,
- startAngle: startAngle,
- endAngle: endAngle,
- circumference: circumference,
- outerRadius: outerRadius,
- innerRadius: innerRadius,
- label: helpers$1.valueAtIndexOrDefault(dataset.label, index, chart.data.labels[index])
- }
- });
-
- var model = arc._model;
-
- // Set correct angles if not resetting
- if (!reset || !animationOpts.animateRotate) {
- if (index === 0) {
- model.startAngle = opts.rotation;
- } else {
- model.startAngle = me.getMeta().data[index - 1]._model.endAngle;
- }
-
- model.endAngle = model.startAngle + model.circumference;
- }
-
- arc.pivot();
- },
-
- calculateTotal: function() {
- var dataset = this.getDataset();
- var meta = this.getMeta();
- var total = 0;
- var value;
-
- helpers$1.each(meta.data, function(element, index) {
- value = dataset.data[index];
- if (!isNaN(value) && !element.hidden) {
- total += Math.abs(value);
- }
- });
-
- /* if (total === 0) {
- total = NaN;
- }*/
-
- return total;
- },
-
- calculateCircumference: function(value) {
- var total = this.getMeta().total;
- if (total > 0 && !isNaN(value)) {
- return (Math.PI * 2.0) * (Math.abs(value) / total);
- }
- return 0;
- },
-
- // gets the max border or hover width to properly scale pie charts
- getMaxBorderWidth: function(arcs) {
- var me = this;
- var max = 0;
- var chart = me.chart;
- var i, ilen, meta, arc, controller, options, borderWidth, hoverWidth;
-
- if (!arcs) {
- // Find the outmost visible dataset
- for (i = 0, ilen = chart.data.datasets.length; i < ilen; ++i) {
- if (chart.isDatasetVisible(i)) {
- meta = chart.getDatasetMeta(i);
- arcs = meta.data;
- if (i !== me.index) {
- controller = meta.controller;
- }
- break;
- }
- }
- }
-
- if (!arcs) {
- return 0;
- }
-
- for (i = 0, ilen = arcs.length; i < ilen; ++i) {
- arc = arcs[i];
- options = controller ? controller._resolveElementOptions(arc, i) : arc._options;
- if (options.borderAlign !== 'inner') {
- borderWidth = options.borderWidth;
- hoverWidth = options.hoverBorderWidth;
-
- max = borderWidth > max ? borderWidth : max;
- max = hoverWidth > max ? hoverWidth : max;
- }
- }
- return max;
- },
-
- /**
- * @protected
- */
- setHoverStyle: function(arc) {
- var model = arc._model;
- var options = arc._options;
- var getHoverColor = helpers$1.getHoverColor;
-
- arc.$previousStyle = {
- backgroundColor: model.backgroundColor,
- borderColor: model.borderColor,
- borderWidth: model.borderWidth,
- };
-
- model.backgroundColor = valueOrDefault$4(options.hoverBackgroundColor, getHoverColor(options.backgroundColor));
- model.borderColor = valueOrDefault$4(options.hoverBorderColor, getHoverColor(options.borderColor));
- model.borderWidth = valueOrDefault$4(options.hoverBorderWidth, options.borderWidth);
- },
-
- /**
- * @private
- */
- _resolveElementOptions: function(arc, index) {
- var me = this;
- var chart = me.chart;
- var dataset = me.getDataset();
- var custom = arc.custom || {};
- var options = chart.options.elements.arc;
- var values = {};
- var i, ilen, key;
-
- // Scriptable options
- var context = {
- chart: chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- var keys = [
- 'backgroundColor',
- 'borderColor',
- 'borderWidth',
- 'borderAlign',
- 'hoverBackgroundColor',
- 'hoverBorderColor',
- 'hoverBorderWidth',
- ];
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$3([
- custom[key],
- dataset[key],
- options[key]
- ], context, index);
- }
-
- return values;
- },
-
- /**
- * Get radius length offset of the dataset in relation to the visible datasets weights. This allows determining the inner and outer radius correctly
- * @private
- */
- _getRingWeightOffset: function(datasetIndex) {
- var ringWeightOffset = 0;
-
- for (var i = 0; i < datasetIndex; ++i) {
- if (this.chart.isDatasetVisible(i)) {
- ringWeightOffset += this._getRingWeight(i);
- }
- }
-
- return ringWeightOffset;
- },
-
- /**
- * @private
- */
- _getRingWeight: function(dataSetIndex) {
- return Math.max(valueOrDefault$4(this.chart.data.datasets[dataSetIndex].weight, 1), 0);
- },
-
- /**
- * Returns the sum of all visibile data set weights. This value can be 0.
- * @private
- */
- _getVisibleDatasetWeightTotal: function() {
- return this._getRingWeightOffset(this.chart.data.datasets.length);
- }
-});
-
-core_defaults._set('horizontalBar', {
- hover: {
- mode: 'index',
- axis: 'y'
- },
-
- scales: {
- xAxes: [{
- type: 'linear',
- position: 'bottom'
- }],
-
- yAxes: [{
- type: 'category',
- position: 'left',
- categoryPercentage: 0.8,
- barPercentage: 0.9,
- offset: true,
- gridLines: {
- offsetGridLines: true
- }
- }]
- },
-
- elements: {
- rectangle: {
- borderSkipped: 'left'
- }
- },
-
- tooltips: {
- mode: 'index',
- axis: 'y'
- }
-});
-
-var controller_horizontalBar = controller_bar.extend({
- /**
- * @private
- */
- _getValueScaleId: function() {
- return this.getMeta().xAxisID;
- },
-
- /**
- * @private
- */
- _getIndexScaleId: function() {
- return this.getMeta().yAxisID;
- }
-});
-
-var valueOrDefault$5 = helpers$1.valueOrDefault;
-var resolve$4 = helpers$1.options.resolve;
-var isPointInArea = helpers$1.canvas._isPointInArea;
-
-core_defaults._set('line', {
- showLines: true,
- spanGaps: false,
-
- hover: {
- mode: 'label'
- },
-
- scales: {
- xAxes: [{
- type: 'category',
- id: 'x-axis-0'
- }],
- yAxes: [{
- type: 'linear',
- id: 'y-axis-0'
- }]
- }
-});
-
-function lineEnabled(dataset, options) {
- return valueOrDefault$5(dataset.showLine, options.showLines);
-}
-
-var controller_line = core_datasetController.extend({
-
- datasetElementType: elements.Line,
-
- dataElementType: elements.Point,
-
- update: function(reset) {
- var me = this;
- var meta = me.getMeta();
- var line = meta.dataset;
- var points = meta.data || [];
- var scale = me.getScaleForId(meta.yAxisID);
- var dataset = me.getDataset();
- var showLine = lineEnabled(dataset, me.chart.options);
- var i, ilen;
-
- // Update Line
- if (showLine) {
- // Compatibility: If the properties are defined with only the old name, use those values
- if ((dataset.tension !== undefined) && (dataset.lineTension === undefined)) {
- dataset.lineTension = dataset.tension;
- }
-
- // Utility
- line._scale = scale;
- line._datasetIndex = me.index;
- // Data
- line._children = points;
- // Model
- line._model = me._resolveLineOptions(line);
-
- line.pivot();
- }
-
- // Update Points
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- me.updateElement(points[i], i, reset);
- }
-
- if (showLine && line._model.tension !== 0) {
- me.updateBezierControlPoints();
- }
-
- // Now pivot the point for animation
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- points[i].pivot();
- }
- },
-
- updateElement: function(point, index, reset) {
- var me = this;
- var meta = me.getMeta();
- var custom = point.custom || {};
- var dataset = me.getDataset();
- var datasetIndex = me.index;
- var value = dataset.data[index];
- var yScale = me.getScaleForId(meta.yAxisID);
- var xScale = me.getScaleForId(meta.xAxisID);
- var lineModel = meta.dataset._model;
- var x, y;
-
- var options = me._resolvePointOptions(point, index);
-
- x = xScale.getPixelForValue(typeof value === 'object' ? value : NaN, index, datasetIndex);
- y = reset ? yScale.getBasePixel() : me.calculatePointY(value, index, datasetIndex);
-
- // Utility
- point._xScale = xScale;
- point._yScale = yScale;
- point._options = options;
- point._datasetIndex = datasetIndex;
- point._index = index;
-
- // Desired view properties
- point._model = {
- x: x,
- y: y,
- skip: custom.skip || isNaN(x) || isNaN(y),
- // Appearance
- radius: options.radius,
- pointStyle: options.pointStyle,
- rotation: options.rotation,
- backgroundColor: options.backgroundColor,
- borderColor: options.borderColor,
- borderWidth: options.borderWidth,
- tension: valueOrDefault$5(custom.tension, lineModel ? lineModel.tension : 0),
- steppedLine: lineModel ? lineModel.steppedLine : false,
- // Tooltip
- hitRadius: options.hitRadius
- };
- },
-
- /**
- * @private
- */
- _resolvePointOptions: function(element, index) {
- var me = this;
- var chart = me.chart;
- var dataset = chart.data.datasets[me.index];
- var custom = element.custom || {};
- var options = chart.options.elements.point;
- var values = {};
- var i, ilen, key;
-
- // Scriptable options
- var context = {
- chart: chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- var ELEMENT_OPTIONS = {
- backgroundColor: 'pointBackgroundColor',
- borderColor: 'pointBorderColor',
- borderWidth: 'pointBorderWidth',
- hitRadius: 'pointHitRadius',
- hoverBackgroundColor: 'pointHoverBackgroundColor',
- hoverBorderColor: 'pointHoverBorderColor',
- hoverBorderWidth: 'pointHoverBorderWidth',
- hoverRadius: 'pointHoverRadius',
- pointStyle: 'pointStyle',
- radius: 'pointRadius',
- rotation: 'pointRotation'
- };
- var keys = Object.keys(ELEMENT_OPTIONS);
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$4([
- custom[key],
- dataset[ELEMENT_OPTIONS[key]],
- dataset[key],
- options[key]
- ], context, index);
- }
-
- return values;
- },
-
- /**
- * @private
- */
- _resolveLineOptions: function(element) {
- var me = this;
- var chart = me.chart;
- var dataset = chart.data.datasets[me.index];
- var custom = element.custom || {};
- var options = chart.options;
- var elementOptions = options.elements.line;
- var values = {};
- var i, ilen, key;
-
- var keys = [
- 'backgroundColor',
- 'borderWidth',
- 'borderColor',
- 'borderCapStyle',
- 'borderDash',
- 'borderDashOffset',
- 'borderJoinStyle',
- 'fill',
- 'cubicInterpolationMode'
- ];
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$4([
- custom[key],
- dataset[key],
- elementOptions[key]
- ]);
- }
-
- // The default behavior of lines is to break at null values, according
- // to https://github.com/chartjs/Chart.js/issues/2435#issuecomment-216718158
- // This option gives lines the ability to span gaps
- values.spanGaps = valueOrDefault$5(dataset.spanGaps, options.spanGaps);
- values.tension = valueOrDefault$5(dataset.lineTension, elementOptions.tension);
- values.steppedLine = resolve$4([custom.steppedLine, dataset.steppedLine, elementOptions.stepped]);
-
- return values;
- },
-
- calculatePointY: function(value, index, datasetIndex) {
- var me = this;
- var chart = me.chart;
- var meta = me.getMeta();
- var yScale = me.getScaleForId(meta.yAxisID);
- var sumPos = 0;
- var sumNeg = 0;
- var i, ds, dsMeta;
-
- if (yScale.options.stacked) {
- for (i = 0; i < datasetIndex; i++) {
- ds = chart.data.datasets[i];
- dsMeta = chart.getDatasetMeta(i);
- if (dsMeta.type === 'line' && dsMeta.yAxisID === yScale.id && chart.isDatasetVisible(i)) {
- var stackedRightValue = Number(yScale.getRightValue(ds.data[index]));
- if (stackedRightValue < 0) {
- sumNeg += stackedRightValue || 0;
- } else {
- sumPos += stackedRightValue || 0;
- }
- }
- }
-
- var rightValue = Number(yScale.getRightValue(value));
- if (rightValue < 0) {
- return yScale.getPixelForValue(sumNeg + rightValue);
- }
- return yScale.getPixelForValue(sumPos + rightValue);
- }
-
- return yScale.getPixelForValue(value);
- },
-
- updateBezierControlPoints: function() {
- var me = this;
- var chart = me.chart;
- var meta = me.getMeta();
- var lineModel = meta.dataset._model;
- var area = chart.chartArea;
- var points = meta.data || [];
- var i, ilen, model, controlPoints;
-
- // Only consider points that are drawn in case the spanGaps option is used
- if (lineModel.spanGaps) {
- points = points.filter(function(pt) {
- return !pt._model.skip;
- });
- }
-
- function capControlPoint(pt, min, max) {
- return Math.max(Math.min(pt, max), min);
- }
-
- if (lineModel.cubicInterpolationMode === 'monotone') {
- helpers$1.splineCurveMonotone(points);
- } else {
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- model = points[i]._model;
- controlPoints = helpers$1.splineCurve(
- helpers$1.previousItem(points, i)._model,
- model,
- helpers$1.nextItem(points, i)._model,
- lineModel.tension
- );
- model.controlPointPreviousX = controlPoints.previous.x;
- model.controlPointPreviousY = controlPoints.previous.y;
- model.controlPointNextX = controlPoints.next.x;
- model.controlPointNextY = controlPoints.next.y;
- }
- }
-
- if (chart.options.elements.line.capBezierPoints) {
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- model = points[i]._model;
- if (isPointInArea(model, area)) {
- if (i > 0 && isPointInArea(points[i - 1]._model, area)) {
- model.controlPointPreviousX = capControlPoint(model.controlPointPreviousX, area.left, area.right);
- model.controlPointPreviousY = capControlPoint(model.controlPointPreviousY, area.top, area.bottom);
- }
- if (i < points.length - 1 && isPointInArea(points[i + 1]._model, area)) {
- model.controlPointNextX = capControlPoint(model.controlPointNextX, area.left, area.right);
- model.controlPointNextY = capControlPoint(model.controlPointNextY, area.top, area.bottom);
- }
- }
- }
- }
- },
-
- draw: function() {
- var me = this;
- var chart = me.chart;
- var meta = me.getMeta();
- var points = meta.data || [];
- var area = chart.chartArea;
- var ilen = points.length;
- var halfBorderWidth;
- var i = 0;
-
- if (lineEnabled(me.getDataset(), chart.options)) {
- halfBorderWidth = (meta.dataset._model.borderWidth || 0) / 2;
-
- helpers$1.canvas.clipArea(chart.ctx, {
- left: area.left,
- right: area.right,
- top: area.top - halfBorderWidth,
- bottom: area.bottom + halfBorderWidth
- });
-
- meta.dataset.draw();
-
- helpers$1.canvas.unclipArea(chart.ctx);
- }
-
- // Draw the points
- for (; i < ilen; ++i) {
- points[i].draw(area);
- }
- },
-
- /**
- * @protected
- */
- setHoverStyle: function(point) {
- var model = point._model;
- var options = point._options;
- var getHoverColor = helpers$1.getHoverColor;
-
- point.$previousStyle = {
- backgroundColor: model.backgroundColor,
- borderColor: model.borderColor,
- borderWidth: model.borderWidth,
- radius: model.radius
- };
-
- model.backgroundColor = valueOrDefault$5(options.hoverBackgroundColor, getHoverColor(options.backgroundColor));
- model.borderColor = valueOrDefault$5(options.hoverBorderColor, getHoverColor(options.borderColor));
- model.borderWidth = valueOrDefault$5(options.hoverBorderWidth, options.borderWidth);
- model.radius = valueOrDefault$5(options.hoverRadius, options.radius);
- },
-});
-
-var resolve$5 = helpers$1.options.resolve;
-
-core_defaults._set('polarArea', {
- scale: {
- type: 'radialLinear',
- angleLines: {
- display: false
- },
- gridLines: {
- circular: true
- },
- pointLabels: {
- display: false
- },
- ticks: {
- beginAtZero: true
- }
- },
-
- // Boolean - Whether to animate the rotation of the chart
- animation: {
- animateRotate: true,
- animateScale: true
- },
-
- startAngle: -0.5 * Math.PI,
- legendCallback: function(chart) {
- var text = [];
- text.push('
');
-
- var data = chart.data;
- var datasets = data.datasets;
- var labels = data.labels;
-
- if (datasets.length) {
- for (var i = 0; i < datasets[0].data.length; ++i) {
- text.push(' ');
- if (labels[i]) {
- text.push(labels[i]);
- }
- text.push(' ');
- }
- }
-
- text.push(' ');
- return text.join('');
- },
- legend: {
- labels: {
- generateLabels: function(chart) {
- var data = chart.data;
- if (data.labels.length && data.datasets.length) {
- return data.labels.map(function(label, i) {
- var meta = chart.getDatasetMeta(0);
- var ds = data.datasets[0];
- var arc = meta.data[i];
- var custom = arc.custom || {};
- var arcOpts = chart.options.elements.arc;
- var fill = resolve$5([custom.backgroundColor, ds.backgroundColor, arcOpts.backgroundColor], undefined, i);
- var stroke = resolve$5([custom.borderColor, ds.borderColor, arcOpts.borderColor], undefined, i);
- var bw = resolve$5([custom.borderWidth, ds.borderWidth, arcOpts.borderWidth], undefined, i);
-
- return {
- text: label,
- fillStyle: fill,
- strokeStyle: stroke,
- lineWidth: bw,
- hidden: isNaN(ds.data[i]) || meta.data[i].hidden,
-
- // Extra data used for toggling the correct item
- index: i
- };
- });
- }
- return [];
- }
- },
-
- onClick: function(e, legendItem) {
- var index = legendItem.index;
- var chart = this.chart;
- var i, ilen, meta;
-
- for (i = 0, ilen = (chart.data.datasets || []).length; i < ilen; ++i) {
- meta = chart.getDatasetMeta(i);
- meta.data[index].hidden = !meta.data[index].hidden;
- }
-
- chart.update();
- }
- },
-
- // Need to override these to give a nice default
- tooltips: {
- callbacks: {
- title: function() {
- return '';
- },
- label: function(item, data) {
- return data.labels[item.index] + ': ' + item.yLabel;
- }
- }
- }
-});
-
-var controller_polarArea = core_datasetController.extend({
-
- dataElementType: elements.Arc,
-
- linkScales: helpers$1.noop,
-
- update: function(reset) {
- var me = this;
- var dataset = me.getDataset();
- var meta = me.getMeta();
- var start = me.chart.options.startAngle || 0;
- var starts = me._starts = [];
- var angles = me._angles = [];
- var arcs = meta.data;
- var i, ilen, angle;
-
- me._updateRadius();
-
- meta.count = me.countVisibleElements();
-
- for (i = 0, ilen = dataset.data.length; i < ilen; i++) {
- starts[i] = start;
- angle = me._computeAngle(i);
- angles[i] = angle;
- start += angle;
- }
-
- for (i = 0, ilen = arcs.length; i < ilen; ++i) {
- arcs[i]._options = me._resolveElementOptions(arcs[i], i);
- me.updateElement(arcs[i], i, reset);
- }
- },
-
- /**
- * @private
- */
- _updateRadius: function() {
- var me = this;
- var chart = me.chart;
- var chartArea = chart.chartArea;
- var opts = chart.options;
- var minSize = Math.min(chartArea.right - chartArea.left, chartArea.bottom - chartArea.top);
-
- chart.outerRadius = Math.max(minSize / 2, 0);
- chart.innerRadius = Math.max(opts.cutoutPercentage ? (chart.outerRadius / 100) * (opts.cutoutPercentage) : 1, 0);
- chart.radiusLength = (chart.outerRadius - chart.innerRadius) / chart.getVisibleDatasetCount();
-
- me.outerRadius = chart.outerRadius - (chart.radiusLength * me.index);
- me.innerRadius = me.outerRadius - chart.radiusLength;
- },
-
- updateElement: function(arc, index, reset) {
- var me = this;
- var chart = me.chart;
- var dataset = me.getDataset();
- var opts = chart.options;
- var animationOpts = opts.animation;
- var scale = chart.scale;
- var labels = chart.data.labels;
-
- var centerX = scale.xCenter;
- var centerY = scale.yCenter;
-
- // var negHalfPI = -0.5 * Math.PI;
- var datasetStartAngle = opts.startAngle;
- var distance = arc.hidden ? 0 : scale.getDistanceFromCenterForValue(dataset.data[index]);
- var startAngle = me._starts[index];
- var endAngle = startAngle + (arc.hidden ? 0 : me._angles[index]);
-
- var resetRadius = animationOpts.animateScale ? 0 : scale.getDistanceFromCenterForValue(dataset.data[index]);
- var options = arc._options || {};
-
- helpers$1.extend(arc, {
- // Utility
- _datasetIndex: me.index,
- _index: index,
- _scale: scale,
-
- // Desired view properties
- _model: {
- backgroundColor: options.backgroundColor,
- borderColor: options.borderColor,
- borderWidth: options.borderWidth,
- borderAlign: options.borderAlign,
- x: centerX,
- y: centerY,
- innerRadius: 0,
- outerRadius: reset ? resetRadius : distance,
- startAngle: reset && animationOpts.animateRotate ? datasetStartAngle : startAngle,
- endAngle: reset && animationOpts.animateRotate ? datasetStartAngle : endAngle,
- label: helpers$1.valueAtIndexOrDefault(labels, index, labels[index])
- }
- });
-
- arc.pivot();
- },
-
- countVisibleElements: function() {
- var dataset = this.getDataset();
- var meta = this.getMeta();
- var count = 0;
-
- helpers$1.each(meta.data, function(element, index) {
- if (!isNaN(dataset.data[index]) && !element.hidden) {
- count++;
- }
- });
-
- return count;
- },
-
- /**
- * @protected
- */
- setHoverStyle: function(arc) {
- var model = arc._model;
- var options = arc._options;
- var getHoverColor = helpers$1.getHoverColor;
- var valueOrDefault = helpers$1.valueOrDefault;
-
- arc.$previousStyle = {
- backgroundColor: model.backgroundColor,
- borderColor: model.borderColor,
- borderWidth: model.borderWidth,
- };
-
- model.backgroundColor = valueOrDefault(options.hoverBackgroundColor, getHoverColor(options.backgroundColor));
- model.borderColor = valueOrDefault(options.hoverBorderColor, getHoverColor(options.borderColor));
- model.borderWidth = valueOrDefault(options.hoverBorderWidth, options.borderWidth);
- },
-
- /**
- * @private
- */
- _resolveElementOptions: function(arc, index) {
- var me = this;
- var chart = me.chart;
- var dataset = me.getDataset();
- var custom = arc.custom || {};
- var options = chart.options.elements.arc;
- var values = {};
- var i, ilen, key;
-
- // Scriptable options
- var context = {
- chart: chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- var keys = [
- 'backgroundColor',
- 'borderColor',
- 'borderWidth',
- 'borderAlign',
- 'hoverBackgroundColor',
- 'hoverBorderColor',
- 'hoverBorderWidth',
- ];
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$5([
- custom[key],
- dataset[key],
- options[key]
- ], context, index);
- }
-
- return values;
- },
-
- /**
- * @private
- */
- _computeAngle: function(index) {
- var me = this;
- var count = this.getMeta().count;
- var dataset = me.getDataset();
- var meta = me.getMeta();
-
- if (isNaN(dataset.data[index]) || meta.data[index].hidden) {
- return 0;
- }
-
- // Scriptable options
- var context = {
- chart: me.chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- return resolve$5([
- me.chart.options.elements.arc.angle,
- (2 * Math.PI) / count
- ], context, index);
- }
-});
-
-core_defaults._set('pie', helpers$1.clone(core_defaults.doughnut));
-core_defaults._set('pie', {
- cutoutPercentage: 0
-});
-
-// Pie charts are Doughnut chart with different defaults
-var controller_pie = controller_doughnut;
-
-var valueOrDefault$6 = helpers$1.valueOrDefault;
-var resolve$6 = helpers$1.options.resolve;
-
-core_defaults._set('radar', {
- scale: {
- type: 'radialLinear'
- },
- elements: {
- line: {
- tension: 0 // no bezier in radar
- }
- }
-});
-
-var controller_radar = core_datasetController.extend({
-
- datasetElementType: elements.Line,
-
- dataElementType: elements.Point,
-
- linkScales: helpers$1.noop,
-
- update: function(reset) {
- var me = this;
- var meta = me.getMeta();
- var line = meta.dataset;
- var points = meta.data || [];
- var scale = me.chart.scale;
- var dataset = me.getDataset();
- var i, ilen;
-
- // Compatibility: If the properties are defined with only the old name, use those values
- if ((dataset.tension !== undefined) && (dataset.lineTension === undefined)) {
- dataset.lineTension = dataset.tension;
- }
-
- // Utility
- line._scale = scale;
- line._datasetIndex = me.index;
- // Data
- line._children = points;
- line._loop = true;
- // Model
- line._model = me._resolveLineOptions(line);
-
- line.pivot();
-
- // Update Points
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- me.updateElement(points[i], i, reset);
- }
-
- // Update bezier control points
- me.updateBezierControlPoints();
-
- // Now pivot the point for animation
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- points[i].pivot();
- }
- },
-
- updateElement: function(point, index, reset) {
- var me = this;
- var custom = point.custom || {};
- var dataset = me.getDataset();
- var scale = me.chart.scale;
- var pointPosition = scale.getPointPositionForValue(index, dataset.data[index]);
- var options = me._resolvePointOptions(point, index);
- var lineModel = me.getMeta().dataset._model;
- var x = reset ? scale.xCenter : pointPosition.x;
- var y = reset ? scale.yCenter : pointPosition.y;
-
- // Utility
- point._scale = scale;
- point._options = options;
- point._datasetIndex = me.index;
- point._index = index;
-
- // Desired view properties
- point._model = {
- x: x, // value not used in dataset scale, but we want a consistent API between scales
- y: y,
- skip: custom.skip || isNaN(x) || isNaN(y),
- // Appearance
- radius: options.radius,
- pointStyle: options.pointStyle,
- rotation: options.rotation,
- backgroundColor: options.backgroundColor,
- borderColor: options.borderColor,
- borderWidth: options.borderWidth,
- tension: valueOrDefault$6(custom.tension, lineModel ? lineModel.tension : 0),
-
- // Tooltip
- hitRadius: options.hitRadius
- };
- },
-
- /**
- * @private
- */
- _resolvePointOptions: function(element, index) {
- var me = this;
- var chart = me.chart;
- var dataset = chart.data.datasets[me.index];
- var custom = element.custom || {};
- var options = chart.options.elements.point;
- var values = {};
- var i, ilen, key;
-
- // Scriptable options
- var context = {
- chart: chart,
- dataIndex: index,
- dataset: dataset,
- datasetIndex: me.index
- };
-
- var ELEMENT_OPTIONS = {
- backgroundColor: 'pointBackgroundColor',
- borderColor: 'pointBorderColor',
- borderWidth: 'pointBorderWidth',
- hitRadius: 'pointHitRadius',
- hoverBackgroundColor: 'pointHoverBackgroundColor',
- hoverBorderColor: 'pointHoverBorderColor',
- hoverBorderWidth: 'pointHoverBorderWidth',
- hoverRadius: 'pointHoverRadius',
- pointStyle: 'pointStyle',
- radius: 'pointRadius',
- rotation: 'pointRotation'
- };
- var keys = Object.keys(ELEMENT_OPTIONS);
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$6([
- custom[key],
- dataset[ELEMENT_OPTIONS[key]],
- dataset[key],
- options[key]
- ], context, index);
- }
-
- return values;
- },
-
- /**
- * @private
- */
- _resolveLineOptions: function(element) {
- var me = this;
- var chart = me.chart;
- var dataset = chart.data.datasets[me.index];
- var custom = element.custom || {};
- var options = chart.options.elements.line;
- var values = {};
- var i, ilen, key;
-
- var keys = [
- 'backgroundColor',
- 'borderWidth',
- 'borderColor',
- 'borderCapStyle',
- 'borderDash',
- 'borderDashOffset',
- 'borderJoinStyle',
- 'fill'
- ];
-
- for (i = 0, ilen = keys.length; i < ilen; ++i) {
- key = keys[i];
- values[key] = resolve$6([
- custom[key],
- dataset[key],
- options[key]
- ]);
- }
-
- values.tension = valueOrDefault$6(dataset.lineTension, options.tension);
-
- return values;
- },
-
- updateBezierControlPoints: function() {
- var me = this;
- var meta = me.getMeta();
- var area = me.chart.chartArea;
- var points = meta.data || [];
- var i, ilen, model, controlPoints;
-
- function capControlPoint(pt, min, max) {
- return Math.max(Math.min(pt, max), min);
- }
-
- for (i = 0, ilen = points.length; i < ilen; ++i) {
- model = points[i]._model;
- controlPoints = helpers$1.splineCurve(
- helpers$1.previousItem(points, i, true)._model,
- model,
- helpers$1.nextItem(points, i, true)._model,
- model.tension
- );
-
- // Prevent the bezier going outside of the bounds of the graph
- model.controlPointPreviousX = capControlPoint(controlPoints.previous.x, area.left, area.right);
- model.controlPointPreviousY = capControlPoint(controlPoints.previous.y, area.top, area.bottom);
- model.controlPointNextX = capControlPoint(controlPoints.next.x, area.left, area.right);
- model.controlPointNextY = capControlPoint(controlPoints.next.y, area.top, area.bottom);
- }
- },
-
- setHoverStyle: function(point) {
- var model = point._model;
- var options = point._options;
- var getHoverColor = helpers$1.getHoverColor;
-
- point.$previousStyle = {
- backgroundColor: model.backgroundColor,
- borderColor: model.borderColor,
- borderWidth: model.borderWidth,
- radius: model.radius
- };
-
- model.backgroundColor = valueOrDefault$6(options.hoverBackgroundColor, getHoverColor(options.backgroundColor));
- model.borderColor = valueOrDefault$6(options.hoverBorderColor, getHoverColor(options.borderColor));
- model.borderWidth = valueOrDefault$6(options.hoverBorderWidth, options.borderWidth);
- model.radius = valueOrDefault$6(options.hoverRadius, options.radius);
- }
-});
-
-core_defaults._set('scatter', {
- hover: {
- mode: 'single'
- },
-
- scales: {
- xAxes: [{
- id: 'x-axis-1', // need an ID so datasets can reference the scale
- type: 'linear', // scatter should not use a category axis
- position: 'bottom'
- }],
- yAxes: [{
- id: 'y-axis-1',
- type: 'linear',
- position: 'left'
- }]
- },
-
- showLines: false,
-
- tooltips: {
- callbacks: {
- title: function() {
- return ''; // doesn't make sense for scatter since data are formatted as a point
- },
- label: function(item) {
- return '(' + item.xLabel + ', ' + item.yLabel + ')';
- }
- }
- }
-});
-
-// Scatter charts use line controllers
-var controller_scatter = controller_line;
-
-// NOTE export a map in which the key represents the controller type, not
-// the class, and so must be CamelCase in order to be correctly retrieved
-// by the controller in core.controller.js (`controllers[meta.type]`).
-
-var controllers = {
- bar: controller_bar,
- bubble: controller_bubble,
- doughnut: controller_doughnut,
- horizontalBar: controller_horizontalBar,
- line: controller_line,
- polarArea: controller_polarArea,
- pie: controller_pie,
- radar: controller_radar,
- scatter: controller_scatter
-};
-
-/**
- * Helper function to get relative position for an event
- * @param {Event|IEvent} event - The event to get the position for
- * @param {Chart} chart - The chart
- * @returns {object} the event position
- */
-function getRelativePosition(e, chart) {
- if (e.native) {
- return {
- x: e.x,
- y: e.y
- };
- }
-
- return helpers$1.getRelativePosition(e, chart);
-}
-
-/**
- * Helper function to traverse all of the visible elements in the chart
- * @param {Chart} chart - the chart
- * @param {function} handler - the callback to execute for each visible item
- */
-function parseVisibleItems(chart, handler) {
- var datasets = chart.data.datasets;
- var meta, i, j, ilen, jlen;
-
- for (i = 0, ilen = datasets.length; i < ilen; ++i) {
- if (!chart.isDatasetVisible(i)) {
- continue;
- }
-
- meta = chart.getDatasetMeta(i);
- for (j = 0, jlen = meta.data.length; j < jlen; ++j) {
- var element = meta.data[j];
- if (!element._view.skip) {
- handler(element);
- }
- }
- }
-}
-
-/**
- * Helper function to get the items that intersect the event position
- * @param {ChartElement[]} items - elements to filter
- * @param {object} position - the point to be nearest to
- * @return {ChartElement[]} the nearest items
- */
-function getIntersectItems(chart, position) {
- var elements = [];
-
- parseVisibleItems(chart, function(element) {
- if (element.inRange(position.x, position.y)) {
- elements.push(element);
- }
- });
-
- return elements;
-}
-
-/**
- * Helper function to get the items nearest to the event position considering all visible items in teh chart
- * @param {Chart} chart - the chart to look at elements from
- * @param {object} position - the point to be nearest to
- * @param {boolean} intersect - if true, only consider items that intersect the position
- * @param {function} distanceMetric - function to provide the distance between points
- * @return {ChartElement[]} the nearest items
- */
-function getNearestItems(chart, position, intersect, distanceMetric) {
- var minDistance = Number.POSITIVE_INFINITY;
- var nearestItems = [];
-
- parseVisibleItems(chart, function(element) {
- if (intersect && !element.inRange(position.x, position.y)) {
- return;
- }
-
- var center = element.getCenterPoint();
- var distance = distanceMetric(position, center);
- if (distance < minDistance) {
- nearestItems = [element];
- minDistance = distance;
- } else if (distance === minDistance) {
- // Can have multiple items at the same distance in which case we sort by size
- nearestItems.push(element);
- }
- });
-
- return nearestItems;
-}
-
-/**
- * Get a distance metric function for two points based on the
- * axis mode setting
- * @param {string} axis - the axis mode. x|y|xy
- */
-function getDistanceMetricForAxis(axis) {
- var useX = axis.indexOf('x') !== -1;
- var useY = axis.indexOf('y') !== -1;
-
- return function(pt1, pt2) {
- var deltaX = useX ? Math.abs(pt1.x - pt2.x) : 0;
- var deltaY = useY ? Math.abs(pt1.y - pt2.y) : 0;
- return Math.sqrt(Math.pow(deltaX, 2) + Math.pow(deltaY, 2));
- };
-}
-
-function indexMode(chart, e, options) {
- var position = getRelativePosition(e, chart);
- // Default axis for index mode is 'x' to match old behaviour
- options.axis = options.axis || 'x';
- var distanceMetric = getDistanceMetricForAxis(options.axis);
- var items = options.intersect ? getIntersectItems(chart, position) : getNearestItems(chart, position, false, distanceMetric);
- var elements = [];
-
- if (!items.length) {
- return [];
- }
-
- chart.data.datasets.forEach(function(dataset, datasetIndex) {
- if (chart.isDatasetVisible(datasetIndex)) {
- var meta = chart.getDatasetMeta(datasetIndex);
- var element = meta.data[items[0]._index];
-
- // don't count items that are skipped (null data)
- if (element && !element._view.skip) {
- elements.push(element);
- }
- }
- });
-
- return elements;
-}
-
-/**
- * @interface IInteractionOptions
- */
-/**
- * If true, only consider items that intersect the point
- * @name IInterfaceOptions#boolean
- * @type Boolean
- */
-
-/**
- * Contains interaction related functions
- * @namespace Chart.Interaction
- */
-var core_interaction = {
- // Helper function for different modes
- modes: {
- single: function(chart, e) {
- var position = getRelativePosition(e, chart);
- var elements = [];
-
- parseVisibleItems(chart, function(element) {
- if (element.inRange(position.x, position.y)) {
- elements.push(element);
- return elements;
- }
- });
-
- return elements.slice(0, 1);
- },
-
- /**
- * @function Chart.Interaction.modes.label
- * @deprecated since version 2.4.0
- * @todo remove at version 3
- * @private
- */
- label: indexMode,
-
- /**
- * Returns items at the same index. If the options.intersect parameter is true, we only return items if we intersect something
- * If the options.intersect mode is false, we find the nearest item and return the items at the same index as that item
- * @function Chart.Interaction.modes.index
- * @since v2.4.0
- * @param {Chart} chart - the chart we are returning items from
- * @param {Event} e - the event we are find things at
- * @param {IInteractionOptions} options - options to use during interaction
- * @return {Chart.Element[]} Array of elements that are under the point. If none are found, an empty array is returned
- */
- index: indexMode,
-
- /**
- * Returns items in the same dataset. If the options.intersect parameter is true, we only return items if we intersect something
- * If the options.intersect is false, we find the nearest item and return the items in that dataset
- * @function Chart.Interaction.modes.dataset
- * @param {Chart} chart - the chart we are returning items from
- * @param {Event} e - the event we are find things at
- * @param {IInteractionOptions} options - options to use during interaction
- * @return {Chart.Element[]} Array of elements that are under the point. If none are found, an empty array is returned
- */
- dataset: function(chart, e, options) {
- var position = getRelativePosition(e, chart);
- options.axis = options.axis || 'xy';
- var distanceMetric = getDistanceMetricForAxis(options.axis);
- var items = options.intersect ? getIntersectItems(chart, position) : getNearestItems(chart, position, false, distanceMetric);
-
- if (items.length > 0) {
- items = chart.getDatasetMeta(items[0]._datasetIndex).data;
- }
-
- return items;
- },
-
- /**
- * @function Chart.Interaction.modes.x-axis
- * @deprecated since version 2.4.0. Use index mode and intersect == true
- * @todo remove at version 3
- * @private
- */
- 'x-axis': function(chart, e) {
- return indexMode(chart, e, {intersect: false});
- },
-
- /**
- * Point mode returns all elements that hit test based on the event position
- * of the event
- * @function Chart.Interaction.modes.intersect
- * @param {Chart} chart - the chart we are returning items from
- * @param {Event} e - the event we are find things at
- * @return {Chart.Element[]} Array of elements that are under the point. If none are found, an empty array is returned
- */
- point: function(chart, e) {
- var position = getRelativePosition(e, chart);
- return getIntersectItems(chart, position);
- },
-
- /**
- * nearest mode returns the element closest to the point
- * @function Chart.Interaction.modes.intersect
- * @param {Chart} chart - the chart we are returning items from
- * @param {Event} e - the event we are find things at
- * @param {IInteractionOptions} options - options to use
- * @return {Chart.Element[]} Array of elements that are under the point. If none are found, an empty array is returned
- */
- nearest: function(chart, e, options) {
- var position = getRelativePosition(e, chart);
- options.axis = options.axis || 'xy';
- var distanceMetric = getDistanceMetricForAxis(options.axis);
- return getNearestItems(chart, position, options.intersect, distanceMetric);
- },
-
- /**
- * x mode returns the elements that hit-test at the current x coordinate
- * @function Chart.Interaction.modes.x
- * @param {Chart} chart - the chart we are returning items from
- * @param {Event} e - the event we are find things at
- * @param {IInteractionOptions} options - options to use
- * @return {Chart.Element[]} Array of elements that are under the point. If none are found, an empty array is returned
- */
- x: function(chart, e, options) {
- var position = getRelativePosition(e, chart);
- var items = [];
- var intersectsItem = false;
-
- parseVisibleItems(chart, function(element) {
- if (element.inXRange(position.x)) {
- items.push(element);
- }
-
- if (element.inRange(position.x, position.y)) {
- intersectsItem = true;
- }
- });
-
- // If we want to trigger on an intersect and we don't have any items
- // that intersect the position, return nothing
- if (options.intersect && !intersectsItem) {
- items = [];
- }
- return items;
- },
-
- /**
- * y mode returns the elements that hit-test at the current y coordinate
- * @function Chart.Interaction.modes.y
- * @param {Chart} chart - the chart we are returning items from
- * @param {Event} e - the event we are find things at
- * @param {IInteractionOptions} options - options to use
- * @return {Chart.Element[]} Array of elements that are under the point. If none are found, an empty array is returned
- */
- y: function(chart, e, options) {
- var position = getRelativePosition(e, chart);
- var items = [];
- var intersectsItem = false;
-
- parseVisibleItems(chart, function(element) {
- if (element.inYRange(position.y)) {
- items.push(element);
- }
-
- if (element.inRange(position.x, position.y)) {
- intersectsItem = true;
- }
- });
-
- // If we want to trigger on an intersect and we don't have any items
- // that intersect the position, return nothing
- if (options.intersect && !intersectsItem) {
- items = [];
- }
- return items;
- }
- }
-};
-
-function filterByPosition(array, position) {
- return helpers$1.where(array, function(v) {
- return v.position === position;
- });
-}
-
-function sortByWeight(array, reverse) {
- array.forEach(function(v, i) {
- v._tmpIndex_ = i;
- return v;
- });
- array.sort(function(a, b) {
- var v0 = reverse ? b : a;
- var v1 = reverse ? a : b;
- return v0.weight === v1.weight ?
- v0._tmpIndex_ - v1._tmpIndex_ :
- v0.weight - v1.weight;
- });
- array.forEach(function(v) {
- delete v._tmpIndex_;
- });
-}
-
-function findMaxPadding(boxes) {
- var top = 0;
- var left = 0;
- var bottom = 0;
- var right = 0;
- helpers$1.each(boxes, function(box) {
- if (box.getPadding) {
- var boxPadding = box.getPadding();
- top = Math.max(top, boxPadding.top);
- left = Math.max(left, boxPadding.left);
- bottom = Math.max(bottom, boxPadding.bottom);
- right = Math.max(right, boxPadding.right);
- }
- });
- return {
- top: top,
- left: left,
- bottom: bottom,
- right: right
- };
-}
-
-function addSizeByPosition(boxes, size) {
- helpers$1.each(boxes, function(box) {
- size[box.position] += box.isHorizontal() ? box.height : box.width;
- });
-}
-
-core_defaults._set('global', {
- layout: {
- padding: {
- top: 0,
- right: 0,
- bottom: 0,
- left: 0
- }
- }
-});
-
-/**
- * @interface ILayoutItem
- * @prop {string} position - The position of the item in the chart layout. Possible values are
- * 'left', 'top', 'right', 'bottom', and 'chartArea'
- * @prop {number} weight - The weight used to sort the item. Higher weights are further away from the chart area
- * @prop {boolean} fullWidth - if true, and the item is horizontal, then push vertical boxes down
- * @prop {function} isHorizontal - returns true if the layout item is horizontal (ie. top or bottom)
- * @prop {function} update - Takes two parameters: width and height. Returns size of item
- * @prop {function} getPadding - Returns an object with padding on the edges
- * @prop {number} width - Width of item. Must be valid after update()
- * @prop {number} height - Height of item. Must be valid after update()
- * @prop {number} left - Left edge of the item. Set by layout system and cannot be used in update
- * @prop {number} top - Top edge of the item. Set by layout system and cannot be used in update
- * @prop {number} right - Right edge of the item. Set by layout system and cannot be used in update
- * @prop {number} bottom - Bottom edge of the item. Set by layout system and cannot be used in update
- */
-
-// The layout service is very self explanatory. It's responsible for the layout within a chart.
-// Scales, Legends and Plugins all rely on the layout service and can easily register to be placed anywhere they need
-// It is this service's responsibility of carrying out that layout.
-var core_layouts = {
- defaults: {},
-
- /**
- * Register a box to a chart.
- * A box is simply a reference to an object that requires layout. eg. Scales, Legend, Title.
- * @param {Chart} chart - the chart to use
- * @param {ILayoutItem} item - the item to add to be layed out
- */
- addBox: function(chart, item) {
- if (!chart.boxes) {
- chart.boxes = [];
- }
-
- // initialize item with default values
- item.fullWidth = item.fullWidth || false;
- item.position = item.position || 'top';
- item.weight = item.weight || 0;
-
- chart.boxes.push(item);
- },
-
- /**
- * Remove a layoutItem from a chart
- * @param {Chart} chart - the chart to remove the box from
- * @param {ILayoutItem} layoutItem - the item to remove from the layout
- */
- removeBox: function(chart, layoutItem) {
- var index = chart.boxes ? chart.boxes.indexOf(layoutItem) : -1;
- if (index !== -1) {
- chart.boxes.splice(index, 1);
- }
- },
-
- /**
- * Sets (or updates) options on the given `item`.
- * @param {Chart} chart - the chart in which the item lives (or will be added to)
- * @param {ILayoutItem} item - the item to configure with the given options
- * @param {object} options - the new item options.
- */
- configure: function(chart, item, options) {
- var props = ['fullWidth', 'position', 'weight'];
- var ilen = props.length;
- var i = 0;
- var prop;
-
- for (; i < ilen; ++i) {
- prop = props[i];
- if (options.hasOwnProperty(prop)) {
- item[prop] = options[prop];
- }
- }
- },
-
- /**
- * Fits boxes of the given chart into the given size by having each box measure itself
- * then running a fitting algorithm
- * @param {Chart} chart - the chart
- * @param {number} width - the width to fit into
- * @param {number} height - the height to fit into
- */
- update: function(chart, width, height) {
- if (!chart) {
- return;
- }
-
- var layoutOptions = chart.options.layout || {};
- var padding = helpers$1.options.toPadding(layoutOptions.padding);
- var leftPadding = padding.left;
- var rightPadding = padding.right;
- var topPadding = padding.top;
- var bottomPadding = padding.bottom;
-
- var leftBoxes = filterByPosition(chart.boxes, 'left');
- var rightBoxes = filterByPosition(chart.boxes, 'right');
- var topBoxes = filterByPosition(chart.boxes, 'top');
- var bottomBoxes = filterByPosition(chart.boxes, 'bottom');
- var chartAreaBoxes = filterByPosition(chart.boxes, 'chartArea');
-
- // Sort boxes by weight. A higher weight is further away from the chart area
- sortByWeight(leftBoxes, true);
- sortByWeight(rightBoxes, false);
- sortByWeight(topBoxes, true);
- sortByWeight(bottomBoxes, false);
-
- var verticalBoxes = leftBoxes.concat(rightBoxes);
- var horizontalBoxes = topBoxes.concat(bottomBoxes);
- var outerBoxes = verticalBoxes.concat(horizontalBoxes);
-
- // Essentially we now have any number of boxes on each of the 4 sides.
- // Our canvas looks like the following.
- // The areas L1 and L2 are the left axes. R1 is the right axis, T1 is the top axis and
- // B1 is the bottom axis
- // There are also 4 quadrant-like locations (left to right instead of clockwise) reserved for chart overlays
- // These locations are single-box locations only, when trying to register a chartArea location that is already taken,
- // an error will be thrown.
- //
- // |----------------------------------------------------|
- // | T1 (Full Width) |
- // |----------------------------------------------------|
- // | | | T2 | |
- // | |----|-------------------------------------|----|
- // | | | C1 | | C2 | |
- // | | |----| |----| |
- // | | | | |
- // | L1 | L2 | ChartArea (C0) | R1 |
- // | | | | |
- // | | |----| |----| |
- // | | | C3 | | C4 | |
- // | |----|-------------------------------------|----|
- // | | | B1 | |
- // |----------------------------------------------------|
- // | B2 (Full Width) |
- // |----------------------------------------------------|
- //
- // What we do to find the best sizing, we do the following
- // 1. Determine the minimum size of the chart area.
- // 2. Split the remaining width equally between each vertical axis
- // 3. Split the remaining height equally between each horizontal axis
- // 4. Give each layout the maximum size it can be. The layout will return it's minimum size
- // 5. Adjust the sizes of each axis based on it's minimum reported size.
- // 6. Refit each axis
- // 7. Position each axis in the final location
- // 8. Tell the chart the final location of the chart area
- // 9. Tell any axes that overlay the chart area the positions of the chart area
-
- // Step 1
- var chartWidth = width - leftPadding - rightPadding;
- var chartHeight = height - topPadding - bottomPadding;
- var chartAreaWidth = chartWidth / 2; // min 50%
-
- // Step 2
- var verticalBoxWidth = (width - chartAreaWidth) / verticalBoxes.length;
-
- // Step 3
- // TODO re-limit horizontal axis height (this limit has affected only padding calculation since PR 1837)
- // var horizontalBoxHeight = (height - chartAreaHeight) / horizontalBoxes.length;
-
- // Step 4
- var maxChartAreaWidth = chartWidth;
- var maxChartAreaHeight = chartHeight;
- var outerBoxSizes = {top: topPadding, left: leftPadding, bottom: bottomPadding, right: rightPadding};
- var minBoxSizes = [];
- var maxPadding;
-
- function getMinimumBoxSize(box) {
- var minSize;
- var isHorizontal = box.isHorizontal();
-
- if (isHorizontal) {
- minSize = box.update(box.fullWidth ? chartWidth : maxChartAreaWidth, chartHeight / 2);
- maxChartAreaHeight -= minSize.height;
- } else {
- minSize = box.update(verticalBoxWidth, maxChartAreaHeight);
- maxChartAreaWidth -= minSize.width;
- }
-
- minBoxSizes.push({
- horizontal: isHorizontal,
- width: minSize.width,
- box: box,
- });
- }
-
- helpers$1.each(outerBoxes, getMinimumBoxSize);
-
- // If a horizontal box has padding, we move the left boxes over to avoid ugly charts (see issue #2478)
- maxPadding = findMaxPadding(outerBoxes);
-
- // At this point, maxChartAreaHeight and maxChartAreaWidth are the size the chart area could
- // be if the axes are drawn at their minimum sizes.
- // Steps 5 & 6
-
- // Function to fit a box
- function fitBox(box) {
- var minBoxSize = helpers$1.findNextWhere(minBoxSizes, function(minBox) {
- return minBox.box === box;
- });
-
- if (minBoxSize) {
- if (minBoxSize.horizontal) {
- var scaleMargin = {
- left: Math.max(outerBoxSizes.left, maxPadding.left),
- right: Math.max(outerBoxSizes.right, maxPadding.right),
- top: 0,
- bottom: 0
- };
-
- // Don't use min size here because of label rotation. When the labels are rotated, their rotation highly depends
- // on the margin. Sometimes they need to increase in size slightly
- box.update(box.fullWidth ? chartWidth : maxChartAreaWidth, chartHeight / 2, scaleMargin);
- } else {
- box.update(minBoxSize.width, maxChartAreaHeight);
- }
- }
- }
-
- // Update, and calculate the left and right margins for the horizontal boxes
- helpers$1.each(verticalBoxes, fitBox);
- addSizeByPosition(verticalBoxes, outerBoxSizes);
-
- // Set the Left and Right margins for the horizontal boxes
- helpers$1.each(horizontalBoxes, fitBox);
- addSizeByPosition(horizontalBoxes, outerBoxSizes);
-
- function finalFitVerticalBox(box) {
- var minBoxSize = helpers$1.findNextWhere(minBoxSizes, function(minSize) {
- return minSize.box === box;
- });
-
- var scaleMargin = {
- left: 0,
- right: 0,
- top: outerBoxSizes.top,
- bottom: outerBoxSizes.bottom
- };
-
- if (minBoxSize) {
- box.update(minBoxSize.width, maxChartAreaHeight, scaleMargin);
- }
- }
-
- // Let the left layout know the final margin
- helpers$1.each(verticalBoxes, finalFitVerticalBox);
-
- // Recalculate because the size of each layout might have changed slightly due to the margins (label rotation for instance)
- outerBoxSizes = {top: topPadding, left: leftPadding, bottom: bottomPadding, right: rightPadding};
- addSizeByPosition(outerBoxes, outerBoxSizes);
-
- // We may be adding some padding to account for rotated x axis labels
- var leftPaddingAddition = Math.max(maxPadding.left - outerBoxSizes.left, 0);
- outerBoxSizes.left += leftPaddingAddition;
- outerBoxSizes.right += Math.max(maxPadding.right - outerBoxSizes.right, 0);
-
- var topPaddingAddition = Math.max(maxPadding.top - outerBoxSizes.top, 0);
- outerBoxSizes.top += topPaddingAddition;
- outerBoxSizes.bottom += Math.max(maxPadding.bottom - outerBoxSizes.bottom, 0);
-
- // Figure out if our chart area changed. This would occur if the dataset layout label rotation
- // changed due to the application of the margins in step 6. Since we can only get bigger, this is safe to do
- // without calling `fit` again
- var newMaxChartAreaHeight = height - outerBoxSizes.top - outerBoxSizes.bottom;
- var newMaxChartAreaWidth = width - outerBoxSizes.left - outerBoxSizes.right;
-
- if (newMaxChartAreaWidth !== maxChartAreaWidth || newMaxChartAreaHeight !== maxChartAreaHeight) {
- helpers$1.each(verticalBoxes, function(box) {
- box.height = newMaxChartAreaHeight;
- });
-
- helpers$1.each(horizontalBoxes, function(box) {
- if (!box.fullWidth) {
- box.width = newMaxChartAreaWidth;
- }
- });
-
- maxChartAreaHeight = newMaxChartAreaHeight;
- maxChartAreaWidth = newMaxChartAreaWidth;
- }
-
- // Step 7 - Position the boxes
- var left = leftPadding + leftPaddingAddition;
- var top = topPadding + topPaddingAddition;
-
- function placeBox(box) {
- if (box.isHorizontal()) {
- box.left = box.fullWidth ? leftPadding : outerBoxSizes.left;
- box.right = box.fullWidth ? width - rightPadding : outerBoxSizes.left + maxChartAreaWidth;
- box.top = top;
- box.bottom = top + box.height;
-
- // Move to next point
- top = box.bottom;
-
- } else {
-
- box.left = left;
- box.right = left + box.width;
- box.top = outerBoxSizes.top;
- box.bottom = outerBoxSizes.top + maxChartAreaHeight;
-
- // Move to next point
- left = box.right;
- }
- }
-
- helpers$1.each(leftBoxes.concat(topBoxes), placeBox);
-
- // Account for chart width and height
- left += maxChartAreaWidth;
- top += maxChartAreaHeight;
-
- helpers$1.each(rightBoxes, placeBox);
- helpers$1.each(bottomBoxes, placeBox);
-
- // Step 8
- chart.chartArea = {
- left: outerBoxSizes.left,
- top: outerBoxSizes.top,
- right: outerBoxSizes.left + maxChartAreaWidth,
- bottom: outerBoxSizes.top + maxChartAreaHeight
- };
-
- // Step 9
- helpers$1.each(chartAreaBoxes, function(box) {
- box.left = chart.chartArea.left;
- box.top = chart.chartArea.top;
- box.right = chart.chartArea.right;
- box.bottom = chart.chartArea.bottom;
-
- box.update(maxChartAreaWidth, maxChartAreaHeight);
- });
- }
-};
-
-/**
- * Platform fallback implementation (minimal).
- * @see https://github.com/chartjs/Chart.js/pull/4591#issuecomment-319575939
- */
-
-var platform_basic = {
- acquireContext: function(item) {
- if (item && item.canvas) {
- // Support for any object associated to a canvas (including a context2d)
- item = item.canvas;
- }
-
- return item && item.getContext('2d') || null;
- }
-};
-
-var platform_dom = "/*\n * DOM element rendering detection\n * https://davidwalsh.name/detect-node-insertion\n */\n@keyframes chartjs-render-animation {\n\tfrom { opacity: 0.99; }\n\tto { opacity: 1; }\n}\n\n.chartjs-render-monitor {\n\tanimation: chartjs-render-animation 0.001s;\n}\n\n/*\n * DOM element resizing detection\n * https://github.com/marcj/css-element-queries\n */\n.chartjs-size-monitor,\n.chartjs-size-monitor-expand,\n.chartjs-size-monitor-shrink {\n\tposition: absolute;\n\tdirection: ltr;\n\tleft: 0;\n\ttop: 0;\n\tright: 0;\n\tbottom: 0;\n\toverflow: hidden;\n\tpointer-events: none;\n\tvisibility: hidden;\n\tz-index: -1;\n}\n\n.chartjs-size-monitor-expand > div {\n\tposition: absolute;\n\twidth: 1000000px;\n\theight: 1000000px;\n\tleft: 0;\n\ttop: 0;\n}\n\n.chartjs-size-monitor-shrink > div {\n\tposition: absolute;\n\twidth: 200%;\n\theight: 200%;\n\tleft: 0;\n\ttop: 0;\n}\n";
-
-var platform_dom$1 = /*#__PURE__*/Object.freeze({
-default: platform_dom
-});
-
-var commonjsGlobal = typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
-
-function commonjsRequire () {
- throw new Error('Dynamic requires are not currently supported by rollup-plugin-commonjs');
-}
-
-function createCommonjsModule(fn, module) {
- return module = { exports: {} }, fn(module, module.exports), module.exports;
-}
-
-function getCjsExportFromNamespace (n) {
- return n && n.default || n;
-}
-
-var stylesheet = getCjsExportFromNamespace(platform_dom$1);
-
-var EXPANDO_KEY = '$chartjs';
-var CSS_PREFIX = 'chartjs-';
-var CSS_SIZE_MONITOR = CSS_PREFIX + 'size-monitor';
-var CSS_RENDER_MONITOR = CSS_PREFIX + 'render-monitor';
-var CSS_RENDER_ANIMATION = CSS_PREFIX + 'render-animation';
-var ANIMATION_START_EVENTS = ['animationstart', 'webkitAnimationStart'];
-
-/**
- * DOM event types -> Chart.js event types.
- * Note: only events with different types are mapped.
- * @see https://developer.mozilla.org/en-US/docs/Web/Events
- */
-var EVENT_TYPES = {
- touchstart: 'mousedown',
- touchmove: 'mousemove',
- touchend: 'mouseup',
- pointerenter: 'mouseenter',
- pointerdown: 'mousedown',
- pointermove: 'mousemove',
- pointerup: 'mouseup',
- pointerleave: 'mouseout',
- pointerout: 'mouseout'
-};
-
-/**
- * The "used" size is the final value of a dimension property after all calculations have
- * been performed. This method uses the computed style of `element` but returns undefined
- * if the computed style is not expressed in pixels. That can happen in some cases where
- * `element` has a size relative to its parent and this last one is not yet displayed,
- * for example because of `display: none` on a parent node.
- * @see https://developer.mozilla.org/en-US/docs/Web/CSS/used_value
- * @returns {number} Size in pixels or undefined if unknown.
- */
-function readUsedSize(element, property) {
- var value = helpers$1.getStyle(element, property);
- var matches = value && value.match(/^(\d+)(\.\d+)?px$/);
- return matches ? Number(matches[1]) : undefined;
-}
-
-/**
- * Initializes the canvas style and render size without modifying the canvas display size,
- * since responsiveness is handled by the controller.resize() method. The config is used
- * to determine the aspect ratio to apply in case no explicit height has been specified.
- */
-function initCanvas(canvas, config) {
- var style = canvas.style;
-
- // NOTE(SB) canvas.getAttribute('width') !== canvas.width: in the first case it
- // returns null or '' if no explicit value has been set to the canvas attribute.
- var renderHeight = canvas.getAttribute('height');
- var renderWidth = canvas.getAttribute('width');
-
- // Chart.js modifies some canvas values that we want to restore on destroy
- canvas[EXPANDO_KEY] = {
- initial: {
- height: renderHeight,
- width: renderWidth,
- style: {
- display: style.display,
- height: style.height,
- width: style.width
- }
- }
- };
-
- // Force canvas to display as block to avoid extra space caused by inline
- // elements, which would interfere with the responsive resize process.
- // https://github.com/chartjs/Chart.js/issues/2538
- style.display = style.display || 'block';
-
- if (renderWidth === null || renderWidth === '') {
- var displayWidth = readUsedSize(canvas, 'width');
- if (displayWidth !== undefined) {
- canvas.width = displayWidth;
- }
- }
-
- if (renderHeight === null || renderHeight === '') {
- if (canvas.style.height === '') {
- // If no explicit render height and style height, let's apply the aspect ratio,
- // which one can be specified by the user but also by charts as default option
- // (i.e. options.aspectRatio). If not specified, use canvas aspect ratio of 2.
- canvas.height = canvas.width / (config.options.aspectRatio || 2);
- } else {
- var displayHeight = readUsedSize(canvas, 'height');
- if (displayWidth !== undefined) {
- canvas.height = displayHeight;
- }
- }
- }
-
- return canvas;
-}
-
-/**
- * Detects support for options object argument in addEventListener.
- * https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/addEventListener#Safely_detecting_option_support
- * @private
- */
-var supportsEventListenerOptions = (function() {
- var supports = false;
- try {
- var options = Object.defineProperty({}, 'passive', {
- // eslint-disable-next-line getter-return
- get: function() {
- supports = true;
- }
- });
- window.addEventListener('e', null, options);
- } catch (e) {
- // continue regardless of error
- }
- return supports;
-}());
-
-// Default passive to true as expected by Chrome for 'touchstart' and 'touchend' events.
-// https://github.com/chartjs/Chart.js/issues/4287
-var eventListenerOptions = supportsEventListenerOptions ? {passive: true} : false;
-
-function addListener(node, type, listener) {
- node.addEventListener(type, listener, eventListenerOptions);
-}
-
-function removeListener(node, type, listener) {
- node.removeEventListener(type, listener, eventListenerOptions);
-}
-
-function createEvent(type, chart, x, y, nativeEvent) {
- return {
- type: type,
- chart: chart,
- native: nativeEvent || null,
- x: x !== undefined ? x : null,
- y: y !== undefined ? y : null,
- };
-}
-
-function fromNativeEvent(event, chart) {
- var type = EVENT_TYPES[event.type] || event.type;
- var pos = helpers$1.getRelativePosition(event, chart);
- return createEvent(type, chart, pos.x, pos.y, event);
-}
-
-function throttled(fn, thisArg) {
- var ticking = false;
- var args = [];
-
- return function() {
- args = Array.prototype.slice.call(arguments);
- thisArg = thisArg || this;
-
- if (!ticking) {
- ticking = true;
- helpers$1.requestAnimFrame.call(window, function() {
- ticking = false;
- fn.apply(thisArg, args);
- });
- }
- };
-}
-
-function createDiv(cls) {
- var el = document.createElement('div');
- el.className = cls || '';
- return el;
-}
-
-// Implementation based on https://github.com/marcj/css-element-queries
-function createResizer(handler) {
- var maxSize = 1000000;
-
- // NOTE(SB) Don't use innerHTML because it could be considered unsafe.
- // https://github.com/chartjs/Chart.js/issues/5902
- var resizer = createDiv(CSS_SIZE_MONITOR);
- var expand = createDiv(CSS_SIZE_MONITOR + '-expand');
- var shrink = createDiv(CSS_SIZE_MONITOR + '-shrink');
-
- expand.appendChild(createDiv());
- shrink.appendChild(createDiv());
-
- resizer.appendChild(expand);
- resizer.appendChild(shrink);
- resizer._reset = function() {
- expand.scrollLeft = maxSize;
- expand.scrollTop = maxSize;
- shrink.scrollLeft = maxSize;
- shrink.scrollTop = maxSize;
- };
-
- var onScroll = function() {
- resizer._reset();
- handler();
- };
-
- addListener(expand, 'scroll', onScroll.bind(expand, 'expand'));
- addListener(shrink, 'scroll', onScroll.bind(shrink, 'shrink'));
-
- return resizer;
-}
-
-// https://davidwalsh.name/detect-node-insertion
-function watchForRender(node, handler) {
- var expando = node[EXPANDO_KEY] || (node[EXPANDO_KEY] = {});
- var proxy = expando.renderProxy = function(e) {
- if (e.animationName === CSS_RENDER_ANIMATION) {
- handler();
- }
- };
-
- helpers$1.each(ANIMATION_START_EVENTS, function(type) {
- addListener(node, type, proxy);
- });
-
- // #4737: Chrome might skip the CSS animation when the CSS_RENDER_MONITOR class
- // is removed then added back immediately (same animation frame?). Accessing the
- // `offsetParent` property will force a reflow and re-evaluate the CSS animation.
- // https://gist.github.com/paulirish/5d52fb081b3570c81e3a#box-metrics
- // https://github.com/chartjs/Chart.js/issues/4737
- expando.reflow = !!node.offsetParent;
-
- node.classList.add(CSS_RENDER_MONITOR);
-}
-
-function unwatchForRender(node) {
- var expando = node[EXPANDO_KEY] || {};
- var proxy = expando.renderProxy;
-
- if (proxy) {
- helpers$1.each(ANIMATION_START_EVENTS, function(type) {
- removeListener(node, type, proxy);
- });
-
- delete expando.renderProxy;
- }
-
- node.classList.remove(CSS_RENDER_MONITOR);
-}
-
-function addResizeListener(node, listener, chart) {
- var expando = node[EXPANDO_KEY] || (node[EXPANDO_KEY] = {});
-
- // Let's keep track of this added resizer and thus avoid DOM query when removing it.
- var resizer = expando.resizer = createResizer(throttled(function() {
- if (expando.resizer) {
- var container = chart.options.maintainAspectRatio && node.parentNode;
- var w = container ? container.clientWidth : 0;
- listener(createEvent('resize', chart));
- if (container && container.clientWidth < w && chart.canvas) {
- // If the container size shrank during chart resize, let's assume
- // scrollbar appeared. So we resize again with the scrollbar visible -
- // effectively making chart smaller and the scrollbar hidden again.
- // Because we are inside `throttled`, and currently `ticking`, scroll
- // events are ignored during this whole 2 resize process.
- // If we assumed wrong and something else happened, we are resizing
- // twice in a frame (potential performance issue)
- listener(createEvent('resize', chart));
- }
- }
- }));
-
- // The resizer needs to be attached to the node parent, so we first need to be
- // sure that `node` is attached to the DOM before injecting the resizer element.
- watchForRender(node, function() {
- if (expando.resizer) {
- var container = node.parentNode;
- if (container && container !== resizer.parentNode) {
- container.insertBefore(resizer, container.firstChild);
- }
-
- // The container size might have changed, let's reset the resizer state.
- resizer._reset();
- }
- });
-}
-
-function removeResizeListener(node) {
- var expando = node[EXPANDO_KEY] || {};
- var resizer = expando.resizer;
-
- delete expando.resizer;
- unwatchForRender(node);
-
- if (resizer && resizer.parentNode) {
- resizer.parentNode.removeChild(resizer);
- }
-}
-
-function injectCSS(platform, css) {
- // https://stackoverflow.com/q/3922139
- var style = platform._style || document.createElement('style');
- if (!platform._style) {
- platform._style = style;
- css = '/* Chart.js */\n' + css;
- style.setAttribute('type', 'text/css');
- document.getElementsByTagName('head')[0].appendChild(style);
- }
-
- style.appendChild(document.createTextNode(css));
-}
-
-var platform_dom$2 = {
- /**
- * When `true`, prevents the automatic injection of the stylesheet required to
- * correctly detect when the chart is added to the DOM and then resized. This
- * switch has been added to allow external stylesheet (`dist/Chart(.min)?.js`)
- * to be manually imported to make this library compatible with any CSP.
- * See https://github.com/chartjs/Chart.js/issues/5208
- */
- disableCSSInjection: false,
-
- /**
- * This property holds whether this platform is enabled for the current environment.
- * Currently used by platform.js to select the proper implementation.
- * @private
- */
- _enabled: typeof window !== 'undefined' && typeof document !== 'undefined',
-
- /**
- * @private
- */
- _ensureLoaded: function() {
- if (this._loaded) {
- return;
- }
-
- this._loaded = true;
-
- // https://github.com/chartjs/Chart.js/issues/5208
- if (!this.disableCSSInjection) {
- injectCSS(this, stylesheet);
- }
- },
-
- acquireContext: function(item, config) {
- if (typeof item === 'string') {
- item = document.getElementById(item);
- } else if (item.length) {
- // Support for array based queries (such as jQuery)
- item = item[0];
- }
-
- if (item && item.canvas) {
- // Support for any object associated to a canvas (including a context2d)
- item = item.canvas;
- }
-
- // To prevent canvas fingerprinting, some add-ons undefine the getContext
- // method, for example: https://github.com/kkapsner/CanvasBlocker
- // https://github.com/chartjs/Chart.js/issues/2807
- var context = item && item.getContext && item.getContext('2d');
-
- // Load platform resources on first chart creation, to make possible to change
- // platform options after importing the library (e.g. `disableCSSInjection`).
- this._ensureLoaded();
-
- // `instanceof HTMLCanvasElement/CanvasRenderingContext2D` fails when the item is
- // inside an iframe or when running in a protected environment. We could guess the
- // types from their toString() value but let's keep things flexible and assume it's
- // a sufficient condition if the item has a context2D which has item as `canvas`.
- // https://github.com/chartjs/Chart.js/issues/3887
- // https://github.com/chartjs/Chart.js/issues/4102
- // https://github.com/chartjs/Chart.js/issues/4152
- if (context && context.canvas === item) {
- initCanvas(item, config);
- return context;
- }
-
- return null;
- },
-
- releaseContext: function(context) {
- var canvas = context.canvas;
- if (!canvas[EXPANDO_KEY]) {
- return;
- }
-
- var initial = canvas[EXPANDO_KEY].initial;
- ['height', 'width'].forEach(function(prop) {
- var value = initial[prop];
- if (helpers$1.isNullOrUndef(value)) {
- canvas.removeAttribute(prop);
- } else {
- canvas.setAttribute(prop, value);
- }
- });
-
- helpers$1.each(initial.style || {}, function(value, key) {
- canvas.style[key] = value;
- });
-
- // The canvas render size might have been changed (and thus the state stack discarded),
- // we can't use save() and restore() to restore the initial state. So make sure that at
- // least the canvas context is reset to the default state by setting the canvas width.
- // https://www.w3.org/TR/2011/WD-html5-20110525/the-canvas-element.html
- // eslint-disable-next-line no-self-assign
- canvas.width = canvas.width;
-
- delete canvas[EXPANDO_KEY];
- },
-
- addEventListener: function(chart, type, listener) {
- var canvas = chart.canvas;
- if (type === 'resize') {
- // Note: the resize event is not supported on all browsers.
- addResizeListener(canvas, listener, chart);
- return;
- }
-
- var expando = listener[EXPANDO_KEY] || (listener[EXPANDO_KEY] = {});
- var proxies = expando.proxies || (expando.proxies = {});
- var proxy = proxies[chart.id + '_' + type] = function(event) {
- listener(fromNativeEvent(event, chart));
- };
-
- addListener(canvas, type, proxy);
- },
-
- removeEventListener: function(chart, type, listener) {
- var canvas = chart.canvas;
- if (type === 'resize') {
- // Note: the resize event is not supported on all browsers.
- removeResizeListener(canvas);
- return;
- }
-
- var expando = listener[EXPANDO_KEY] || {};
- var proxies = expando.proxies || {};
- var proxy = proxies[chart.id + '_' + type];
- if (!proxy) {
- return;
- }
-
- removeListener(canvas, type, proxy);
- }
-};
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, use EventTarget.addEventListener instead.
- * EventTarget.addEventListener compatibility: Chrome, Opera 7, Safari, FF1.5+, IE9+
- * @see https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/addEventListener
- * @function Chart.helpers.addEvent
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers$1.addEvent = addListener;
-
-/**
- * Provided for backward compatibility, use EventTarget.removeEventListener instead.
- * EventTarget.removeEventListener compatibility: Chrome, Opera 7, Safari, FF1.5+, IE9+
- * @see https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/removeEventListener
- * @function Chart.helpers.removeEvent
- * @deprecated since version 2.7.0
- * @todo remove at version 3
- * @private
- */
-helpers$1.removeEvent = removeListener;
-
-// @TODO Make possible to select another platform at build time.
-var implementation = platform_dom$2._enabled ? platform_dom$2 : platform_basic;
-
-/**
- * @namespace Chart.platform
- * @see https://chartjs.gitbooks.io/proposals/content/Platform.html
- * @since 2.4.0
- */
-var platform = helpers$1.extend({
- /**
- * @since 2.7.0
- */
- initialize: function() {},
-
- /**
- * Called at chart construction time, returns a context2d instance implementing
- * the [W3C Canvas 2D Context API standard]{@link https://www.w3.org/TR/2dcontext/}.
- * @param {*} item - The native item from which to acquire context (platform specific)
- * @param {object} options - The chart options
- * @returns {CanvasRenderingContext2D} context2d instance
- */
- acquireContext: function() {},
-
- /**
- * Called at chart destruction time, releases any resources associated to the context
- * previously returned by the acquireContext() method.
- * @param {CanvasRenderingContext2D} context - The context2d instance
- * @returns {boolean} true if the method succeeded, else false
- */
- releaseContext: function() {},
-
- /**
- * Registers the specified listener on the given chart.
- * @param {Chart} chart - Chart from which to listen for event
- * @param {string} type - The ({@link IEvent}) type to listen for
- * @param {function} listener - Receives a notification (an object that implements
- * the {@link IEvent} interface) when an event of the specified type occurs.
- */
- addEventListener: function() {},
-
- /**
- * Removes the specified listener previously registered with addEventListener.
- * @param {Chart} chart - Chart from which to remove the listener
- * @param {string} type - The ({@link IEvent}) type to remove
- * @param {function} listener - The listener function to remove from the event target.
- */
- removeEventListener: function() {}
-
-}, implementation);
-
-core_defaults._set('global', {
- plugins: {}
-});
-
-/**
- * The plugin service singleton
- * @namespace Chart.plugins
- * @since 2.1.0
- */
-var core_plugins = {
- /**
- * Globally registered plugins.
- * @private
- */
- _plugins: [],
-
- /**
- * This identifier is used to invalidate the descriptors cache attached to each chart
- * when a global plugin is registered or unregistered. In this case, the cache ID is
- * incremented and descriptors are regenerated during following API calls.
- * @private
- */
- _cacheId: 0,
-
- /**
- * Registers the given plugin(s) if not already registered.
- * @param {IPlugin[]|IPlugin} plugins plugin instance(s).
- */
- register: function(plugins) {
- var p = this._plugins;
- ([]).concat(plugins).forEach(function(plugin) {
- if (p.indexOf(plugin) === -1) {
- p.push(plugin);
- }
- });
-
- this._cacheId++;
- },
-
- /**
- * Unregisters the given plugin(s) only if registered.
- * @param {IPlugin[]|IPlugin} plugins plugin instance(s).
- */
- unregister: function(plugins) {
- var p = this._plugins;
- ([]).concat(plugins).forEach(function(plugin) {
- var idx = p.indexOf(plugin);
- if (idx !== -1) {
- p.splice(idx, 1);
- }
- });
-
- this._cacheId++;
- },
-
- /**
- * Remove all registered plugins.
- * @since 2.1.5
- */
- clear: function() {
- this._plugins = [];
- this._cacheId++;
- },
-
- /**
- * Returns the number of registered plugins?
- * @returns {number}
- * @since 2.1.5
- */
- count: function() {
- return this._plugins.length;
- },
-
- /**
- * Returns all registered plugin instances.
- * @returns {IPlugin[]} array of plugin objects.
- * @since 2.1.5
- */
- getAll: function() {
- return this._plugins;
- },
-
- /**
- * Calls enabled plugins for `chart` on the specified hook and with the given args.
- * This method immediately returns as soon as a plugin explicitly returns false. The
- * returned value can be used, for instance, to interrupt the current action.
- * @param {Chart} chart - The chart instance for which plugins should be called.
- * @param {string} hook - The name of the plugin method to call (e.g. 'beforeUpdate').
- * @param {Array} [args] - Extra arguments to apply to the hook call.
- * @returns {boolean} false if any of the plugins return false, else returns true.
- */
- notify: function(chart, hook, args) {
- var descriptors = this.descriptors(chart);
- var ilen = descriptors.length;
- var i, descriptor, plugin, params, method;
-
- for (i = 0; i < ilen; ++i) {
- descriptor = descriptors[i];
- plugin = descriptor.plugin;
- method = plugin[hook];
- if (typeof method === 'function') {
- params = [chart].concat(args || []);
- params.push(descriptor.options);
- if (method.apply(plugin, params) === false) {
- return false;
- }
- }
- }
-
- return true;
- },
-
- /**
- * Returns descriptors of enabled plugins for the given chart.
- * @returns {object[]} [{ plugin, options }]
- * @private
- */
- descriptors: function(chart) {
- var cache = chart.$plugins || (chart.$plugins = {});
- if (cache.id === this._cacheId) {
- return cache.descriptors;
- }
-
- var plugins = [];
- var descriptors = [];
- var config = (chart && chart.config) || {};
- var options = (config.options && config.options.plugins) || {};
-
- this._plugins.concat(config.plugins || []).forEach(function(plugin) {
- var idx = plugins.indexOf(plugin);
- if (idx !== -1) {
- return;
- }
-
- var id = plugin.id;
- var opts = options[id];
- if (opts === false) {
- return;
- }
-
- if (opts === true) {
- opts = helpers$1.clone(core_defaults.global.plugins[id]);
- }
-
- plugins.push(plugin);
- descriptors.push({
- plugin: plugin,
- options: opts || {}
- });
- });
-
- cache.descriptors = descriptors;
- cache.id = this._cacheId;
- return descriptors;
- },
-
- /**
- * Invalidates cache for the given chart: descriptors hold a reference on plugin option,
- * but in some cases, this reference can be changed by the user when updating options.
- * https://github.com/chartjs/Chart.js/issues/5111#issuecomment-355934167
- * @private
- */
- _invalidate: function(chart) {
- delete chart.$plugins;
- }
-};
-
-var core_scaleService = {
- // Scale registration object. Extensions can register new scale types (such as log or DB scales) and then
- // use the new chart options to grab the correct scale
- constructors: {},
- // Use a registration function so that we can move to an ES6 map when we no longer need to support
- // old browsers
-
- // Scale config defaults
- defaults: {},
- registerScaleType: function(type, scaleConstructor, scaleDefaults) {
- this.constructors[type] = scaleConstructor;
- this.defaults[type] = helpers$1.clone(scaleDefaults);
- },
- getScaleConstructor: function(type) {
- return this.constructors.hasOwnProperty(type) ? this.constructors[type] : undefined;
- },
- getScaleDefaults: function(type) {
- // Return the scale defaults merged with the global settings so that we always use the latest ones
- return this.defaults.hasOwnProperty(type) ? helpers$1.merge({}, [core_defaults.scale, this.defaults[type]]) : {};
- },
- updateScaleDefaults: function(type, additions) {
- var me = this;
- if (me.defaults.hasOwnProperty(type)) {
- me.defaults[type] = helpers$1.extend(me.defaults[type], additions);
- }
- },
- addScalesToLayout: function(chart) {
- // Adds each scale to the chart.boxes array to be sized accordingly
- helpers$1.each(chart.scales, function(scale) {
- // Set ILayoutItem parameters for backwards compatibility
- scale.fullWidth = scale.options.fullWidth;
- scale.position = scale.options.position;
- scale.weight = scale.options.weight;
- core_layouts.addBox(chart, scale);
- });
- }
-};
-
-var valueOrDefault$7 = helpers$1.valueOrDefault;
-
-core_defaults._set('global', {
- tooltips: {
- enabled: true,
- custom: null,
- mode: 'nearest',
- position: 'average',
- intersect: true,
- backgroundColor: 'rgba(0,0,0,0.8)',
- titleFontStyle: 'bold',
- titleSpacing: 2,
- titleMarginBottom: 6,
- titleFontColor: '#fff',
- titleAlign: 'left',
- bodySpacing: 2,
- bodyFontColor: '#fff',
- bodyAlign: 'left',
- footerFontStyle: 'bold',
- footerSpacing: 2,
- footerMarginTop: 6,
- footerFontColor: '#fff',
- footerAlign: 'left',
- yPadding: 6,
- xPadding: 6,
- caretPadding: 2,
- caretSize: 5,
- cornerRadius: 6,
- multiKeyBackground: '#fff',
- displayColors: true,
- borderColor: 'rgba(0,0,0,0)',
- borderWidth: 0,
- callbacks: {
- // Args are: (tooltipItems, data)
- beforeTitle: helpers$1.noop,
- title: function(tooltipItems, data) {
- var title = '';
- var labels = data.labels;
- var labelCount = labels ? labels.length : 0;
-
- if (tooltipItems.length > 0) {
- var item = tooltipItems[0];
- if (item.label) {
- title = item.label;
- } else if (item.xLabel) {
- title = item.xLabel;
- } else if (labelCount > 0 && item.index < labelCount) {
- title = labels[item.index];
- }
- }
-
- return title;
- },
- afterTitle: helpers$1.noop,
-
- // Args are: (tooltipItems, data)
- beforeBody: helpers$1.noop,
-
- // Args are: (tooltipItem, data)
- beforeLabel: helpers$1.noop,
- label: function(tooltipItem, data) {
- var label = data.datasets[tooltipItem.datasetIndex].label || '';
-
- if (label) {
- label += ': ';
- }
- if (!helpers$1.isNullOrUndef(tooltipItem.value)) {
- label += tooltipItem.value;
- } else {
- label += tooltipItem.yLabel;
- }
- return label;
- },
- labelColor: function(tooltipItem, chart) {
- var meta = chart.getDatasetMeta(tooltipItem.datasetIndex);
- var activeElement = meta.data[tooltipItem.index];
- var view = activeElement._view;
- return {
- borderColor: view.borderColor,
- backgroundColor: view.backgroundColor
- };
- },
- labelTextColor: function() {
- return this._options.bodyFontColor;
- },
- afterLabel: helpers$1.noop,
-
- // Args are: (tooltipItems, data)
- afterBody: helpers$1.noop,
-
- // Args are: (tooltipItems, data)
- beforeFooter: helpers$1.noop,
- footer: helpers$1.noop,
- afterFooter: helpers$1.noop
- }
- }
-});
-
-var positioners = {
- /**
- * Average mode places the tooltip at the average position of the elements shown
- * @function Chart.Tooltip.positioners.average
- * @param elements {ChartElement[]} the elements being displayed in the tooltip
- * @returns {object} tooltip position
- */
- average: function(elements) {
- if (!elements.length) {
- return false;
- }
-
- var i, len;
- var x = 0;
- var y = 0;
- var count = 0;
-
- for (i = 0, len = elements.length; i < len; ++i) {
- var el = elements[i];
- if (el && el.hasValue()) {
- var pos = el.tooltipPosition();
- x += pos.x;
- y += pos.y;
- ++count;
- }
- }
-
- return {
- x: x / count,
- y: y / count
- };
- },
-
- /**
- * Gets the tooltip position nearest of the item nearest to the event position
- * @function Chart.Tooltip.positioners.nearest
- * @param elements {Chart.Element[]} the tooltip elements
- * @param eventPosition {object} the position of the event in canvas coordinates
- * @returns {object} the tooltip position
- */
- nearest: function(elements, eventPosition) {
- var x = eventPosition.x;
- var y = eventPosition.y;
- var minDistance = Number.POSITIVE_INFINITY;
- var i, len, nearestElement;
-
- for (i = 0, len = elements.length; i < len; ++i) {
- var el = elements[i];
- if (el && el.hasValue()) {
- var center = el.getCenterPoint();
- var d = helpers$1.distanceBetweenPoints(eventPosition, center);
-
- if (d < minDistance) {
- minDistance = d;
- nearestElement = el;
- }
- }
- }
-
- if (nearestElement) {
- var tp = nearestElement.tooltipPosition();
- x = tp.x;
- y = tp.y;
- }
-
- return {
- x: x,
- y: y
- };
- }
-};
-
-// Helper to push or concat based on if the 2nd parameter is an array or not
-function pushOrConcat(base, toPush) {
- if (toPush) {
- if (helpers$1.isArray(toPush)) {
- // base = base.concat(toPush);
- Array.prototype.push.apply(base, toPush);
- } else {
- base.push(toPush);
- }
- }
-
- return base;
-}
-
-/**
- * Returns array of strings split by newline
- * @param {string} value - The value to split by newline.
- * @returns {string[]} value if newline present - Returned from String split() method
- * @function
- */
-function splitNewlines(str) {
- if ((typeof str === 'string' || str instanceof String) && str.indexOf('\n') > -1) {
- return str.split('\n');
- }
- return str;
-}
-
-
-/**
- * Private helper to create a tooltip item model
- * @param element - the chart element (point, arc, bar) to create the tooltip item for
- * @return new tooltip item
- */
-function createTooltipItem(element) {
- var xScale = element._xScale;
- var yScale = element._yScale || element._scale; // handle radar || polarArea charts
- var index = element._index;
- var datasetIndex = element._datasetIndex;
- var controller = element._chart.getDatasetMeta(datasetIndex).controller;
- var indexScale = controller._getIndexScale();
- var valueScale = controller._getValueScale();
-
- return {
- xLabel: xScale ? xScale.getLabelForIndex(index, datasetIndex) : '',
- yLabel: yScale ? yScale.getLabelForIndex(index, datasetIndex) : '',
- label: indexScale ? '' + indexScale.getLabelForIndex(index, datasetIndex) : '',
- value: valueScale ? '' + valueScale.getLabelForIndex(index, datasetIndex) : '',
- index: index,
- datasetIndex: datasetIndex,
- x: element._model.x,
- y: element._model.y
- };
-}
-
-/**
- * Helper to get the reset model for the tooltip
- * @param tooltipOpts {object} the tooltip options
- */
-function getBaseModel(tooltipOpts) {
- var globalDefaults = core_defaults.global;
-
- return {
- // Positioning
- xPadding: tooltipOpts.xPadding,
- yPadding: tooltipOpts.yPadding,
- xAlign: tooltipOpts.xAlign,
- yAlign: tooltipOpts.yAlign,
-
- // Body
- bodyFontColor: tooltipOpts.bodyFontColor,
- _bodyFontFamily: valueOrDefault$7(tooltipOpts.bodyFontFamily, globalDefaults.defaultFontFamily),
- _bodyFontStyle: valueOrDefault$7(tooltipOpts.bodyFontStyle, globalDefaults.defaultFontStyle),
- _bodyAlign: tooltipOpts.bodyAlign,
- bodyFontSize: valueOrDefault$7(tooltipOpts.bodyFontSize, globalDefaults.defaultFontSize),
- bodySpacing: tooltipOpts.bodySpacing,
-
- // Title
- titleFontColor: tooltipOpts.titleFontColor,
- _titleFontFamily: valueOrDefault$7(tooltipOpts.titleFontFamily, globalDefaults.defaultFontFamily),
- _titleFontStyle: valueOrDefault$7(tooltipOpts.titleFontStyle, globalDefaults.defaultFontStyle),
- titleFontSize: valueOrDefault$7(tooltipOpts.titleFontSize, globalDefaults.defaultFontSize),
- _titleAlign: tooltipOpts.titleAlign,
- titleSpacing: tooltipOpts.titleSpacing,
- titleMarginBottom: tooltipOpts.titleMarginBottom,
-
- // Footer
- footerFontColor: tooltipOpts.footerFontColor,
- _footerFontFamily: valueOrDefault$7(tooltipOpts.footerFontFamily, globalDefaults.defaultFontFamily),
- _footerFontStyle: valueOrDefault$7(tooltipOpts.footerFontStyle, globalDefaults.defaultFontStyle),
- footerFontSize: valueOrDefault$7(tooltipOpts.footerFontSize, globalDefaults.defaultFontSize),
- _footerAlign: tooltipOpts.footerAlign,
- footerSpacing: tooltipOpts.footerSpacing,
- footerMarginTop: tooltipOpts.footerMarginTop,
-
- // Appearance
- caretSize: tooltipOpts.caretSize,
- cornerRadius: tooltipOpts.cornerRadius,
- backgroundColor: tooltipOpts.backgroundColor,
- opacity: 0,
- legendColorBackground: tooltipOpts.multiKeyBackground,
- displayColors: tooltipOpts.displayColors,
- borderColor: tooltipOpts.borderColor,
- borderWidth: tooltipOpts.borderWidth
- };
-}
-
-/**
- * Get the size of the tooltip
- */
-function getTooltipSize(tooltip, model) {
- var ctx = tooltip._chart.ctx;
-
- var height = model.yPadding * 2; // Tooltip Padding
- var width = 0;
-
- // Count of all lines in the body
- var body = model.body;
- var combinedBodyLength = body.reduce(function(count, bodyItem) {
- return count + bodyItem.before.length + bodyItem.lines.length + bodyItem.after.length;
- }, 0);
- combinedBodyLength += model.beforeBody.length + model.afterBody.length;
-
- var titleLineCount = model.title.length;
- var footerLineCount = model.footer.length;
- var titleFontSize = model.titleFontSize;
- var bodyFontSize = model.bodyFontSize;
- var footerFontSize = model.footerFontSize;
-
- height += titleLineCount * titleFontSize; // Title Lines
- height += titleLineCount ? (titleLineCount - 1) * model.titleSpacing : 0; // Title Line Spacing
- height += titleLineCount ? model.titleMarginBottom : 0; // Title's bottom Margin
- height += combinedBodyLength * bodyFontSize; // Body Lines
- height += combinedBodyLength ? (combinedBodyLength - 1) * model.bodySpacing : 0; // Body Line Spacing
- height += footerLineCount ? model.footerMarginTop : 0; // Footer Margin
- height += footerLineCount * (footerFontSize); // Footer Lines
- height += footerLineCount ? (footerLineCount - 1) * model.footerSpacing : 0; // Footer Line Spacing
-
- // Title width
- var widthPadding = 0;
- var maxLineWidth = function(line) {
- width = Math.max(width, ctx.measureText(line).width + widthPadding);
- };
-
- ctx.font = helpers$1.fontString(titleFontSize, model._titleFontStyle, model._titleFontFamily);
- helpers$1.each(model.title, maxLineWidth);
-
- // Body width
- ctx.font = helpers$1.fontString(bodyFontSize, model._bodyFontStyle, model._bodyFontFamily);
- helpers$1.each(model.beforeBody.concat(model.afterBody), maxLineWidth);
-
- // Body lines may include some extra width due to the color box
- widthPadding = model.displayColors ? (bodyFontSize + 2) : 0;
- helpers$1.each(body, function(bodyItem) {
- helpers$1.each(bodyItem.before, maxLineWidth);
- helpers$1.each(bodyItem.lines, maxLineWidth);
- helpers$1.each(bodyItem.after, maxLineWidth);
- });
-
- // Reset back to 0
- widthPadding = 0;
-
- // Footer width
- ctx.font = helpers$1.fontString(footerFontSize, model._footerFontStyle, model._footerFontFamily);
- helpers$1.each(model.footer, maxLineWidth);
-
- // Add padding
- width += 2 * model.xPadding;
-
- return {
- width: width,
- height: height
- };
-}
-
-/**
- * Helper to get the alignment of a tooltip given the size
- */
-function determineAlignment(tooltip, size) {
- var model = tooltip._model;
- var chart = tooltip._chart;
- var chartArea = tooltip._chart.chartArea;
- var xAlign = 'center';
- var yAlign = 'center';
-
- if (model.y < size.height) {
- yAlign = 'top';
- } else if (model.y > (chart.height - size.height)) {
- yAlign = 'bottom';
- }
-
- var lf, rf; // functions to determine left, right alignment
- var olf, orf; // functions to determine if left/right alignment causes tooltip to go outside chart
- var yf; // function to get the y alignment if the tooltip goes outside of the left or right edges
- var midX = (chartArea.left + chartArea.right) / 2;
- var midY = (chartArea.top + chartArea.bottom) / 2;
-
- if (yAlign === 'center') {
- lf = function(x) {
- return x <= midX;
- };
- rf = function(x) {
- return x > midX;
- };
- } else {
- lf = function(x) {
- return x <= (size.width / 2);
- };
- rf = function(x) {
- return x >= (chart.width - (size.width / 2));
- };
- }
-
- olf = function(x) {
- return x + size.width + model.caretSize + model.caretPadding > chart.width;
- };
- orf = function(x) {
- return x - size.width - model.caretSize - model.caretPadding < 0;
- };
- yf = function(y) {
- return y <= midY ? 'top' : 'bottom';
- };
-
- if (lf(model.x)) {
- xAlign = 'left';
-
- // Is tooltip too wide and goes over the right side of the chart.?
- if (olf(model.x)) {
- xAlign = 'center';
- yAlign = yf(model.y);
- }
- } else if (rf(model.x)) {
- xAlign = 'right';
-
- // Is tooltip too wide and goes outside left edge of canvas?
- if (orf(model.x)) {
- xAlign = 'center';
- yAlign = yf(model.y);
- }
- }
-
- var opts = tooltip._options;
- return {
- xAlign: opts.xAlign ? opts.xAlign : xAlign,
- yAlign: opts.yAlign ? opts.yAlign : yAlign
- };
-}
-
-/**
- * Helper to get the location a tooltip needs to be placed at given the initial position (via the vm) and the size and alignment
- */
-function getBackgroundPoint(vm, size, alignment, chart) {
- // Background Position
- var x = vm.x;
- var y = vm.y;
-
- var caretSize = vm.caretSize;
- var caretPadding = vm.caretPadding;
- var cornerRadius = vm.cornerRadius;
- var xAlign = alignment.xAlign;
- var yAlign = alignment.yAlign;
- var paddingAndSize = caretSize + caretPadding;
- var radiusAndPadding = cornerRadius + caretPadding;
-
- if (xAlign === 'right') {
- x -= size.width;
- } else if (xAlign === 'center') {
- x -= (size.width / 2);
- if (x + size.width > chart.width) {
- x = chart.width - size.width;
- }
- if (x < 0) {
- x = 0;
- }
- }
-
- if (yAlign === 'top') {
- y += paddingAndSize;
- } else if (yAlign === 'bottom') {
- y -= size.height + paddingAndSize;
- } else {
- y -= (size.height / 2);
- }
-
- if (yAlign === 'center') {
- if (xAlign === 'left') {
- x += paddingAndSize;
- } else if (xAlign === 'right') {
- x -= paddingAndSize;
- }
- } else if (xAlign === 'left') {
- x -= radiusAndPadding;
- } else if (xAlign === 'right') {
- x += radiusAndPadding;
- }
-
- return {
- x: x,
- y: y
- };
-}
-
-function getAlignedX(vm, align) {
- return align === 'center'
- ? vm.x + vm.width / 2
- : align === 'right'
- ? vm.x + vm.width - vm.xPadding
- : vm.x + vm.xPadding;
-}
-
-/**
- * Helper to build before and after body lines
- */
-function getBeforeAfterBodyLines(callback) {
- return pushOrConcat([], splitNewlines(callback));
-}
-
-var exports$3 = core_element.extend({
- initialize: function() {
- this._model = getBaseModel(this._options);
- this._lastActive = [];
- },
-
- // Get the title
- // Args are: (tooltipItem, data)
- getTitle: function() {
- var me = this;
- var opts = me._options;
- var callbacks = opts.callbacks;
-
- var beforeTitle = callbacks.beforeTitle.apply(me, arguments);
- var title = callbacks.title.apply(me, arguments);
- var afterTitle = callbacks.afterTitle.apply(me, arguments);
-
- var lines = [];
- lines = pushOrConcat(lines, splitNewlines(beforeTitle));
- lines = pushOrConcat(lines, splitNewlines(title));
- lines = pushOrConcat(lines, splitNewlines(afterTitle));
-
- return lines;
- },
-
- // Args are: (tooltipItem, data)
- getBeforeBody: function() {
- return getBeforeAfterBodyLines(this._options.callbacks.beforeBody.apply(this, arguments));
- },
-
- // Args are: (tooltipItem, data)
- getBody: function(tooltipItems, data) {
- var me = this;
- var callbacks = me._options.callbacks;
- var bodyItems = [];
-
- helpers$1.each(tooltipItems, function(tooltipItem) {
- var bodyItem = {
- before: [],
- lines: [],
- after: []
- };
- pushOrConcat(bodyItem.before, splitNewlines(callbacks.beforeLabel.call(me, tooltipItem, data)));
- pushOrConcat(bodyItem.lines, callbacks.label.call(me, tooltipItem, data));
- pushOrConcat(bodyItem.after, splitNewlines(callbacks.afterLabel.call(me, tooltipItem, data)));
-
- bodyItems.push(bodyItem);
- });
-
- return bodyItems;
- },
-
- // Args are: (tooltipItem, data)
- getAfterBody: function() {
- return getBeforeAfterBodyLines(this._options.callbacks.afterBody.apply(this, arguments));
- },
-
- // Get the footer and beforeFooter and afterFooter lines
- // Args are: (tooltipItem, data)
- getFooter: function() {
- var me = this;
- var callbacks = me._options.callbacks;
-
- var beforeFooter = callbacks.beforeFooter.apply(me, arguments);
- var footer = callbacks.footer.apply(me, arguments);
- var afterFooter = callbacks.afterFooter.apply(me, arguments);
-
- var lines = [];
- lines = pushOrConcat(lines, splitNewlines(beforeFooter));
- lines = pushOrConcat(lines, splitNewlines(footer));
- lines = pushOrConcat(lines, splitNewlines(afterFooter));
-
- return lines;
- },
-
- update: function(changed) {
- var me = this;
- var opts = me._options;
-
- // Need to regenerate the model because its faster than using extend and it is necessary due to the optimization in Chart.Element.transition
- // that does _view = _model if ease === 1. This causes the 2nd tooltip update to set properties in both the view and model at the same time
- // which breaks any animations.
- var existingModel = me._model;
- var model = me._model = getBaseModel(opts);
- var active = me._active;
-
- var data = me._data;
-
- // In the case where active.length === 0 we need to keep these at existing values for good animations
- var alignment = {
- xAlign: existingModel.xAlign,
- yAlign: existingModel.yAlign
- };
- var backgroundPoint = {
- x: existingModel.x,
- y: existingModel.y
- };
- var tooltipSize = {
- width: existingModel.width,
- height: existingModel.height
- };
- var tooltipPosition = {
- x: existingModel.caretX,
- y: existingModel.caretY
- };
-
- var i, len;
-
- if (active.length) {
- model.opacity = 1;
-
- var labelColors = [];
- var labelTextColors = [];
- tooltipPosition = positioners[opts.position].call(me, active, me._eventPosition);
-
- var tooltipItems = [];
- for (i = 0, len = active.length; i < len; ++i) {
- tooltipItems.push(createTooltipItem(active[i]));
- }
-
- // If the user provided a filter function, use it to modify the tooltip items
- if (opts.filter) {
- tooltipItems = tooltipItems.filter(function(a) {
- return opts.filter(a, data);
- });
- }
-
- // If the user provided a sorting function, use it to modify the tooltip items
- if (opts.itemSort) {
- tooltipItems = tooltipItems.sort(function(a, b) {
- return opts.itemSort(a, b, data);
- });
- }
-
- // Determine colors for boxes
- helpers$1.each(tooltipItems, function(tooltipItem) {
- labelColors.push(opts.callbacks.labelColor.call(me, tooltipItem, me._chart));
- labelTextColors.push(opts.callbacks.labelTextColor.call(me, tooltipItem, me._chart));
- });
-
-
- // Build the Text Lines
- model.title = me.getTitle(tooltipItems, data);
- model.beforeBody = me.getBeforeBody(tooltipItems, data);
- model.body = me.getBody(tooltipItems, data);
- model.afterBody = me.getAfterBody(tooltipItems, data);
- model.footer = me.getFooter(tooltipItems, data);
-
- // Initial positioning and colors
- model.x = tooltipPosition.x;
- model.y = tooltipPosition.y;
- model.caretPadding = opts.caretPadding;
- model.labelColors = labelColors;
- model.labelTextColors = labelTextColors;
-
- // data points
- model.dataPoints = tooltipItems;
-
- // We need to determine alignment of the tooltip
- tooltipSize = getTooltipSize(this, model);
- alignment = determineAlignment(this, tooltipSize);
- // Final Size and Position
- backgroundPoint = getBackgroundPoint(model, tooltipSize, alignment, me._chart);
- } else {
- model.opacity = 0;
- }
-
- model.xAlign = alignment.xAlign;
- model.yAlign = alignment.yAlign;
- model.x = backgroundPoint.x;
- model.y = backgroundPoint.y;
- model.width = tooltipSize.width;
- model.height = tooltipSize.height;
-
- // Point where the caret on the tooltip points to
- model.caretX = tooltipPosition.x;
- model.caretY = tooltipPosition.y;
-
- me._model = model;
-
- if (changed && opts.custom) {
- opts.custom.call(me, model);
- }
-
- return me;
- },
-
- drawCaret: function(tooltipPoint, size) {
- var ctx = this._chart.ctx;
- var vm = this._view;
- var caretPosition = this.getCaretPosition(tooltipPoint, size, vm);
-
- ctx.lineTo(caretPosition.x1, caretPosition.y1);
- ctx.lineTo(caretPosition.x2, caretPosition.y2);
- ctx.lineTo(caretPosition.x3, caretPosition.y3);
- },
- getCaretPosition: function(tooltipPoint, size, vm) {
- var x1, x2, x3, y1, y2, y3;
- var caretSize = vm.caretSize;
- var cornerRadius = vm.cornerRadius;
- var xAlign = vm.xAlign;
- var yAlign = vm.yAlign;
- var ptX = tooltipPoint.x;
- var ptY = tooltipPoint.y;
- var width = size.width;
- var height = size.height;
-
- if (yAlign === 'center') {
- y2 = ptY + (height / 2);
-
- if (xAlign === 'left') {
- x1 = ptX;
- x2 = x1 - caretSize;
- x3 = x1;
-
- y1 = y2 + caretSize;
- y3 = y2 - caretSize;
- } else {
- x1 = ptX + width;
- x2 = x1 + caretSize;
- x3 = x1;
-
- y1 = y2 - caretSize;
- y3 = y2 + caretSize;
- }
- } else {
- if (xAlign === 'left') {
- x2 = ptX + cornerRadius + (caretSize);
- x1 = x2 - caretSize;
- x3 = x2 + caretSize;
- } else if (xAlign === 'right') {
- x2 = ptX + width - cornerRadius - caretSize;
- x1 = x2 - caretSize;
- x3 = x2 + caretSize;
- } else {
- x2 = vm.caretX;
- x1 = x2 - caretSize;
- x3 = x2 + caretSize;
- }
- if (yAlign === 'top') {
- y1 = ptY;
- y2 = y1 - caretSize;
- y3 = y1;
- } else {
- y1 = ptY + height;
- y2 = y1 + caretSize;
- y3 = y1;
- // invert drawing order
- var tmp = x3;
- x3 = x1;
- x1 = tmp;
- }
- }
- return {x1: x1, x2: x2, x3: x3, y1: y1, y2: y2, y3: y3};
- },
-
- drawTitle: function(pt, vm, ctx) {
- var title = vm.title;
-
- if (title.length) {
- pt.x = getAlignedX(vm, vm._titleAlign);
-
- ctx.textAlign = vm._titleAlign;
- ctx.textBaseline = 'top';
-
- var titleFontSize = vm.titleFontSize;
- var titleSpacing = vm.titleSpacing;
-
- ctx.fillStyle = vm.titleFontColor;
- ctx.font = helpers$1.fontString(titleFontSize, vm._titleFontStyle, vm._titleFontFamily);
-
- var i, len;
- for (i = 0, len = title.length; i < len; ++i) {
- ctx.fillText(title[i], pt.x, pt.y);
- pt.y += titleFontSize + titleSpacing; // Line Height and spacing
-
- if (i + 1 === title.length) {
- pt.y += vm.titleMarginBottom - titleSpacing; // If Last, add margin, remove spacing
- }
- }
- }
- },
-
- drawBody: function(pt, vm, ctx) {
- var bodyFontSize = vm.bodyFontSize;
- var bodySpacing = vm.bodySpacing;
- var bodyAlign = vm._bodyAlign;
- var body = vm.body;
- var drawColorBoxes = vm.displayColors;
- var labelColors = vm.labelColors;
- var xLinePadding = 0;
- var colorX = drawColorBoxes ? getAlignedX(vm, 'left') : 0;
- var textColor;
-
- ctx.textAlign = bodyAlign;
- ctx.textBaseline = 'top';
- ctx.font = helpers$1.fontString(bodyFontSize, vm._bodyFontStyle, vm._bodyFontFamily);
-
- pt.x = getAlignedX(vm, bodyAlign);
-
- // Before Body
- var fillLineOfText = function(line) {
- ctx.fillText(line, pt.x + xLinePadding, pt.y);
- pt.y += bodyFontSize + bodySpacing;
- };
-
- // Before body lines
- ctx.fillStyle = vm.bodyFontColor;
- helpers$1.each(vm.beforeBody, fillLineOfText);
-
- xLinePadding = drawColorBoxes && bodyAlign !== 'right'
- ? bodyAlign === 'center' ? (bodyFontSize / 2 + 1) : (bodyFontSize + 2)
- : 0;
-
- // Draw body lines now
- helpers$1.each(body, function(bodyItem, i) {
- textColor = vm.labelTextColors[i];
- ctx.fillStyle = textColor;
- helpers$1.each(bodyItem.before, fillLineOfText);
-
- helpers$1.each(bodyItem.lines, function(line) {
- // Draw Legend-like boxes if needed
- if (drawColorBoxes) {
- // Fill a white rect so that colours merge nicely if the opacity is < 1
- ctx.fillStyle = vm.legendColorBackground;
- ctx.fillRect(colorX, pt.y, bodyFontSize, bodyFontSize);
-
- // Border
- ctx.lineWidth = 1;
- ctx.strokeStyle = labelColors[i].borderColor;
- ctx.strokeRect(colorX, pt.y, bodyFontSize, bodyFontSize);
-
- // Inner square
- ctx.fillStyle = labelColors[i].backgroundColor;
- ctx.fillRect(colorX + 1, pt.y + 1, bodyFontSize - 2, bodyFontSize - 2);
- ctx.fillStyle = textColor;
- }
-
- fillLineOfText(line);
- });
-
- helpers$1.each(bodyItem.after, fillLineOfText);
- });
-
- // Reset back to 0 for after body
- xLinePadding = 0;
-
- // After body lines
- helpers$1.each(vm.afterBody, fillLineOfText);
- pt.y -= bodySpacing; // Remove last body spacing
- },
-
- drawFooter: function(pt, vm, ctx) {
- var footer = vm.footer;
-
- if (footer.length) {
- pt.x = getAlignedX(vm, vm._footerAlign);
- pt.y += vm.footerMarginTop;
-
- ctx.textAlign = vm._footerAlign;
- ctx.textBaseline = 'top';
-
- ctx.fillStyle = vm.footerFontColor;
- ctx.font = helpers$1.fontString(vm.footerFontSize, vm._footerFontStyle, vm._footerFontFamily);
-
- helpers$1.each(footer, function(line) {
- ctx.fillText(line, pt.x, pt.y);
- pt.y += vm.footerFontSize + vm.footerSpacing;
- });
- }
- },
-
- drawBackground: function(pt, vm, ctx, tooltipSize) {
- ctx.fillStyle = vm.backgroundColor;
- ctx.strokeStyle = vm.borderColor;
- ctx.lineWidth = vm.borderWidth;
- var xAlign = vm.xAlign;
- var yAlign = vm.yAlign;
- var x = pt.x;
- var y = pt.y;
- var width = tooltipSize.width;
- var height = tooltipSize.height;
- var radius = vm.cornerRadius;
-
- ctx.beginPath();
- ctx.moveTo(x + radius, y);
- if (yAlign === 'top') {
- this.drawCaret(pt, tooltipSize);
- }
- ctx.lineTo(x + width - radius, y);
- ctx.quadraticCurveTo(x + width, y, x + width, y + radius);
- if (yAlign === 'center' && xAlign === 'right') {
- this.drawCaret(pt, tooltipSize);
- }
- ctx.lineTo(x + width, y + height - radius);
- ctx.quadraticCurveTo(x + width, y + height, x + width - radius, y + height);
- if (yAlign === 'bottom') {
- this.drawCaret(pt, tooltipSize);
- }
- ctx.lineTo(x + radius, y + height);
- ctx.quadraticCurveTo(x, y + height, x, y + height - radius);
- if (yAlign === 'center' && xAlign === 'left') {
- this.drawCaret(pt, tooltipSize);
- }
- ctx.lineTo(x, y + radius);
- ctx.quadraticCurveTo(x, y, x + radius, y);
- ctx.closePath();
-
- ctx.fill();
-
- if (vm.borderWidth > 0) {
- ctx.stroke();
- }
- },
-
- draw: function() {
- var ctx = this._chart.ctx;
- var vm = this._view;
-
- if (vm.opacity === 0) {
- return;
- }
-
- var tooltipSize = {
- width: vm.width,
- height: vm.height
- };
- var pt = {
- x: vm.x,
- y: vm.y
- };
-
- // IE11/Edge does not like very small opacities, so snap to 0
- var opacity = Math.abs(vm.opacity < 1e-3) ? 0 : vm.opacity;
-
- // Truthy/falsey value for empty tooltip
- var hasTooltipContent = vm.title.length || vm.beforeBody.length || vm.body.length || vm.afterBody.length || vm.footer.length;
-
- if (this._options.enabled && hasTooltipContent) {
- ctx.save();
- ctx.globalAlpha = opacity;
-
- // Draw Background
- this.drawBackground(pt, vm, ctx, tooltipSize);
-
- // Draw Title, Body, and Footer
- pt.y += vm.yPadding;
-
- // Titles
- this.drawTitle(pt, vm, ctx);
-
- // Body
- this.drawBody(pt, vm, ctx);
-
- // Footer
- this.drawFooter(pt, vm, ctx);
-
- ctx.restore();
- }
- },
-
- /**
- * Handle an event
- * @private
- * @param {IEvent} event - The event to handle
- * @returns {boolean} true if the tooltip changed
- */
- handleEvent: function(e) {
- var me = this;
- var options = me._options;
- var changed = false;
-
- me._lastActive = me._lastActive || [];
-
- // Find Active Elements for tooltips
- if (e.type === 'mouseout') {
- me._active = [];
- } else {
- me._active = me._chart.getElementsAtEventForMode(e, options.mode, options);
- }
-
- // Remember Last Actives
- changed = !helpers$1.arrayEquals(me._active, me._lastActive);
-
- // Only handle target event on tooltip change
- if (changed) {
- me._lastActive = me._active;
-
- if (options.enabled || options.custom) {
- me._eventPosition = {
- x: e.x,
- y: e.y
- };
-
- me.update(true);
- me.pivot();
- }
- }
-
- return changed;
- }
-});
-
-/**
- * @namespace Chart.Tooltip.positioners
- */
-var positioners_1 = positioners;
-
-var core_tooltip = exports$3;
-core_tooltip.positioners = positioners_1;
-
-var valueOrDefault$8 = helpers$1.valueOrDefault;
-
-core_defaults._set('global', {
- elements: {},
- events: [
- 'mousemove',
- 'mouseout',
- 'click',
- 'touchstart',
- 'touchmove'
- ],
- hover: {
- onHover: null,
- mode: 'nearest',
- intersect: true,
- animationDuration: 400
- },
- onClick: null,
- maintainAspectRatio: true,
- responsive: true,
- responsiveAnimationDuration: 0
-});
-
-/**
- * Recursively merge the given config objects representing the `scales` option
- * by incorporating scale defaults in `xAxes` and `yAxes` array items, then
- * returns a deep copy of the result, thus doesn't alter inputs.
- */
-function mergeScaleConfig(/* config objects ... */) {
- return helpers$1.merge({}, [].slice.call(arguments), {
- merger: function(key, target, source, options) {
- if (key === 'xAxes' || key === 'yAxes') {
- var slen = source[key].length;
- var i, type, scale;
-
- if (!target[key]) {
- target[key] = [];
- }
-
- for (i = 0; i < slen; ++i) {
- scale = source[key][i];
- type = valueOrDefault$8(scale.type, key === 'xAxes' ? 'category' : 'linear');
-
- if (i >= target[key].length) {
- target[key].push({});
- }
-
- if (!target[key][i].type || (scale.type && scale.type !== target[key][i].type)) {
- // new/untyped scale or type changed: let's apply the new defaults
- // then merge source scale to correctly overwrite the defaults.
- helpers$1.merge(target[key][i], [core_scaleService.getScaleDefaults(type), scale]);
- } else {
- // scales type are the same
- helpers$1.merge(target[key][i], scale);
- }
- }
- } else {
- helpers$1._merger(key, target, source, options);
- }
- }
- });
-}
-
-/**
- * Recursively merge the given config objects as the root options by handling
- * default scale options for the `scales` and `scale` properties, then returns
- * a deep copy of the result, thus doesn't alter inputs.
- */
-function mergeConfig(/* config objects ... */) {
- return helpers$1.merge({}, [].slice.call(arguments), {
- merger: function(key, target, source, options) {
- var tval = target[key] || {};
- var sval = source[key];
-
- if (key === 'scales') {
- // scale config merging is complex. Add our own function here for that
- target[key] = mergeScaleConfig(tval, sval);
- } else if (key === 'scale') {
- // used in polar area & radar charts since there is only one scale
- target[key] = helpers$1.merge(tval, [core_scaleService.getScaleDefaults(sval.type), sval]);
- } else {
- helpers$1._merger(key, target, source, options);
- }
- }
- });
-}
-
-function initConfig(config) {
- config = config || {};
-
- // Do NOT use mergeConfig for the data object because this method merges arrays
- // and so would change references to labels and datasets, preventing data updates.
- var data = config.data = config.data || {};
- data.datasets = data.datasets || [];
- data.labels = data.labels || [];
-
- config.options = mergeConfig(
- core_defaults.global,
- core_defaults[config.type],
- config.options || {});
-
- return config;
-}
-
-function updateConfig(chart) {
- var newOptions = chart.options;
-
- helpers$1.each(chart.scales, function(scale) {
- core_layouts.removeBox(chart, scale);
- });
-
- newOptions = mergeConfig(
- core_defaults.global,
- core_defaults[chart.config.type],
- newOptions);
-
- chart.options = chart.config.options = newOptions;
- chart.ensureScalesHaveIDs();
- chart.buildOrUpdateScales();
-
- // Tooltip
- chart.tooltip._options = newOptions.tooltips;
- chart.tooltip.initialize();
-}
-
-function positionIsHorizontal(position) {
- return position === 'top' || position === 'bottom';
-}
-
-var Chart = function(item, config) {
- this.construct(item, config);
- return this;
-};
-
-helpers$1.extend(Chart.prototype, /** @lends Chart */ {
- /**
- * @private
- */
- construct: function(item, config) {
- var me = this;
-
- config = initConfig(config);
-
- var context = platform.acquireContext(item, config);
- var canvas = context && context.canvas;
- var height = canvas && canvas.height;
- var width = canvas && canvas.width;
-
- me.id = helpers$1.uid();
- me.ctx = context;
- me.canvas = canvas;
- me.config = config;
- me.width = width;
- me.height = height;
- me.aspectRatio = height ? width / height : null;
- me.options = config.options;
- me._bufferedRender = false;
-
- /**
- * Provided for backward compatibility, Chart and Chart.Controller have been merged,
- * the "instance" still need to be defined since it might be called from plugins.
- * @prop Chart#chart
- * @deprecated since version 2.6.0
- * @todo remove at version 3
- * @private
- */
- me.chart = me;
- me.controller = me; // chart.chart.controller #inception
-
- // Add the chart instance to the global namespace
- Chart.instances[me.id] = me;
-
- // Define alias to the config data: `chart.data === chart.config.data`
- Object.defineProperty(me, 'data', {
- get: function() {
- return me.config.data;
- },
- set: function(value) {
- me.config.data = value;
- }
- });
-
- if (!context || !canvas) {
- // The given item is not a compatible context2d element, let's return before finalizing
- // the chart initialization but after setting basic chart / controller properties that
- // can help to figure out that the chart is not valid (e.g chart.canvas !== null);
- // https://github.com/chartjs/Chart.js/issues/2807
- console.error("Failed to create chart: can't acquire context from the given item");
- return;
- }
-
- me.initialize();
- me.update();
- },
-
- /**
- * @private
- */
- initialize: function() {
- var me = this;
-
- // Before init plugin notification
- core_plugins.notify(me, 'beforeInit');
-
- helpers$1.retinaScale(me, me.options.devicePixelRatio);
-
- me.bindEvents();
-
- if (me.options.responsive) {
- // Initial resize before chart draws (must be silent to preserve initial animations).
- me.resize(true);
- }
-
- // Make sure scales have IDs and are built before we build any controllers.
- me.ensureScalesHaveIDs();
- me.buildOrUpdateScales();
- me.initToolTip();
-
- // After init plugin notification
- core_plugins.notify(me, 'afterInit');
-
- return me;
- },
-
- clear: function() {
- helpers$1.canvas.clear(this);
- return this;
- },
-
- stop: function() {
- // Stops any current animation loop occurring
- core_animations.cancelAnimation(this);
- return this;
- },
-
- resize: function(silent) {
- var me = this;
- var options = me.options;
- var canvas = me.canvas;
- var aspectRatio = (options.maintainAspectRatio && me.aspectRatio) || null;
-
- // the canvas render width and height will be casted to integers so make sure that
- // the canvas display style uses the same integer values to avoid blurring effect.
-
- // Set to 0 instead of canvas.size because the size defaults to 300x150 if the element is collapsed
- var newWidth = Math.max(0, Math.floor(helpers$1.getMaximumWidth(canvas)));
- var newHeight = Math.max(0, Math.floor(aspectRatio ? newWidth / aspectRatio : helpers$1.getMaximumHeight(canvas)));
-
- if (me.width === newWidth && me.height === newHeight) {
- return;
- }
-
- canvas.width = me.width = newWidth;
- canvas.height = me.height = newHeight;
- canvas.style.width = newWidth + 'px';
- canvas.style.height = newHeight + 'px';
-
- helpers$1.retinaScale(me, options.devicePixelRatio);
-
- if (!silent) {
- // Notify any plugins about the resize
- var newSize = {width: newWidth, height: newHeight};
- core_plugins.notify(me, 'resize', [newSize]);
-
- // Notify of resize
- if (options.onResize) {
- options.onResize(me, newSize);
- }
-
- me.stop();
- me.update({
- duration: options.responsiveAnimationDuration
- });
- }
- },
-
- ensureScalesHaveIDs: function() {
- var options = this.options;
- var scalesOptions = options.scales || {};
- var scaleOptions = options.scale;
-
- helpers$1.each(scalesOptions.xAxes, function(xAxisOptions, index) {
- xAxisOptions.id = xAxisOptions.id || ('x-axis-' + index);
- });
-
- helpers$1.each(scalesOptions.yAxes, function(yAxisOptions, index) {
- yAxisOptions.id = yAxisOptions.id || ('y-axis-' + index);
- });
-
- if (scaleOptions) {
- scaleOptions.id = scaleOptions.id || 'scale';
- }
- },
-
- /**
- * Builds a map of scale ID to scale object for future lookup.
- */
- buildOrUpdateScales: function() {
- var me = this;
- var options = me.options;
- var scales = me.scales || {};
- var items = [];
- var updated = Object.keys(scales).reduce(function(obj, id) {
- obj[id] = false;
- return obj;
- }, {});
-
- if (options.scales) {
- items = items.concat(
- (options.scales.xAxes || []).map(function(xAxisOptions) {
- return {options: xAxisOptions, dtype: 'category', dposition: 'bottom'};
- }),
- (options.scales.yAxes || []).map(function(yAxisOptions) {
- return {options: yAxisOptions, dtype: 'linear', dposition: 'left'};
- })
- );
- }
-
- if (options.scale) {
- items.push({
- options: options.scale,
- dtype: 'radialLinear',
- isDefault: true,
- dposition: 'chartArea'
- });
- }
-
- helpers$1.each(items, function(item) {
- var scaleOptions = item.options;
- var id = scaleOptions.id;
- var scaleType = valueOrDefault$8(scaleOptions.type, item.dtype);
-
- if (positionIsHorizontal(scaleOptions.position) !== positionIsHorizontal(item.dposition)) {
- scaleOptions.position = item.dposition;
- }
-
- updated[id] = true;
- var scale = null;
- if (id in scales && scales[id].type === scaleType) {
- scale = scales[id];
- scale.options = scaleOptions;
- scale.ctx = me.ctx;
- scale.chart = me;
- } else {
- var scaleClass = core_scaleService.getScaleConstructor(scaleType);
- if (!scaleClass) {
- return;
- }
- scale = new scaleClass({
- id: id,
- type: scaleType,
- options: scaleOptions,
- ctx: me.ctx,
- chart: me
- });
- scales[scale.id] = scale;
- }
-
- scale.mergeTicksOptions();
-
- // TODO(SB): I think we should be able to remove this custom case (options.scale)
- // and consider it as a regular scale part of the "scales"" map only! This would
- // make the logic easier and remove some useless? custom code.
- if (item.isDefault) {
- me.scale = scale;
- }
- });
- // clear up discarded scales
- helpers$1.each(updated, function(hasUpdated, id) {
- if (!hasUpdated) {
- delete scales[id];
- }
- });
-
- me.scales = scales;
-
- core_scaleService.addScalesToLayout(this);
- },
-
- buildOrUpdateControllers: function() {
- var me = this;
- var newControllers = [];
-
- helpers$1.each(me.data.datasets, function(dataset, datasetIndex) {
- var meta = me.getDatasetMeta(datasetIndex);
- var type = dataset.type || me.config.type;
-
- if (meta.type && meta.type !== type) {
- me.destroyDatasetMeta(datasetIndex);
- meta = me.getDatasetMeta(datasetIndex);
- }
- meta.type = type;
-
- if (meta.controller) {
- meta.controller.updateIndex(datasetIndex);
- meta.controller.linkScales();
- } else {
- var ControllerClass = controllers[meta.type];
- if (ControllerClass === undefined) {
- throw new Error('"' + meta.type + '" is not a chart type.');
- }
-
- meta.controller = new ControllerClass(me, datasetIndex);
- newControllers.push(meta.controller);
- }
- }, me);
-
- return newControllers;
- },
-
- /**
- * Reset the elements of all datasets
- * @private
- */
- resetElements: function() {
- var me = this;
- helpers$1.each(me.data.datasets, function(dataset, datasetIndex) {
- me.getDatasetMeta(datasetIndex).controller.reset();
- }, me);
- },
-
- /**
- * Resets the chart back to it's state before the initial animation
- */
- reset: function() {
- this.resetElements();
- this.tooltip.initialize();
- },
-
- update: function(config) {
- var me = this;
-
- if (!config || typeof config !== 'object') {
- // backwards compatibility
- config = {
- duration: config,
- lazy: arguments[1]
- };
- }
-
- updateConfig(me);
-
- // plugins options references might have change, let's invalidate the cache
- // https://github.com/chartjs/Chart.js/issues/5111#issuecomment-355934167
- core_plugins._invalidate(me);
-
- if (core_plugins.notify(me, 'beforeUpdate') === false) {
- return;
- }
-
- // In case the entire data object changed
- me.tooltip._data = me.data;
-
- // Make sure dataset controllers are updated and new controllers are reset
- var newControllers = me.buildOrUpdateControllers();
-
- // Make sure all dataset controllers have correct meta data counts
- helpers$1.each(me.data.datasets, function(dataset, datasetIndex) {
- me.getDatasetMeta(datasetIndex).controller.buildOrUpdateElements();
- }, me);
-
- me.updateLayout();
-
- // Can only reset the new controllers after the scales have been updated
- if (me.options.animation && me.options.animation.duration) {
- helpers$1.each(newControllers, function(controller) {
- controller.reset();
- });
- }
-
- me.updateDatasets();
-
- // Need to reset tooltip in case it is displayed with elements that are removed
- // after update.
- me.tooltip.initialize();
-
- // Last active contains items that were previously in the tooltip.
- // When we reset the tooltip, we need to clear it
- me.lastActive = [];
-
- // Do this before render so that any plugins that need final scale updates can use it
- core_plugins.notify(me, 'afterUpdate');
-
- if (me._bufferedRender) {
- me._bufferedRequest = {
- duration: config.duration,
- easing: config.easing,
- lazy: config.lazy
- };
- } else {
- me.render(config);
- }
- },
-
- /**
- * Updates the chart layout unless a plugin returns `false` to the `beforeLayout`
- * hook, in which case, plugins will not be called on `afterLayout`.
- * @private
- */
- updateLayout: function() {
- var me = this;
-
- if (core_plugins.notify(me, 'beforeLayout') === false) {
- return;
- }
-
- core_layouts.update(this, this.width, this.height);
-
- /**
- * Provided for backward compatibility, use `afterLayout` instead.
- * @method IPlugin#afterScaleUpdate
- * @deprecated since version 2.5.0
- * @todo remove at version 3
- * @private
- */
- core_plugins.notify(me, 'afterScaleUpdate');
- core_plugins.notify(me, 'afterLayout');
- },
-
- /**
- * Updates all datasets unless a plugin returns `false` to the `beforeDatasetsUpdate`
- * hook, in which case, plugins will not be called on `afterDatasetsUpdate`.
- * @private
- */
- updateDatasets: function() {
- var me = this;
-
- if (core_plugins.notify(me, 'beforeDatasetsUpdate') === false) {
- return;
- }
-
- for (var i = 0, ilen = me.data.datasets.length; i < ilen; ++i) {
- me.updateDataset(i);
- }
-
- core_plugins.notify(me, 'afterDatasetsUpdate');
- },
-
- /**
- * Updates dataset at index unless a plugin returns `false` to the `beforeDatasetUpdate`
- * hook, in which case, plugins will not be called on `afterDatasetUpdate`.
- * @private
- */
- updateDataset: function(index) {
- var me = this;
- var meta = me.getDatasetMeta(index);
- var args = {
- meta: meta,
- index: index
- };
-
- if (core_plugins.notify(me, 'beforeDatasetUpdate', [args]) === false) {
- return;
- }
-
- meta.controller.update();
-
- core_plugins.notify(me, 'afterDatasetUpdate', [args]);
- },
-
- render: function(config) {
- var me = this;
-
- if (!config || typeof config !== 'object') {
- // backwards compatibility
- config = {
- duration: config,
- lazy: arguments[1]
- };
- }
-
- var animationOptions = me.options.animation;
- var duration = valueOrDefault$8(config.duration, animationOptions && animationOptions.duration);
- var lazy = config.lazy;
-
- if (core_plugins.notify(me, 'beforeRender') === false) {
- return;
- }
-
- var onComplete = function(animation) {
- core_plugins.notify(me, 'afterRender');
- helpers$1.callback(animationOptions && animationOptions.onComplete, [animation], me);
- };
-
- if (animationOptions && duration) {
- var animation = new core_animation({
- numSteps: duration / 16.66, // 60 fps
- easing: config.easing || animationOptions.easing,
-
- render: function(chart, animationObject) {
- var easingFunction = helpers$1.easing.effects[animationObject.easing];
- var currentStep = animationObject.currentStep;
- var stepDecimal = currentStep / animationObject.numSteps;
-
- chart.draw(easingFunction(stepDecimal), stepDecimal, currentStep);
- },
-
- onAnimationProgress: animationOptions.onProgress,
- onAnimationComplete: onComplete
- });
-
- core_animations.addAnimation(me, animation, duration, lazy);
- } else {
- me.draw();
-
- // See https://github.com/chartjs/Chart.js/issues/3781
- onComplete(new core_animation({numSteps: 0, chart: me}));
- }
-
- return me;
- },
-
- draw: function(easingValue) {
- var me = this;
-
- me.clear();
-
- if (helpers$1.isNullOrUndef(easingValue)) {
- easingValue = 1;
- }
-
- me.transition(easingValue);
-
- if (me.width <= 0 || me.height <= 0) {
- return;
- }
-
- if (core_plugins.notify(me, 'beforeDraw', [easingValue]) === false) {
- return;
- }
-
- // Draw all the scales
- helpers$1.each(me.boxes, function(box) {
- box.draw(me.chartArea);
- }, me);
-
- me.drawDatasets(easingValue);
- me._drawTooltip(easingValue);
-
- core_plugins.notify(me, 'afterDraw', [easingValue]);
- },
-
- /**
- * @private
- */
- transition: function(easingValue) {
- var me = this;
-
- for (var i = 0, ilen = (me.data.datasets || []).length; i < ilen; ++i) {
- if (me.isDatasetVisible(i)) {
- me.getDatasetMeta(i).controller.transition(easingValue);
- }
- }
-
- me.tooltip.transition(easingValue);
- },
-
- /**
- * Draws all datasets unless a plugin returns `false` to the `beforeDatasetsDraw`
- * hook, in which case, plugins will not be called on `afterDatasetsDraw`.
- * @private
- */
- drawDatasets: function(easingValue) {
- var me = this;
-
- if (core_plugins.notify(me, 'beforeDatasetsDraw', [easingValue]) === false) {
- return;
- }
-
- // Draw datasets reversed to support proper line stacking
- for (var i = (me.data.datasets || []).length - 1; i >= 0; --i) {
- if (me.isDatasetVisible(i)) {
- me.drawDataset(i, easingValue);
- }
- }
-
- core_plugins.notify(me, 'afterDatasetsDraw', [easingValue]);
- },
-
- /**
- * Draws dataset at index unless a plugin returns `false` to the `beforeDatasetDraw`
- * hook, in which case, plugins will not be called on `afterDatasetDraw`.
- * @private
- */
- drawDataset: function(index, easingValue) {
- var me = this;
- var meta = me.getDatasetMeta(index);
- var args = {
- meta: meta,
- index: index,
- easingValue: easingValue
- };
-
- if (core_plugins.notify(me, 'beforeDatasetDraw', [args]) === false) {
- return;
- }
-
- meta.controller.draw(easingValue);
-
- core_plugins.notify(me, 'afterDatasetDraw', [args]);
- },
-
- /**
- * Draws tooltip unless a plugin returns `false` to the `beforeTooltipDraw`
- * hook, in which case, plugins will not be called on `afterTooltipDraw`.
- * @private
- */
- _drawTooltip: function(easingValue) {
- var me = this;
- var tooltip = me.tooltip;
- var args = {
- tooltip: tooltip,
- easingValue: easingValue
- };
-
- if (core_plugins.notify(me, 'beforeTooltipDraw', [args]) === false) {
- return;
- }
-
- tooltip.draw();
-
- core_plugins.notify(me, 'afterTooltipDraw', [args]);
- },
-
- /**
- * Get the single element that was clicked on
- * @return An object containing the dataset index and element index of the matching element. Also contains the rectangle that was draw
- */
- getElementAtEvent: function(e) {
- return core_interaction.modes.single(this, e);
- },
-
- getElementsAtEvent: function(e) {
- return core_interaction.modes.label(this, e, {intersect: true});
- },
-
- getElementsAtXAxis: function(e) {
- return core_interaction.modes['x-axis'](this, e, {intersect: true});
- },
-
- getElementsAtEventForMode: function(e, mode, options) {
- var method = core_interaction.modes[mode];
- if (typeof method === 'function') {
- return method(this, e, options);
- }
-
- return [];
- },
-
- getDatasetAtEvent: function(e) {
- return core_interaction.modes.dataset(this, e, {intersect: true});
- },
-
- getDatasetMeta: function(datasetIndex) {
- var me = this;
- var dataset = me.data.datasets[datasetIndex];
- if (!dataset._meta) {
- dataset._meta = {};
- }
-
- var meta = dataset._meta[me.id];
- if (!meta) {
- meta = dataset._meta[me.id] = {
- type: null,
- data: [],
- dataset: null,
- controller: null,
- hidden: null, // See isDatasetVisible() comment
- xAxisID: null,
- yAxisID: null
- };
- }
-
- return meta;
- },
-
- getVisibleDatasetCount: function() {
- var count = 0;
- for (var i = 0, ilen = this.data.datasets.length; i < ilen; ++i) {
- if (this.isDatasetVisible(i)) {
- count++;
- }
- }
- return count;
- },
-
- isDatasetVisible: function(datasetIndex) {
- var meta = this.getDatasetMeta(datasetIndex);
-
- // meta.hidden is a per chart dataset hidden flag override with 3 states: if true or false,
- // the dataset.hidden value is ignored, else if null, the dataset hidden state is returned.
- return typeof meta.hidden === 'boolean' ? !meta.hidden : !this.data.datasets[datasetIndex].hidden;
- },
-
- generateLegend: function() {
- return this.options.legendCallback(this);
- },
-
- /**
- * @private
- */
- destroyDatasetMeta: function(datasetIndex) {
- var id = this.id;
- var dataset = this.data.datasets[datasetIndex];
- var meta = dataset._meta && dataset._meta[id];
-
- if (meta) {
- meta.controller.destroy();
- delete dataset._meta[id];
- }
- },
-
- destroy: function() {
- var me = this;
- var canvas = me.canvas;
- var i, ilen;
-
- me.stop();
-
- // dataset controllers need to cleanup associated data
- for (i = 0, ilen = me.data.datasets.length; i < ilen; ++i) {
- me.destroyDatasetMeta(i);
- }
-
- if (canvas) {
- me.unbindEvents();
- helpers$1.canvas.clear(me);
- platform.releaseContext(me.ctx);
- me.canvas = null;
- me.ctx = null;
- }
-
- core_plugins.notify(me, 'destroy');
-
- delete Chart.instances[me.id];
- },
-
- toBase64Image: function() {
- return this.canvas.toDataURL.apply(this.canvas, arguments);
- },
-
- initToolTip: function() {
- var me = this;
- me.tooltip = new core_tooltip({
- _chart: me,
- _chartInstance: me, // deprecated, backward compatibility
- _data: me.data,
- _options: me.options.tooltips
- }, me);
- },
-
- /**
- * @private
- */
- bindEvents: function() {
- var me = this;
- var listeners = me._listeners = {};
- var listener = function() {
- me.eventHandler.apply(me, arguments);
- };
-
- helpers$1.each(me.options.events, function(type) {
- platform.addEventListener(me, type, listener);
- listeners[type] = listener;
- });
-
- // Elements used to detect size change should not be injected for non responsive charts.
- // See https://github.com/chartjs/Chart.js/issues/2210
- if (me.options.responsive) {
- listener = function() {
- me.resize();
- };
-
- platform.addEventListener(me, 'resize', listener);
- listeners.resize = listener;
- }
- },
-
- /**
- * @private
- */
- unbindEvents: function() {
- var me = this;
- var listeners = me._listeners;
- if (!listeners) {
- return;
- }
-
- delete me._listeners;
- helpers$1.each(listeners, function(listener, type) {
- platform.removeEventListener(me, type, listener);
- });
- },
-
- updateHoverStyle: function(elements, mode, enabled) {
- var method = enabled ? 'setHoverStyle' : 'removeHoverStyle';
- var element, i, ilen;
-
- for (i = 0, ilen = elements.length; i < ilen; ++i) {
- element = elements[i];
- if (element) {
- this.getDatasetMeta(element._datasetIndex).controller[method](element);
- }
- }
- },
-
- /**
- * @private
- */
- eventHandler: function(e) {
- var me = this;
- var tooltip = me.tooltip;
-
- if (core_plugins.notify(me, 'beforeEvent', [e]) === false) {
- return;
- }
-
- // Buffer any update calls so that renders do not occur
- me._bufferedRender = true;
- me._bufferedRequest = null;
-
- var changed = me.handleEvent(e);
- // for smooth tooltip animations issue #4989
- // the tooltip should be the source of change
- // Animation check workaround:
- // tooltip._start will be null when tooltip isn't animating
- if (tooltip) {
- changed = tooltip._start
- ? tooltip.handleEvent(e)
- : changed | tooltip.handleEvent(e);
- }
-
- core_plugins.notify(me, 'afterEvent', [e]);
-
- var bufferedRequest = me._bufferedRequest;
- if (bufferedRequest) {
- // If we have an update that was triggered, we need to do a normal render
- me.render(bufferedRequest);
- } else if (changed && !me.animating) {
- // If entering, leaving, or changing elements, animate the change via pivot
- me.stop();
-
- // We only need to render at this point. Updating will cause scales to be
- // recomputed generating flicker & using more memory than necessary.
- me.render({
- duration: me.options.hover.animationDuration,
- lazy: true
- });
- }
-
- me._bufferedRender = false;
- me._bufferedRequest = null;
-
- return me;
- },
-
- /**
- * Handle an event
- * @private
- * @param {IEvent} event the event to handle
- * @return {boolean} true if the chart needs to re-render
- */
- handleEvent: function(e) {
- var me = this;
- var options = me.options || {};
- var hoverOptions = options.hover;
- var changed = false;
-
- me.lastActive = me.lastActive || [];
-
- // Find Active Elements for hover and tooltips
- if (e.type === 'mouseout') {
- me.active = [];
- } else {
- me.active = me.getElementsAtEventForMode(e, hoverOptions.mode, hoverOptions);
- }
-
- // Invoke onHover hook
- // Need to call with native event here to not break backwards compatibility
- helpers$1.callback(options.onHover || options.hover.onHover, [e.native, me.active], me);
-
- if (e.type === 'mouseup' || e.type === 'click') {
- if (options.onClick) {
- // Use e.native here for backwards compatibility
- options.onClick.call(me, e.native, me.active);
- }
- }
-
- // Remove styling for last active (even if it may still be active)
- if (me.lastActive.length) {
- me.updateHoverStyle(me.lastActive, hoverOptions.mode, false);
- }
-
- // Built in hover styling
- if (me.active.length && hoverOptions.mode) {
- me.updateHoverStyle(me.active, hoverOptions.mode, true);
- }
-
- changed = !helpers$1.arrayEquals(me.active, me.lastActive);
-
- // Remember Last Actives
- me.lastActive = me.active;
-
- return changed;
- }
-});
-
-/**
- * NOTE(SB) We actually don't use this container anymore but we need to keep it
- * for backward compatibility. Though, it can still be useful for plugins that
- * would need to work on multiple charts?!
- */
-Chart.instances = {};
-
-var core_controller = Chart;
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, use Chart instead.
- * @class Chart.Controller
- * @deprecated since version 2.6
- * @todo remove at version 3
- * @private
- */
-Chart.Controller = Chart;
-
-/**
- * Provided for backward compatibility, not available anymore.
- * @namespace Chart
- * @deprecated since version 2.8
- * @todo remove at version 3
- * @private
- */
-Chart.types = {};
-
-/**
- * Provided for backward compatibility, not available anymore.
- * @namespace Chart.helpers.configMerge
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- * @private
- */
-helpers$1.configMerge = mergeConfig;
-
-/**
- * Provided for backward compatibility, not available anymore.
- * @namespace Chart.helpers.scaleMerge
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- * @private
- */
-helpers$1.scaleMerge = mergeScaleConfig;
-
-var core_helpers = function() {
-
- // -- Basic js utility methods
-
- helpers$1.where = function(collection, filterCallback) {
- if (helpers$1.isArray(collection) && Array.prototype.filter) {
- return collection.filter(filterCallback);
- }
- var filtered = [];
-
- helpers$1.each(collection, function(item) {
- if (filterCallback(item)) {
- filtered.push(item);
- }
- });
-
- return filtered;
- };
- helpers$1.findIndex = Array.prototype.findIndex ?
- function(array, callback, scope) {
- return array.findIndex(callback, scope);
- } :
- function(array, callback, scope) {
- scope = scope === undefined ? array : scope;
- for (var i = 0, ilen = array.length; i < ilen; ++i) {
- if (callback.call(scope, array[i], i, array)) {
- return i;
- }
- }
- return -1;
- };
- helpers$1.findNextWhere = function(arrayToSearch, filterCallback, startIndex) {
- // Default to start of the array
- if (helpers$1.isNullOrUndef(startIndex)) {
- startIndex = -1;
- }
- for (var i = startIndex + 1; i < arrayToSearch.length; i++) {
- var currentItem = arrayToSearch[i];
- if (filterCallback(currentItem)) {
- return currentItem;
- }
- }
- };
- helpers$1.findPreviousWhere = function(arrayToSearch, filterCallback, startIndex) {
- // Default to end of the array
- if (helpers$1.isNullOrUndef(startIndex)) {
- startIndex = arrayToSearch.length;
- }
- for (var i = startIndex - 1; i >= 0; i--) {
- var currentItem = arrayToSearch[i];
- if (filterCallback(currentItem)) {
- return currentItem;
- }
- }
- };
-
- // -- Math methods
- helpers$1.isNumber = function(n) {
- return !isNaN(parseFloat(n)) && isFinite(n);
- };
- helpers$1.almostEquals = function(x, y, epsilon) {
- return Math.abs(x - y) < epsilon;
- };
- helpers$1.almostWhole = function(x, epsilon) {
- var rounded = Math.round(x);
- return (((rounded - epsilon) < x) && ((rounded + epsilon) > x));
- };
- helpers$1.max = function(array) {
- return array.reduce(function(max, value) {
- if (!isNaN(value)) {
- return Math.max(max, value);
- }
- return max;
- }, Number.NEGATIVE_INFINITY);
- };
- helpers$1.min = function(array) {
- return array.reduce(function(min, value) {
- if (!isNaN(value)) {
- return Math.min(min, value);
- }
- return min;
- }, Number.POSITIVE_INFINITY);
- };
- helpers$1.sign = Math.sign ?
- function(x) {
- return Math.sign(x);
- } :
- function(x) {
- x = +x; // convert to a number
- if (x === 0 || isNaN(x)) {
- return x;
- }
- return x > 0 ? 1 : -1;
- };
- helpers$1.log10 = Math.log10 ?
- function(x) {
- return Math.log10(x);
- } :
- function(x) {
- var exponent = Math.log(x) * Math.LOG10E; // Math.LOG10E = 1 / Math.LN10.
- // Check for whole powers of 10,
- // which due to floating point rounding error should be corrected.
- var powerOf10 = Math.round(exponent);
- var isPowerOf10 = x === Math.pow(10, powerOf10);
-
- return isPowerOf10 ? powerOf10 : exponent;
- };
- helpers$1.toRadians = function(degrees) {
- return degrees * (Math.PI / 180);
- };
- helpers$1.toDegrees = function(radians) {
- return radians * (180 / Math.PI);
- };
-
- /**
- * Returns the number of decimal places
- * i.e. the number of digits after the decimal point, of the value of this Number.
- * @param {number} x - A number.
- * @returns {number} The number of decimal places.
- * @private
- */
- helpers$1._decimalPlaces = function(x) {
- if (!helpers$1.isFinite(x)) {
- return;
- }
- var e = 1;
- var p = 0;
- while (Math.round(x * e) / e !== x) {
- e *= 10;
- p++;
- }
- return p;
- };
-
- // Gets the angle from vertical upright to the point about a centre.
- helpers$1.getAngleFromPoint = function(centrePoint, anglePoint) {
- var distanceFromXCenter = anglePoint.x - centrePoint.x;
- var distanceFromYCenter = anglePoint.y - centrePoint.y;
- var radialDistanceFromCenter = Math.sqrt(distanceFromXCenter * distanceFromXCenter + distanceFromYCenter * distanceFromYCenter);
-
- var angle = Math.atan2(distanceFromYCenter, distanceFromXCenter);
-
- if (angle < (-0.5 * Math.PI)) {
- angle += 2.0 * Math.PI; // make sure the returned angle is in the range of (-PI/2, 3PI/2]
- }
-
- return {
- angle: angle,
- distance: radialDistanceFromCenter
- };
- };
- helpers$1.distanceBetweenPoints = function(pt1, pt2) {
- return Math.sqrt(Math.pow(pt2.x - pt1.x, 2) + Math.pow(pt2.y - pt1.y, 2));
- };
-
- /**
- * Provided for backward compatibility, not available anymore
- * @function Chart.helpers.aliasPixel
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- */
- helpers$1.aliasPixel = function(pixelWidth) {
- return (pixelWidth % 2 === 0) ? 0 : 0.5;
- };
-
- /**
- * Returns the aligned pixel value to avoid anti-aliasing blur
- * @param {Chart} chart - The chart instance.
- * @param {number} pixel - A pixel value.
- * @param {number} width - The width of the element.
- * @returns {number} The aligned pixel value.
- * @private
- */
- helpers$1._alignPixel = function(chart, pixel, width) {
- var devicePixelRatio = chart.currentDevicePixelRatio;
- var halfWidth = width / 2;
- return Math.round((pixel - halfWidth) * devicePixelRatio) / devicePixelRatio + halfWidth;
- };
-
- helpers$1.splineCurve = function(firstPoint, middlePoint, afterPoint, t) {
- // Props to Rob Spencer at scaled innovation for his post on splining between points
- // http://scaledinnovation.com/analytics/splines/aboutSplines.html
-
- // This function must also respect "skipped" points
-
- var previous = firstPoint.skip ? middlePoint : firstPoint;
- var current = middlePoint;
- var next = afterPoint.skip ? middlePoint : afterPoint;
-
- var d01 = Math.sqrt(Math.pow(current.x - previous.x, 2) + Math.pow(current.y - previous.y, 2));
- var d12 = Math.sqrt(Math.pow(next.x - current.x, 2) + Math.pow(next.y - current.y, 2));
-
- var s01 = d01 / (d01 + d12);
- var s12 = d12 / (d01 + d12);
-
- // If all points are the same, s01 & s02 will be inf
- s01 = isNaN(s01) ? 0 : s01;
- s12 = isNaN(s12) ? 0 : s12;
-
- var fa = t * s01; // scaling factor for triangle Ta
- var fb = t * s12;
-
- return {
- previous: {
- x: current.x - fa * (next.x - previous.x),
- y: current.y - fa * (next.y - previous.y)
- },
- next: {
- x: current.x + fb * (next.x - previous.x),
- y: current.y + fb * (next.y - previous.y)
- }
- };
- };
- helpers$1.EPSILON = Number.EPSILON || 1e-14;
- helpers$1.splineCurveMonotone = function(points) {
- // This function calculates Bézier control points in a similar way than |splineCurve|,
- // but preserves monotonicity of the provided data and ensures no local extremums are added
- // between the dataset discrete points due to the interpolation.
- // See : https://en.wikipedia.org/wiki/Monotone_cubic_interpolation
-
- var pointsWithTangents = (points || []).map(function(point) {
- return {
- model: point._model,
- deltaK: 0,
- mK: 0
- };
- });
-
- // Calculate slopes (deltaK) and initialize tangents (mK)
- var pointsLen = pointsWithTangents.length;
- var i, pointBefore, pointCurrent, pointAfter;
- for (i = 0; i < pointsLen; ++i) {
- pointCurrent = pointsWithTangents[i];
- if (pointCurrent.model.skip) {
- continue;
- }
-
- pointBefore = i > 0 ? pointsWithTangents[i - 1] : null;
- pointAfter = i < pointsLen - 1 ? pointsWithTangents[i + 1] : null;
- if (pointAfter && !pointAfter.model.skip) {
- var slopeDeltaX = (pointAfter.model.x - pointCurrent.model.x);
-
- // In the case of two points that appear at the same x pixel, slopeDeltaX is 0
- pointCurrent.deltaK = slopeDeltaX !== 0 ? (pointAfter.model.y - pointCurrent.model.y) / slopeDeltaX : 0;
- }
-
- if (!pointBefore || pointBefore.model.skip) {
- pointCurrent.mK = pointCurrent.deltaK;
- } else if (!pointAfter || pointAfter.model.skip) {
- pointCurrent.mK = pointBefore.deltaK;
- } else if (this.sign(pointBefore.deltaK) !== this.sign(pointCurrent.deltaK)) {
- pointCurrent.mK = 0;
- } else {
- pointCurrent.mK = (pointBefore.deltaK + pointCurrent.deltaK) / 2;
- }
- }
-
- // Adjust tangents to ensure monotonic properties
- var alphaK, betaK, tauK, squaredMagnitude;
- for (i = 0; i < pointsLen - 1; ++i) {
- pointCurrent = pointsWithTangents[i];
- pointAfter = pointsWithTangents[i + 1];
- if (pointCurrent.model.skip || pointAfter.model.skip) {
- continue;
- }
-
- if (helpers$1.almostEquals(pointCurrent.deltaK, 0, this.EPSILON)) {
- pointCurrent.mK = pointAfter.mK = 0;
- continue;
- }
-
- alphaK = pointCurrent.mK / pointCurrent.deltaK;
- betaK = pointAfter.mK / pointCurrent.deltaK;
- squaredMagnitude = Math.pow(alphaK, 2) + Math.pow(betaK, 2);
- if (squaredMagnitude <= 9) {
- continue;
- }
-
- tauK = 3 / Math.sqrt(squaredMagnitude);
- pointCurrent.mK = alphaK * tauK * pointCurrent.deltaK;
- pointAfter.mK = betaK * tauK * pointCurrent.deltaK;
- }
-
- // Compute control points
- var deltaX;
- for (i = 0; i < pointsLen; ++i) {
- pointCurrent = pointsWithTangents[i];
- if (pointCurrent.model.skip) {
- continue;
- }
-
- pointBefore = i > 0 ? pointsWithTangents[i - 1] : null;
- pointAfter = i < pointsLen - 1 ? pointsWithTangents[i + 1] : null;
- if (pointBefore && !pointBefore.model.skip) {
- deltaX = (pointCurrent.model.x - pointBefore.model.x) / 3;
- pointCurrent.model.controlPointPreviousX = pointCurrent.model.x - deltaX;
- pointCurrent.model.controlPointPreviousY = pointCurrent.model.y - deltaX * pointCurrent.mK;
- }
- if (pointAfter && !pointAfter.model.skip) {
- deltaX = (pointAfter.model.x - pointCurrent.model.x) / 3;
- pointCurrent.model.controlPointNextX = pointCurrent.model.x + deltaX;
- pointCurrent.model.controlPointNextY = pointCurrent.model.y + deltaX * pointCurrent.mK;
- }
- }
- };
- helpers$1.nextItem = function(collection, index, loop) {
- if (loop) {
- return index >= collection.length - 1 ? collection[0] : collection[index + 1];
- }
- return index >= collection.length - 1 ? collection[collection.length - 1] : collection[index + 1];
- };
- helpers$1.previousItem = function(collection, index, loop) {
- if (loop) {
- return index <= 0 ? collection[collection.length - 1] : collection[index - 1];
- }
- return index <= 0 ? collection[0] : collection[index - 1];
- };
- // Implementation of the nice number algorithm used in determining where axis labels will go
- helpers$1.niceNum = function(range, round) {
- var exponent = Math.floor(helpers$1.log10(range));
- var fraction = range / Math.pow(10, exponent);
- var niceFraction;
-
- if (round) {
- if (fraction < 1.5) {
- niceFraction = 1;
- } else if (fraction < 3) {
- niceFraction = 2;
- } else if (fraction < 7) {
- niceFraction = 5;
- } else {
- niceFraction = 10;
- }
- } else if (fraction <= 1.0) {
- niceFraction = 1;
- } else if (fraction <= 2) {
- niceFraction = 2;
- } else if (fraction <= 5) {
- niceFraction = 5;
- } else {
- niceFraction = 10;
- }
-
- return niceFraction * Math.pow(10, exponent);
- };
- // Request animation polyfill - https://www.paulirish.com/2011/requestanimationframe-for-smart-animating/
- helpers$1.requestAnimFrame = (function() {
- if (typeof window === 'undefined') {
- return function(callback) {
- callback();
- };
- }
- return window.requestAnimationFrame ||
- window.webkitRequestAnimationFrame ||
- window.mozRequestAnimationFrame ||
- window.oRequestAnimationFrame ||
- window.msRequestAnimationFrame ||
- function(callback) {
- return window.setTimeout(callback, 1000 / 60);
- };
- }());
- // -- DOM methods
- helpers$1.getRelativePosition = function(evt, chart) {
- var mouseX, mouseY;
- var e = evt.originalEvent || evt;
- var canvas = evt.target || evt.srcElement;
- var boundingRect = canvas.getBoundingClientRect();
-
- var touches = e.touches;
- if (touches && touches.length > 0) {
- mouseX = touches[0].clientX;
- mouseY = touches[0].clientY;
-
- } else {
- mouseX = e.clientX;
- mouseY = e.clientY;
- }
-
- // Scale mouse coordinates into canvas coordinates
- // by following the pattern laid out by 'jerryj' in the comments of
- // https://www.html5canvastutorials.com/advanced/html5-canvas-mouse-coordinates/
- var paddingLeft = parseFloat(helpers$1.getStyle(canvas, 'padding-left'));
- var paddingTop = parseFloat(helpers$1.getStyle(canvas, 'padding-top'));
- var paddingRight = parseFloat(helpers$1.getStyle(canvas, 'padding-right'));
- var paddingBottom = parseFloat(helpers$1.getStyle(canvas, 'padding-bottom'));
- var width = boundingRect.right - boundingRect.left - paddingLeft - paddingRight;
- var height = boundingRect.bottom - boundingRect.top - paddingTop - paddingBottom;
-
- // We divide by the current device pixel ratio, because the canvas is scaled up by that amount in each direction. However
- // the backend model is in unscaled coordinates. Since we are going to deal with our model coordinates, we go back here
- mouseX = Math.round((mouseX - boundingRect.left - paddingLeft) / (width) * canvas.width / chart.currentDevicePixelRatio);
- mouseY = Math.round((mouseY - boundingRect.top - paddingTop) / (height) * canvas.height / chart.currentDevicePixelRatio);
-
- return {
- x: mouseX,
- y: mouseY
- };
-
- };
-
- // Private helper function to convert max-width/max-height values that may be percentages into a number
- function parseMaxStyle(styleValue, node, parentProperty) {
- var valueInPixels;
- if (typeof styleValue === 'string') {
- valueInPixels = parseInt(styleValue, 10);
-
- if (styleValue.indexOf('%') !== -1) {
- // percentage * size in dimension
- valueInPixels = valueInPixels / 100 * node.parentNode[parentProperty];
- }
- } else {
- valueInPixels = styleValue;
- }
-
- return valueInPixels;
- }
-
- /**
- * Returns if the given value contains an effective constraint.
- * @private
- */
- function isConstrainedValue(value) {
- return value !== undefined && value !== null && value !== 'none';
- }
-
- /**
- * Returns the max width or height of the given DOM node in a cross-browser compatible fashion
- * @param {HTMLElement} domNode - the node to check the constraint on
- * @param {string} maxStyle - the style that defines the maximum for the direction we are using ('max-width' / 'max-height')
- * @param {string} percentageProperty - property of parent to use when calculating width as a percentage
- * @see {@link https://www.nathanaeljones.com/blog/2013/reading-max-width-cross-browser}
- */
- function getConstraintDimension(domNode, maxStyle, percentageProperty) {
- var view = document.defaultView;
- var parentNode = helpers$1._getParentNode(domNode);
- var constrainedNode = view.getComputedStyle(domNode)[maxStyle];
- var constrainedContainer = view.getComputedStyle(parentNode)[maxStyle];
- var hasCNode = isConstrainedValue(constrainedNode);
- var hasCContainer = isConstrainedValue(constrainedContainer);
- var infinity = Number.POSITIVE_INFINITY;
-
- if (hasCNode || hasCContainer) {
- return Math.min(
- hasCNode ? parseMaxStyle(constrainedNode, domNode, percentageProperty) : infinity,
- hasCContainer ? parseMaxStyle(constrainedContainer, parentNode, percentageProperty) : infinity);
- }
-
- return 'none';
- }
- // returns Number or undefined if no constraint
- helpers$1.getConstraintWidth = function(domNode) {
- return getConstraintDimension(domNode, 'max-width', 'clientWidth');
- };
- // returns Number or undefined if no constraint
- helpers$1.getConstraintHeight = function(domNode) {
- return getConstraintDimension(domNode, 'max-height', 'clientHeight');
- };
- /**
- * @private
- */
- helpers$1._calculatePadding = function(container, padding, parentDimension) {
- padding = helpers$1.getStyle(container, padding);
-
- return padding.indexOf('%') > -1 ? parentDimension * parseInt(padding, 10) / 100 : parseInt(padding, 10);
- };
- /**
- * @private
- */
- helpers$1._getParentNode = function(domNode) {
- var parent = domNode.parentNode;
- if (parent && parent.toString() === '[object ShadowRoot]') {
- parent = parent.host;
- }
- return parent;
- };
- helpers$1.getMaximumWidth = function(domNode) {
- var container = helpers$1._getParentNode(domNode);
- if (!container) {
- return domNode.clientWidth;
- }
-
- var clientWidth = container.clientWidth;
- var paddingLeft = helpers$1._calculatePadding(container, 'padding-left', clientWidth);
- var paddingRight = helpers$1._calculatePadding(container, 'padding-right', clientWidth);
-
- var w = clientWidth - paddingLeft - paddingRight;
- var cw = helpers$1.getConstraintWidth(domNode);
- return isNaN(cw) ? w : Math.min(w, cw);
- };
- helpers$1.getMaximumHeight = function(domNode) {
- var container = helpers$1._getParentNode(domNode);
- if (!container) {
- return domNode.clientHeight;
- }
-
- var clientHeight = container.clientHeight;
- var paddingTop = helpers$1._calculatePadding(container, 'padding-top', clientHeight);
- var paddingBottom = helpers$1._calculatePadding(container, 'padding-bottom', clientHeight);
-
- var h = clientHeight - paddingTop - paddingBottom;
- var ch = helpers$1.getConstraintHeight(domNode);
- return isNaN(ch) ? h : Math.min(h, ch);
- };
- helpers$1.getStyle = function(el, property) {
- return el.currentStyle ?
- el.currentStyle[property] :
- document.defaultView.getComputedStyle(el, null).getPropertyValue(property);
- };
- helpers$1.retinaScale = function(chart, forceRatio) {
- var pixelRatio = chart.currentDevicePixelRatio = forceRatio || (typeof window !== 'undefined' && window.devicePixelRatio) || 1;
- if (pixelRatio === 1) {
- return;
- }
-
- var canvas = chart.canvas;
- var height = chart.height;
- var width = chart.width;
-
- canvas.height = height * pixelRatio;
- canvas.width = width * pixelRatio;
- chart.ctx.scale(pixelRatio, pixelRatio);
-
- // If no style has been set on the canvas, the render size is used as display size,
- // making the chart visually bigger, so let's enforce it to the "correct" values.
- // See https://github.com/chartjs/Chart.js/issues/3575
- if (!canvas.style.height && !canvas.style.width) {
- canvas.style.height = height + 'px';
- canvas.style.width = width + 'px';
- }
- };
- // -- Canvas methods
- helpers$1.fontString = function(pixelSize, fontStyle, fontFamily) {
- return fontStyle + ' ' + pixelSize + 'px ' + fontFamily;
- };
- helpers$1.longestText = function(ctx, font, arrayOfThings, cache) {
- cache = cache || {};
- var data = cache.data = cache.data || {};
- var gc = cache.garbageCollect = cache.garbageCollect || [];
-
- if (cache.font !== font) {
- data = cache.data = {};
- gc = cache.garbageCollect = [];
- cache.font = font;
- }
-
- ctx.font = font;
- var longest = 0;
- helpers$1.each(arrayOfThings, function(thing) {
- // Undefined strings and arrays should not be measured
- if (thing !== undefined && thing !== null && helpers$1.isArray(thing) !== true) {
- longest = helpers$1.measureText(ctx, data, gc, longest, thing);
- } else if (helpers$1.isArray(thing)) {
- // if it is an array lets measure each element
- // to do maybe simplify this function a bit so we can do this more recursively?
- helpers$1.each(thing, function(nestedThing) {
- // Undefined strings and arrays should not be measured
- if (nestedThing !== undefined && nestedThing !== null && !helpers$1.isArray(nestedThing)) {
- longest = helpers$1.measureText(ctx, data, gc, longest, nestedThing);
- }
- });
- }
- });
-
- var gcLen = gc.length / 2;
- if (gcLen > arrayOfThings.length) {
- for (var i = 0; i < gcLen; i++) {
- delete data[gc[i]];
- }
- gc.splice(0, gcLen);
- }
- return longest;
- };
- helpers$1.measureText = function(ctx, data, gc, longest, string) {
- var textWidth = data[string];
- if (!textWidth) {
- textWidth = data[string] = ctx.measureText(string).width;
- gc.push(string);
- }
- if (textWidth > longest) {
- longest = textWidth;
- }
- return longest;
- };
- helpers$1.numberOfLabelLines = function(arrayOfThings) {
- var numberOfLines = 1;
- helpers$1.each(arrayOfThings, function(thing) {
- if (helpers$1.isArray(thing)) {
- if (thing.length > numberOfLines) {
- numberOfLines = thing.length;
- }
- }
- });
- return numberOfLines;
- };
-
- helpers$1.color = !chartjsColor ?
- function(value) {
- console.error('Color.js not found!');
- return value;
- } :
- function(value) {
- /* global CanvasGradient */
- if (value instanceof CanvasGradient) {
- value = core_defaults.global.defaultColor;
- }
-
- return chartjsColor(value);
- };
-
- helpers$1.getHoverColor = function(colorValue) {
- /* global CanvasPattern */
- return (colorValue instanceof CanvasPattern || colorValue instanceof CanvasGradient) ?
- colorValue :
- helpers$1.color(colorValue).saturate(0.5).darken(0.1).rgbString();
- };
-};
-
-function abstract() {
- throw new Error(
- 'This method is not implemented: either no adapter can ' +
- 'be found or an incomplete integration was provided.'
- );
-}
-
-/**
- * Date adapter (current used by the time scale)
- * @namespace Chart._adapters._date
- * @memberof Chart._adapters
- * @private
- */
-
-/**
- * Currently supported unit string values.
- * @typedef {('millisecond'|'second'|'minute'|'hour'|'day'|'week'|'month'|'quarter'|'year')}
- * @memberof Chart._adapters._date
- * @name Unit
- */
-
-/**
- * @class
- */
-function DateAdapter(options) {
- this.options = options || {};
-}
-
-helpers$1.extend(DateAdapter.prototype, /** @lends DateAdapter */ {
- /**
- * Returns a map of time formats for the supported formatting units defined
- * in Unit as well as 'datetime' representing a detailed date/time string.
- * @returns {{string: string}}
- */
- formats: abstract,
-
- /**
- * Parses the given `value` and return the associated timestamp.
- * @param {any} value - the value to parse (usually comes from the data)
- * @param {string} [format] - the expected data format
- * @returns {(number|null)}
- * @function
- */
- parse: abstract,
-
- /**
- * Returns the formatted date in the specified `format` for a given `timestamp`.
- * @param {number} timestamp - the timestamp to format
- * @param {string} format - the date/time token
- * @return {string}
- * @function
- */
- format: abstract,
-
- /**
- * Adds the specified `amount` of `unit` to the given `timestamp`.
- * @param {number} timestamp - the input timestamp
- * @param {number} amount - the amount to add
- * @param {Unit} unit - the unit as string
- * @return {number}
- * @function
- */
- add: abstract,
-
- /**
- * Returns the number of `unit` between the given timestamps.
- * @param {number} max - the input timestamp (reference)
- * @param {number} min - the timestamp to substract
- * @param {Unit} unit - the unit as string
- * @return {number}
- * @function
- */
- diff: abstract,
-
- /**
- * Returns start of `unit` for the given `timestamp`.
- * @param {number} timestamp - the input timestamp
- * @param {Unit} unit - the unit as string
- * @param {number} [weekday] - the ISO day of the week with 1 being Monday
- * and 7 being Sunday (only needed if param *unit* is `isoWeek`).
- * @function
- */
- startOf: abstract,
-
- /**
- * Returns end of `unit` for the given `timestamp`.
- * @param {number} timestamp - the input timestamp
- * @param {Unit} unit - the unit as string
- * @function
- */
- endOf: abstract,
-
- // DEPRECATIONS
-
- /**
- * Provided for backward compatibility for scale.getValueForPixel(),
- * this method should be overridden only by the moment adapter.
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- * @private
- */
- _create: function(value) {
- return value;
- }
-});
-
-DateAdapter.override = function(members) {
- helpers$1.extend(DateAdapter.prototype, members);
-};
-
-var _date = DateAdapter;
-
-var core_adapters = {
- _date: _date
-};
-
-/**
- * Namespace to hold static tick generation functions
- * @namespace Chart.Ticks
- */
-var core_ticks = {
- /**
- * Namespace to hold formatters for different types of ticks
- * @namespace Chart.Ticks.formatters
- */
- formatters: {
- /**
- * Formatter for value labels
- * @method Chart.Ticks.formatters.values
- * @param value the value to display
- * @return {string|string[]} the label to display
- */
- values: function(value) {
- return helpers$1.isArray(value) ? value : '' + value;
- },
-
- /**
- * Formatter for linear numeric ticks
- * @method Chart.Ticks.formatters.linear
- * @param tickValue {number} the value to be formatted
- * @param index {number} the position of the tickValue parameter in the ticks array
- * @param ticks {number[]} the list of ticks being converted
- * @return {string} string representation of the tickValue parameter
- */
- linear: function(tickValue, index, ticks) {
- // If we have lots of ticks, don't use the ones
- var delta = ticks.length > 3 ? ticks[2] - ticks[1] : ticks[1] - ticks[0];
-
- // If we have a number like 2.5 as the delta, figure out how many decimal places we need
- if (Math.abs(delta) > 1) {
- if (tickValue !== Math.floor(tickValue)) {
- // not an integer
- delta = tickValue - Math.floor(tickValue);
- }
- }
-
- var logDelta = helpers$1.log10(Math.abs(delta));
- var tickString = '';
-
- if (tickValue !== 0) {
- var maxTick = Math.max(Math.abs(ticks[0]), Math.abs(ticks[ticks.length - 1]));
- if (maxTick < 1e-4) { // all ticks are small numbers; use scientific notation
- var logTick = helpers$1.log10(Math.abs(tickValue));
- tickString = tickValue.toExponential(Math.floor(logTick) - Math.floor(logDelta));
- } else {
- var numDecimal = -1 * Math.floor(logDelta);
- numDecimal = Math.max(Math.min(numDecimal, 20), 0); // toFixed has a max of 20 decimal places
- tickString = tickValue.toFixed(numDecimal);
- }
- } else {
- tickString = '0'; // never show decimal places for 0
- }
-
- return tickString;
- },
-
- logarithmic: function(tickValue, index, ticks) {
- var remain = tickValue / (Math.pow(10, Math.floor(helpers$1.log10(tickValue))));
-
- if (tickValue === 0) {
- return '0';
- } else if (remain === 1 || remain === 2 || remain === 5 || index === 0 || index === ticks.length - 1) {
- return tickValue.toExponential();
- }
- return '';
- }
- }
-};
-
-var valueOrDefault$9 = helpers$1.valueOrDefault;
-var valueAtIndexOrDefault = helpers$1.valueAtIndexOrDefault;
-
-core_defaults._set('scale', {
- display: true,
- position: 'left',
- offset: false,
-
- // grid line settings
- gridLines: {
- display: true,
- color: 'rgba(0, 0, 0, 0.1)',
- lineWidth: 1,
- drawBorder: true,
- drawOnChartArea: true,
- drawTicks: true,
- tickMarkLength: 10,
- zeroLineWidth: 1,
- zeroLineColor: 'rgba(0,0,0,0.25)',
- zeroLineBorderDash: [],
- zeroLineBorderDashOffset: 0.0,
- offsetGridLines: false,
- borderDash: [],
- borderDashOffset: 0.0
- },
-
- // scale label
- scaleLabel: {
- // display property
- display: false,
-
- // actual label
- labelString: '',
-
- // top/bottom padding
- padding: {
- top: 4,
- bottom: 4
- }
- },
-
- // label settings
- ticks: {
- beginAtZero: false,
- minRotation: 0,
- maxRotation: 50,
- mirror: false,
- padding: 0,
- reverse: false,
- display: true,
- autoSkip: true,
- autoSkipPadding: 0,
- labelOffset: 0,
- // We pass through arrays to be rendered as multiline labels, we convert Others to strings here.
- callback: core_ticks.formatters.values,
- minor: {},
- major: {}
- }
-});
-
-function labelsFromTicks(ticks) {
- var labels = [];
- var i, ilen;
-
- for (i = 0, ilen = ticks.length; i < ilen; ++i) {
- labels.push(ticks[i].label);
- }
-
- return labels;
-}
-
-function getPixelForGridLine(scale, index, offsetGridLines) {
- var lineValue = scale.getPixelForTick(index);
-
- if (offsetGridLines) {
- if (scale.getTicks().length === 1) {
- lineValue -= scale.isHorizontal() ?
- Math.max(lineValue - scale.left, scale.right - lineValue) :
- Math.max(lineValue - scale.top, scale.bottom - lineValue);
- } else if (index === 0) {
- lineValue -= (scale.getPixelForTick(1) - lineValue) / 2;
- } else {
- lineValue -= (lineValue - scale.getPixelForTick(index - 1)) / 2;
- }
- }
- return lineValue;
-}
-
-function computeTextSize(context, tick, font) {
- return helpers$1.isArray(tick) ?
- helpers$1.longestText(context, font, tick) :
- context.measureText(tick).width;
-}
-
-var core_scale = core_element.extend({
- /**
- * Get the padding needed for the scale
- * @method getPadding
- * @private
- * @returns {Padding} the necessary padding
- */
- getPadding: function() {
- var me = this;
- return {
- left: me.paddingLeft || 0,
- top: me.paddingTop || 0,
- right: me.paddingRight || 0,
- bottom: me.paddingBottom || 0
- };
- },
-
- /**
- * Returns the scale tick objects ({label, major})
- * @since 2.7
- */
- getTicks: function() {
- return this._ticks;
- },
-
- // These methods are ordered by lifecyle. Utilities then follow.
- // Any function defined here is inherited by all scale types.
- // Any function can be extended by the scale type
-
- mergeTicksOptions: function() {
- var ticks = this.options.ticks;
- if (ticks.minor === false) {
- ticks.minor = {
- display: false
- };
- }
- if (ticks.major === false) {
- ticks.major = {
- display: false
- };
- }
- for (var key in ticks) {
- if (key !== 'major' && key !== 'minor') {
- if (typeof ticks.minor[key] === 'undefined') {
- ticks.minor[key] = ticks[key];
- }
- if (typeof ticks.major[key] === 'undefined') {
- ticks.major[key] = ticks[key];
- }
- }
- }
- },
- beforeUpdate: function() {
- helpers$1.callback(this.options.beforeUpdate, [this]);
- },
-
- update: function(maxWidth, maxHeight, margins) {
- var me = this;
- var i, ilen, labels, label, ticks, tick;
-
- // Update Lifecycle - Probably don't want to ever extend or overwrite this function ;)
- me.beforeUpdate();
-
- // Absorb the master measurements
- me.maxWidth = maxWidth;
- me.maxHeight = maxHeight;
- me.margins = helpers$1.extend({
- left: 0,
- right: 0,
- top: 0,
- bottom: 0
- }, margins);
-
- me._maxLabelLines = 0;
- me.longestLabelWidth = 0;
- me.longestTextCache = me.longestTextCache || {};
-
- // Dimensions
- me.beforeSetDimensions();
- me.setDimensions();
- me.afterSetDimensions();
-
- // Data min/max
- me.beforeDataLimits();
- me.determineDataLimits();
- me.afterDataLimits();
-
- // Ticks - `this.ticks` is now DEPRECATED!
- // Internal ticks are now stored as objects in the PRIVATE `this._ticks` member
- // and must not be accessed directly from outside this class. `this.ticks` being
- // around for long time and not marked as private, we can't change its structure
- // without unexpected breaking changes. If you need to access the scale ticks,
- // use scale.getTicks() instead.
-
- me.beforeBuildTicks();
-
- // New implementations should return an array of objects but for BACKWARD COMPAT,
- // we still support no return (`this.ticks` internally set by calling this method).
- ticks = me.buildTicks() || [];
-
- // Allow modification of ticks in callback.
- ticks = me.afterBuildTicks(ticks) || ticks;
-
- me.beforeTickToLabelConversion();
-
- // New implementations should return the formatted tick labels but for BACKWARD
- // COMPAT, we still support no return (`this.ticks` internally changed by calling
- // this method and supposed to contain only string values).
- labels = me.convertTicksToLabels(ticks) || me.ticks;
-
- me.afterTickToLabelConversion();
-
- me.ticks = labels; // BACKWARD COMPATIBILITY
-
- // IMPORTANT: from this point, we consider that `this.ticks` will NEVER change!
-
- // BACKWARD COMPAT: synchronize `_ticks` with labels (so potentially `this.ticks`)
- for (i = 0, ilen = labels.length; i < ilen; ++i) {
- label = labels[i];
- tick = ticks[i];
- if (!tick) {
- ticks.push(tick = {
- label: label,
- major: false
- });
- } else {
- tick.label = label;
- }
- }
-
- me._ticks = ticks;
-
- // Tick Rotation
- me.beforeCalculateTickRotation();
- me.calculateTickRotation();
- me.afterCalculateTickRotation();
- // Fit
- me.beforeFit();
- me.fit();
- me.afterFit();
- //
- me.afterUpdate();
-
- return me.minSize;
-
- },
- afterUpdate: function() {
- helpers$1.callback(this.options.afterUpdate, [this]);
- },
-
- //
-
- beforeSetDimensions: function() {
- helpers$1.callback(this.options.beforeSetDimensions, [this]);
- },
- setDimensions: function() {
- var me = this;
- // Set the unconstrained dimension before label rotation
- if (me.isHorizontal()) {
- // Reset position before calculating rotation
- me.width = me.maxWidth;
- me.left = 0;
- me.right = me.width;
- } else {
- me.height = me.maxHeight;
-
- // Reset position before calculating rotation
- me.top = 0;
- me.bottom = me.height;
- }
-
- // Reset padding
- me.paddingLeft = 0;
- me.paddingTop = 0;
- me.paddingRight = 0;
- me.paddingBottom = 0;
- },
- afterSetDimensions: function() {
- helpers$1.callback(this.options.afterSetDimensions, [this]);
- },
-
- // Data limits
- beforeDataLimits: function() {
- helpers$1.callback(this.options.beforeDataLimits, [this]);
- },
- determineDataLimits: helpers$1.noop,
- afterDataLimits: function() {
- helpers$1.callback(this.options.afterDataLimits, [this]);
- },
-
- //
- beforeBuildTicks: function() {
- helpers$1.callback(this.options.beforeBuildTicks, [this]);
- },
- buildTicks: helpers$1.noop,
- afterBuildTicks: function(ticks) {
- var me = this;
- // ticks is empty for old axis implementations here
- if (helpers$1.isArray(ticks) && ticks.length) {
- return helpers$1.callback(me.options.afterBuildTicks, [me, ticks]);
- }
- // Support old implementations (that modified `this.ticks` directly in buildTicks)
- me.ticks = helpers$1.callback(me.options.afterBuildTicks, [me, me.ticks]) || me.ticks;
- return ticks;
- },
-
- beforeTickToLabelConversion: function() {
- helpers$1.callback(this.options.beforeTickToLabelConversion, [this]);
- },
- convertTicksToLabels: function() {
- var me = this;
- // Convert ticks to strings
- var tickOpts = me.options.ticks;
- me.ticks = me.ticks.map(tickOpts.userCallback || tickOpts.callback, this);
- },
- afterTickToLabelConversion: function() {
- helpers$1.callback(this.options.afterTickToLabelConversion, [this]);
- },
-
- //
-
- beforeCalculateTickRotation: function() {
- helpers$1.callback(this.options.beforeCalculateTickRotation, [this]);
- },
- calculateTickRotation: function() {
- var me = this;
- var context = me.ctx;
- var tickOpts = me.options.ticks;
- var labels = labelsFromTicks(me._ticks);
-
- // Get the width of each grid by calculating the difference
- // between x offsets between 0 and 1.
- var tickFont = helpers$1.options._parseFont(tickOpts);
- context.font = tickFont.string;
-
- var labelRotation = tickOpts.minRotation || 0;
-
- if (labels.length && me.options.display && me.isHorizontal()) {
- var originalLabelWidth = helpers$1.longestText(context, tickFont.string, labels, me.longestTextCache);
- var labelWidth = originalLabelWidth;
- var cosRotation, sinRotation;
-
- // Allow 3 pixels x2 padding either side for label readability
- var tickWidth = me.getPixelForTick(1) - me.getPixelForTick(0) - 6;
-
- // Max label rotation can be set or default to 90 - also act as a loop counter
- while (labelWidth > tickWidth && labelRotation < tickOpts.maxRotation) {
- var angleRadians = helpers$1.toRadians(labelRotation);
- cosRotation = Math.cos(angleRadians);
- sinRotation = Math.sin(angleRadians);
-
- if (sinRotation * originalLabelWidth > me.maxHeight) {
- // go back one step
- labelRotation--;
- break;
- }
-
- labelRotation++;
- labelWidth = cosRotation * originalLabelWidth;
- }
- }
-
- me.labelRotation = labelRotation;
- },
- afterCalculateTickRotation: function() {
- helpers$1.callback(this.options.afterCalculateTickRotation, [this]);
- },
-
- //
-
- beforeFit: function() {
- helpers$1.callback(this.options.beforeFit, [this]);
- },
- fit: function() {
- var me = this;
- // Reset
- var minSize = me.minSize = {
- width: 0,
- height: 0
- };
-
- var labels = labelsFromTicks(me._ticks);
-
- var opts = me.options;
- var tickOpts = opts.ticks;
- var scaleLabelOpts = opts.scaleLabel;
- var gridLineOpts = opts.gridLines;
- var display = me._isVisible();
- var position = opts.position;
- var isHorizontal = me.isHorizontal();
-
- var parseFont = helpers$1.options._parseFont;
- var tickFont = parseFont(tickOpts);
- var tickMarkLength = opts.gridLines.tickMarkLength;
-
- // Width
- if (isHorizontal) {
- // subtract the margins to line up with the chartArea if we are a full width scale
- minSize.width = me.isFullWidth() ? me.maxWidth - me.margins.left - me.margins.right : me.maxWidth;
- } else {
- minSize.width = display && gridLineOpts.drawTicks ? tickMarkLength : 0;
- }
-
- // height
- if (isHorizontal) {
- minSize.height = display && gridLineOpts.drawTicks ? tickMarkLength : 0;
- } else {
- minSize.height = me.maxHeight; // fill all the height
- }
-
- // Are we showing a title for the scale?
- if (scaleLabelOpts.display && display) {
- var scaleLabelFont = parseFont(scaleLabelOpts);
- var scaleLabelPadding = helpers$1.options.toPadding(scaleLabelOpts.padding);
- var deltaHeight = scaleLabelFont.lineHeight + scaleLabelPadding.height;
-
- if (isHorizontal) {
- minSize.height += deltaHeight;
- } else {
- minSize.width += deltaHeight;
- }
- }
-
- // Don't bother fitting the ticks if we are not showing the labels
- if (tickOpts.display && display) {
- var largestTextWidth = helpers$1.longestText(me.ctx, tickFont.string, labels, me.longestTextCache);
- var tallestLabelHeightInLines = helpers$1.numberOfLabelLines(labels);
- var lineSpace = tickFont.size * 0.5;
- var tickPadding = me.options.ticks.padding;
-
- // Store max number of lines and widest label for _autoSkip
- me._maxLabelLines = tallestLabelHeightInLines;
- me.longestLabelWidth = largestTextWidth;
-
- if (isHorizontal) {
- var angleRadians = helpers$1.toRadians(me.labelRotation);
- var cosRotation = Math.cos(angleRadians);
- var sinRotation = Math.sin(angleRadians);
-
- // TODO - improve this calculation
- var labelHeight = (sinRotation * largestTextWidth)
- + (tickFont.lineHeight * tallestLabelHeightInLines)
- + lineSpace; // padding
-
- minSize.height = Math.min(me.maxHeight, minSize.height + labelHeight + tickPadding);
-
- me.ctx.font = tickFont.string;
- var firstLabelWidth = computeTextSize(me.ctx, labels[0], tickFont.string);
- var lastLabelWidth = computeTextSize(me.ctx, labels[labels.length - 1], tickFont.string);
- var offsetLeft = me.getPixelForTick(0) - me.left;
- var offsetRight = me.right - me.getPixelForTick(labels.length - 1);
- var paddingLeft, paddingRight;
-
- // Ensure that our ticks are always inside the canvas. When rotated, ticks are right aligned
- // which means that the right padding is dominated by the font height
- if (me.labelRotation !== 0) {
- paddingLeft = position === 'bottom' ? (cosRotation * firstLabelWidth) : (cosRotation * lineSpace);
- paddingRight = position === 'bottom' ? (cosRotation * lineSpace) : (cosRotation * lastLabelWidth);
- } else {
- paddingLeft = firstLabelWidth / 2;
- paddingRight = lastLabelWidth / 2;
- }
- me.paddingLeft = Math.max(paddingLeft - offsetLeft, 0) + 3; // add 3 px to move away from canvas edges
- me.paddingRight = Math.max(paddingRight - offsetRight, 0) + 3;
- } else {
- // A vertical axis is more constrained by the width. Labels are the
- // dominant factor here, so get that length first and account for padding
- if (tickOpts.mirror) {
- largestTextWidth = 0;
- } else {
- // use lineSpace for consistency with horizontal axis
- // tickPadding is not implemented for horizontal
- largestTextWidth += tickPadding + lineSpace;
- }
-
- minSize.width = Math.min(me.maxWidth, minSize.width + largestTextWidth);
-
- me.paddingTop = tickFont.size / 2;
- me.paddingBottom = tickFont.size / 2;
- }
- }
-
- me.handleMargins();
-
- me.width = minSize.width;
- me.height = minSize.height;
- },
-
- /**
- * Handle margins and padding interactions
- * @private
- */
- handleMargins: function() {
- var me = this;
- if (me.margins) {
- me.paddingLeft = Math.max(me.paddingLeft - me.margins.left, 0);
- me.paddingTop = Math.max(me.paddingTop - me.margins.top, 0);
- me.paddingRight = Math.max(me.paddingRight - me.margins.right, 0);
- me.paddingBottom = Math.max(me.paddingBottom - me.margins.bottom, 0);
- }
- },
-
- afterFit: function() {
- helpers$1.callback(this.options.afterFit, [this]);
- },
-
- // Shared Methods
- isHorizontal: function() {
- return this.options.position === 'top' || this.options.position === 'bottom';
- },
- isFullWidth: function() {
- return (this.options.fullWidth);
- },
-
- // Get the correct value. NaN bad inputs, If the value type is object get the x or y based on whether we are horizontal or not
- getRightValue: function(rawValue) {
- // Null and undefined values first
- if (helpers$1.isNullOrUndef(rawValue)) {
- return NaN;
- }
- // isNaN(object) returns true, so make sure NaN is checking for a number; Discard Infinite values
- if ((typeof rawValue === 'number' || rawValue instanceof Number) && !isFinite(rawValue)) {
- return NaN;
- }
- // If it is in fact an object, dive in one more level
- if (rawValue) {
- if (this.isHorizontal()) {
- if (rawValue.x !== undefined) {
- return this.getRightValue(rawValue.x);
- }
- } else if (rawValue.y !== undefined) {
- return this.getRightValue(rawValue.y);
- }
- }
-
- // Value is good, return it
- return rawValue;
- },
-
- /**
- * Used to get the value to display in the tooltip for the data at the given index
- * @param index
- * @param datasetIndex
- */
- getLabelForIndex: helpers$1.noop,
-
- /**
- * Returns the location of the given data point. Value can either be an index or a numerical value
- * The coordinate (0, 0) is at the upper-left corner of the canvas
- * @param value
- * @param index
- * @param datasetIndex
- */
- getPixelForValue: helpers$1.noop,
-
- /**
- * Used to get the data value from a given pixel. This is the inverse of getPixelForValue
- * The coordinate (0, 0) is at the upper-left corner of the canvas
- * @param pixel
- */
- getValueForPixel: helpers$1.noop,
-
- /**
- * Returns the location of the tick at the given index
- * The coordinate (0, 0) is at the upper-left corner of the canvas
- */
- getPixelForTick: function(index) {
- var me = this;
- var offset = me.options.offset;
- if (me.isHorizontal()) {
- var innerWidth = me.width - (me.paddingLeft + me.paddingRight);
- var tickWidth = innerWidth / Math.max((me._ticks.length - (offset ? 0 : 1)), 1);
- var pixel = (tickWidth * index) + me.paddingLeft;
-
- if (offset) {
- pixel += tickWidth / 2;
- }
-
- var finalVal = me.left + pixel;
- finalVal += me.isFullWidth() ? me.margins.left : 0;
- return finalVal;
- }
- var innerHeight = me.height - (me.paddingTop + me.paddingBottom);
- return me.top + (index * (innerHeight / (me._ticks.length - 1)));
- },
-
- /**
- * Utility for getting the pixel location of a percentage of scale
- * The coordinate (0, 0) is at the upper-left corner of the canvas
- */
- getPixelForDecimal: function(decimal) {
- var me = this;
- if (me.isHorizontal()) {
- var innerWidth = me.width - (me.paddingLeft + me.paddingRight);
- var valueOffset = (innerWidth * decimal) + me.paddingLeft;
-
- var finalVal = me.left + valueOffset;
- finalVal += me.isFullWidth() ? me.margins.left : 0;
- return finalVal;
- }
- return me.top + (decimal * me.height);
- },
-
- /**
- * Returns the pixel for the minimum chart value
- * The coordinate (0, 0) is at the upper-left corner of the canvas
- */
- getBasePixel: function() {
- return this.getPixelForValue(this.getBaseValue());
- },
-
- getBaseValue: function() {
- var me = this;
- var min = me.min;
- var max = me.max;
-
- return me.beginAtZero ? 0 :
- min < 0 && max < 0 ? max :
- min > 0 && max > 0 ? min :
- 0;
- },
-
- /**
- * Returns a subset of ticks to be plotted to avoid overlapping labels.
- * @private
- */
- _autoSkip: function(ticks) {
- var me = this;
- var isHorizontal = me.isHorizontal();
- var optionTicks = me.options.ticks.minor;
- var tickCount = ticks.length;
- var skipRatio = false;
- var maxTicks = optionTicks.maxTicksLimit;
-
- // Total space needed to display all ticks. First and last ticks are
- // drawn as their center at end of axis, so tickCount-1
- var ticksLength = me._tickSize() * (tickCount - 1);
-
- // Axis length
- var axisLength = isHorizontal
- ? me.width - (me.paddingLeft + me.paddingRight)
- : me.height - (me.paddingTop + me.PaddingBottom);
-
- var result = [];
- var i, tick;
-
- if (ticksLength > axisLength) {
- skipRatio = 1 + Math.floor(ticksLength / axisLength);
- }
-
- // if they defined a max number of optionTicks,
- // increase skipRatio until that number is met
- if (tickCount > maxTicks) {
- skipRatio = Math.max(skipRatio, 1 + Math.floor(tickCount / maxTicks));
- }
-
- for (i = 0; i < tickCount; i++) {
- tick = ticks[i];
-
- if (skipRatio > 1 && i % skipRatio > 0) {
- // leave tick in place but make sure it's not displayed (#4635)
- delete tick.label;
- }
- result.push(tick);
- }
- return result;
- },
-
- /**
- * @private
- */
- _tickSize: function() {
- var me = this;
- var isHorizontal = me.isHorizontal();
- var optionTicks = me.options.ticks.minor;
-
- // Calculate space needed by label in axis direction.
- var rot = helpers$1.toRadians(me.labelRotation);
- var cos = Math.abs(Math.cos(rot));
- var sin = Math.abs(Math.sin(rot));
-
- var padding = optionTicks.autoSkipPadding || 0;
- var w = (me.longestLabelWidth + padding) || 0;
-
- var tickFont = helpers$1.options._parseFont(optionTicks);
- var h = (me._maxLabelLines * tickFont.lineHeight + padding) || 0;
-
- // Calculate space needed for 1 tick in axis direction.
- return isHorizontal
- ? h * cos > w * sin ? w / cos : h / sin
- : h * sin < w * cos ? h / cos : w / sin;
- },
-
- /**
- * @private
- */
- _isVisible: function() {
- var me = this;
- var chart = me.chart;
- var display = me.options.display;
- var i, ilen, meta;
-
- if (display !== 'auto') {
- return !!display;
- }
-
- // When 'auto', the scale is visible if at least one associated dataset is visible.
- for (i = 0, ilen = chart.data.datasets.length; i < ilen; ++i) {
- if (chart.isDatasetVisible(i)) {
- meta = chart.getDatasetMeta(i);
- if (meta.xAxisID === me.id || meta.yAxisID === me.id) {
- return true;
- }
- }
- }
-
- return false;
- },
-
- /**
- * Actually draw the scale on the canvas
- * @param {object} chartArea - the area of the chart to draw full grid lines on
- */
- draw: function(chartArea) {
- var me = this;
- var options = me.options;
-
- if (!me._isVisible()) {
- return;
- }
-
- var chart = me.chart;
- var context = me.ctx;
- var globalDefaults = core_defaults.global;
- var defaultFontColor = globalDefaults.defaultFontColor;
- var optionTicks = options.ticks.minor;
- var optionMajorTicks = options.ticks.major || optionTicks;
- var gridLines = options.gridLines;
- var scaleLabel = options.scaleLabel;
- var position = options.position;
-
- var isRotated = me.labelRotation !== 0;
- var isMirrored = optionTicks.mirror;
- var isHorizontal = me.isHorizontal();
-
- var parseFont = helpers$1.options._parseFont;
- var ticks = optionTicks.display && optionTicks.autoSkip ? me._autoSkip(me.getTicks()) : me.getTicks();
- var tickFontColor = valueOrDefault$9(optionTicks.fontColor, defaultFontColor);
- var tickFont = parseFont(optionTicks);
- var lineHeight = tickFont.lineHeight;
- var majorTickFontColor = valueOrDefault$9(optionMajorTicks.fontColor, defaultFontColor);
- var majorTickFont = parseFont(optionMajorTicks);
- var tickPadding = optionTicks.padding;
- var labelOffset = optionTicks.labelOffset;
-
- var tl = gridLines.drawTicks ? gridLines.tickMarkLength : 0;
-
- var scaleLabelFontColor = valueOrDefault$9(scaleLabel.fontColor, defaultFontColor);
- var scaleLabelFont = parseFont(scaleLabel);
- var scaleLabelPadding = helpers$1.options.toPadding(scaleLabel.padding);
- var labelRotationRadians = helpers$1.toRadians(me.labelRotation);
-
- var itemsToDraw = [];
-
- var axisWidth = gridLines.drawBorder ? valueAtIndexOrDefault(gridLines.lineWidth, 0, 0) : 0;
- var alignPixel = helpers$1._alignPixel;
- var borderValue, tickStart, tickEnd;
-
- if (position === 'top') {
- borderValue = alignPixel(chart, me.bottom, axisWidth);
- tickStart = me.bottom - tl;
- tickEnd = borderValue - axisWidth / 2;
- } else if (position === 'bottom') {
- borderValue = alignPixel(chart, me.top, axisWidth);
- tickStart = borderValue + axisWidth / 2;
- tickEnd = me.top + tl;
- } else if (position === 'left') {
- borderValue = alignPixel(chart, me.right, axisWidth);
- tickStart = me.right - tl;
- tickEnd = borderValue - axisWidth / 2;
- } else {
- borderValue = alignPixel(chart, me.left, axisWidth);
- tickStart = borderValue + axisWidth / 2;
- tickEnd = me.left + tl;
- }
-
- var epsilon = 0.0000001; // 0.0000001 is margin in pixels for Accumulated error.
-
- helpers$1.each(ticks, function(tick, index) {
- // autoskipper skipped this tick (#4635)
- if (helpers$1.isNullOrUndef(tick.label)) {
- return;
- }
-
- var label = tick.label;
- var lineWidth, lineColor, borderDash, borderDashOffset;
- if (index === me.zeroLineIndex && options.offset === gridLines.offsetGridLines) {
- // Draw the first index specially
- lineWidth = gridLines.zeroLineWidth;
- lineColor = gridLines.zeroLineColor;
- borderDash = gridLines.zeroLineBorderDash || [];
- borderDashOffset = gridLines.zeroLineBorderDashOffset || 0.0;
- } else {
- lineWidth = valueAtIndexOrDefault(gridLines.lineWidth, index);
- lineColor = valueAtIndexOrDefault(gridLines.color, index);
- borderDash = gridLines.borderDash || [];
- borderDashOffset = gridLines.borderDashOffset || 0.0;
- }
-
- // Common properties
- var tx1, ty1, tx2, ty2, x1, y1, x2, y2, labelX, labelY, textOffset, textAlign;
- var labelCount = helpers$1.isArray(label) ? label.length : 1;
- var lineValue = getPixelForGridLine(me, index, gridLines.offsetGridLines);
-
- if (isHorizontal) {
- var labelYOffset = tl + tickPadding;
-
- if (lineValue < me.left - epsilon) {
- lineColor = 'rgba(0,0,0,0)';
- }
-
- tx1 = tx2 = x1 = x2 = alignPixel(chart, lineValue, lineWidth);
- ty1 = tickStart;
- ty2 = tickEnd;
- labelX = me.getPixelForTick(index) + labelOffset; // x values for optionTicks (need to consider offsetLabel option)
-
- if (position === 'top') {
- y1 = alignPixel(chart, chartArea.top, axisWidth) + axisWidth / 2;
- y2 = chartArea.bottom;
- textOffset = ((!isRotated ? 0.5 : 1) - labelCount) * lineHeight;
- textAlign = !isRotated ? 'center' : 'left';
- labelY = me.bottom - labelYOffset;
- } else {
- y1 = chartArea.top;
- y2 = alignPixel(chart, chartArea.bottom, axisWidth) - axisWidth / 2;
- textOffset = (!isRotated ? 0.5 : 0) * lineHeight;
- textAlign = !isRotated ? 'center' : 'right';
- labelY = me.top + labelYOffset;
- }
- } else {
- var labelXOffset = (isMirrored ? 0 : tl) + tickPadding;
-
- if (lineValue < me.top - epsilon) {
- lineColor = 'rgba(0,0,0,0)';
- }
-
- tx1 = tickStart;
- tx2 = tickEnd;
- ty1 = ty2 = y1 = y2 = alignPixel(chart, lineValue, lineWidth);
- labelY = me.getPixelForTick(index) + labelOffset;
- textOffset = (1 - labelCount) * lineHeight / 2;
-
- if (position === 'left') {
- x1 = alignPixel(chart, chartArea.left, axisWidth) + axisWidth / 2;
- x2 = chartArea.right;
- textAlign = isMirrored ? 'left' : 'right';
- labelX = me.right - labelXOffset;
- } else {
- x1 = chartArea.left;
- x2 = alignPixel(chart, chartArea.right, axisWidth) - axisWidth / 2;
- textAlign = isMirrored ? 'right' : 'left';
- labelX = me.left + labelXOffset;
- }
- }
-
- itemsToDraw.push({
- tx1: tx1,
- ty1: ty1,
- tx2: tx2,
- ty2: ty2,
- x1: x1,
- y1: y1,
- x2: x2,
- y2: y2,
- labelX: labelX,
- labelY: labelY,
- glWidth: lineWidth,
- glColor: lineColor,
- glBorderDash: borderDash,
- glBorderDashOffset: borderDashOffset,
- rotation: -1 * labelRotationRadians,
- label: label,
- major: tick.major,
- textOffset: textOffset,
- textAlign: textAlign
- });
- });
-
- // Draw all of the tick labels, tick marks, and grid lines at the correct places
- helpers$1.each(itemsToDraw, function(itemToDraw) {
- var glWidth = itemToDraw.glWidth;
- var glColor = itemToDraw.glColor;
-
- if (gridLines.display && glWidth && glColor) {
- context.save();
- context.lineWidth = glWidth;
- context.strokeStyle = glColor;
- if (context.setLineDash) {
- context.setLineDash(itemToDraw.glBorderDash);
- context.lineDashOffset = itemToDraw.glBorderDashOffset;
- }
-
- context.beginPath();
-
- if (gridLines.drawTicks) {
- context.moveTo(itemToDraw.tx1, itemToDraw.ty1);
- context.lineTo(itemToDraw.tx2, itemToDraw.ty2);
- }
-
- if (gridLines.drawOnChartArea) {
- context.moveTo(itemToDraw.x1, itemToDraw.y1);
- context.lineTo(itemToDraw.x2, itemToDraw.y2);
- }
-
- context.stroke();
- context.restore();
- }
-
- if (optionTicks.display) {
- // Make sure we draw text in the correct color and font
- context.save();
- context.translate(itemToDraw.labelX, itemToDraw.labelY);
- context.rotate(itemToDraw.rotation);
- context.font = itemToDraw.major ? majorTickFont.string : tickFont.string;
- context.fillStyle = itemToDraw.major ? majorTickFontColor : tickFontColor;
- context.textBaseline = 'middle';
- context.textAlign = itemToDraw.textAlign;
-
- var label = itemToDraw.label;
- var y = itemToDraw.textOffset;
- if (helpers$1.isArray(label)) {
- for (var i = 0; i < label.length; ++i) {
- // We just make sure the multiline element is a string here..
- context.fillText('' + label[i], 0, y);
- y += lineHeight;
- }
- } else {
- context.fillText(label, 0, y);
- }
- context.restore();
- }
- });
-
- if (scaleLabel.display) {
- // Draw the scale label
- var scaleLabelX;
- var scaleLabelY;
- var rotation = 0;
- var halfLineHeight = scaleLabelFont.lineHeight / 2;
-
- if (isHorizontal) {
- scaleLabelX = me.left + ((me.right - me.left) / 2); // midpoint of the width
- scaleLabelY = position === 'bottom'
- ? me.bottom - halfLineHeight - scaleLabelPadding.bottom
- : me.top + halfLineHeight + scaleLabelPadding.top;
- } else {
- var isLeft = position === 'left';
- scaleLabelX = isLeft
- ? me.left + halfLineHeight + scaleLabelPadding.top
- : me.right - halfLineHeight - scaleLabelPadding.top;
- scaleLabelY = me.top + ((me.bottom - me.top) / 2);
- rotation = isLeft ? -0.5 * Math.PI : 0.5 * Math.PI;
- }
-
- context.save();
- context.translate(scaleLabelX, scaleLabelY);
- context.rotate(rotation);
- context.textAlign = 'center';
- context.textBaseline = 'middle';
- context.fillStyle = scaleLabelFontColor; // render in correct colour
- context.font = scaleLabelFont.string;
- context.fillText(scaleLabel.labelString, 0, 0);
- context.restore();
- }
-
- if (axisWidth) {
- // Draw the line at the edge of the axis
- var firstLineWidth = axisWidth;
- var lastLineWidth = valueAtIndexOrDefault(gridLines.lineWidth, ticks.length - 1, 0);
- var x1, x2, y1, y2;
-
- if (isHorizontal) {
- x1 = alignPixel(chart, me.left, firstLineWidth) - firstLineWidth / 2;
- x2 = alignPixel(chart, me.right, lastLineWidth) + lastLineWidth / 2;
- y1 = y2 = borderValue;
- } else {
- y1 = alignPixel(chart, me.top, firstLineWidth) - firstLineWidth / 2;
- y2 = alignPixel(chart, me.bottom, lastLineWidth) + lastLineWidth / 2;
- x1 = x2 = borderValue;
- }
-
- context.lineWidth = axisWidth;
- context.strokeStyle = valueAtIndexOrDefault(gridLines.color, 0);
- context.beginPath();
- context.moveTo(x1, y1);
- context.lineTo(x2, y2);
- context.stroke();
- }
- }
-});
-
-var defaultConfig = {
- position: 'bottom'
-};
-
-var scale_category = core_scale.extend({
- /**
- * Internal function to get the correct labels. If data.xLabels or data.yLabels are defined, use those
- * else fall back to data.labels
- * @private
- */
- getLabels: function() {
- var data = this.chart.data;
- return this.options.labels || (this.isHorizontal() ? data.xLabels : data.yLabels) || data.labels;
- },
-
- determineDataLimits: function() {
- var me = this;
- var labels = me.getLabels();
- me.minIndex = 0;
- me.maxIndex = labels.length - 1;
- var findIndex;
-
- if (me.options.ticks.min !== undefined) {
- // user specified min value
- findIndex = labels.indexOf(me.options.ticks.min);
- me.minIndex = findIndex !== -1 ? findIndex : me.minIndex;
- }
-
- if (me.options.ticks.max !== undefined) {
- // user specified max value
- findIndex = labels.indexOf(me.options.ticks.max);
- me.maxIndex = findIndex !== -1 ? findIndex : me.maxIndex;
- }
-
- me.min = labels[me.minIndex];
- me.max = labels[me.maxIndex];
- },
-
- buildTicks: function() {
- var me = this;
- var labels = me.getLabels();
- // If we are viewing some subset of labels, slice the original array
- me.ticks = (me.minIndex === 0 && me.maxIndex === labels.length - 1) ? labels : labels.slice(me.minIndex, me.maxIndex + 1);
- },
-
- getLabelForIndex: function(index, datasetIndex) {
- var me = this;
- var chart = me.chart;
-
- if (chart.getDatasetMeta(datasetIndex).controller._getValueScaleId() === me.id) {
- return me.getRightValue(chart.data.datasets[datasetIndex].data[index]);
- }
-
- return me.ticks[index - me.minIndex];
- },
-
- // Used to get data value locations. Value can either be an index or a numerical value
- getPixelForValue: function(value, index) {
- var me = this;
- var offset = me.options.offset;
- // 1 is added because we need the length but we have the indexes
- var offsetAmt = Math.max((me.maxIndex + 1 - me.minIndex - (offset ? 0 : 1)), 1);
-
- // If value is a data object, then index is the index in the data array,
- // not the index of the scale. We need to change that.
- var valueCategory;
- if (value !== undefined && value !== null) {
- valueCategory = me.isHorizontal() ? value.x : value.y;
- }
- if (valueCategory !== undefined || (value !== undefined && isNaN(index))) {
- var labels = me.getLabels();
- value = valueCategory || value;
- var idx = labels.indexOf(value);
- index = idx !== -1 ? idx : index;
- }
-
- if (me.isHorizontal()) {
- var valueWidth = me.width / offsetAmt;
- var widthOffset = (valueWidth * (index - me.minIndex));
-
- if (offset) {
- widthOffset += (valueWidth / 2);
- }
-
- return me.left + widthOffset;
- }
- var valueHeight = me.height / offsetAmt;
- var heightOffset = (valueHeight * (index - me.minIndex));
-
- if (offset) {
- heightOffset += (valueHeight / 2);
- }
-
- return me.top + heightOffset;
- },
-
- getPixelForTick: function(index) {
- return this.getPixelForValue(this.ticks[index], index + this.minIndex, null);
- },
-
- getValueForPixel: function(pixel) {
- var me = this;
- var offset = me.options.offset;
- var value;
- var offsetAmt = Math.max((me._ticks.length - (offset ? 0 : 1)), 1);
- var horz = me.isHorizontal();
- var valueDimension = (horz ? me.width : me.height) / offsetAmt;
-
- pixel -= horz ? me.left : me.top;
-
- if (offset) {
- pixel -= (valueDimension / 2);
- }
-
- if (pixel <= 0) {
- value = 0;
- } else {
- value = Math.round(pixel / valueDimension);
- }
-
- return value + me.minIndex;
- },
-
- getBasePixel: function() {
- return this.bottom;
- }
-});
-
-// INTERNAL: static default options, registered in src/index.js
-var _defaults = defaultConfig;
-scale_category._defaults = _defaults;
-
-var noop = helpers$1.noop;
-var isNullOrUndef = helpers$1.isNullOrUndef;
-
-/**
- * Generate a set of linear ticks
- * @param generationOptions the options used to generate the ticks
- * @param dataRange the range of the data
- * @returns {number[]} array of tick values
- */
-function generateTicks(generationOptions, dataRange) {
- var ticks = [];
- // To get a "nice" value for the tick spacing, we will use the appropriately named
- // "nice number" algorithm. See https://stackoverflow.com/questions/8506881/nice-label-algorithm-for-charts-with-minimum-ticks
- // for details.
-
- var MIN_SPACING = 1e-14;
- var stepSize = generationOptions.stepSize;
- var unit = stepSize || 1;
- var maxNumSpaces = generationOptions.maxTicks - 1;
- var min = generationOptions.min;
- var max = generationOptions.max;
- var precision = generationOptions.precision;
- var rmin = dataRange.min;
- var rmax = dataRange.max;
- var spacing = helpers$1.niceNum((rmax - rmin) / maxNumSpaces / unit) * unit;
- var factor, niceMin, niceMax, numSpaces;
-
- // Beyond MIN_SPACING floating point numbers being to lose precision
- // such that we can't do the math necessary to generate ticks
- if (spacing < MIN_SPACING && isNullOrUndef(min) && isNullOrUndef(max)) {
- return [rmin, rmax];
- }
-
- numSpaces = Math.ceil(rmax / spacing) - Math.floor(rmin / spacing);
- if (numSpaces > maxNumSpaces) {
- // If the calculated num of spaces exceeds maxNumSpaces, recalculate it
- spacing = helpers$1.niceNum(numSpaces * spacing / maxNumSpaces / unit) * unit;
- }
-
- if (stepSize || isNullOrUndef(precision)) {
- // If a precision is not specified, calculate factor based on spacing
- factor = Math.pow(10, helpers$1._decimalPlaces(spacing));
- } else {
- // If the user specified a precision, round to that number of decimal places
- factor = Math.pow(10, precision);
- spacing = Math.ceil(spacing * factor) / factor;
- }
-
- niceMin = Math.floor(rmin / spacing) * spacing;
- niceMax = Math.ceil(rmax / spacing) * spacing;
-
- // If min, max and stepSize is set and they make an evenly spaced scale use it.
- if (stepSize) {
- // If very close to our whole number, use it.
- if (!isNullOrUndef(min) && helpers$1.almostWhole(min / spacing, spacing / 1000)) {
- niceMin = min;
- }
- if (!isNullOrUndef(max) && helpers$1.almostWhole(max / spacing, spacing / 1000)) {
- niceMax = max;
- }
- }
-
- numSpaces = (niceMax - niceMin) / spacing;
- // If very close to our rounded value, use it.
- if (helpers$1.almostEquals(numSpaces, Math.round(numSpaces), spacing / 1000)) {
- numSpaces = Math.round(numSpaces);
- } else {
- numSpaces = Math.ceil(numSpaces);
- }
-
- niceMin = Math.round(niceMin * factor) / factor;
- niceMax = Math.round(niceMax * factor) / factor;
- ticks.push(isNullOrUndef(min) ? niceMin : min);
- for (var j = 1; j < numSpaces; ++j) {
- ticks.push(Math.round((niceMin + j * spacing) * factor) / factor);
- }
- ticks.push(isNullOrUndef(max) ? niceMax : max);
-
- return ticks;
-}
-
-var scale_linearbase = core_scale.extend({
- getRightValue: function(value) {
- if (typeof value === 'string') {
- return +value;
- }
- return core_scale.prototype.getRightValue.call(this, value);
- },
-
- handleTickRangeOptions: function() {
- var me = this;
- var opts = me.options;
- var tickOpts = opts.ticks;
-
- // If we are forcing it to begin at 0, but 0 will already be rendered on the chart,
- // do nothing since that would make the chart weird. If the user really wants a weird chart
- // axis, they can manually override it
- if (tickOpts.beginAtZero) {
- var minSign = helpers$1.sign(me.min);
- var maxSign = helpers$1.sign(me.max);
-
- if (minSign < 0 && maxSign < 0) {
- // move the top up to 0
- me.max = 0;
- } else if (minSign > 0 && maxSign > 0) {
- // move the bottom down to 0
- me.min = 0;
- }
- }
-
- var setMin = tickOpts.min !== undefined || tickOpts.suggestedMin !== undefined;
- var setMax = tickOpts.max !== undefined || tickOpts.suggestedMax !== undefined;
-
- if (tickOpts.min !== undefined) {
- me.min = tickOpts.min;
- } else if (tickOpts.suggestedMin !== undefined) {
- if (me.min === null) {
- me.min = tickOpts.suggestedMin;
- } else {
- me.min = Math.min(me.min, tickOpts.suggestedMin);
- }
- }
-
- if (tickOpts.max !== undefined) {
- me.max = tickOpts.max;
- } else if (tickOpts.suggestedMax !== undefined) {
- if (me.max === null) {
- me.max = tickOpts.suggestedMax;
- } else {
- me.max = Math.max(me.max, tickOpts.suggestedMax);
- }
- }
-
- if (setMin !== setMax) {
- // We set the min or the max but not both.
- // So ensure that our range is good
- // Inverted or 0 length range can happen when
- // ticks.min is set, and no datasets are visible
- if (me.min >= me.max) {
- if (setMin) {
- me.max = me.min + 1;
- } else {
- me.min = me.max - 1;
- }
- }
- }
-
- if (me.min === me.max) {
- me.max++;
-
- if (!tickOpts.beginAtZero) {
- me.min--;
- }
- }
- },
-
- getTickLimit: function() {
- var me = this;
- var tickOpts = me.options.ticks;
- var stepSize = tickOpts.stepSize;
- var maxTicksLimit = tickOpts.maxTicksLimit;
- var maxTicks;
-
- if (stepSize) {
- maxTicks = Math.ceil(me.max / stepSize) - Math.floor(me.min / stepSize) + 1;
- } else {
- maxTicks = me._computeTickLimit();
- maxTicksLimit = maxTicksLimit || 11;
- }
-
- if (maxTicksLimit) {
- maxTicks = Math.min(maxTicksLimit, maxTicks);
- }
-
- return maxTicks;
- },
-
- _computeTickLimit: function() {
- return Number.POSITIVE_INFINITY;
- },
-
- handleDirectionalChanges: noop,
-
- buildTicks: function() {
- var me = this;
- var opts = me.options;
- var tickOpts = opts.ticks;
-
- // Figure out what the max number of ticks we can support it is based on the size of
- // the axis area. For now, we say that the minimum tick spacing in pixels must be 40
- // We also limit the maximum number of ticks to 11 which gives a nice 10 squares on
- // the graph. Make sure we always have at least 2 ticks
- var maxTicks = me.getTickLimit();
- maxTicks = Math.max(2, maxTicks);
-
- var numericGeneratorOptions = {
- maxTicks: maxTicks,
- min: tickOpts.min,
- max: tickOpts.max,
- precision: tickOpts.precision,
- stepSize: helpers$1.valueOrDefault(tickOpts.fixedStepSize, tickOpts.stepSize)
- };
- var ticks = me.ticks = generateTicks(numericGeneratorOptions, me);
-
- me.handleDirectionalChanges();
-
- // At this point, we need to update our max and min given the tick values since we have expanded the
- // range of the scale
- me.max = helpers$1.max(ticks);
- me.min = helpers$1.min(ticks);
-
- if (tickOpts.reverse) {
- ticks.reverse();
-
- me.start = me.max;
- me.end = me.min;
- } else {
- me.start = me.min;
- me.end = me.max;
- }
- },
-
- convertTicksToLabels: function() {
- var me = this;
- me.ticksAsNumbers = me.ticks.slice();
- me.zeroLineIndex = me.ticks.indexOf(0);
-
- core_scale.prototype.convertTicksToLabels.call(me);
- }
-});
-
-var defaultConfig$1 = {
- position: 'left',
- ticks: {
- callback: core_ticks.formatters.linear
- }
-};
-
-var scale_linear = scale_linearbase.extend({
- determineDataLimits: function() {
- var me = this;
- var opts = me.options;
- var chart = me.chart;
- var data = chart.data;
- var datasets = data.datasets;
- var isHorizontal = me.isHorizontal();
- var DEFAULT_MIN = 0;
- var DEFAULT_MAX = 1;
-
- function IDMatches(meta) {
- return isHorizontal ? meta.xAxisID === me.id : meta.yAxisID === me.id;
- }
-
- // First Calculate the range
- me.min = null;
- me.max = null;
-
- var hasStacks = opts.stacked;
- if (hasStacks === undefined) {
- helpers$1.each(datasets, function(dataset, datasetIndex) {
- if (hasStacks) {
- return;
- }
-
- var meta = chart.getDatasetMeta(datasetIndex);
- if (chart.isDatasetVisible(datasetIndex) && IDMatches(meta) &&
- meta.stack !== undefined) {
- hasStacks = true;
- }
- });
- }
-
- if (opts.stacked || hasStacks) {
- var valuesPerStack = {};
-
- helpers$1.each(datasets, function(dataset, datasetIndex) {
- var meta = chart.getDatasetMeta(datasetIndex);
- var key = [
- meta.type,
- // we have a separate stack for stack=undefined datasets when the opts.stacked is undefined
- ((opts.stacked === undefined && meta.stack === undefined) ? datasetIndex : ''),
- meta.stack
- ].join('.');
-
- if (valuesPerStack[key] === undefined) {
- valuesPerStack[key] = {
- positiveValues: [],
- negativeValues: []
- };
- }
-
- // Store these per type
- var positiveValues = valuesPerStack[key].positiveValues;
- var negativeValues = valuesPerStack[key].negativeValues;
-
- if (chart.isDatasetVisible(datasetIndex) && IDMatches(meta)) {
- helpers$1.each(dataset.data, function(rawValue, index) {
- var value = +me.getRightValue(rawValue);
- if (isNaN(value) || meta.data[index].hidden) {
- return;
- }
-
- positiveValues[index] = positiveValues[index] || 0;
- negativeValues[index] = negativeValues[index] || 0;
-
- if (opts.relativePoints) {
- positiveValues[index] = 100;
- } else if (value < 0) {
- negativeValues[index] += value;
- } else {
- positiveValues[index] += value;
- }
- });
- }
- });
-
- helpers$1.each(valuesPerStack, function(valuesForType) {
- var values = valuesForType.positiveValues.concat(valuesForType.negativeValues);
- var minVal = helpers$1.min(values);
- var maxVal = helpers$1.max(values);
- me.min = me.min === null ? minVal : Math.min(me.min, minVal);
- me.max = me.max === null ? maxVal : Math.max(me.max, maxVal);
- });
-
- } else {
- helpers$1.each(datasets, function(dataset, datasetIndex) {
- var meta = chart.getDatasetMeta(datasetIndex);
- if (chart.isDatasetVisible(datasetIndex) && IDMatches(meta)) {
- helpers$1.each(dataset.data, function(rawValue, index) {
- var value = +me.getRightValue(rawValue);
- if (isNaN(value) || meta.data[index].hidden) {
- return;
- }
-
- if (me.min === null) {
- me.min = value;
- } else if (value < me.min) {
- me.min = value;
- }
-
- if (me.max === null) {
- me.max = value;
- } else if (value > me.max) {
- me.max = value;
- }
- });
- }
- });
- }
-
- me.min = isFinite(me.min) && !isNaN(me.min) ? me.min : DEFAULT_MIN;
- me.max = isFinite(me.max) && !isNaN(me.max) ? me.max : DEFAULT_MAX;
-
- // Common base implementation to handle ticks.min, ticks.max, ticks.beginAtZero
- this.handleTickRangeOptions();
- },
-
- // Returns the maximum number of ticks based on the scale dimension
- _computeTickLimit: function() {
- var me = this;
- var tickFont;
-
- if (me.isHorizontal()) {
- return Math.ceil(me.width / 40);
- }
- tickFont = helpers$1.options._parseFont(me.options.ticks);
- return Math.ceil(me.height / tickFont.lineHeight);
- },
-
- // Called after the ticks are built. We need
- handleDirectionalChanges: function() {
- if (!this.isHorizontal()) {
- // We are in a vertical orientation. The top value is the highest. So reverse the array
- this.ticks.reverse();
- }
- },
-
- getLabelForIndex: function(index, datasetIndex) {
- return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
- },
-
- // Utils
- getPixelForValue: function(value) {
- // This must be called after fit has been run so that
- // this.left, this.top, this.right, and this.bottom have been defined
- var me = this;
- var start = me.start;
-
- var rightValue = +me.getRightValue(value);
- var pixel;
- var range = me.end - start;
-
- if (me.isHorizontal()) {
- pixel = me.left + (me.width / range * (rightValue - start));
- } else {
- pixel = me.bottom - (me.height / range * (rightValue - start));
- }
- return pixel;
- },
-
- getValueForPixel: function(pixel) {
- var me = this;
- var isHorizontal = me.isHorizontal();
- var innerDimension = isHorizontal ? me.width : me.height;
- var offset = (isHorizontal ? pixel - me.left : me.bottom - pixel) / innerDimension;
- return me.start + ((me.end - me.start) * offset);
- },
-
- getPixelForTick: function(index) {
- return this.getPixelForValue(this.ticksAsNumbers[index]);
- }
-});
-
-// INTERNAL: static default options, registered in src/index.js
-var _defaults$1 = defaultConfig$1;
-scale_linear._defaults = _defaults$1;
-
-var valueOrDefault$a = helpers$1.valueOrDefault;
-
-/**
- * Generate a set of logarithmic ticks
- * @param generationOptions the options used to generate the ticks
- * @param dataRange the range of the data
- * @returns {number[]} array of tick values
- */
-function generateTicks$1(generationOptions, dataRange) {
- var ticks = [];
-
- var tickVal = valueOrDefault$a(generationOptions.min, Math.pow(10, Math.floor(helpers$1.log10(dataRange.min))));
-
- var endExp = Math.floor(helpers$1.log10(dataRange.max));
- var endSignificand = Math.ceil(dataRange.max / Math.pow(10, endExp));
- var exp, significand;
-
- if (tickVal === 0) {
- exp = Math.floor(helpers$1.log10(dataRange.minNotZero));
- significand = Math.floor(dataRange.minNotZero / Math.pow(10, exp));
-
- ticks.push(tickVal);
- tickVal = significand * Math.pow(10, exp);
- } else {
- exp = Math.floor(helpers$1.log10(tickVal));
- significand = Math.floor(tickVal / Math.pow(10, exp));
- }
- var precision = exp < 0 ? Math.pow(10, Math.abs(exp)) : 1;
-
- do {
- ticks.push(tickVal);
-
- ++significand;
- if (significand === 10) {
- significand = 1;
- ++exp;
- precision = exp >= 0 ? 1 : precision;
- }
-
- tickVal = Math.round(significand * Math.pow(10, exp) * precision) / precision;
- } while (exp < endExp || (exp === endExp && significand < endSignificand));
-
- var lastTick = valueOrDefault$a(generationOptions.max, tickVal);
- ticks.push(lastTick);
-
- return ticks;
-}
-
-var defaultConfig$2 = {
- position: 'left',
-
- // label settings
- ticks: {
- callback: core_ticks.formatters.logarithmic
- }
-};
-
-// TODO(v3): change this to positiveOrDefault
-function nonNegativeOrDefault(value, defaultValue) {
- return helpers$1.isFinite(value) && value >= 0 ? value : defaultValue;
-}
-
-var scale_logarithmic = core_scale.extend({
- determineDataLimits: function() {
- var me = this;
- var opts = me.options;
- var chart = me.chart;
- var data = chart.data;
- var datasets = data.datasets;
- var isHorizontal = me.isHorizontal();
- function IDMatches(meta) {
- return isHorizontal ? meta.xAxisID === me.id : meta.yAxisID === me.id;
- }
-
- // Calculate Range
- me.min = null;
- me.max = null;
- me.minNotZero = null;
-
- var hasStacks = opts.stacked;
- if (hasStacks === undefined) {
- helpers$1.each(datasets, function(dataset, datasetIndex) {
- if (hasStacks) {
- return;
- }
-
- var meta = chart.getDatasetMeta(datasetIndex);
- if (chart.isDatasetVisible(datasetIndex) && IDMatches(meta) &&
- meta.stack !== undefined) {
- hasStacks = true;
- }
- });
- }
-
- if (opts.stacked || hasStacks) {
- var valuesPerStack = {};
-
- helpers$1.each(datasets, function(dataset, datasetIndex) {
- var meta = chart.getDatasetMeta(datasetIndex);
- var key = [
- meta.type,
- // we have a separate stack for stack=undefined datasets when the opts.stacked is undefined
- ((opts.stacked === undefined && meta.stack === undefined) ? datasetIndex : ''),
- meta.stack
- ].join('.');
-
- if (chart.isDatasetVisible(datasetIndex) && IDMatches(meta)) {
- if (valuesPerStack[key] === undefined) {
- valuesPerStack[key] = [];
- }
-
- helpers$1.each(dataset.data, function(rawValue, index) {
- var values = valuesPerStack[key];
- var value = +me.getRightValue(rawValue);
- // invalid, hidden and negative values are ignored
- if (isNaN(value) || meta.data[index].hidden || value < 0) {
- return;
- }
- values[index] = values[index] || 0;
- values[index] += value;
- });
- }
- });
-
- helpers$1.each(valuesPerStack, function(valuesForType) {
- if (valuesForType.length > 0) {
- var minVal = helpers$1.min(valuesForType);
- var maxVal = helpers$1.max(valuesForType);
- me.min = me.min === null ? minVal : Math.min(me.min, minVal);
- me.max = me.max === null ? maxVal : Math.max(me.max, maxVal);
- }
- });
-
- } else {
- helpers$1.each(datasets, function(dataset, datasetIndex) {
- var meta = chart.getDatasetMeta(datasetIndex);
- if (chart.isDatasetVisible(datasetIndex) && IDMatches(meta)) {
- helpers$1.each(dataset.data, function(rawValue, index) {
- var value = +me.getRightValue(rawValue);
- // invalid, hidden and negative values are ignored
- if (isNaN(value) || meta.data[index].hidden || value < 0) {
- return;
- }
-
- if (me.min === null) {
- me.min = value;
- } else if (value < me.min) {
- me.min = value;
- }
-
- if (me.max === null) {
- me.max = value;
- } else if (value > me.max) {
- me.max = value;
- }
-
- if (value !== 0 && (me.minNotZero === null || value < me.minNotZero)) {
- me.minNotZero = value;
- }
- });
- }
- });
- }
-
- // Common base implementation to handle ticks.min, ticks.max
- this.handleTickRangeOptions();
- },
-
- handleTickRangeOptions: function() {
- var me = this;
- var tickOpts = me.options.ticks;
- var DEFAULT_MIN = 1;
- var DEFAULT_MAX = 10;
-
- me.min = nonNegativeOrDefault(tickOpts.min, me.min);
- me.max = nonNegativeOrDefault(tickOpts.max, me.max);
-
- if (me.min === me.max) {
- if (me.min !== 0 && me.min !== null) {
- me.min = Math.pow(10, Math.floor(helpers$1.log10(me.min)) - 1);
- me.max = Math.pow(10, Math.floor(helpers$1.log10(me.max)) + 1);
- } else {
- me.min = DEFAULT_MIN;
- me.max = DEFAULT_MAX;
- }
- }
- if (me.min === null) {
- me.min = Math.pow(10, Math.floor(helpers$1.log10(me.max)) - 1);
- }
- if (me.max === null) {
- me.max = me.min !== 0
- ? Math.pow(10, Math.floor(helpers$1.log10(me.min)) + 1)
- : DEFAULT_MAX;
- }
- if (me.minNotZero === null) {
- if (me.min > 0) {
- me.minNotZero = me.min;
- } else if (me.max < 1) {
- me.minNotZero = Math.pow(10, Math.floor(helpers$1.log10(me.max)));
- } else {
- me.minNotZero = DEFAULT_MIN;
- }
- }
- },
-
- buildTicks: function() {
- var me = this;
- var tickOpts = me.options.ticks;
- var reverse = !me.isHorizontal();
-
- var generationOptions = {
- min: nonNegativeOrDefault(tickOpts.min),
- max: nonNegativeOrDefault(tickOpts.max)
- };
- var ticks = me.ticks = generateTicks$1(generationOptions, me);
-
- // At this point, we need to update our max and min given the tick values since we have expanded the
- // range of the scale
- me.max = helpers$1.max(ticks);
- me.min = helpers$1.min(ticks);
-
- if (tickOpts.reverse) {
- reverse = !reverse;
- me.start = me.max;
- me.end = me.min;
- } else {
- me.start = me.min;
- me.end = me.max;
- }
- if (reverse) {
- ticks.reverse();
- }
- },
-
- convertTicksToLabels: function() {
- this.tickValues = this.ticks.slice();
-
- core_scale.prototype.convertTicksToLabels.call(this);
- },
-
- // Get the correct tooltip label
- getLabelForIndex: function(index, datasetIndex) {
- return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
- },
-
- getPixelForTick: function(index) {
- return this.getPixelForValue(this.tickValues[index]);
- },
-
- /**
- * Returns the value of the first tick.
- * @param {number} value - The minimum not zero value.
- * @return {number} The first tick value.
- * @private
- */
- _getFirstTickValue: function(value) {
- var exp = Math.floor(helpers$1.log10(value));
- var significand = Math.floor(value / Math.pow(10, exp));
-
- return significand * Math.pow(10, exp);
- },
-
- getPixelForValue: function(value) {
- var me = this;
- var tickOpts = me.options.ticks;
- var reverse = tickOpts.reverse;
- var log10 = helpers$1.log10;
- var firstTickValue = me._getFirstTickValue(me.minNotZero);
- var offset = 0;
- var innerDimension, pixel, start, end, sign;
-
- value = +me.getRightValue(value);
- if (reverse) {
- start = me.end;
- end = me.start;
- sign = -1;
- } else {
- start = me.start;
- end = me.end;
- sign = 1;
- }
- if (me.isHorizontal()) {
- innerDimension = me.width;
- pixel = reverse ? me.right : me.left;
- } else {
- innerDimension = me.height;
- sign *= -1; // invert, since the upper-left corner of the canvas is at pixel (0, 0)
- pixel = reverse ? me.top : me.bottom;
- }
- if (value !== start) {
- if (start === 0) { // include zero tick
- offset = valueOrDefault$a(tickOpts.fontSize, core_defaults.global.defaultFontSize);
- innerDimension -= offset;
- start = firstTickValue;
- }
- if (value !== 0) {
- offset += innerDimension / (log10(end) - log10(start)) * (log10(value) - log10(start));
- }
- pixel += sign * offset;
- }
- return pixel;
- },
-
- getValueForPixel: function(pixel) {
- var me = this;
- var tickOpts = me.options.ticks;
- var reverse = tickOpts.reverse;
- var log10 = helpers$1.log10;
- var firstTickValue = me._getFirstTickValue(me.minNotZero);
- var innerDimension, start, end, value;
-
- if (reverse) {
- start = me.end;
- end = me.start;
- } else {
- start = me.start;
- end = me.end;
- }
- if (me.isHorizontal()) {
- innerDimension = me.width;
- value = reverse ? me.right - pixel : pixel - me.left;
- } else {
- innerDimension = me.height;
- value = reverse ? pixel - me.top : me.bottom - pixel;
- }
- if (value !== start) {
- if (start === 0) { // include zero tick
- var offset = valueOrDefault$a(tickOpts.fontSize, core_defaults.global.defaultFontSize);
- value -= offset;
- innerDimension -= offset;
- start = firstTickValue;
- }
- value *= log10(end) - log10(start);
- value /= innerDimension;
- value = Math.pow(10, log10(start) + value);
- }
- return value;
- }
-});
-
-// INTERNAL: static default options, registered in src/index.js
-var _defaults$2 = defaultConfig$2;
-scale_logarithmic._defaults = _defaults$2;
-
-var valueOrDefault$b = helpers$1.valueOrDefault;
-var valueAtIndexOrDefault$1 = helpers$1.valueAtIndexOrDefault;
-var resolve$7 = helpers$1.options.resolve;
-
-var defaultConfig$3 = {
- display: true,
-
- // Boolean - Whether to animate scaling the chart from the centre
- animate: true,
- position: 'chartArea',
-
- angleLines: {
- display: true,
- color: 'rgba(0, 0, 0, 0.1)',
- lineWidth: 1,
- borderDash: [],
- borderDashOffset: 0.0
- },
-
- gridLines: {
- circular: false
- },
-
- // label settings
- ticks: {
- // Boolean - Show a backdrop to the scale label
- showLabelBackdrop: true,
-
- // String - The colour of the label backdrop
- backdropColor: 'rgba(255,255,255,0.75)',
-
- // Number - The backdrop padding above & below the label in pixels
- backdropPaddingY: 2,
-
- // Number - The backdrop padding to the side of the label in pixels
- backdropPaddingX: 2,
-
- callback: core_ticks.formatters.linear
- },
-
- pointLabels: {
- // Boolean - if true, show point labels
- display: true,
-
- // Number - Point label font size in pixels
- fontSize: 10,
-
- // Function - Used to convert point labels
- callback: function(label) {
- return label;
- }
- }
-};
-
-function getValueCount(scale) {
- var opts = scale.options;
- return opts.angleLines.display || opts.pointLabels.display ? scale.chart.data.labels.length : 0;
-}
-
-function getTickBackdropHeight(opts) {
- var tickOpts = opts.ticks;
-
- if (tickOpts.display && opts.display) {
- return valueOrDefault$b(tickOpts.fontSize, core_defaults.global.defaultFontSize) + tickOpts.backdropPaddingY * 2;
- }
- return 0;
-}
-
-function measureLabelSize(ctx, lineHeight, label) {
- if (helpers$1.isArray(label)) {
- return {
- w: helpers$1.longestText(ctx, ctx.font, label),
- h: label.length * lineHeight
- };
- }
-
- return {
- w: ctx.measureText(label).width,
- h: lineHeight
- };
-}
-
-function determineLimits(angle, pos, size, min, max) {
- if (angle === min || angle === max) {
- return {
- start: pos - (size / 2),
- end: pos + (size / 2)
- };
- } else if (angle < min || angle > max) {
- return {
- start: pos - size,
- end: pos
- };
- }
-
- return {
- start: pos,
- end: pos + size
- };
-}
-
-/**
- * Helper function to fit a radial linear scale with point labels
- */
-function fitWithPointLabels(scale) {
-
- // Right, this is really confusing and there is a lot of maths going on here
- // The gist of the problem is here: https://gist.github.com/nnnick/696cc9c55f4b0beb8fe9
- //
- // Reaction: https://dl.dropboxusercontent.com/u/34601363/toomuchscience.gif
- //
- // Solution:
- //
- // We assume the radius of the polygon is half the size of the canvas at first
- // at each index we check if the text overlaps.
- //
- // Where it does, we store that angle and that index.
- //
- // After finding the largest index and angle we calculate how much we need to remove
- // from the shape radius to move the point inwards by that x.
- //
- // We average the left and right distances to get the maximum shape radius that can fit in the box
- // along with labels.
- //
- // Once we have that, we can find the centre point for the chart, by taking the x text protrusion
- // on each side, removing that from the size, halving it and adding the left x protrusion width.
- //
- // This will mean we have a shape fitted to the canvas, as large as it can be with the labels
- // and position it in the most space efficient manner
- //
- // https://dl.dropboxusercontent.com/u/34601363/yeahscience.gif
-
- var plFont = helpers$1.options._parseFont(scale.options.pointLabels);
-
- // Get maximum radius of the polygon. Either half the height (minus the text width) or half the width.
- // Use this to calculate the offset + change. - Make sure L/R protrusion is at least 0 to stop issues with centre points
- var furthestLimits = {
- l: 0,
- r: scale.width,
- t: 0,
- b: scale.height - scale.paddingTop
- };
- var furthestAngles = {};
- var i, textSize, pointPosition;
-
- scale.ctx.font = plFont.string;
- scale._pointLabelSizes = [];
-
- var valueCount = getValueCount(scale);
- for (i = 0; i < valueCount; i++) {
- pointPosition = scale.getPointPosition(i, scale.drawingArea + 5);
- textSize = measureLabelSize(scale.ctx, plFont.lineHeight, scale.pointLabels[i] || '');
- scale._pointLabelSizes[i] = textSize;
-
- // Add quarter circle to make degree 0 mean top of circle
- var angleRadians = scale.getIndexAngle(i);
- var angle = helpers$1.toDegrees(angleRadians) % 360;
- var hLimits = determineLimits(angle, pointPosition.x, textSize.w, 0, 180);
- var vLimits = determineLimits(angle, pointPosition.y, textSize.h, 90, 270);
-
- if (hLimits.start < furthestLimits.l) {
- furthestLimits.l = hLimits.start;
- furthestAngles.l = angleRadians;
- }
-
- if (hLimits.end > furthestLimits.r) {
- furthestLimits.r = hLimits.end;
- furthestAngles.r = angleRadians;
- }
-
- if (vLimits.start < furthestLimits.t) {
- furthestLimits.t = vLimits.start;
- furthestAngles.t = angleRadians;
- }
-
- if (vLimits.end > furthestLimits.b) {
- furthestLimits.b = vLimits.end;
- furthestAngles.b = angleRadians;
- }
- }
-
- scale.setReductions(scale.drawingArea, furthestLimits, furthestAngles);
-}
-
-function getTextAlignForAngle(angle) {
- if (angle === 0 || angle === 180) {
- return 'center';
- } else if (angle < 180) {
- return 'left';
- }
-
- return 'right';
-}
-
-function fillText(ctx, text, position, lineHeight) {
- var y = position.y + lineHeight / 2;
- var i, ilen;
-
- if (helpers$1.isArray(text)) {
- for (i = 0, ilen = text.length; i < ilen; ++i) {
- ctx.fillText(text[i], position.x, y);
- y += lineHeight;
- }
- } else {
- ctx.fillText(text, position.x, y);
- }
-}
-
-function adjustPointPositionForLabelHeight(angle, textSize, position) {
- if (angle === 90 || angle === 270) {
- position.y -= (textSize.h / 2);
- } else if (angle > 270 || angle < 90) {
- position.y -= textSize.h;
- }
-}
-
-function drawPointLabels(scale) {
- var ctx = scale.ctx;
- var opts = scale.options;
- var angleLineOpts = opts.angleLines;
- var gridLineOpts = opts.gridLines;
- var pointLabelOpts = opts.pointLabels;
- var lineWidth = valueOrDefault$b(angleLineOpts.lineWidth, gridLineOpts.lineWidth);
- var lineColor = valueOrDefault$b(angleLineOpts.color, gridLineOpts.color);
- var tickBackdropHeight = getTickBackdropHeight(opts);
-
- ctx.save();
- ctx.lineWidth = lineWidth;
- ctx.strokeStyle = lineColor;
- if (ctx.setLineDash) {
- ctx.setLineDash(resolve$7([angleLineOpts.borderDash, gridLineOpts.borderDash, []]));
- ctx.lineDashOffset = resolve$7([angleLineOpts.borderDashOffset, gridLineOpts.borderDashOffset, 0.0]);
- }
-
- var outerDistance = scale.getDistanceFromCenterForValue(opts.ticks.reverse ? scale.min : scale.max);
-
- // Point Label Font
- var plFont = helpers$1.options._parseFont(pointLabelOpts);
-
- ctx.font = plFont.string;
- ctx.textBaseline = 'middle';
-
- for (var i = getValueCount(scale) - 1; i >= 0; i--) {
- if (angleLineOpts.display && lineWidth && lineColor) {
- var outerPosition = scale.getPointPosition(i, outerDistance);
- ctx.beginPath();
- ctx.moveTo(scale.xCenter, scale.yCenter);
- ctx.lineTo(outerPosition.x, outerPosition.y);
- ctx.stroke();
- }
-
- if (pointLabelOpts.display) {
- // Extra pixels out for some label spacing
- var extra = (i === 0 ? tickBackdropHeight / 2 : 0);
- var pointLabelPosition = scale.getPointPosition(i, outerDistance + extra + 5);
-
- // Keep this in loop since we may support array properties here
- var pointLabelFontColor = valueAtIndexOrDefault$1(pointLabelOpts.fontColor, i, core_defaults.global.defaultFontColor);
- ctx.fillStyle = pointLabelFontColor;
-
- var angleRadians = scale.getIndexAngle(i);
- var angle = helpers$1.toDegrees(angleRadians);
- ctx.textAlign = getTextAlignForAngle(angle);
- adjustPointPositionForLabelHeight(angle, scale._pointLabelSizes[i], pointLabelPosition);
- fillText(ctx, scale.pointLabels[i] || '', pointLabelPosition, plFont.lineHeight);
- }
- }
- ctx.restore();
-}
-
-function drawRadiusLine(scale, gridLineOpts, radius, index) {
- var ctx = scale.ctx;
- var circular = gridLineOpts.circular;
- var valueCount = getValueCount(scale);
- var lineColor = valueAtIndexOrDefault$1(gridLineOpts.color, index - 1);
- var lineWidth = valueAtIndexOrDefault$1(gridLineOpts.lineWidth, index - 1);
- var pointPosition;
-
- if ((!circular && !valueCount) || !lineColor || !lineWidth) {
- return;
- }
-
- ctx.save();
- ctx.strokeStyle = lineColor;
- ctx.lineWidth = lineWidth;
- if (ctx.setLineDash) {
- ctx.setLineDash(gridLineOpts.borderDash || []);
- ctx.lineDashOffset = gridLineOpts.borderDashOffset || 0.0;
- }
-
- ctx.beginPath();
- if (circular) {
- // Draw circular arcs between the points
- ctx.arc(scale.xCenter, scale.yCenter, radius, 0, Math.PI * 2);
- } else {
- // Draw straight lines connecting each index
- pointPosition = scale.getPointPosition(0, radius);
- ctx.moveTo(pointPosition.x, pointPosition.y);
-
- for (var i = 1; i < valueCount; i++) {
- pointPosition = scale.getPointPosition(i, radius);
- ctx.lineTo(pointPosition.x, pointPosition.y);
- }
- }
- ctx.closePath();
- ctx.stroke();
- ctx.restore();
-}
-
-function numberOrZero(param) {
- return helpers$1.isNumber(param) ? param : 0;
-}
-
-var scale_radialLinear = scale_linearbase.extend({
- setDimensions: function() {
- var me = this;
-
- // Set the unconstrained dimension before label rotation
- me.width = me.maxWidth;
- me.height = me.maxHeight;
- me.paddingTop = getTickBackdropHeight(me.options) / 2;
- me.xCenter = Math.floor(me.width / 2);
- me.yCenter = Math.floor((me.height - me.paddingTop) / 2);
- me.drawingArea = Math.min(me.height - me.paddingTop, me.width) / 2;
- },
-
- determineDataLimits: function() {
- var me = this;
- var chart = me.chart;
- var min = Number.POSITIVE_INFINITY;
- var max = Number.NEGATIVE_INFINITY;
-
- helpers$1.each(chart.data.datasets, function(dataset, datasetIndex) {
- if (chart.isDatasetVisible(datasetIndex)) {
- var meta = chart.getDatasetMeta(datasetIndex);
-
- helpers$1.each(dataset.data, function(rawValue, index) {
- var value = +me.getRightValue(rawValue);
- if (isNaN(value) || meta.data[index].hidden) {
- return;
- }
-
- min = Math.min(value, min);
- max = Math.max(value, max);
- });
- }
- });
-
- me.min = (min === Number.POSITIVE_INFINITY ? 0 : min);
- me.max = (max === Number.NEGATIVE_INFINITY ? 0 : max);
-
- // Common base implementation to handle ticks.min, ticks.max, ticks.beginAtZero
- me.handleTickRangeOptions();
- },
-
- // Returns the maximum number of ticks based on the scale dimension
- _computeTickLimit: function() {
- return Math.ceil(this.drawingArea / getTickBackdropHeight(this.options));
- },
-
- convertTicksToLabels: function() {
- var me = this;
-
- scale_linearbase.prototype.convertTicksToLabels.call(me);
-
- // Point labels
- me.pointLabels = me.chart.data.labels.map(me.options.pointLabels.callback, me);
- },
-
- getLabelForIndex: function(index, datasetIndex) {
- return +this.getRightValue(this.chart.data.datasets[datasetIndex].data[index]);
- },
-
- fit: function() {
- var me = this;
- var opts = me.options;
-
- if (opts.display && opts.pointLabels.display) {
- fitWithPointLabels(me);
- } else {
- me.setCenterPoint(0, 0, 0, 0);
- }
- },
-
- /**
- * Set radius reductions and determine new radius and center point
- * @private
- */
- setReductions: function(largestPossibleRadius, furthestLimits, furthestAngles) {
- var me = this;
- var radiusReductionLeft = furthestLimits.l / Math.sin(furthestAngles.l);
- var radiusReductionRight = Math.max(furthestLimits.r - me.width, 0) / Math.sin(furthestAngles.r);
- var radiusReductionTop = -furthestLimits.t / Math.cos(furthestAngles.t);
- var radiusReductionBottom = -Math.max(furthestLimits.b - (me.height - me.paddingTop), 0) / Math.cos(furthestAngles.b);
-
- radiusReductionLeft = numberOrZero(radiusReductionLeft);
- radiusReductionRight = numberOrZero(radiusReductionRight);
- radiusReductionTop = numberOrZero(radiusReductionTop);
- radiusReductionBottom = numberOrZero(radiusReductionBottom);
-
- me.drawingArea = Math.min(
- Math.floor(largestPossibleRadius - (radiusReductionLeft + radiusReductionRight) / 2),
- Math.floor(largestPossibleRadius - (radiusReductionTop + radiusReductionBottom) / 2));
- me.setCenterPoint(radiusReductionLeft, radiusReductionRight, radiusReductionTop, radiusReductionBottom);
- },
-
- setCenterPoint: function(leftMovement, rightMovement, topMovement, bottomMovement) {
- var me = this;
- var maxRight = me.width - rightMovement - me.drawingArea;
- var maxLeft = leftMovement + me.drawingArea;
- var maxTop = topMovement + me.drawingArea;
- var maxBottom = (me.height - me.paddingTop) - bottomMovement - me.drawingArea;
-
- me.xCenter = Math.floor(((maxLeft + maxRight) / 2) + me.left);
- me.yCenter = Math.floor(((maxTop + maxBottom) / 2) + me.top + me.paddingTop);
- },
-
- getIndexAngle: function(index) {
- var angleMultiplier = (Math.PI * 2) / getValueCount(this);
- var startAngle = this.chart.options && this.chart.options.startAngle ?
- this.chart.options.startAngle :
- 0;
-
- var startAngleRadians = startAngle * Math.PI * 2 / 360;
-
- // Start from the top instead of right, so remove a quarter of the circle
- return index * angleMultiplier + startAngleRadians;
- },
-
- getDistanceFromCenterForValue: function(value) {
- var me = this;
-
- if (value === null) {
- return 0; // null always in center
- }
-
- // Take into account half font size + the yPadding of the top value
- var scalingFactor = me.drawingArea / (me.max - me.min);
- if (me.options.ticks.reverse) {
- return (me.max - value) * scalingFactor;
- }
- return (value - me.min) * scalingFactor;
- },
-
- getPointPosition: function(index, distanceFromCenter) {
- var me = this;
- var thisAngle = me.getIndexAngle(index) - (Math.PI / 2);
- return {
- x: Math.cos(thisAngle) * distanceFromCenter + me.xCenter,
- y: Math.sin(thisAngle) * distanceFromCenter + me.yCenter
- };
- },
-
- getPointPositionForValue: function(index, value) {
- return this.getPointPosition(index, this.getDistanceFromCenterForValue(value));
- },
-
- getBasePosition: function() {
- var me = this;
- var min = me.min;
- var max = me.max;
-
- return me.getPointPositionForValue(0,
- me.beginAtZero ? 0 :
- min < 0 && max < 0 ? max :
- min > 0 && max > 0 ? min :
- 0);
- },
-
- draw: function() {
- var me = this;
- var opts = me.options;
- var gridLineOpts = opts.gridLines;
- var tickOpts = opts.ticks;
-
- if (opts.display) {
- var ctx = me.ctx;
- var startAngle = this.getIndexAngle(0);
- var tickFont = helpers$1.options._parseFont(tickOpts);
-
- if (opts.angleLines.display || opts.pointLabels.display) {
- drawPointLabels(me);
- }
-
- helpers$1.each(me.ticks, function(label, index) {
- // Don't draw a centre value (if it is minimum)
- if (index > 0 || tickOpts.reverse) {
- var yCenterOffset = me.getDistanceFromCenterForValue(me.ticksAsNumbers[index]);
-
- // Draw circular lines around the scale
- if (gridLineOpts.display && index !== 0) {
- drawRadiusLine(me, gridLineOpts, yCenterOffset, index);
- }
-
- if (tickOpts.display) {
- var tickFontColor = valueOrDefault$b(tickOpts.fontColor, core_defaults.global.defaultFontColor);
- ctx.font = tickFont.string;
-
- ctx.save();
- ctx.translate(me.xCenter, me.yCenter);
- ctx.rotate(startAngle);
-
- if (tickOpts.showLabelBackdrop) {
- var labelWidth = ctx.measureText(label).width;
- ctx.fillStyle = tickOpts.backdropColor;
- ctx.fillRect(
- -labelWidth / 2 - tickOpts.backdropPaddingX,
- -yCenterOffset - tickFont.size / 2 - tickOpts.backdropPaddingY,
- labelWidth + tickOpts.backdropPaddingX * 2,
- tickFont.size + tickOpts.backdropPaddingY * 2
- );
- }
-
- ctx.textAlign = 'center';
- ctx.textBaseline = 'middle';
- ctx.fillStyle = tickFontColor;
- ctx.fillText(label, 0, -yCenterOffset);
- ctx.restore();
- }
- }
- });
- }
- }
-});
-
-// INTERNAL: static default options, registered in src/index.js
-var _defaults$3 = defaultConfig$3;
-scale_radialLinear._defaults = _defaults$3;
-
-var valueOrDefault$c = helpers$1.valueOrDefault;
-
-// Integer constants are from the ES6 spec.
-var MIN_INTEGER = Number.MIN_SAFE_INTEGER || -9007199254740991;
-var MAX_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991;
-
-var INTERVALS = {
- millisecond: {
- common: true,
- size: 1,
- steps: [1, 2, 5, 10, 20, 50, 100, 250, 500]
- },
- second: {
- common: true,
- size: 1000,
- steps: [1, 2, 5, 10, 15, 30]
- },
- minute: {
- common: true,
- size: 60000,
- steps: [1, 2, 5, 10, 15, 30]
- },
- hour: {
- common: true,
- size: 3600000,
- steps: [1, 2, 3, 6, 12]
- },
- day: {
- common: true,
- size: 86400000,
- steps: [1, 2, 5]
- },
- week: {
- common: false,
- size: 604800000,
- steps: [1, 2, 3, 4]
- },
- month: {
- common: true,
- size: 2.628e9,
- steps: [1, 2, 3]
- },
- quarter: {
- common: false,
- size: 7.884e9,
- steps: [1, 2, 3, 4]
- },
- year: {
- common: true,
- size: 3.154e10
- }
-};
-
-var UNITS = Object.keys(INTERVALS);
-
-function sorter(a, b) {
- return a - b;
-}
-
-function arrayUnique(items) {
- var hash = {};
- var out = [];
- var i, ilen, item;
-
- for (i = 0, ilen = items.length; i < ilen; ++i) {
- item = items[i];
- if (!hash[item]) {
- hash[item] = true;
- out.push(item);
- }
- }
-
- return out;
-}
-
-/**
- * Returns an array of {time, pos} objects used to interpolate a specific `time` or position
- * (`pos`) on the scale, by searching entries before and after the requested value. `pos` is
- * a decimal between 0 and 1: 0 being the start of the scale (left or top) and 1 the other
- * extremity (left + width or top + height). Note that it would be more optimized to directly
- * store pre-computed pixels, but the scale dimensions are not guaranteed at the time we need
- * to create the lookup table. The table ALWAYS contains at least two items: min and max.
- *
- * @param {number[]} timestamps - timestamps sorted from lowest to highest.
- * @param {string} distribution - If 'linear', timestamps will be spread linearly along the min
- * and max range, so basically, the table will contains only two items: {min, 0} and {max, 1}.
- * If 'series', timestamps will be positioned at the same distance from each other. In this
- * case, only timestamps that break the time linearity are registered, meaning that in the
- * best case, all timestamps are linear, the table contains only min and max.
- */
-function buildLookupTable(timestamps, min, max, distribution) {
- if (distribution === 'linear' || !timestamps.length) {
- return [
- {time: min, pos: 0},
- {time: max, pos: 1}
- ];
- }
-
- var table = [];
- var items = [min];
- var i, ilen, prev, curr, next;
-
- for (i = 0, ilen = timestamps.length; i < ilen; ++i) {
- curr = timestamps[i];
- if (curr > min && curr < max) {
- items.push(curr);
- }
- }
-
- items.push(max);
-
- for (i = 0, ilen = items.length; i < ilen; ++i) {
- next = items[i + 1];
- prev = items[i - 1];
- curr = items[i];
-
- // only add points that breaks the scale linearity
- if (prev === undefined || next === undefined || Math.round((next + prev) / 2) !== curr) {
- table.push({time: curr, pos: i / (ilen - 1)});
- }
- }
-
- return table;
-}
-
-// @see adapted from https://www.anujgakhar.com/2014/03/01/binary-search-in-javascript/
-function lookup(table, key, value) {
- var lo = 0;
- var hi = table.length - 1;
- var mid, i0, i1;
-
- while (lo >= 0 && lo <= hi) {
- mid = (lo + hi) >> 1;
- i0 = table[mid - 1] || null;
- i1 = table[mid];
-
- if (!i0) {
- // given value is outside table (before first item)
- return {lo: null, hi: i1};
- } else if (i1[key] < value) {
- lo = mid + 1;
- } else if (i0[key] > value) {
- hi = mid - 1;
- } else {
- return {lo: i0, hi: i1};
- }
- }
-
- // given value is outside table (after last item)
- return {lo: i1, hi: null};
-}
-
-/**
- * Linearly interpolates the given source `value` using the table items `skey` values and
- * returns the associated `tkey` value. For example, interpolate(table, 'time', 42, 'pos')
- * returns the position for a timestamp equal to 42. If value is out of bounds, values at
- * index [0, 1] or [n - 1, n] are used for the interpolation.
- */
-function interpolate$1(table, skey, sval, tkey) {
- var range = lookup(table, skey, sval);
-
- // Note: the lookup table ALWAYS contains at least 2 items (min and max)
- var prev = !range.lo ? table[0] : !range.hi ? table[table.length - 2] : range.lo;
- var next = !range.lo ? table[1] : !range.hi ? table[table.length - 1] : range.hi;
-
- var span = next[skey] - prev[skey];
- var ratio = span ? (sval - prev[skey]) / span : 0;
- var offset = (next[tkey] - prev[tkey]) * ratio;
-
- return prev[tkey] + offset;
-}
-
-function toTimestamp(scale, input) {
- var adapter = scale._adapter;
- var options = scale.options.time;
- var parser = options.parser;
- var format = parser || options.format;
- var value = input;
-
- if (typeof parser === 'function') {
- value = parser(value);
- }
-
- // Only parse if its not a timestamp already
- if (!helpers$1.isFinite(value)) {
- value = typeof format === 'string'
- ? adapter.parse(value, format)
- : adapter.parse(value);
- }
-
- if (value !== null) {
- return +value;
- }
-
- // Labels are in an incompatible format and no `parser` has been provided.
- // The user might still use the deprecated `format` option for parsing.
- if (!parser && typeof format === 'function') {
- value = format(input);
-
- // `format` could return something else than a timestamp, if so, parse it
- if (!helpers$1.isFinite(value)) {
- value = adapter.parse(value);
- }
- }
-
- return value;
-}
-
-function parse(scale, input) {
- if (helpers$1.isNullOrUndef(input)) {
- return null;
- }
-
- var options = scale.options.time;
- var value = toTimestamp(scale, scale.getRightValue(input));
- if (value === null) {
- return value;
- }
-
- if (options.round) {
- value = +scale._adapter.startOf(value, options.round);
- }
-
- return value;
-}
-
-/**
- * Returns the number of unit to skip to be able to display up to `capacity` number of ticks
- * in `unit` for the given `min` / `max` range and respecting the interval steps constraints.
- */
-function determineStepSize(min, max, unit, capacity) {
- var range = max - min;
- var interval = INTERVALS[unit];
- var milliseconds = interval.size;
- var steps = interval.steps;
- var i, ilen, factor;
-
- if (!steps) {
- return Math.ceil(range / (capacity * milliseconds));
- }
-
- for (i = 0, ilen = steps.length; i < ilen; ++i) {
- factor = steps[i];
- if (Math.ceil(range / (milliseconds * factor)) <= capacity) {
- break;
- }
- }
-
- return factor;
-}
-
-/**
- * Figures out what unit results in an appropriate number of auto-generated ticks
- */
-function determineUnitForAutoTicks(minUnit, min, max, capacity) {
- var ilen = UNITS.length;
- var i, interval, factor;
-
- for (i = UNITS.indexOf(minUnit); i < ilen - 1; ++i) {
- interval = INTERVALS[UNITS[i]];
- factor = interval.steps ? interval.steps[interval.steps.length - 1] : MAX_INTEGER;
-
- if (interval.common && Math.ceil((max - min) / (factor * interval.size)) <= capacity) {
- return UNITS[i];
- }
- }
-
- return UNITS[ilen - 1];
-}
-
-/**
- * Figures out what unit to format a set of ticks with
- */
-function determineUnitForFormatting(scale, ticks, minUnit, min, max) {
- var ilen = UNITS.length;
- var i, unit;
-
- for (i = ilen - 1; i >= UNITS.indexOf(minUnit); i--) {
- unit = UNITS[i];
- if (INTERVALS[unit].common && scale._adapter.diff(max, min, unit) >= ticks.length) {
- return unit;
- }
- }
-
- return UNITS[minUnit ? UNITS.indexOf(minUnit) : 0];
-}
-
-function determineMajorUnit(unit) {
- for (var i = UNITS.indexOf(unit) + 1, ilen = UNITS.length; i < ilen; ++i) {
- if (INTERVALS[UNITS[i]].common) {
- return UNITS[i];
- }
- }
-}
-
-/**
- * Generates a maximum of `capacity` timestamps between min and max, rounded to the
- * `minor` unit, aligned on the `major` unit and using the given scale time `options`.
- * Important: this method can return ticks outside the min and max range, it's the
- * responsibility of the calling code to clamp values if needed.
- */
-function generate(scale, min, max, capacity) {
- var adapter = scale._adapter;
- var options = scale.options;
- var timeOpts = options.time;
- var minor = timeOpts.unit || determineUnitForAutoTicks(timeOpts.minUnit, min, max, capacity);
- var major = determineMajorUnit(minor);
- var stepSize = valueOrDefault$c(timeOpts.stepSize, timeOpts.unitStepSize);
- var weekday = minor === 'week' ? timeOpts.isoWeekday : false;
- var majorTicksEnabled = options.ticks.major.enabled;
- var interval = INTERVALS[minor];
- var first = min;
- var last = max;
- var ticks = [];
- var time;
-
- if (!stepSize) {
- stepSize = determineStepSize(min, max, minor, capacity);
- }
-
- // For 'week' unit, handle the first day of week option
- if (weekday) {
- first = +adapter.startOf(first, 'isoWeek', weekday);
- last = +adapter.startOf(last, 'isoWeek', weekday);
- }
-
- // Align first/last ticks on unit
- first = +adapter.startOf(first, weekday ? 'day' : minor);
- last = +adapter.startOf(last, weekday ? 'day' : minor);
-
- // Make sure that the last tick include max
- if (last < max) {
- last = +adapter.add(last, 1, minor);
- }
-
- time = first;
-
- if (majorTicksEnabled && major && !weekday && !timeOpts.round) {
- // Align the first tick on the previous `minor` unit aligned on the `major` unit:
- // we first aligned time on the previous `major` unit then add the number of full
- // stepSize there is between first and the previous major time.
- time = +adapter.startOf(time, major);
- time = +adapter.add(time, ~~((first - time) / (interval.size * stepSize)) * stepSize, minor);
- }
-
- for (; time < last; time = +adapter.add(time, stepSize, minor)) {
- ticks.push(+time);
- }
-
- ticks.push(+time);
-
- return ticks;
-}
-
-/**
- * Returns the start and end offsets from edges in the form of {start, end}
- * where each value is a relative width to the scale and ranges between 0 and 1.
- * They add extra margins on the both sides by scaling down the original scale.
- * Offsets are added when the `offset` option is true.
- */
-function computeOffsets(table, ticks, min, max, options) {
- var start = 0;
- var end = 0;
- var first, last;
-
- if (options.offset && ticks.length) {
- if (!options.time.min) {
- first = interpolate$1(table, 'time', ticks[0], 'pos');
- if (ticks.length === 1) {
- start = 1 - first;
- } else {
- start = (interpolate$1(table, 'time', ticks[1], 'pos') - first) / 2;
- }
- }
- if (!options.time.max) {
- last = interpolate$1(table, 'time', ticks[ticks.length - 1], 'pos');
- if (ticks.length === 1) {
- end = last;
- } else {
- end = (last - interpolate$1(table, 'time', ticks[ticks.length - 2], 'pos')) / 2;
- }
- }
- }
-
- return {start: start, end: end};
-}
-
-function ticksFromTimestamps(scale, values, majorUnit) {
- var ticks = [];
- var i, ilen, value, major;
-
- for (i = 0, ilen = values.length; i < ilen; ++i) {
- value = values[i];
- major = majorUnit ? value === +scale._adapter.startOf(value, majorUnit) : false;
-
- ticks.push({
- value: value,
- major: major
- });
- }
-
- return ticks;
-}
-
-var defaultConfig$4 = {
- position: 'bottom',
-
- /**
- * Data distribution along the scale:
- * - 'linear': data are spread according to their time (distances can vary),
- * - 'series': data are spread at the same distance from each other.
- * @see https://github.com/chartjs/Chart.js/pull/4507
- * @since 2.7.0
- */
- distribution: 'linear',
-
- /**
- * Scale boundary strategy (bypassed by min/max time options)
- * - `data`: make sure data are fully visible, ticks outside are removed
- * - `ticks`: make sure ticks are fully visible, data outside are truncated
- * @see https://github.com/chartjs/Chart.js/pull/4556
- * @since 2.7.0
- */
- bounds: 'data',
-
- adapters: {},
- time: {
- parser: false, // false == a pattern string from https://momentjs.com/docs/#/parsing/string-format/ or a custom callback that converts its argument to a moment
- format: false, // DEPRECATED false == date objects, moment object, callback or a pattern string from https://momentjs.com/docs/#/parsing/string-format/
- unit: false, // false == automatic or override with week, month, year, etc.
- round: false, // none, or override with week, month, year, etc.
- displayFormat: false, // DEPRECATED
- isoWeekday: false, // override week start day - see https://momentjs.com/docs/#/get-set/iso-weekday/
- minUnit: 'millisecond',
- displayFormats: {}
- },
- ticks: {
- autoSkip: false,
-
- /**
- * Ticks generation input values:
- * - 'auto': generates "optimal" ticks based on scale size and time options.
- * - 'data': generates ticks from data (including labels from data {t|x|y} objects).
- * - 'labels': generates ticks from user given `data.labels` values ONLY.
- * @see https://github.com/chartjs/Chart.js/pull/4507
- * @since 2.7.0
- */
- source: 'auto',
-
- major: {
- enabled: false
- }
- }
-};
-
-var scale_time = core_scale.extend({
- initialize: function() {
- this.mergeTicksOptions();
- core_scale.prototype.initialize.call(this);
- },
-
- update: function() {
- var me = this;
- var options = me.options;
- var time = options.time || (options.time = {});
- var adapter = me._adapter = new core_adapters._date(options.adapters.date);
-
- // DEPRECATIONS: output a message only one time per update
- if (time.format) {
- console.warn('options.time.format is deprecated and replaced by options.time.parser.');
- }
-
- // Backward compatibility: before introducing adapter, `displayFormats` was
- // supposed to contain *all* unit/string pairs but this can't be resolved
- // when loading the scale (adapters are loaded afterward), so let's populate
- // missing formats on update
- helpers$1.mergeIf(time.displayFormats, adapter.formats());
-
- return core_scale.prototype.update.apply(me, arguments);
- },
-
- /**
- * Allows data to be referenced via 't' attribute
- */
- getRightValue: function(rawValue) {
- if (rawValue && rawValue.t !== undefined) {
- rawValue = rawValue.t;
- }
- return core_scale.prototype.getRightValue.call(this, rawValue);
- },
-
- determineDataLimits: function() {
- var me = this;
- var chart = me.chart;
- var adapter = me._adapter;
- var timeOpts = me.options.time;
- var unit = timeOpts.unit || 'day';
- var min = MAX_INTEGER;
- var max = MIN_INTEGER;
- var timestamps = [];
- var datasets = [];
- var labels = [];
- var i, j, ilen, jlen, data, timestamp;
- var dataLabels = chart.data.labels || [];
-
- // Convert labels to timestamps
- for (i = 0, ilen = dataLabels.length; i < ilen; ++i) {
- labels.push(parse(me, dataLabels[i]));
- }
-
- // Convert data to timestamps
- for (i = 0, ilen = (chart.data.datasets || []).length; i < ilen; ++i) {
- if (chart.isDatasetVisible(i)) {
- data = chart.data.datasets[i].data;
-
- // Let's consider that all data have the same format.
- if (helpers$1.isObject(data[0])) {
- datasets[i] = [];
-
- for (j = 0, jlen = data.length; j < jlen; ++j) {
- timestamp = parse(me, data[j]);
- timestamps.push(timestamp);
- datasets[i][j] = timestamp;
- }
- } else {
- for (j = 0, jlen = labels.length; j < jlen; ++j) {
- timestamps.push(labels[j]);
- }
- datasets[i] = labels.slice(0);
- }
- } else {
- datasets[i] = [];
- }
- }
-
- if (labels.length) {
- // Sort labels **after** data have been converted
- labels = arrayUnique(labels).sort(sorter);
- min = Math.min(min, labels[0]);
- max = Math.max(max, labels[labels.length - 1]);
- }
-
- if (timestamps.length) {
- timestamps = arrayUnique(timestamps).sort(sorter);
- min = Math.min(min, timestamps[0]);
- max = Math.max(max, timestamps[timestamps.length - 1]);
- }
-
- min = parse(me, timeOpts.min) || min;
- max = parse(me, timeOpts.max) || max;
-
- // In case there is no valid min/max, set limits based on unit time option
- min = min === MAX_INTEGER ? +adapter.startOf(Date.now(), unit) : min;
- max = max === MIN_INTEGER ? +adapter.endOf(Date.now(), unit) + 1 : max;
-
- // Make sure that max is strictly higher than min (required by the lookup table)
- me.min = Math.min(min, max);
- me.max = Math.max(min + 1, max);
-
- // PRIVATE
- me._horizontal = me.isHorizontal();
- me._table = [];
- me._timestamps = {
- data: timestamps,
- datasets: datasets,
- labels: labels
- };
- },
-
- buildTicks: function() {
- var me = this;
- var min = me.min;
- var max = me.max;
- var options = me.options;
- var timeOpts = options.time;
- var timestamps = [];
- var ticks = [];
- var i, ilen, timestamp;
-
- switch (options.ticks.source) {
- case 'data':
- timestamps = me._timestamps.data;
- break;
- case 'labels':
- timestamps = me._timestamps.labels;
- break;
- case 'auto':
- default:
- timestamps = generate(me, min, max, me.getLabelCapacity(min), options);
- }
-
- if (options.bounds === 'ticks' && timestamps.length) {
- min = timestamps[0];
- max = timestamps[timestamps.length - 1];
- }
-
- // Enforce limits with user min/max options
- min = parse(me, timeOpts.min) || min;
- max = parse(me, timeOpts.max) || max;
-
- // Remove ticks outside the min/max range
- for (i = 0, ilen = timestamps.length; i < ilen; ++i) {
- timestamp = timestamps[i];
- if (timestamp >= min && timestamp <= max) {
- ticks.push(timestamp);
- }
- }
-
- me.min = min;
- me.max = max;
-
- // PRIVATE
- me._unit = timeOpts.unit || determineUnitForFormatting(me, ticks, timeOpts.minUnit, me.min, me.max);
- me._majorUnit = determineMajorUnit(me._unit);
- me._table = buildLookupTable(me._timestamps.data, min, max, options.distribution);
- me._offsets = computeOffsets(me._table, ticks, min, max, options);
-
- if (options.ticks.reverse) {
- ticks.reverse();
- }
-
- return ticksFromTimestamps(me, ticks, me._majorUnit);
- },
-
- getLabelForIndex: function(index, datasetIndex) {
- var me = this;
- var adapter = me._adapter;
- var data = me.chart.data;
- var timeOpts = me.options.time;
- var label = data.labels && index < data.labels.length ? data.labels[index] : '';
- var value = data.datasets[datasetIndex].data[index];
-
- if (helpers$1.isObject(value)) {
- label = me.getRightValue(value);
- }
- if (timeOpts.tooltipFormat) {
- return adapter.format(toTimestamp(me, label), timeOpts.tooltipFormat);
- }
- if (typeof label === 'string') {
- return label;
- }
- return adapter.format(toTimestamp(me, label), timeOpts.displayFormats.datetime);
- },
-
- /**
- * Function to format an individual tick mark
- * @private
- */
- tickFormatFunction: function(time, index, ticks, format) {
- var me = this;
- var adapter = me._adapter;
- var options = me.options;
- var formats = options.time.displayFormats;
- var minorFormat = formats[me._unit];
- var majorUnit = me._majorUnit;
- var majorFormat = formats[majorUnit];
- var majorTime = +adapter.startOf(time, majorUnit);
- var majorTickOpts = options.ticks.major;
- var major = majorTickOpts.enabled && majorUnit && majorFormat && time === majorTime;
- var label = adapter.format(time, format ? format : major ? majorFormat : minorFormat);
- var tickOpts = major ? majorTickOpts : options.ticks.minor;
- var formatter = valueOrDefault$c(tickOpts.callback, tickOpts.userCallback);
-
- return formatter ? formatter(label, index, ticks) : label;
- },
-
- convertTicksToLabels: function(ticks) {
- var labels = [];
- var i, ilen;
-
- for (i = 0, ilen = ticks.length; i < ilen; ++i) {
- labels.push(this.tickFormatFunction(ticks[i].value, i, ticks));
- }
-
- return labels;
- },
-
- /**
- * @private
- */
- getPixelForOffset: function(time) {
- var me = this;
- var isReverse = me.options.ticks.reverse;
- var size = me._horizontal ? me.width : me.height;
- var start = me._horizontal ? isReverse ? me.right : me.left : isReverse ? me.bottom : me.top;
- var pos = interpolate$1(me._table, 'time', time, 'pos');
- var offset = size * (me._offsets.start + pos) / (me._offsets.start + 1 + me._offsets.end);
-
- return isReverse ? start - offset : start + offset;
- },
-
- getPixelForValue: function(value, index, datasetIndex) {
- var me = this;
- var time = null;
-
- if (index !== undefined && datasetIndex !== undefined) {
- time = me._timestamps.datasets[datasetIndex][index];
- }
-
- if (time === null) {
- time = parse(me, value);
- }
-
- if (time !== null) {
- return me.getPixelForOffset(time);
- }
- },
-
- getPixelForTick: function(index) {
- var ticks = this.getTicks();
- return index >= 0 && index < ticks.length ?
- this.getPixelForOffset(ticks[index].value) :
- null;
- },
-
- getValueForPixel: function(pixel) {
- var me = this;
- var size = me._horizontal ? me.width : me.height;
- var start = me._horizontal ? me.left : me.top;
- var pos = (size ? (pixel - start) / size : 0) * (me._offsets.start + 1 + me._offsets.start) - me._offsets.end;
- var time = interpolate$1(me._table, 'pos', pos, 'time');
-
- // DEPRECATION, we should return time directly
- return me._adapter._create(time);
- },
-
- /**
- * Crude approximation of what the label width might be
- * @private
- */
- getLabelWidth: function(label) {
- var me = this;
- var ticksOpts = me.options.ticks;
- var tickLabelWidth = me.ctx.measureText(label).width;
- var angle = helpers$1.toRadians(ticksOpts.maxRotation);
- var cosRotation = Math.cos(angle);
- var sinRotation = Math.sin(angle);
- var tickFontSize = valueOrDefault$c(ticksOpts.fontSize, core_defaults.global.defaultFontSize);
-
- return (tickLabelWidth * cosRotation) + (tickFontSize * sinRotation);
- },
-
- /**
- * @private
- */
- getLabelCapacity: function(exampleTime) {
- var me = this;
-
- // pick the longest format (milliseconds) for guestimation
- var format = me.options.time.displayFormats.millisecond;
- var exampleLabel = me.tickFormatFunction(exampleTime, 0, [], format);
- var tickLabelWidth = me.getLabelWidth(exampleLabel);
- var innerWidth = me.isHorizontal() ? me.width : me.height;
- var capacity = Math.floor(innerWidth / tickLabelWidth);
-
- return capacity > 0 ? capacity : 1;
- }
-});
-
-// INTERNAL: static default options, registered in src/index.js
-var _defaults$4 = defaultConfig$4;
-scale_time._defaults = _defaults$4;
-
-var scales = {
- category: scale_category,
- linear: scale_linear,
- logarithmic: scale_logarithmic,
- radialLinear: scale_radialLinear,
- time: scale_time
-};
-
-var moment = createCommonjsModule(function (module, exports) {
-(function (global, factory) {
- module.exports = factory();
-}(commonjsGlobal, (function () {
- var hookCallback;
-
- function hooks () {
- return hookCallback.apply(null, arguments);
- }
-
- // This is done to register the method called with moment()
- // without creating circular dependencies.
- function setHookCallback (callback) {
- hookCallback = callback;
- }
-
- function isArray(input) {
- return input instanceof Array || Object.prototype.toString.call(input) === '[object Array]';
- }
-
- function isObject(input) {
- // IE8 will treat undefined and null as object if it wasn't for
- // input != null
- return input != null && Object.prototype.toString.call(input) === '[object Object]';
- }
-
- function isObjectEmpty(obj) {
- if (Object.getOwnPropertyNames) {
- return (Object.getOwnPropertyNames(obj).length === 0);
- } else {
- var k;
- for (k in obj) {
- if (obj.hasOwnProperty(k)) {
- return false;
- }
- }
- return true;
- }
- }
-
- function isUndefined(input) {
- return input === void 0;
- }
-
- function isNumber(input) {
- return typeof input === 'number' || Object.prototype.toString.call(input) === '[object Number]';
- }
-
- function isDate(input) {
- return input instanceof Date || Object.prototype.toString.call(input) === '[object Date]';
- }
-
- function map(arr, fn) {
- var res = [], i;
- for (i = 0; i < arr.length; ++i) {
- res.push(fn(arr[i], i));
- }
- return res;
- }
-
- function hasOwnProp(a, b) {
- return Object.prototype.hasOwnProperty.call(a, b);
- }
-
- function extend(a, b) {
- for (var i in b) {
- if (hasOwnProp(b, i)) {
- a[i] = b[i];
- }
- }
-
- if (hasOwnProp(b, 'toString')) {
- a.toString = b.toString;
- }
-
- if (hasOwnProp(b, 'valueOf')) {
- a.valueOf = b.valueOf;
- }
-
- return a;
- }
-
- function createUTC (input, format, locale, strict) {
- return createLocalOrUTC(input, format, locale, strict, true).utc();
- }
-
- function defaultParsingFlags() {
- // We need to deep clone this object.
- return {
- empty : false,
- unusedTokens : [],
- unusedInput : [],
- overflow : -2,
- charsLeftOver : 0,
- nullInput : false,
- invalidMonth : null,
- invalidFormat : false,
- userInvalidated : false,
- iso : false,
- parsedDateParts : [],
- meridiem : null,
- rfc2822 : false,
- weekdayMismatch : false
- };
- }
-
- function getParsingFlags(m) {
- if (m._pf == null) {
- m._pf = defaultParsingFlags();
- }
- return m._pf;
- }
-
- var some;
- if (Array.prototype.some) {
- some = Array.prototype.some;
- } else {
- some = function (fun) {
- var t = Object(this);
- var len = t.length >>> 0;
-
- for (var i = 0; i < len; i++) {
- if (i in t && fun.call(this, t[i], i, t)) {
- return true;
- }
- }
-
- return false;
- };
- }
-
- function isValid(m) {
- if (m._isValid == null) {
- var flags = getParsingFlags(m);
- var parsedParts = some.call(flags.parsedDateParts, function (i) {
- return i != null;
- });
- var isNowValid = !isNaN(m._d.getTime()) &&
- flags.overflow < 0 &&
- !flags.empty &&
- !flags.invalidMonth &&
- !flags.invalidWeekday &&
- !flags.weekdayMismatch &&
- !flags.nullInput &&
- !flags.invalidFormat &&
- !flags.userInvalidated &&
- (!flags.meridiem || (flags.meridiem && parsedParts));
-
- if (m._strict) {
- isNowValid = isNowValid &&
- flags.charsLeftOver === 0 &&
- flags.unusedTokens.length === 0 &&
- flags.bigHour === undefined;
- }
-
- if (Object.isFrozen == null || !Object.isFrozen(m)) {
- m._isValid = isNowValid;
- }
- else {
- return isNowValid;
- }
- }
- return m._isValid;
- }
-
- function createInvalid (flags) {
- var m = createUTC(NaN);
- if (flags != null) {
- extend(getParsingFlags(m), flags);
- }
- else {
- getParsingFlags(m).userInvalidated = true;
- }
-
- return m;
- }
-
- // Plugins that add properties should also add the key here (null value),
- // so we can properly clone ourselves.
- var momentProperties = hooks.momentProperties = [];
-
- function copyConfig(to, from) {
- var i, prop, val;
-
- if (!isUndefined(from._isAMomentObject)) {
- to._isAMomentObject = from._isAMomentObject;
- }
- if (!isUndefined(from._i)) {
- to._i = from._i;
- }
- if (!isUndefined(from._f)) {
- to._f = from._f;
- }
- if (!isUndefined(from._l)) {
- to._l = from._l;
- }
- if (!isUndefined(from._strict)) {
- to._strict = from._strict;
- }
- if (!isUndefined(from._tzm)) {
- to._tzm = from._tzm;
- }
- if (!isUndefined(from._isUTC)) {
- to._isUTC = from._isUTC;
- }
- if (!isUndefined(from._offset)) {
- to._offset = from._offset;
- }
- if (!isUndefined(from._pf)) {
- to._pf = getParsingFlags(from);
- }
- if (!isUndefined(from._locale)) {
- to._locale = from._locale;
- }
-
- if (momentProperties.length > 0) {
- for (i = 0; i < momentProperties.length; i++) {
- prop = momentProperties[i];
- val = from[prop];
- if (!isUndefined(val)) {
- to[prop] = val;
- }
- }
- }
-
- return to;
- }
-
- var updateInProgress = false;
-
- // Moment prototype object
- function Moment(config) {
- copyConfig(this, config);
- this._d = new Date(config._d != null ? config._d.getTime() : NaN);
- if (!this.isValid()) {
- this._d = new Date(NaN);
- }
- // Prevent infinite loop in case updateOffset creates new moment
- // objects.
- if (updateInProgress === false) {
- updateInProgress = true;
- hooks.updateOffset(this);
- updateInProgress = false;
- }
- }
-
- function isMoment (obj) {
- return obj instanceof Moment || (obj != null && obj._isAMomentObject != null);
- }
-
- function absFloor (number) {
- if (number < 0) {
- // -0 -> 0
- return Math.ceil(number) || 0;
- } else {
- return Math.floor(number);
- }
- }
-
- function toInt(argumentForCoercion) {
- var coercedNumber = +argumentForCoercion,
- value = 0;
-
- if (coercedNumber !== 0 && isFinite(coercedNumber)) {
- value = absFloor(coercedNumber);
- }
-
- return value;
- }
-
- // compare two arrays, return the number of differences
- function compareArrays(array1, array2, dontConvert) {
- var len = Math.min(array1.length, array2.length),
- lengthDiff = Math.abs(array1.length - array2.length),
- diffs = 0,
- i;
- for (i = 0; i < len; i++) {
- if ((dontConvert && array1[i] !== array2[i]) ||
- (!dontConvert && toInt(array1[i]) !== toInt(array2[i]))) {
- diffs++;
- }
- }
- return diffs + lengthDiff;
- }
-
- function warn(msg) {
- if (hooks.suppressDeprecationWarnings === false &&
- (typeof console !== 'undefined') && console.warn) {
- console.warn('Deprecation warning: ' + msg);
- }
- }
-
- function deprecate(msg, fn) {
- var firstTime = true;
-
- return extend(function () {
- if (hooks.deprecationHandler != null) {
- hooks.deprecationHandler(null, msg);
- }
- if (firstTime) {
- var args = [];
- var arg;
- for (var i = 0; i < arguments.length; i++) {
- arg = '';
- if (typeof arguments[i] === 'object') {
- arg += '\n[' + i + '] ';
- for (var key in arguments[0]) {
- arg += key + ': ' + arguments[0][key] + ', ';
- }
- arg = arg.slice(0, -2); // Remove trailing comma and space
- } else {
- arg = arguments[i];
- }
- args.push(arg);
- }
- warn(msg + '\nArguments: ' + Array.prototype.slice.call(args).join('') + '\n' + (new Error()).stack);
- firstTime = false;
- }
- return fn.apply(this, arguments);
- }, fn);
- }
-
- var deprecations = {};
-
- function deprecateSimple(name, msg) {
- if (hooks.deprecationHandler != null) {
- hooks.deprecationHandler(name, msg);
- }
- if (!deprecations[name]) {
- warn(msg);
- deprecations[name] = true;
- }
- }
-
- hooks.suppressDeprecationWarnings = false;
- hooks.deprecationHandler = null;
-
- function isFunction(input) {
- return input instanceof Function || Object.prototype.toString.call(input) === '[object Function]';
- }
-
- function set (config) {
- var prop, i;
- for (i in config) {
- prop = config[i];
- if (isFunction(prop)) {
- this[i] = prop;
- } else {
- this['_' + i] = prop;
- }
- }
- this._config = config;
- // Lenient ordinal parsing accepts just a number in addition to
- // number + (possibly) stuff coming from _dayOfMonthOrdinalParse.
- // TODO: Remove "ordinalParse" fallback in next major release.
- this._dayOfMonthOrdinalParseLenient = new RegExp(
- (this._dayOfMonthOrdinalParse.source || this._ordinalParse.source) +
- '|' + (/\d{1,2}/).source);
- }
-
- function mergeConfigs(parentConfig, childConfig) {
- var res = extend({}, parentConfig), prop;
- for (prop in childConfig) {
- if (hasOwnProp(childConfig, prop)) {
- if (isObject(parentConfig[prop]) && isObject(childConfig[prop])) {
- res[prop] = {};
- extend(res[prop], parentConfig[prop]);
- extend(res[prop], childConfig[prop]);
- } else if (childConfig[prop] != null) {
- res[prop] = childConfig[prop];
- } else {
- delete res[prop];
- }
- }
- }
- for (prop in parentConfig) {
- if (hasOwnProp(parentConfig, prop) &&
- !hasOwnProp(childConfig, prop) &&
- isObject(parentConfig[prop])) {
- // make sure changes to properties don't modify parent config
- res[prop] = extend({}, res[prop]);
- }
- }
- return res;
- }
-
- function Locale(config) {
- if (config != null) {
- this.set(config);
- }
- }
-
- var keys;
-
- if (Object.keys) {
- keys = Object.keys;
- } else {
- keys = function (obj) {
- var i, res = [];
- for (i in obj) {
- if (hasOwnProp(obj, i)) {
- res.push(i);
- }
- }
- return res;
- };
- }
-
- var defaultCalendar = {
- sameDay : '[Today at] LT',
- nextDay : '[Tomorrow at] LT',
- nextWeek : 'dddd [at] LT',
- lastDay : '[Yesterday at] LT',
- lastWeek : '[Last] dddd [at] LT',
- sameElse : 'L'
- };
-
- function calendar (key, mom, now) {
- var output = this._calendar[key] || this._calendar['sameElse'];
- return isFunction(output) ? output.call(mom, now) : output;
- }
-
- var defaultLongDateFormat = {
- LTS : 'h:mm:ss A',
- LT : 'h:mm A',
- L : 'MM/DD/YYYY',
- LL : 'MMMM D, YYYY',
- LLL : 'MMMM D, YYYY h:mm A',
- LLLL : 'dddd, MMMM D, YYYY h:mm A'
- };
-
- function longDateFormat (key) {
- var format = this._longDateFormat[key],
- formatUpper = this._longDateFormat[key.toUpperCase()];
-
- if (format || !formatUpper) {
- return format;
- }
-
- this._longDateFormat[key] = formatUpper.replace(/MMMM|MM|DD|dddd/g, function (val) {
- return val.slice(1);
- });
-
- return this._longDateFormat[key];
- }
-
- var defaultInvalidDate = 'Invalid date';
-
- function invalidDate () {
- return this._invalidDate;
- }
-
- var defaultOrdinal = '%d';
- var defaultDayOfMonthOrdinalParse = /\d{1,2}/;
-
- function ordinal (number) {
- return this._ordinal.replace('%d', number);
- }
-
- var defaultRelativeTime = {
- future : 'in %s',
- past : '%s ago',
- s : 'a few seconds',
- ss : '%d seconds',
- m : 'a minute',
- mm : '%d minutes',
- h : 'an hour',
- hh : '%d hours',
- d : 'a day',
- dd : '%d days',
- M : 'a month',
- MM : '%d months',
- y : 'a year',
- yy : '%d years'
- };
-
- function relativeTime (number, withoutSuffix, string, isFuture) {
- var output = this._relativeTime[string];
- return (isFunction(output)) ?
- output(number, withoutSuffix, string, isFuture) :
- output.replace(/%d/i, number);
- }
-
- function pastFuture (diff, output) {
- var format = this._relativeTime[diff > 0 ? 'future' : 'past'];
- return isFunction(format) ? format(output) : format.replace(/%s/i, output);
- }
-
- var aliases = {};
-
- function addUnitAlias (unit, shorthand) {
- var lowerCase = unit.toLowerCase();
- aliases[lowerCase] = aliases[lowerCase + 's'] = aliases[shorthand] = unit;
- }
-
- function normalizeUnits(units) {
- return typeof units === 'string' ? aliases[units] || aliases[units.toLowerCase()] : undefined;
- }
-
- function normalizeObjectUnits(inputObject) {
- var normalizedInput = {},
- normalizedProp,
- prop;
-
- for (prop in inputObject) {
- if (hasOwnProp(inputObject, prop)) {
- normalizedProp = normalizeUnits(prop);
- if (normalizedProp) {
- normalizedInput[normalizedProp] = inputObject[prop];
- }
- }
- }
-
- return normalizedInput;
- }
-
- var priorities = {};
-
- function addUnitPriority(unit, priority) {
- priorities[unit] = priority;
- }
-
- function getPrioritizedUnits(unitsObj) {
- var units = [];
- for (var u in unitsObj) {
- units.push({unit: u, priority: priorities[u]});
- }
- units.sort(function (a, b) {
- return a.priority - b.priority;
- });
- return units;
- }
-
- function zeroFill(number, targetLength, forceSign) {
- var absNumber = '' + Math.abs(number),
- zerosToFill = targetLength - absNumber.length,
- sign = number >= 0;
- return (sign ? (forceSign ? '+' : '') : '-') +
- Math.pow(10, Math.max(0, zerosToFill)).toString().substr(1) + absNumber;
- }
-
- var formattingTokens = /(\[[^\[]*\])|(\\)?([Hh]mm(ss)?|Mo|MM?M?M?|Do|DDDo|DD?D?D?|ddd?d?|do?|w[o|w]?|W[o|W]?|Qo?|YYYYYY|YYYYY|YYYY|YY|gg(ggg?)?|GG(GGG?)?|e|E|a|A|hh?|HH?|kk?|mm?|ss?|S{1,9}|x|X|zz?|ZZ?|.)/g;
-
- var localFormattingTokens = /(\[[^\[]*\])|(\\)?(LTS|LT|LL?L?L?|l{1,4})/g;
-
- var formatFunctions = {};
-
- var formatTokenFunctions = {};
-
- // token: 'M'
- // padded: ['MM', 2]
- // ordinal: 'Mo'
- // callback: function () { this.month() + 1 }
- function addFormatToken (token, padded, ordinal, callback) {
- var func = callback;
- if (typeof callback === 'string') {
- func = function () {
- return this[callback]();
- };
- }
- if (token) {
- formatTokenFunctions[token] = func;
- }
- if (padded) {
- formatTokenFunctions[padded[0]] = function () {
- return zeroFill(func.apply(this, arguments), padded[1], padded[2]);
- };
- }
- if (ordinal) {
- formatTokenFunctions[ordinal] = function () {
- return this.localeData().ordinal(func.apply(this, arguments), token);
- };
- }
- }
-
- function removeFormattingTokens(input) {
- if (input.match(/\[[\s\S]/)) {
- return input.replace(/^\[|\]$/g, '');
- }
- return input.replace(/\\/g, '');
- }
-
- function makeFormatFunction(format) {
- var array = format.match(formattingTokens), i, length;
-
- for (i = 0, length = array.length; i < length; i++) {
- if (formatTokenFunctions[array[i]]) {
- array[i] = formatTokenFunctions[array[i]];
- } else {
- array[i] = removeFormattingTokens(array[i]);
- }
- }
-
- return function (mom) {
- var output = '', i;
- for (i = 0; i < length; i++) {
- output += isFunction(array[i]) ? array[i].call(mom, format) : array[i];
- }
- return output;
- };
- }
-
- // format date using native date object
- function formatMoment(m, format) {
- if (!m.isValid()) {
- return m.localeData().invalidDate();
- }
-
- format = expandFormat(format, m.localeData());
- formatFunctions[format] = formatFunctions[format] || makeFormatFunction(format);
-
- return formatFunctions[format](m);
- }
-
- function expandFormat(format, locale) {
- var i = 5;
-
- function replaceLongDateFormatTokens(input) {
- return locale.longDateFormat(input) || input;
- }
-
- localFormattingTokens.lastIndex = 0;
- while (i >= 0 && localFormattingTokens.test(format)) {
- format = format.replace(localFormattingTokens, replaceLongDateFormatTokens);
- localFormattingTokens.lastIndex = 0;
- i -= 1;
- }
-
- return format;
- }
-
- var match1 = /\d/; // 0 - 9
- var match2 = /\d\d/; // 00 - 99
- var match3 = /\d{3}/; // 000 - 999
- var match4 = /\d{4}/; // 0000 - 9999
- var match6 = /[+-]?\d{6}/; // -999999 - 999999
- var match1to2 = /\d\d?/; // 0 - 99
- var match3to4 = /\d\d\d\d?/; // 999 - 9999
- var match5to6 = /\d\d\d\d\d\d?/; // 99999 - 999999
- var match1to3 = /\d{1,3}/; // 0 - 999
- var match1to4 = /\d{1,4}/; // 0 - 9999
- var match1to6 = /[+-]?\d{1,6}/; // -999999 - 999999
-
- var matchUnsigned = /\d+/; // 0 - inf
- var matchSigned = /[+-]?\d+/; // -inf - inf
-
- var matchOffset = /Z|[+-]\d\d:?\d\d/gi; // +00:00 -00:00 +0000 -0000 or Z
- var matchShortOffset = /Z|[+-]\d\d(?::?\d\d)?/gi; // +00 -00 +00:00 -00:00 +0000 -0000 or Z
-
- var matchTimestamp = /[+-]?\d+(\.\d{1,3})?/; // 123456789 123456789.123
-
- // any word (or two) characters or numbers including two/three word month in arabic.
- // includes scottish gaelic two word and hyphenated months
- var matchWord = /[0-9]{0,256}['a-z\u00A0-\u05FF\u0700-\uD7FF\uF900-\uFDCF\uFDF0-\uFF07\uFF10-\uFFEF]{1,256}|[\u0600-\u06FF\/]{1,256}(\s*?[\u0600-\u06FF]{1,256}){1,2}/i;
-
- var regexes = {};
-
- function addRegexToken (token, regex, strictRegex) {
- regexes[token] = isFunction(regex) ? regex : function (isStrict, localeData) {
- return (isStrict && strictRegex) ? strictRegex : regex;
- };
- }
-
- function getParseRegexForToken (token, config) {
- if (!hasOwnProp(regexes, token)) {
- return new RegExp(unescapeFormat(token));
- }
-
- return regexes[token](config._strict, config._locale);
- }
-
- // Code from http://stackoverflow.com/questions/3561493/is-there-a-regexp-escape-function-in-javascript
- function unescapeFormat(s) {
- return regexEscape(s.replace('\\', '').replace(/\\(\[)|\\(\])|\[([^\]\[]*)\]|\\(.)/g, function (matched, p1, p2, p3, p4) {
- return p1 || p2 || p3 || p4;
- }));
- }
-
- function regexEscape(s) {
- return s.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
- }
-
- var tokens = {};
-
- function addParseToken (token, callback) {
- var i, func = callback;
- if (typeof token === 'string') {
- token = [token];
- }
- if (isNumber(callback)) {
- func = function (input, array) {
- array[callback] = toInt(input);
- };
- }
- for (i = 0; i < token.length; i++) {
- tokens[token[i]] = func;
- }
- }
-
- function addWeekParseToken (token, callback) {
- addParseToken(token, function (input, array, config, token) {
- config._w = config._w || {};
- callback(input, config._w, config, token);
- });
- }
-
- function addTimeToArrayFromToken(token, input, config) {
- if (input != null && hasOwnProp(tokens, token)) {
- tokens[token](input, config._a, config, token);
- }
- }
-
- var YEAR = 0;
- var MONTH = 1;
- var DATE = 2;
- var HOUR = 3;
- var MINUTE = 4;
- var SECOND = 5;
- var MILLISECOND = 6;
- var WEEK = 7;
- var WEEKDAY = 8;
-
- // FORMATTING
-
- addFormatToken('Y', 0, 0, function () {
- var y = this.year();
- return y <= 9999 ? '' + y : '+' + y;
- });
-
- addFormatToken(0, ['YY', 2], 0, function () {
- return this.year() % 100;
- });
-
- addFormatToken(0, ['YYYY', 4], 0, 'year');
- addFormatToken(0, ['YYYYY', 5], 0, 'year');
- addFormatToken(0, ['YYYYYY', 6, true], 0, 'year');
-
- // ALIASES
-
- addUnitAlias('year', 'y');
-
- // PRIORITIES
-
- addUnitPriority('year', 1);
-
- // PARSING
-
- addRegexToken('Y', matchSigned);
- addRegexToken('YY', match1to2, match2);
- addRegexToken('YYYY', match1to4, match4);
- addRegexToken('YYYYY', match1to6, match6);
- addRegexToken('YYYYYY', match1to6, match6);
-
- addParseToken(['YYYYY', 'YYYYYY'], YEAR);
- addParseToken('YYYY', function (input, array) {
- array[YEAR] = input.length === 2 ? hooks.parseTwoDigitYear(input) : toInt(input);
- });
- addParseToken('YY', function (input, array) {
- array[YEAR] = hooks.parseTwoDigitYear(input);
- });
- addParseToken('Y', function (input, array) {
- array[YEAR] = parseInt(input, 10);
- });
-
- // HELPERS
-
- function daysInYear(year) {
- return isLeapYear(year) ? 366 : 365;
- }
-
- function isLeapYear(year) {
- return (year % 4 === 0 && year % 100 !== 0) || year % 400 === 0;
- }
-
- // HOOKS
-
- hooks.parseTwoDigitYear = function (input) {
- return toInt(input) + (toInt(input) > 68 ? 1900 : 2000);
- };
-
- // MOMENTS
-
- var getSetYear = makeGetSet('FullYear', true);
-
- function getIsLeapYear () {
- return isLeapYear(this.year());
- }
-
- function makeGetSet (unit, keepTime) {
- return function (value) {
- if (value != null) {
- set$1(this, unit, value);
- hooks.updateOffset(this, keepTime);
- return this;
- } else {
- return get(this, unit);
- }
- };
- }
-
- function get (mom, unit) {
- return mom.isValid() ?
- mom._d['get' + (mom._isUTC ? 'UTC' : '') + unit]() : NaN;
- }
-
- function set$1 (mom, unit, value) {
- if (mom.isValid() && !isNaN(value)) {
- if (unit === 'FullYear' && isLeapYear(mom.year()) && mom.month() === 1 && mom.date() === 29) {
- mom._d['set' + (mom._isUTC ? 'UTC' : '') + unit](value, mom.month(), daysInMonth(value, mom.month()));
- }
- else {
- mom._d['set' + (mom._isUTC ? 'UTC' : '') + unit](value);
- }
- }
- }
-
- // MOMENTS
-
- function stringGet (units) {
- units = normalizeUnits(units);
- if (isFunction(this[units])) {
- return this[units]();
- }
- return this;
- }
-
-
- function stringSet (units, value) {
- if (typeof units === 'object') {
- units = normalizeObjectUnits(units);
- var prioritized = getPrioritizedUnits(units);
- for (var i = 0; i < prioritized.length; i++) {
- this[prioritized[i].unit](units[prioritized[i].unit]);
- }
- } else {
- units = normalizeUnits(units);
- if (isFunction(this[units])) {
- return this[units](value);
- }
- }
- return this;
- }
-
- function mod(n, x) {
- return ((n % x) + x) % x;
- }
-
- var indexOf;
-
- if (Array.prototype.indexOf) {
- indexOf = Array.prototype.indexOf;
- } else {
- indexOf = function (o) {
- // I know
- var i;
- for (i = 0; i < this.length; ++i) {
- if (this[i] === o) {
- return i;
- }
- }
- return -1;
- };
- }
-
- function daysInMonth(year, month) {
- if (isNaN(year) || isNaN(month)) {
- return NaN;
- }
- var modMonth = mod(month, 12);
- year += (month - modMonth) / 12;
- return modMonth === 1 ? (isLeapYear(year) ? 29 : 28) : (31 - modMonth % 7 % 2);
- }
-
- // FORMATTING
-
- addFormatToken('M', ['MM', 2], 'Mo', function () {
- return this.month() + 1;
- });
-
- addFormatToken('MMM', 0, 0, function (format) {
- return this.localeData().monthsShort(this, format);
- });
-
- addFormatToken('MMMM', 0, 0, function (format) {
- return this.localeData().months(this, format);
- });
-
- // ALIASES
-
- addUnitAlias('month', 'M');
-
- // PRIORITY
-
- addUnitPriority('month', 8);
-
- // PARSING
-
- addRegexToken('M', match1to2);
- addRegexToken('MM', match1to2, match2);
- addRegexToken('MMM', function (isStrict, locale) {
- return locale.monthsShortRegex(isStrict);
- });
- addRegexToken('MMMM', function (isStrict, locale) {
- return locale.monthsRegex(isStrict);
- });
-
- addParseToken(['M', 'MM'], function (input, array) {
- array[MONTH] = toInt(input) - 1;
- });
-
- addParseToken(['MMM', 'MMMM'], function (input, array, config, token) {
- var month = config._locale.monthsParse(input, token, config._strict);
- // if we didn't find a month name, mark the date as invalid.
- if (month != null) {
- array[MONTH] = month;
- } else {
- getParsingFlags(config).invalidMonth = input;
- }
- });
-
- // LOCALES
-
- var MONTHS_IN_FORMAT = /D[oD]?(\[[^\[\]]*\]|\s)+MMMM?/;
- var defaultLocaleMonths = 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_');
- function localeMonths (m, format) {
- if (!m) {
- return isArray(this._months) ? this._months :
- this._months['standalone'];
- }
- return isArray(this._months) ? this._months[m.month()] :
- this._months[(this._months.isFormat || MONTHS_IN_FORMAT).test(format) ? 'format' : 'standalone'][m.month()];
- }
-
- var defaultLocaleMonthsShort = 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_');
- function localeMonthsShort (m, format) {
- if (!m) {
- return isArray(this._monthsShort) ? this._monthsShort :
- this._monthsShort['standalone'];
- }
- return isArray(this._monthsShort) ? this._monthsShort[m.month()] :
- this._monthsShort[MONTHS_IN_FORMAT.test(format) ? 'format' : 'standalone'][m.month()];
- }
-
- function handleStrictParse(monthName, format, strict) {
- var i, ii, mom, llc = monthName.toLocaleLowerCase();
- if (!this._monthsParse) {
- // this is not used
- this._monthsParse = [];
- this._longMonthsParse = [];
- this._shortMonthsParse = [];
- for (i = 0; i < 12; ++i) {
- mom = createUTC([2000, i]);
- this._shortMonthsParse[i] = this.monthsShort(mom, '').toLocaleLowerCase();
- this._longMonthsParse[i] = this.months(mom, '').toLocaleLowerCase();
- }
- }
-
- if (strict) {
- if (format === 'MMM') {
- ii = indexOf.call(this._shortMonthsParse, llc);
- return ii !== -1 ? ii : null;
- } else {
- ii = indexOf.call(this._longMonthsParse, llc);
- return ii !== -1 ? ii : null;
- }
- } else {
- if (format === 'MMM') {
- ii = indexOf.call(this._shortMonthsParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._longMonthsParse, llc);
- return ii !== -1 ? ii : null;
- } else {
- ii = indexOf.call(this._longMonthsParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._shortMonthsParse, llc);
- return ii !== -1 ? ii : null;
- }
- }
- }
-
- function localeMonthsParse (monthName, format, strict) {
- var i, mom, regex;
-
- if (this._monthsParseExact) {
- return handleStrictParse.call(this, monthName, format, strict);
- }
-
- if (!this._monthsParse) {
- this._monthsParse = [];
- this._longMonthsParse = [];
- this._shortMonthsParse = [];
- }
-
- // TODO: add sorting
- // Sorting makes sure if one month (or abbr) is a prefix of another
- // see sorting in computeMonthsParse
- for (i = 0; i < 12; i++) {
- // make the regex if we don't have it already
- mom = createUTC([2000, i]);
- if (strict && !this._longMonthsParse[i]) {
- this._longMonthsParse[i] = new RegExp('^' + this.months(mom, '').replace('.', '') + '$', 'i');
- this._shortMonthsParse[i] = new RegExp('^' + this.monthsShort(mom, '').replace('.', '') + '$', 'i');
- }
- if (!strict && !this._monthsParse[i]) {
- regex = '^' + this.months(mom, '') + '|^' + this.monthsShort(mom, '');
- this._monthsParse[i] = new RegExp(regex.replace('.', ''), 'i');
- }
- // test the regex
- if (strict && format === 'MMMM' && this._longMonthsParse[i].test(monthName)) {
- return i;
- } else if (strict && format === 'MMM' && this._shortMonthsParse[i].test(monthName)) {
- return i;
- } else if (!strict && this._monthsParse[i].test(monthName)) {
- return i;
- }
- }
- }
-
- // MOMENTS
-
- function setMonth (mom, value) {
- var dayOfMonth;
-
- if (!mom.isValid()) {
- // No op
- return mom;
- }
-
- if (typeof value === 'string') {
- if (/^\d+$/.test(value)) {
- value = toInt(value);
- } else {
- value = mom.localeData().monthsParse(value);
- // TODO: Another silent failure?
- if (!isNumber(value)) {
- return mom;
- }
- }
- }
-
- dayOfMonth = Math.min(mom.date(), daysInMonth(mom.year(), value));
- mom._d['set' + (mom._isUTC ? 'UTC' : '') + 'Month'](value, dayOfMonth);
- return mom;
- }
-
- function getSetMonth (value) {
- if (value != null) {
- setMonth(this, value);
- hooks.updateOffset(this, true);
- return this;
- } else {
- return get(this, 'Month');
- }
- }
-
- function getDaysInMonth () {
- return daysInMonth(this.year(), this.month());
- }
-
- var defaultMonthsShortRegex = matchWord;
- function monthsShortRegex (isStrict) {
- if (this._monthsParseExact) {
- if (!hasOwnProp(this, '_monthsRegex')) {
- computeMonthsParse.call(this);
- }
- if (isStrict) {
- return this._monthsShortStrictRegex;
- } else {
- return this._monthsShortRegex;
- }
- } else {
- if (!hasOwnProp(this, '_monthsShortRegex')) {
- this._monthsShortRegex = defaultMonthsShortRegex;
- }
- return this._monthsShortStrictRegex && isStrict ?
- this._monthsShortStrictRegex : this._monthsShortRegex;
- }
- }
-
- var defaultMonthsRegex = matchWord;
- function monthsRegex (isStrict) {
- if (this._monthsParseExact) {
- if (!hasOwnProp(this, '_monthsRegex')) {
- computeMonthsParse.call(this);
- }
- if (isStrict) {
- return this._monthsStrictRegex;
- } else {
- return this._monthsRegex;
- }
- } else {
- if (!hasOwnProp(this, '_monthsRegex')) {
- this._monthsRegex = defaultMonthsRegex;
- }
- return this._monthsStrictRegex && isStrict ?
- this._monthsStrictRegex : this._monthsRegex;
- }
- }
-
- function computeMonthsParse () {
- function cmpLenRev(a, b) {
- return b.length - a.length;
- }
-
- var shortPieces = [], longPieces = [], mixedPieces = [],
- i, mom;
- for (i = 0; i < 12; i++) {
- // make the regex if we don't have it already
- mom = createUTC([2000, i]);
- shortPieces.push(this.monthsShort(mom, ''));
- longPieces.push(this.months(mom, ''));
- mixedPieces.push(this.months(mom, ''));
- mixedPieces.push(this.monthsShort(mom, ''));
- }
- // Sorting makes sure if one month (or abbr) is a prefix of another it
- // will match the longer piece.
- shortPieces.sort(cmpLenRev);
- longPieces.sort(cmpLenRev);
- mixedPieces.sort(cmpLenRev);
- for (i = 0; i < 12; i++) {
- shortPieces[i] = regexEscape(shortPieces[i]);
- longPieces[i] = regexEscape(longPieces[i]);
- }
- for (i = 0; i < 24; i++) {
- mixedPieces[i] = regexEscape(mixedPieces[i]);
- }
-
- this._monthsRegex = new RegExp('^(' + mixedPieces.join('|') + ')', 'i');
- this._monthsShortRegex = this._monthsRegex;
- this._monthsStrictRegex = new RegExp('^(' + longPieces.join('|') + ')', 'i');
- this._monthsShortStrictRegex = new RegExp('^(' + shortPieces.join('|') + ')', 'i');
- }
-
- function createDate (y, m, d, h, M, s, ms) {
- // can't just apply() to create a date:
- // https://stackoverflow.com/q/181348
- var date;
- // the date constructor remaps years 0-99 to 1900-1999
- if (y < 100 && y >= 0) {
- // preserve leap years using a full 400 year cycle, then reset
- date = new Date(y + 400, m, d, h, M, s, ms);
- if (isFinite(date.getFullYear())) {
- date.setFullYear(y);
- }
- } else {
- date = new Date(y, m, d, h, M, s, ms);
- }
-
- return date;
- }
-
- function createUTCDate (y) {
- var date;
- // the Date.UTC function remaps years 0-99 to 1900-1999
- if (y < 100 && y >= 0) {
- var args = Array.prototype.slice.call(arguments);
- // preserve leap years using a full 400 year cycle, then reset
- args[0] = y + 400;
- date = new Date(Date.UTC.apply(null, args));
- if (isFinite(date.getUTCFullYear())) {
- date.setUTCFullYear(y);
- }
- } else {
- date = new Date(Date.UTC.apply(null, arguments));
- }
-
- return date;
- }
-
- // start-of-first-week - start-of-year
- function firstWeekOffset(year, dow, doy) {
- var // first-week day -- which january is always in the first week (4 for iso, 1 for other)
- fwd = 7 + dow - doy,
- // first-week day local weekday -- which local weekday is fwd
- fwdlw = (7 + createUTCDate(year, 0, fwd).getUTCDay() - dow) % 7;
-
- return -fwdlw + fwd - 1;
- }
-
- // https://en.wikipedia.org/wiki/ISO_week_date#Calculating_a_date_given_the_year.2C_week_number_and_weekday
- function dayOfYearFromWeeks(year, week, weekday, dow, doy) {
- var localWeekday = (7 + weekday - dow) % 7,
- weekOffset = firstWeekOffset(year, dow, doy),
- dayOfYear = 1 + 7 * (week - 1) + localWeekday + weekOffset,
- resYear, resDayOfYear;
-
- if (dayOfYear <= 0) {
- resYear = year - 1;
- resDayOfYear = daysInYear(resYear) + dayOfYear;
- } else if (dayOfYear > daysInYear(year)) {
- resYear = year + 1;
- resDayOfYear = dayOfYear - daysInYear(year);
- } else {
- resYear = year;
- resDayOfYear = dayOfYear;
- }
-
- return {
- year: resYear,
- dayOfYear: resDayOfYear
- };
- }
-
- function weekOfYear(mom, dow, doy) {
- var weekOffset = firstWeekOffset(mom.year(), dow, doy),
- week = Math.floor((mom.dayOfYear() - weekOffset - 1) / 7) + 1,
- resWeek, resYear;
-
- if (week < 1) {
- resYear = mom.year() - 1;
- resWeek = week + weeksInYear(resYear, dow, doy);
- } else if (week > weeksInYear(mom.year(), dow, doy)) {
- resWeek = week - weeksInYear(mom.year(), dow, doy);
- resYear = mom.year() + 1;
- } else {
- resYear = mom.year();
- resWeek = week;
- }
-
- return {
- week: resWeek,
- year: resYear
- };
- }
-
- function weeksInYear(year, dow, doy) {
- var weekOffset = firstWeekOffset(year, dow, doy),
- weekOffsetNext = firstWeekOffset(year + 1, dow, doy);
- return (daysInYear(year) - weekOffset + weekOffsetNext) / 7;
- }
-
- // FORMATTING
-
- addFormatToken('w', ['ww', 2], 'wo', 'week');
- addFormatToken('W', ['WW', 2], 'Wo', 'isoWeek');
-
- // ALIASES
-
- addUnitAlias('week', 'w');
- addUnitAlias('isoWeek', 'W');
-
- // PRIORITIES
-
- addUnitPriority('week', 5);
- addUnitPriority('isoWeek', 5);
-
- // PARSING
-
- addRegexToken('w', match1to2);
- addRegexToken('ww', match1to2, match2);
- addRegexToken('W', match1to2);
- addRegexToken('WW', match1to2, match2);
-
- addWeekParseToken(['w', 'ww', 'W', 'WW'], function (input, week, config, token) {
- week[token.substr(0, 1)] = toInt(input);
- });
-
- // HELPERS
-
- // LOCALES
-
- function localeWeek (mom) {
- return weekOfYear(mom, this._week.dow, this._week.doy).week;
- }
-
- var defaultLocaleWeek = {
- dow : 0, // Sunday is the first day of the week.
- doy : 6 // The week that contains Jan 6th is the first week of the year.
- };
-
- function localeFirstDayOfWeek () {
- return this._week.dow;
- }
-
- function localeFirstDayOfYear () {
- return this._week.doy;
- }
-
- // MOMENTS
-
- function getSetWeek (input) {
- var week = this.localeData().week(this);
- return input == null ? week : this.add((input - week) * 7, 'd');
- }
-
- function getSetISOWeek (input) {
- var week = weekOfYear(this, 1, 4).week;
- return input == null ? week : this.add((input - week) * 7, 'd');
- }
-
- // FORMATTING
-
- addFormatToken('d', 0, 'do', 'day');
-
- addFormatToken('dd', 0, 0, function (format) {
- return this.localeData().weekdaysMin(this, format);
- });
-
- addFormatToken('ddd', 0, 0, function (format) {
- return this.localeData().weekdaysShort(this, format);
- });
-
- addFormatToken('dddd', 0, 0, function (format) {
- return this.localeData().weekdays(this, format);
- });
-
- addFormatToken('e', 0, 0, 'weekday');
- addFormatToken('E', 0, 0, 'isoWeekday');
-
- // ALIASES
-
- addUnitAlias('day', 'd');
- addUnitAlias('weekday', 'e');
- addUnitAlias('isoWeekday', 'E');
-
- // PRIORITY
- addUnitPriority('day', 11);
- addUnitPriority('weekday', 11);
- addUnitPriority('isoWeekday', 11);
-
- // PARSING
-
- addRegexToken('d', match1to2);
- addRegexToken('e', match1to2);
- addRegexToken('E', match1to2);
- addRegexToken('dd', function (isStrict, locale) {
- return locale.weekdaysMinRegex(isStrict);
- });
- addRegexToken('ddd', function (isStrict, locale) {
- return locale.weekdaysShortRegex(isStrict);
- });
- addRegexToken('dddd', function (isStrict, locale) {
- return locale.weekdaysRegex(isStrict);
- });
-
- addWeekParseToken(['dd', 'ddd', 'dddd'], function (input, week, config, token) {
- var weekday = config._locale.weekdaysParse(input, token, config._strict);
- // if we didn't get a weekday name, mark the date as invalid
- if (weekday != null) {
- week.d = weekday;
- } else {
- getParsingFlags(config).invalidWeekday = input;
- }
- });
-
- addWeekParseToken(['d', 'e', 'E'], function (input, week, config, token) {
- week[token] = toInt(input);
- });
-
- // HELPERS
-
- function parseWeekday(input, locale) {
- if (typeof input !== 'string') {
- return input;
- }
-
- if (!isNaN(input)) {
- return parseInt(input, 10);
- }
-
- input = locale.weekdaysParse(input);
- if (typeof input === 'number') {
- return input;
- }
-
- return null;
- }
-
- function parseIsoWeekday(input, locale) {
- if (typeof input === 'string') {
- return locale.weekdaysParse(input) % 7 || 7;
- }
- return isNaN(input) ? null : input;
- }
-
- // LOCALES
- function shiftWeekdays (ws, n) {
- return ws.slice(n, 7).concat(ws.slice(0, n));
- }
-
- var defaultLocaleWeekdays = 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_');
- function localeWeekdays (m, format) {
- var weekdays = isArray(this._weekdays) ? this._weekdays :
- this._weekdays[(m && m !== true && this._weekdays.isFormat.test(format)) ? 'format' : 'standalone'];
- return (m === true) ? shiftWeekdays(weekdays, this._week.dow)
- : (m) ? weekdays[m.day()] : weekdays;
- }
-
- var defaultLocaleWeekdaysShort = 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_');
- function localeWeekdaysShort (m) {
- return (m === true) ? shiftWeekdays(this._weekdaysShort, this._week.dow)
- : (m) ? this._weekdaysShort[m.day()] : this._weekdaysShort;
- }
-
- var defaultLocaleWeekdaysMin = 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_');
- function localeWeekdaysMin (m) {
- return (m === true) ? shiftWeekdays(this._weekdaysMin, this._week.dow)
- : (m) ? this._weekdaysMin[m.day()] : this._weekdaysMin;
- }
-
- function handleStrictParse$1(weekdayName, format, strict) {
- var i, ii, mom, llc = weekdayName.toLocaleLowerCase();
- if (!this._weekdaysParse) {
- this._weekdaysParse = [];
- this._shortWeekdaysParse = [];
- this._minWeekdaysParse = [];
-
- for (i = 0; i < 7; ++i) {
- mom = createUTC([2000, 1]).day(i);
- this._minWeekdaysParse[i] = this.weekdaysMin(mom, '').toLocaleLowerCase();
- this._shortWeekdaysParse[i] = this.weekdaysShort(mom, '').toLocaleLowerCase();
- this._weekdaysParse[i] = this.weekdays(mom, '').toLocaleLowerCase();
- }
- }
-
- if (strict) {
- if (format === 'dddd') {
- ii = indexOf.call(this._weekdaysParse, llc);
- return ii !== -1 ? ii : null;
- } else if (format === 'ddd') {
- ii = indexOf.call(this._shortWeekdaysParse, llc);
- return ii !== -1 ? ii : null;
- } else {
- ii = indexOf.call(this._minWeekdaysParse, llc);
- return ii !== -1 ? ii : null;
- }
- } else {
- if (format === 'dddd') {
- ii = indexOf.call(this._weekdaysParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._shortWeekdaysParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._minWeekdaysParse, llc);
- return ii !== -1 ? ii : null;
- } else if (format === 'ddd') {
- ii = indexOf.call(this._shortWeekdaysParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._weekdaysParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._minWeekdaysParse, llc);
- return ii !== -1 ? ii : null;
- } else {
- ii = indexOf.call(this._minWeekdaysParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._weekdaysParse, llc);
- if (ii !== -1) {
- return ii;
- }
- ii = indexOf.call(this._shortWeekdaysParse, llc);
- return ii !== -1 ? ii : null;
- }
- }
- }
-
- function localeWeekdaysParse (weekdayName, format, strict) {
- var i, mom, regex;
-
- if (this._weekdaysParseExact) {
- return handleStrictParse$1.call(this, weekdayName, format, strict);
- }
-
- if (!this._weekdaysParse) {
- this._weekdaysParse = [];
- this._minWeekdaysParse = [];
- this._shortWeekdaysParse = [];
- this._fullWeekdaysParse = [];
- }
-
- for (i = 0; i < 7; i++) {
- // make the regex if we don't have it already
-
- mom = createUTC([2000, 1]).day(i);
- if (strict && !this._fullWeekdaysParse[i]) {
- this._fullWeekdaysParse[i] = new RegExp('^' + this.weekdays(mom, '').replace('.', '\\.?') + '$', 'i');
- this._shortWeekdaysParse[i] = new RegExp('^' + this.weekdaysShort(mom, '').replace('.', '\\.?') + '$', 'i');
- this._minWeekdaysParse[i] = new RegExp('^' + this.weekdaysMin(mom, '').replace('.', '\\.?') + '$', 'i');
- }
- if (!this._weekdaysParse[i]) {
- regex = '^' + this.weekdays(mom, '') + '|^' + this.weekdaysShort(mom, '') + '|^' + this.weekdaysMin(mom, '');
- this._weekdaysParse[i] = new RegExp(regex.replace('.', ''), 'i');
- }
- // test the regex
- if (strict && format === 'dddd' && this._fullWeekdaysParse[i].test(weekdayName)) {
- return i;
- } else if (strict && format === 'ddd' && this._shortWeekdaysParse[i].test(weekdayName)) {
- return i;
- } else if (strict && format === 'dd' && this._minWeekdaysParse[i].test(weekdayName)) {
- return i;
- } else if (!strict && this._weekdaysParse[i].test(weekdayName)) {
- return i;
- }
- }
- }
-
- // MOMENTS
-
- function getSetDayOfWeek (input) {
- if (!this.isValid()) {
- return input != null ? this : NaN;
- }
- var day = this._isUTC ? this._d.getUTCDay() : this._d.getDay();
- if (input != null) {
- input = parseWeekday(input, this.localeData());
- return this.add(input - day, 'd');
- } else {
- return day;
- }
- }
-
- function getSetLocaleDayOfWeek (input) {
- if (!this.isValid()) {
- return input != null ? this : NaN;
- }
- var weekday = (this.day() + 7 - this.localeData()._week.dow) % 7;
- return input == null ? weekday : this.add(input - weekday, 'd');
- }
-
- function getSetISODayOfWeek (input) {
- if (!this.isValid()) {
- return input != null ? this : NaN;
- }
-
- // behaves the same as moment#day except
- // as a getter, returns 7 instead of 0 (1-7 range instead of 0-6)
- // as a setter, sunday should belong to the previous week.
-
- if (input != null) {
- var weekday = parseIsoWeekday(input, this.localeData());
- return this.day(this.day() % 7 ? weekday : weekday - 7);
- } else {
- return this.day() || 7;
- }
- }
-
- var defaultWeekdaysRegex = matchWord;
- function weekdaysRegex (isStrict) {
- if (this._weekdaysParseExact) {
- if (!hasOwnProp(this, '_weekdaysRegex')) {
- computeWeekdaysParse.call(this);
- }
- if (isStrict) {
- return this._weekdaysStrictRegex;
- } else {
- return this._weekdaysRegex;
- }
- } else {
- if (!hasOwnProp(this, '_weekdaysRegex')) {
- this._weekdaysRegex = defaultWeekdaysRegex;
- }
- return this._weekdaysStrictRegex && isStrict ?
- this._weekdaysStrictRegex : this._weekdaysRegex;
- }
- }
-
- var defaultWeekdaysShortRegex = matchWord;
- function weekdaysShortRegex (isStrict) {
- if (this._weekdaysParseExact) {
- if (!hasOwnProp(this, '_weekdaysRegex')) {
- computeWeekdaysParse.call(this);
- }
- if (isStrict) {
- return this._weekdaysShortStrictRegex;
- } else {
- return this._weekdaysShortRegex;
- }
- } else {
- if (!hasOwnProp(this, '_weekdaysShortRegex')) {
- this._weekdaysShortRegex = defaultWeekdaysShortRegex;
- }
- return this._weekdaysShortStrictRegex && isStrict ?
- this._weekdaysShortStrictRegex : this._weekdaysShortRegex;
- }
- }
-
- var defaultWeekdaysMinRegex = matchWord;
- function weekdaysMinRegex (isStrict) {
- if (this._weekdaysParseExact) {
- if (!hasOwnProp(this, '_weekdaysRegex')) {
- computeWeekdaysParse.call(this);
- }
- if (isStrict) {
- return this._weekdaysMinStrictRegex;
- } else {
- return this._weekdaysMinRegex;
- }
- } else {
- if (!hasOwnProp(this, '_weekdaysMinRegex')) {
- this._weekdaysMinRegex = defaultWeekdaysMinRegex;
- }
- return this._weekdaysMinStrictRegex && isStrict ?
- this._weekdaysMinStrictRegex : this._weekdaysMinRegex;
- }
- }
-
-
- function computeWeekdaysParse () {
- function cmpLenRev(a, b) {
- return b.length - a.length;
- }
-
- var minPieces = [], shortPieces = [], longPieces = [], mixedPieces = [],
- i, mom, minp, shortp, longp;
- for (i = 0; i < 7; i++) {
- // make the regex if we don't have it already
- mom = createUTC([2000, 1]).day(i);
- minp = this.weekdaysMin(mom, '');
- shortp = this.weekdaysShort(mom, '');
- longp = this.weekdays(mom, '');
- minPieces.push(minp);
- shortPieces.push(shortp);
- longPieces.push(longp);
- mixedPieces.push(minp);
- mixedPieces.push(shortp);
- mixedPieces.push(longp);
- }
- // Sorting makes sure if one weekday (or abbr) is a prefix of another it
- // will match the longer piece.
- minPieces.sort(cmpLenRev);
- shortPieces.sort(cmpLenRev);
- longPieces.sort(cmpLenRev);
- mixedPieces.sort(cmpLenRev);
- for (i = 0; i < 7; i++) {
- shortPieces[i] = regexEscape(shortPieces[i]);
- longPieces[i] = regexEscape(longPieces[i]);
- mixedPieces[i] = regexEscape(mixedPieces[i]);
- }
-
- this._weekdaysRegex = new RegExp('^(' + mixedPieces.join('|') + ')', 'i');
- this._weekdaysShortRegex = this._weekdaysRegex;
- this._weekdaysMinRegex = this._weekdaysRegex;
-
- this._weekdaysStrictRegex = new RegExp('^(' + longPieces.join('|') + ')', 'i');
- this._weekdaysShortStrictRegex = new RegExp('^(' + shortPieces.join('|') + ')', 'i');
- this._weekdaysMinStrictRegex = new RegExp('^(' + minPieces.join('|') + ')', 'i');
- }
-
- // FORMATTING
-
- function hFormat() {
- return this.hours() % 12 || 12;
- }
-
- function kFormat() {
- return this.hours() || 24;
- }
-
- addFormatToken('H', ['HH', 2], 0, 'hour');
- addFormatToken('h', ['hh', 2], 0, hFormat);
- addFormatToken('k', ['kk', 2], 0, kFormat);
-
- addFormatToken('hmm', 0, 0, function () {
- return '' + hFormat.apply(this) + zeroFill(this.minutes(), 2);
- });
-
- addFormatToken('hmmss', 0, 0, function () {
- return '' + hFormat.apply(this) + zeroFill(this.minutes(), 2) +
- zeroFill(this.seconds(), 2);
- });
-
- addFormatToken('Hmm', 0, 0, function () {
- return '' + this.hours() + zeroFill(this.minutes(), 2);
- });
-
- addFormatToken('Hmmss', 0, 0, function () {
- return '' + this.hours() + zeroFill(this.minutes(), 2) +
- zeroFill(this.seconds(), 2);
- });
-
- function meridiem (token, lowercase) {
- addFormatToken(token, 0, 0, function () {
- return this.localeData().meridiem(this.hours(), this.minutes(), lowercase);
- });
- }
-
- meridiem('a', true);
- meridiem('A', false);
-
- // ALIASES
-
- addUnitAlias('hour', 'h');
-
- // PRIORITY
- addUnitPriority('hour', 13);
-
- // PARSING
-
- function matchMeridiem (isStrict, locale) {
- return locale._meridiemParse;
- }
-
- addRegexToken('a', matchMeridiem);
- addRegexToken('A', matchMeridiem);
- addRegexToken('H', match1to2);
- addRegexToken('h', match1to2);
- addRegexToken('k', match1to2);
- addRegexToken('HH', match1to2, match2);
- addRegexToken('hh', match1to2, match2);
- addRegexToken('kk', match1to2, match2);
-
- addRegexToken('hmm', match3to4);
- addRegexToken('hmmss', match5to6);
- addRegexToken('Hmm', match3to4);
- addRegexToken('Hmmss', match5to6);
-
- addParseToken(['H', 'HH'], HOUR);
- addParseToken(['k', 'kk'], function (input, array, config) {
- var kInput = toInt(input);
- array[HOUR] = kInput === 24 ? 0 : kInput;
- });
- addParseToken(['a', 'A'], function (input, array, config) {
- config._isPm = config._locale.isPM(input);
- config._meridiem = input;
- });
- addParseToken(['h', 'hh'], function (input, array, config) {
- array[HOUR] = toInt(input);
- getParsingFlags(config).bigHour = true;
- });
- addParseToken('hmm', function (input, array, config) {
- var pos = input.length - 2;
- array[HOUR] = toInt(input.substr(0, pos));
- array[MINUTE] = toInt(input.substr(pos));
- getParsingFlags(config).bigHour = true;
- });
- addParseToken('hmmss', function (input, array, config) {
- var pos1 = input.length - 4;
- var pos2 = input.length - 2;
- array[HOUR] = toInt(input.substr(0, pos1));
- array[MINUTE] = toInt(input.substr(pos1, 2));
- array[SECOND] = toInt(input.substr(pos2));
- getParsingFlags(config).bigHour = true;
- });
- addParseToken('Hmm', function (input, array, config) {
- var pos = input.length - 2;
- array[HOUR] = toInt(input.substr(0, pos));
- array[MINUTE] = toInt(input.substr(pos));
- });
- addParseToken('Hmmss', function (input, array, config) {
- var pos1 = input.length - 4;
- var pos2 = input.length - 2;
- array[HOUR] = toInt(input.substr(0, pos1));
- array[MINUTE] = toInt(input.substr(pos1, 2));
- array[SECOND] = toInt(input.substr(pos2));
- });
-
- // LOCALES
-
- function localeIsPM (input) {
- // IE8 Quirks Mode & IE7 Standards Mode do not allow accessing strings like arrays
- // Using charAt should be more compatible.
- return ((input + '').toLowerCase().charAt(0) === 'p');
- }
-
- var defaultLocaleMeridiemParse = /[ap]\.?m?\.?/i;
- function localeMeridiem (hours, minutes, isLower) {
- if (hours > 11) {
- return isLower ? 'pm' : 'PM';
- } else {
- return isLower ? 'am' : 'AM';
- }
- }
-
-
- // MOMENTS
-
- // Setting the hour should keep the time, because the user explicitly
- // specified which hour they want. So trying to maintain the same hour (in
- // a new timezone) makes sense. Adding/subtracting hours does not follow
- // this rule.
- var getSetHour = makeGetSet('Hours', true);
-
- var baseConfig = {
- calendar: defaultCalendar,
- longDateFormat: defaultLongDateFormat,
- invalidDate: defaultInvalidDate,
- ordinal: defaultOrdinal,
- dayOfMonthOrdinalParse: defaultDayOfMonthOrdinalParse,
- relativeTime: defaultRelativeTime,
-
- months: defaultLocaleMonths,
- monthsShort: defaultLocaleMonthsShort,
-
- week: defaultLocaleWeek,
-
- weekdays: defaultLocaleWeekdays,
- weekdaysMin: defaultLocaleWeekdaysMin,
- weekdaysShort: defaultLocaleWeekdaysShort,
-
- meridiemParse: defaultLocaleMeridiemParse
- };
-
- // internal storage for locale config files
- var locales = {};
- var localeFamilies = {};
- var globalLocale;
-
- function normalizeLocale(key) {
- return key ? key.toLowerCase().replace('_', '-') : key;
- }
-
- // pick the locale from the array
- // try ['en-au', 'en-gb'] as 'en-au', 'en-gb', 'en', as in move through the list trying each
- // substring from most specific to least, but move to the next array item if it's a more specific variant than the current root
- function chooseLocale(names) {
- var i = 0, j, next, locale, split;
-
- while (i < names.length) {
- split = normalizeLocale(names[i]).split('-');
- j = split.length;
- next = normalizeLocale(names[i + 1]);
- next = next ? next.split('-') : null;
- while (j > 0) {
- locale = loadLocale(split.slice(0, j).join('-'));
- if (locale) {
- return locale;
- }
- if (next && next.length >= j && compareArrays(split, next, true) >= j - 1) {
- //the next array item is better than a shallower substring of this one
- break;
- }
- j--;
- }
- i++;
- }
- return globalLocale;
- }
-
- function loadLocale(name) {
- var oldLocale = null;
- // TODO: Find a better way to register and load all the locales in Node
- if (!locales[name] && ('object' !== 'undefined') &&
- module && module.exports) {
- try {
- oldLocale = globalLocale._abbr;
- var aliasedRequire = commonjsRequire;
- aliasedRequire('./locale/' + name);
- getSetGlobalLocale(oldLocale);
- } catch (e) {}
- }
- return locales[name];
- }
-
- // This function will load locale and then set the global locale. If
- // no arguments are passed in, it will simply return the current global
- // locale key.
- function getSetGlobalLocale (key, values) {
- var data;
- if (key) {
- if (isUndefined(values)) {
- data = getLocale(key);
- }
- else {
- data = defineLocale(key, values);
- }
-
- if (data) {
- // moment.duration._locale = moment._locale = data;
- globalLocale = data;
- }
- else {
- if ((typeof console !== 'undefined') && console.warn) {
- //warn user if arguments are passed but the locale could not be set
- console.warn('Locale ' + key + ' not found. Did you forget to load it?');
- }
- }
- }
-
- return globalLocale._abbr;
- }
-
- function defineLocale (name, config) {
- if (config !== null) {
- var locale, parentConfig = baseConfig;
- config.abbr = name;
- if (locales[name] != null) {
- deprecateSimple('defineLocaleOverride',
- 'use moment.updateLocale(localeName, config) to change ' +
- 'an existing locale. moment.defineLocale(localeName, ' +
- 'config) should only be used for creating a new locale ' +
- 'See http://momentjs.com/guides/#/warnings/define-locale/ for more info.');
- parentConfig = locales[name]._config;
- } else if (config.parentLocale != null) {
- if (locales[config.parentLocale] != null) {
- parentConfig = locales[config.parentLocale]._config;
- } else {
- locale = loadLocale(config.parentLocale);
- if (locale != null) {
- parentConfig = locale._config;
- } else {
- if (!localeFamilies[config.parentLocale]) {
- localeFamilies[config.parentLocale] = [];
- }
- localeFamilies[config.parentLocale].push({
- name: name,
- config: config
- });
- return null;
- }
- }
- }
- locales[name] = new Locale(mergeConfigs(parentConfig, config));
-
- if (localeFamilies[name]) {
- localeFamilies[name].forEach(function (x) {
- defineLocale(x.name, x.config);
- });
- }
-
- // backwards compat for now: also set the locale
- // make sure we set the locale AFTER all child locales have been
- // created, so we won't end up with the child locale set.
- getSetGlobalLocale(name);
-
-
- return locales[name];
- } else {
- // useful for testing
- delete locales[name];
- return null;
- }
- }
-
- function updateLocale(name, config) {
- if (config != null) {
- var locale, tmpLocale, parentConfig = baseConfig;
- // MERGE
- tmpLocale = loadLocale(name);
- if (tmpLocale != null) {
- parentConfig = tmpLocale._config;
- }
- config = mergeConfigs(parentConfig, config);
- locale = new Locale(config);
- locale.parentLocale = locales[name];
- locales[name] = locale;
-
- // backwards compat for now: also set the locale
- getSetGlobalLocale(name);
- } else {
- // pass null for config to unupdate, useful for tests
- if (locales[name] != null) {
- if (locales[name].parentLocale != null) {
- locales[name] = locales[name].parentLocale;
- } else if (locales[name] != null) {
- delete locales[name];
- }
- }
- }
- return locales[name];
- }
-
- // returns locale data
- function getLocale (key) {
- var locale;
-
- if (key && key._locale && key._locale._abbr) {
- key = key._locale._abbr;
- }
-
- if (!key) {
- return globalLocale;
- }
-
- if (!isArray(key)) {
- //short-circuit everything else
- locale = loadLocale(key);
- if (locale) {
- return locale;
- }
- key = [key];
- }
-
- return chooseLocale(key);
- }
-
- function listLocales() {
- return keys(locales);
- }
-
- function checkOverflow (m) {
- var overflow;
- var a = m._a;
-
- if (a && getParsingFlags(m).overflow === -2) {
- overflow =
- a[MONTH] < 0 || a[MONTH] > 11 ? MONTH :
- a[DATE] < 1 || a[DATE] > daysInMonth(a[YEAR], a[MONTH]) ? DATE :
- a[HOUR] < 0 || a[HOUR] > 24 || (a[HOUR] === 24 && (a[MINUTE] !== 0 || a[SECOND] !== 0 || a[MILLISECOND] !== 0)) ? HOUR :
- a[MINUTE] < 0 || a[MINUTE] > 59 ? MINUTE :
- a[SECOND] < 0 || a[SECOND] > 59 ? SECOND :
- a[MILLISECOND] < 0 || a[MILLISECOND] > 999 ? MILLISECOND :
- -1;
-
- if (getParsingFlags(m)._overflowDayOfYear && (overflow < YEAR || overflow > DATE)) {
- overflow = DATE;
- }
- if (getParsingFlags(m)._overflowWeeks && overflow === -1) {
- overflow = WEEK;
- }
- if (getParsingFlags(m)._overflowWeekday && overflow === -1) {
- overflow = WEEKDAY;
- }
-
- getParsingFlags(m).overflow = overflow;
- }
-
- return m;
- }
-
- // Pick the first defined of two or three arguments.
- function defaults(a, b, c) {
- if (a != null) {
- return a;
- }
- if (b != null) {
- return b;
- }
- return c;
- }
-
- function currentDateArray(config) {
- // hooks is actually the exported moment object
- var nowValue = new Date(hooks.now());
- if (config._useUTC) {
- return [nowValue.getUTCFullYear(), nowValue.getUTCMonth(), nowValue.getUTCDate()];
- }
- return [nowValue.getFullYear(), nowValue.getMonth(), nowValue.getDate()];
- }
-
- // convert an array to a date.
- // the array should mirror the parameters below
- // note: all values past the year are optional and will default to the lowest possible value.
- // [year, month, day , hour, minute, second, millisecond]
- function configFromArray (config) {
- var i, date, input = [], currentDate, expectedWeekday, yearToUse;
-
- if (config._d) {
- return;
- }
-
- currentDate = currentDateArray(config);
-
- //compute day of the year from weeks and weekdays
- if (config._w && config._a[DATE] == null && config._a[MONTH] == null) {
- dayOfYearFromWeekInfo(config);
- }
-
- //if the day of the year is set, figure out what it is
- if (config._dayOfYear != null) {
- yearToUse = defaults(config._a[YEAR], currentDate[YEAR]);
-
- if (config._dayOfYear > daysInYear(yearToUse) || config._dayOfYear === 0) {
- getParsingFlags(config)._overflowDayOfYear = true;
- }
-
- date = createUTCDate(yearToUse, 0, config._dayOfYear);
- config._a[MONTH] = date.getUTCMonth();
- config._a[DATE] = date.getUTCDate();
- }
-
- // Default to current date.
- // * if no year, month, day of month are given, default to today
- // * if day of month is given, default month and year
- // * if month is given, default only year
- // * if year is given, don't default anything
- for (i = 0; i < 3 && config._a[i] == null; ++i) {
- config._a[i] = input[i] = currentDate[i];
- }
-
- // Zero out whatever was not defaulted, including time
- for (; i < 7; i++) {
- config._a[i] = input[i] = (config._a[i] == null) ? (i === 2 ? 1 : 0) : config._a[i];
- }
-
- // Check for 24:00:00.000
- if (config._a[HOUR] === 24 &&
- config._a[MINUTE] === 0 &&
- config._a[SECOND] === 0 &&
- config._a[MILLISECOND] === 0) {
- config._nextDay = true;
- config._a[HOUR] = 0;
- }
-
- config._d = (config._useUTC ? createUTCDate : createDate).apply(null, input);
- expectedWeekday = config._useUTC ? config._d.getUTCDay() : config._d.getDay();
-
- // Apply timezone offset from input. The actual utcOffset can be changed
- // with parseZone.
- if (config._tzm != null) {
- config._d.setUTCMinutes(config._d.getUTCMinutes() - config._tzm);
- }
-
- if (config._nextDay) {
- config._a[HOUR] = 24;
- }
-
- // check for mismatching day of week
- if (config._w && typeof config._w.d !== 'undefined' && config._w.d !== expectedWeekday) {
- getParsingFlags(config).weekdayMismatch = true;
- }
- }
-
- function dayOfYearFromWeekInfo(config) {
- var w, weekYear, week, weekday, dow, doy, temp, weekdayOverflow;
-
- w = config._w;
- if (w.GG != null || w.W != null || w.E != null) {
- dow = 1;
- doy = 4;
-
- // TODO: We need to take the current isoWeekYear, but that depends on
- // how we interpret now (local, utc, fixed offset). So create
- // a now version of current config (take local/utc/offset flags, and
- // create now).
- weekYear = defaults(w.GG, config._a[YEAR], weekOfYear(createLocal(), 1, 4).year);
- week = defaults(w.W, 1);
- weekday = defaults(w.E, 1);
- if (weekday < 1 || weekday > 7) {
- weekdayOverflow = true;
- }
- } else {
- dow = config._locale._week.dow;
- doy = config._locale._week.doy;
-
- var curWeek = weekOfYear(createLocal(), dow, doy);
-
- weekYear = defaults(w.gg, config._a[YEAR], curWeek.year);
-
- // Default to current week.
- week = defaults(w.w, curWeek.week);
-
- if (w.d != null) {
- // weekday -- low day numbers are considered next week
- weekday = w.d;
- if (weekday < 0 || weekday > 6) {
- weekdayOverflow = true;
- }
- } else if (w.e != null) {
- // local weekday -- counting starts from beginning of week
- weekday = w.e + dow;
- if (w.e < 0 || w.e > 6) {
- weekdayOverflow = true;
- }
- } else {
- // default to beginning of week
- weekday = dow;
- }
- }
- if (week < 1 || week > weeksInYear(weekYear, dow, doy)) {
- getParsingFlags(config)._overflowWeeks = true;
- } else if (weekdayOverflow != null) {
- getParsingFlags(config)._overflowWeekday = true;
- } else {
- temp = dayOfYearFromWeeks(weekYear, week, weekday, dow, doy);
- config._a[YEAR] = temp.year;
- config._dayOfYear = temp.dayOfYear;
- }
- }
-
- // iso 8601 regex
- // 0000-00-00 0000-W00 or 0000-W00-0 + T + 00 or 00:00 or 00:00:00 or 00:00:00.000 + +00:00 or +0000 or +00)
- var extendedIsoRegex = /^\s*((?:[+-]\d{6}|\d{4})-(?:\d\d-\d\d|W\d\d-\d|W\d\d|\d\d\d|\d\d))(?:(T| )(\d\d(?::\d\d(?::\d\d(?:[.,]\d+)?)?)?)([\+\-]\d\d(?::?\d\d)?|\s*Z)?)?$/;
- var basicIsoRegex = /^\s*((?:[+-]\d{6}|\d{4})(?:\d\d\d\d|W\d\d\d|W\d\d|\d\d\d|\d\d))(?:(T| )(\d\d(?:\d\d(?:\d\d(?:[.,]\d+)?)?)?)([\+\-]\d\d(?::?\d\d)?|\s*Z)?)?$/;
-
- var tzRegex = /Z|[+-]\d\d(?::?\d\d)?/;
-
- var isoDates = [
- ['YYYYYY-MM-DD', /[+-]\d{6}-\d\d-\d\d/],
- ['YYYY-MM-DD', /\d{4}-\d\d-\d\d/],
- ['GGGG-[W]WW-E', /\d{4}-W\d\d-\d/],
- ['GGGG-[W]WW', /\d{4}-W\d\d/, false],
- ['YYYY-DDD', /\d{4}-\d{3}/],
- ['YYYY-MM', /\d{4}-\d\d/, false],
- ['YYYYYYMMDD', /[+-]\d{10}/],
- ['YYYYMMDD', /\d{8}/],
- // YYYYMM is NOT allowed by the standard
- ['GGGG[W]WWE', /\d{4}W\d{3}/],
- ['GGGG[W]WW', /\d{4}W\d{2}/, false],
- ['YYYYDDD', /\d{7}/]
- ];
-
- // iso time formats and regexes
- var isoTimes = [
- ['HH:mm:ss.SSSS', /\d\d:\d\d:\d\d\.\d+/],
- ['HH:mm:ss,SSSS', /\d\d:\d\d:\d\d,\d+/],
- ['HH:mm:ss', /\d\d:\d\d:\d\d/],
- ['HH:mm', /\d\d:\d\d/],
- ['HHmmss.SSSS', /\d\d\d\d\d\d\.\d+/],
- ['HHmmss,SSSS', /\d\d\d\d\d\d,\d+/],
- ['HHmmss', /\d\d\d\d\d\d/],
- ['HHmm', /\d\d\d\d/],
- ['HH', /\d\d/]
- ];
-
- var aspNetJsonRegex = /^\/?Date\((\-?\d+)/i;
-
- // date from iso format
- function configFromISO(config) {
- var i, l,
- string = config._i,
- match = extendedIsoRegex.exec(string) || basicIsoRegex.exec(string),
- allowTime, dateFormat, timeFormat, tzFormat;
-
- if (match) {
- getParsingFlags(config).iso = true;
-
- for (i = 0, l = isoDates.length; i < l; i++) {
- if (isoDates[i][1].exec(match[1])) {
- dateFormat = isoDates[i][0];
- allowTime = isoDates[i][2] !== false;
- break;
- }
- }
- if (dateFormat == null) {
- config._isValid = false;
- return;
- }
- if (match[3]) {
- for (i = 0, l = isoTimes.length; i < l; i++) {
- if (isoTimes[i][1].exec(match[3])) {
- // match[2] should be 'T' or space
- timeFormat = (match[2] || ' ') + isoTimes[i][0];
- break;
- }
- }
- if (timeFormat == null) {
- config._isValid = false;
- return;
- }
- }
- if (!allowTime && timeFormat != null) {
- config._isValid = false;
- return;
- }
- if (match[4]) {
- if (tzRegex.exec(match[4])) {
- tzFormat = 'Z';
- } else {
- config._isValid = false;
- return;
- }
- }
- config._f = dateFormat + (timeFormat || '') + (tzFormat || '');
- configFromStringAndFormat(config);
- } else {
- config._isValid = false;
- }
- }
-
- // RFC 2822 regex: For details see https://tools.ietf.org/html/rfc2822#section-3.3
- var rfc2822 = /^(?:(Mon|Tue|Wed|Thu|Fri|Sat|Sun),?\s)?(\d{1,2})\s(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\s(\d{2,4})\s(\d\d):(\d\d)(?::(\d\d))?\s(?:(UT|GMT|[ECMP][SD]T)|([Zz])|([+-]\d{4}))$/;
-
- function extractFromRFC2822Strings(yearStr, monthStr, dayStr, hourStr, minuteStr, secondStr) {
- var result = [
- untruncateYear(yearStr),
- defaultLocaleMonthsShort.indexOf(monthStr),
- parseInt(dayStr, 10),
- parseInt(hourStr, 10),
- parseInt(minuteStr, 10)
- ];
-
- if (secondStr) {
- result.push(parseInt(secondStr, 10));
- }
-
- return result;
- }
-
- function untruncateYear(yearStr) {
- var year = parseInt(yearStr, 10);
- if (year <= 49) {
- return 2000 + year;
- } else if (year <= 999) {
- return 1900 + year;
- }
- return year;
- }
-
- function preprocessRFC2822(s) {
- // Remove comments and folding whitespace and replace multiple-spaces with a single space
- return s.replace(/\([^)]*\)|[\n\t]/g, ' ').replace(/(\s\s+)/g, ' ').replace(/^\s\s*/, '').replace(/\s\s*$/, '');
- }
-
- function checkWeekday(weekdayStr, parsedInput, config) {
- if (weekdayStr) {
- // TODO: Replace the vanilla JS Date object with an indepentent day-of-week check.
- var weekdayProvided = defaultLocaleWeekdaysShort.indexOf(weekdayStr),
- weekdayActual = new Date(parsedInput[0], parsedInput[1], parsedInput[2]).getDay();
- if (weekdayProvided !== weekdayActual) {
- getParsingFlags(config).weekdayMismatch = true;
- config._isValid = false;
- return false;
- }
- }
- return true;
- }
-
- var obsOffsets = {
- UT: 0,
- GMT: 0,
- EDT: -4 * 60,
- EST: -5 * 60,
- CDT: -5 * 60,
- CST: -6 * 60,
- MDT: -6 * 60,
- MST: -7 * 60,
- PDT: -7 * 60,
- PST: -8 * 60
- };
-
- function calculateOffset(obsOffset, militaryOffset, numOffset) {
- if (obsOffset) {
- return obsOffsets[obsOffset];
- } else if (militaryOffset) {
- // the only allowed military tz is Z
- return 0;
- } else {
- var hm = parseInt(numOffset, 10);
- var m = hm % 100, h = (hm - m) / 100;
- return h * 60 + m;
- }
- }
-
- // date and time from ref 2822 format
- function configFromRFC2822(config) {
- var match = rfc2822.exec(preprocessRFC2822(config._i));
- if (match) {
- var parsedArray = extractFromRFC2822Strings(match[4], match[3], match[2], match[5], match[6], match[7]);
- if (!checkWeekday(match[1], parsedArray, config)) {
- return;
- }
-
- config._a = parsedArray;
- config._tzm = calculateOffset(match[8], match[9], match[10]);
-
- config._d = createUTCDate.apply(null, config._a);
- config._d.setUTCMinutes(config._d.getUTCMinutes() - config._tzm);
-
- getParsingFlags(config).rfc2822 = true;
- } else {
- config._isValid = false;
- }
- }
-
- // date from iso format or fallback
- function configFromString(config) {
- var matched = aspNetJsonRegex.exec(config._i);
-
- if (matched !== null) {
- config._d = new Date(+matched[1]);
- return;
- }
-
- configFromISO(config);
- if (config._isValid === false) {
- delete config._isValid;
- } else {
- return;
- }
-
- configFromRFC2822(config);
- if (config._isValid === false) {
- delete config._isValid;
- } else {
- return;
- }
-
- // Final attempt, use Input Fallback
- hooks.createFromInputFallback(config);
- }
-
- hooks.createFromInputFallback = deprecate(
- 'value provided is not in a recognized RFC2822 or ISO format. moment construction falls back to js Date(), ' +
- 'which is not reliable across all browsers and versions. Non RFC2822/ISO date formats are ' +
- 'discouraged and will be removed in an upcoming major release. Please refer to ' +
- 'http://momentjs.com/guides/#/warnings/js-date/ for more info.',
- function (config) {
- config._d = new Date(config._i + (config._useUTC ? ' UTC' : ''));
- }
- );
-
- // constant that refers to the ISO standard
- hooks.ISO_8601 = function () {};
-
- // constant that refers to the RFC 2822 form
- hooks.RFC_2822 = function () {};
-
- // date from string and format string
- function configFromStringAndFormat(config) {
- // TODO: Move this to another part of the creation flow to prevent circular deps
- if (config._f === hooks.ISO_8601) {
- configFromISO(config);
- return;
- }
- if (config._f === hooks.RFC_2822) {
- configFromRFC2822(config);
- return;
- }
- config._a = [];
- getParsingFlags(config).empty = true;
-
- // This array is used to make a Date, either with `new Date` or `Date.UTC`
- var string = '' + config._i,
- i, parsedInput, tokens, token, skipped,
- stringLength = string.length,
- totalParsedInputLength = 0;
-
- tokens = expandFormat(config._f, config._locale).match(formattingTokens) || [];
-
- for (i = 0; i < tokens.length; i++) {
- token = tokens[i];
- parsedInput = (string.match(getParseRegexForToken(token, config)) || [])[0];
- // console.log('token', token, 'parsedInput', parsedInput,
- // 'regex', getParseRegexForToken(token, config));
- if (parsedInput) {
- skipped = string.substr(0, string.indexOf(parsedInput));
- if (skipped.length > 0) {
- getParsingFlags(config).unusedInput.push(skipped);
- }
- string = string.slice(string.indexOf(parsedInput) + parsedInput.length);
- totalParsedInputLength += parsedInput.length;
- }
- // don't parse if it's not a known token
- if (formatTokenFunctions[token]) {
- if (parsedInput) {
- getParsingFlags(config).empty = false;
- }
- else {
- getParsingFlags(config).unusedTokens.push(token);
- }
- addTimeToArrayFromToken(token, parsedInput, config);
- }
- else if (config._strict && !parsedInput) {
- getParsingFlags(config).unusedTokens.push(token);
- }
- }
-
- // add remaining unparsed input length to the string
- getParsingFlags(config).charsLeftOver = stringLength - totalParsedInputLength;
- if (string.length > 0) {
- getParsingFlags(config).unusedInput.push(string);
- }
-
- // clear _12h flag if hour is <= 12
- if (config._a[HOUR] <= 12 &&
- getParsingFlags(config).bigHour === true &&
- config._a[HOUR] > 0) {
- getParsingFlags(config).bigHour = undefined;
- }
-
- getParsingFlags(config).parsedDateParts = config._a.slice(0);
- getParsingFlags(config).meridiem = config._meridiem;
- // handle meridiem
- config._a[HOUR] = meridiemFixWrap(config._locale, config._a[HOUR], config._meridiem);
-
- configFromArray(config);
- checkOverflow(config);
- }
-
-
- function meridiemFixWrap (locale, hour, meridiem) {
- var isPm;
-
- if (meridiem == null) {
- // nothing to do
- return hour;
- }
- if (locale.meridiemHour != null) {
- return locale.meridiemHour(hour, meridiem);
- } else if (locale.isPM != null) {
- // Fallback
- isPm = locale.isPM(meridiem);
- if (isPm && hour < 12) {
- hour += 12;
- }
- if (!isPm && hour === 12) {
- hour = 0;
- }
- return hour;
- } else {
- // this is not supposed to happen
- return hour;
- }
- }
-
- // date from string and array of format strings
- function configFromStringAndArray(config) {
- var tempConfig,
- bestMoment,
-
- scoreToBeat,
- i,
- currentScore;
-
- if (config._f.length === 0) {
- getParsingFlags(config).invalidFormat = true;
- config._d = new Date(NaN);
- return;
- }
-
- for (i = 0; i < config._f.length; i++) {
- currentScore = 0;
- tempConfig = copyConfig({}, config);
- if (config._useUTC != null) {
- tempConfig._useUTC = config._useUTC;
- }
- tempConfig._f = config._f[i];
- configFromStringAndFormat(tempConfig);
-
- if (!isValid(tempConfig)) {
- continue;
- }
-
- // if there is any input that was not parsed add a penalty for that format
- currentScore += getParsingFlags(tempConfig).charsLeftOver;
-
- //or tokens
- currentScore += getParsingFlags(tempConfig).unusedTokens.length * 10;
-
- getParsingFlags(tempConfig).score = currentScore;
-
- if (scoreToBeat == null || currentScore < scoreToBeat) {
- scoreToBeat = currentScore;
- bestMoment = tempConfig;
- }
- }
-
- extend(config, bestMoment || tempConfig);
- }
-
- function configFromObject(config) {
- if (config._d) {
- return;
- }
-
- var i = normalizeObjectUnits(config._i);
- config._a = map([i.year, i.month, i.day || i.date, i.hour, i.minute, i.second, i.millisecond], function (obj) {
- return obj && parseInt(obj, 10);
- });
-
- configFromArray(config);
- }
-
- function createFromConfig (config) {
- var res = new Moment(checkOverflow(prepareConfig(config)));
- if (res._nextDay) {
- // Adding is smart enough around DST
- res.add(1, 'd');
- res._nextDay = undefined;
- }
-
- return res;
- }
-
- function prepareConfig (config) {
- var input = config._i,
- format = config._f;
-
- config._locale = config._locale || getLocale(config._l);
-
- if (input === null || (format === undefined && input === '')) {
- return createInvalid({nullInput: true});
- }
-
- if (typeof input === 'string') {
- config._i = input = config._locale.preparse(input);
- }
-
- if (isMoment(input)) {
- return new Moment(checkOverflow(input));
- } else if (isDate(input)) {
- config._d = input;
- } else if (isArray(format)) {
- configFromStringAndArray(config);
- } else if (format) {
- configFromStringAndFormat(config);
- } else {
- configFromInput(config);
- }
-
- if (!isValid(config)) {
- config._d = null;
- }
-
- return config;
- }
-
- function configFromInput(config) {
- var input = config._i;
- if (isUndefined(input)) {
- config._d = new Date(hooks.now());
- } else if (isDate(input)) {
- config._d = new Date(input.valueOf());
- } else if (typeof input === 'string') {
- configFromString(config);
- } else if (isArray(input)) {
- config._a = map(input.slice(0), function (obj) {
- return parseInt(obj, 10);
- });
- configFromArray(config);
- } else if (isObject(input)) {
- configFromObject(config);
- } else if (isNumber(input)) {
- // from milliseconds
- config._d = new Date(input);
- } else {
- hooks.createFromInputFallback(config);
- }
- }
-
- function createLocalOrUTC (input, format, locale, strict, isUTC) {
- var c = {};
-
- if (locale === true || locale === false) {
- strict = locale;
- locale = undefined;
- }
-
- if ((isObject(input) && isObjectEmpty(input)) ||
- (isArray(input) && input.length === 0)) {
- input = undefined;
- }
- // object construction must be done this way.
- // https://github.com/moment/moment/issues/1423
- c._isAMomentObject = true;
- c._useUTC = c._isUTC = isUTC;
- c._l = locale;
- c._i = input;
- c._f = format;
- c._strict = strict;
-
- return createFromConfig(c);
- }
-
- function createLocal (input, format, locale, strict) {
- return createLocalOrUTC(input, format, locale, strict, false);
- }
-
- var prototypeMin = deprecate(
- 'moment().min is deprecated, use moment.max instead. http://momentjs.com/guides/#/warnings/min-max/',
- function () {
- var other = createLocal.apply(null, arguments);
- if (this.isValid() && other.isValid()) {
- return other < this ? this : other;
- } else {
- return createInvalid();
- }
- }
- );
-
- var prototypeMax = deprecate(
- 'moment().max is deprecated, use moment.min instead. http://momentjs.com/guides/#/warnings/min-max/',
- function () {
- var other = createLocal.apply(null, arguments);
- if (this.isValid() && other.isValid()) {
- return other > this ? this : other;
- } else {
- return createInvalid();
- }
- }
- );
-
- // Pick a moment m from moments so that m[fn](other) is true for all
- // other. This relies on the function fn to be transitive.
- //
- // moments should either be an array of moment objects or an array, whose
- // first element is an array of moment objects.
- function pickBy(fn, moments) {
- var res, i;
- if (moments.length === 1 && isArray(moments[0])) {
- moments = moments[0];
- }
- if (!moments.length) {
- return createLocal();
- }
- res = moments[0];
- for (i = 1; i < moments.length; ++i) {
- if (!moments[i].isValid() || moments[i][fn](res)) {
- res = moments[i];
- }
- }
- return res;
- }
-
- // TODO: Use [].sort instead?
- function min () {
- var args = [].slice.call(arguments, 0);
-
- return pickBy('isBefore', args);
- }
-
- function max () {
- var args = [].slice.call(arguments, 0);
-
- return pickBy('isAfter', args);
- }
-
- var now = function () {
- return Date.now ? Date.now() : +(new Date());
- };
-
- var ordering = ['year', 'quarter', 'month', 'week', 'day', 'hour', 'minute', 'second', 'millisecond'];
-
- function isDurationValid(m) {
- for (var key in m) {
- if (!(indexOf.call(ordering, key) !== -1 && (m[key] == null || !isNaN(m[key])))) {
- return false;
- }
- }
-
- var unitHasDecimal = false;
- for (var i = 0; i < ordering.length; ++i) {
- if (m[ordering[i]]) {
- if (unitHasDecimal) {
- return false; // only allow non-integers for smallest unit
- }
- if (parseFloat(m[ordering[i]]) !== toInt(m[ordering[i]])) {
- unitHasDecimal = true;
- }
- }
- }
-
- return true;
- }
-
- function isValid$1() {
- return this._isValid;
- }
-
- function createInvalid$1() {
- return createDuration(NaN);
- }
-
- function Duration (duration) {
- var normalizedInput = normalizeObjectUnits(duration),
- years = normalizedInput.year || 0,
- quarters = normalizedInput.quarter || 0,
- months = normalizedInput.month || 0,
- weeks = normalizedInput.week || normalizedInput.isoWeek || 0,
- days = normalizedInput.day || 0,
- hours = normalizedInput.hour || 0,
- minutes = normalizedInput.minute || 0,
- seconds = normalizedInput.second || 0,
- milliseconds = normalizedInput.millisecond || 0;
-
- this._isValid = isDurationValid(normalizedInput);
-
- // representation for dateAddRemove
- this._milliseconds = +milliseconds +
- seconds * 1e3 + // 1000
- minutes * 6e4 + // 1000 * 60
- hours * 1000 * 60 * 60; //using 1000 * 60 * 60 instead of 36e5 to avoid floating point rounding errors https://github.com/moment/moment/issues/2978
- // Because of dateAddRemove treats 24 hours as different from a
- // day when working around DST, we need to store them separately
- this._days = +days +
- weeks * 7;
- // It is impossible to translate months into days without knowing
- // which months you are are talking about, so we have to store
- // it separately.
- this._months = +months +
- quarters * 3 +
- years * 12;
-
- this._data = {};
-
- this._locale = getLocale();
-
- this._bubble();
- }
-
- function isDuration (obj) {
- return obj instanceof Duration;
- }
-
- function absRound (number) {
- if (number < 0) {
- return Math.round(-1 * number) * -1;
- } else {
- return Math.round(number);
- }
- }
-
- // FORMATTING
-
- function offset (token, separator) {
- addFormatToken(token, 0, 0, function () {
- var offset = this.utcOffset();
- var sign = '+';
- if (offset < 0) {
- offset = -offset;
- sign = '-';
- }
- return sign + zeroFill(~~(offset / 60), 2) + separator + zeroFill(~~(offset) % 60, 2);
- });
- }
-
- offset('Z', ':');
- offset('ZZ', '');
-
- // PARSING
-
- addRegexToken('Z', matchShortOffset);
- addRegexToken('ZZ', matchShortOffset);
- addParseToken(['Z', 'ZZ'], function (input, array, config) {
- config._useUTC = true;
- config._tzm = offsetFromString(matchShortOffset, input);
- });
-
- // HELPERS
-
- // timezone chunker
- // '+10:00' > ['10', '00']
- // '-1530' > ['-15', '30']
- var chunkOffset = /([\+\-]|\d\d)/gi;
-
- function offsetFromString(matcher, string) {
- var matches = (string || '').match(matcher);
-
- if (matches === null) {
- return null;
- }
-
- var chunk = matches[matches.length - 1] || [];
- var parts = (chunk + '').match(chunkOffset) || ['-', 0, 0];
- var minutes = +(parts[1] * 60) + toInt(parts[2]);
-
- return minutes === 0 ?
- 0 :
- parts[0] === '+' ? minutes : -minutes;
- }
-
- // Return a moment from input, that is local/utc/zone equivalent to model.
- function cloneWithOffset(input, model) {
- var res, diff;
- if (model._isUTC) {
- res = model.clone();
- diff = (isMoment(input) || isDate(input) ? input.valueOf() : createLocal(input).valueOf()) - res.valueOf();
- // Use low-level api, because this fn is low-level api.
- res._d.setTime(res._d.valueOf() + diff);
- hooks.updateOffset(res, false);
- return res;
- } else {
- return createLocal(input).local();
- }
- }
-
- function getDateOffset (m) {
- // On Firefox.24 Date#getTimezoneOffset returns a floating point.
- // https://github.com/moment/moment/pull/1871
- return -Math.round(m._d.getTimezoneOffset() / 15) * 15;
- }
-
- // HOOKS
-
- // This function will be called whenever a moment is mutated.
- // It is intended to keep the offset in sync with the timezone.
- hooks.updateOffset = function () {};
-
- // MOMENTS
-
- // keepLocalTime = true means only change the timezone, without
- // affecting the local hour. So 5:31:26 +0300 --[utcOffset(2, true)]-->
- // 5:31:26 +0200 It is possible that 5:31:26 doesn't exist with offset
- // +0200, so we adjust the time as needed, to be valid.
- //
- // Keeping the time actually adds/subtracts (one hour)
- // from the actual represented time. That is why we call updateOffset
- // a second time. In case it wants us to change the offset again
- // _changeInProgress == true case, then we have to adjust, because
- // there is no such time in the given timezone.
- function getSetOffset (input, keepLocalTime, keepMinutes) {
- var offset = this._offset || 0,
- localAdjust;
- if (!this.isValid()) {
- return input != null ? this : NaN;
- }
- if (input != null) {
- if (typeof input === 'string') {
- input = offsetFromString(matchShortOffset, input);
- if (input === null) {
- return this;
- }
- } else if (Math.abs(input) < 16 && !keepMinutes) {
- input = input * 60;
- }
- if (!this._isUTC && keepLocalTime) {
- localAdjust = getDateOffset(this);
- }
- this._offset = input;
- this._isUTC = true;
- if (localAdjust != null) {
- this.add(localAdjust, 'm');
- }
- if (offset !== input) {
- if (!keepLocalTime || this._changeInProgress) {
- addSubtract(this, createDuration(input - offset, 'm'), 1, false);
- } else if (!this._changeInProgress) {
- this._changeInProgress = true;
- hooks.updateOffset(this, true);
- this._changeInProgress = null;
- }
- }
- return this;
- } else {
- return this._isUTC ? offset : getDateOffset(this);
- }
- }
-
- function getSetZone (input, keepLocalTime) {
- if (input != null) {
- if (typeof input !== 'string') {
- input = -input;
- }
-
- this.utcOffset(input, keepLocalTime);
-
- return this;
- } else {
- return -this.utcOffset();
- }
- }
-
- function setOffsetToUTC (keepLocalTime) {
- return this.utcOffset(0, keepLocalTime);
- }
-
- function setOffsetToLocal (keepLocalTime) {
- if (this._isUTC) {
- this.utcOffset(0, keepLocalTime);
- this._isUTC = false;
-
- if (keepLocalTime) {
- this.subtract(getDateOffset(this), 'm');
- }
- }
- return this;
- }
-
- function setOffsetToParsedOffset () {
- if (this._tzm != null) {
- this.utcOffset(this._tzm, false, true);
- } else if (typeof this._i === 'string') {
- var tZone = offsetFromString(matchOffset, this._i);
- if (tZone != null) {
- this.utcOffset(tZone);
- }
- else {
- this.utcOffset(0, true);
- }
- }
- return this;
- }
-
- function hasAlignedHourOffset (input) {
- if (!this.isValid()) {
- return false;
- }
- input = input ? createLocal(input).utcOffset() : 0;
-
- return (this.utcOffset() - input) % 60 === 0;
- }
-
- function isDaylightSavingTime () {
- return (
- this.utcOffset() > this.clone().month(0).utcOffset() ||
- this.utcOffset() > this.clone().month(5).utcOffset()
- );
- }
-
- function isDaylightSavingTimeShifted () {
- if (!isUndefined(this._isDSTShifted)) {
- return this._isDSTShifted;
- }
-
- var c = {};
-
- copyConfig(c, this);
- c = prepareConfig(c);
-
- if (c._a) {
- var other = c._isUTC ? createUTC(c._a) : createLocal(c._a);
- this._isDSTShifted = this.isValid() &&
- compareArrays(c._a, other.toArray()) > 0;
- } else {
- this._isDSTShifted = false;
- }
-
- return this._isDSTShifted;
- }
-
- function isLocal () {
- return this.isValid() ? !this._isUTC : false;
- }
-
- function isUtcOffset () {
- return this.isValid() ? this._isUTC : false;
- }
-
- function isUtc () {
- return this.isValid() ? this._isUTC && this._offset === 0 : false;
- }
-
- // ASP.NET json date format regex
- var aspNetRegex = /^(\-|\+)?(?:(\d*)[. ])?(\d+)\:(\d+)(?:\:(\d+)(\.\d*)?)?$/;
-
- // from http://docs.closure-library.googlecode.com/git/closure_goog_date_date.js.source.html
- // somewhat more in line with 4.4.3.2 2004 spec, but allows decimal anywhere
- // and further modified to allow for strings containing both week and day
- var isoRegex = /^(-|\+)?P(?:([-+]?[0-9,.]*)Y)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)W)?(?:([-+]?[0-9,.]*)D)?(?:T(?:([-+]?[0-9,.]*)H)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)S)?)?$/;
-
- function createDuration (input, key) {
- var duration = input,
- // matching against regexp is expensive, do it on demand
- match = null,
- sign,
- ret,
- diffRes;
-
- if (isDuration(input)) {
- duration = {
- ms : input._milliseconds,
- d : input._days,
- M : input._months
- };
- } else if (isNumber(input)) {
- duration = {};
- if (key) {
- duration[key] = input;
- } else {
- duration.milliseconds = input;
- }
- } else if (!!(match = aspNetRegex.exec(input))) {
- sign = (match[1] === '-') ? -1 : 1;
- duration = {
- y : 0,
- d : toInt(match[DATE]) * sign,
- h : toInt(match[HOUR]) * sign,
- m : toInt(match[MINUTE]) * sign,
- s : toInt(match[SECOND]) * sign,
- ms : toInt(absRound(match[MILLISECOND] * 1000)) * sign // the millisecond decimal point is included in the match
- };
- } else if (!!(match = isoRegex.exec(input))) {
- sign = (match[1] === '-') ? -1 : 1;
- duration = {
- y : parseIso(match[2], sign),
- M : parseIso(match[3], sign),
- w : parseIso(match[4], sign),
- d : parseIso(match[5], sign),
- h : parseIso(match[6], sign),
- m : parseIso(match[7], sign),
- s : parseIso(match[8], sign)
- };
- } else if (duration == null) {// checks for null or undefined
- duration = {};
- } else if (typeof duration === 'object' && ('from' in duration || 'to' in duration)) {
- diffRes = momentsDifference(createLocal(duration.from), createLocal(duration.to));
-
- duration = {};
- duration.ms = diffRes.milliseconds;
- duration.M = diffRes.months;
- }
-
- ret = new Duration(duration);
-
- if (isDuration(input) && hasOwnProp(input, '_locale')) {
- ret._locale = input._locale;
- }
-
- return ret;
- }
-
- createDuration.fn = Duration.prototype;
- createDuration.invalid = createInvalid$1;
-
- function parseIso (inp, sign) {
- // We'd normally use ~~inp for this, but unfortunately it also
- // converts floats to ints.
- // inp may be undefined, so careful calling replace on it.
- var res = inp && parseFloat(inp.replace(',', '.'));
- // apply sign while we're at it
- return (isNaN(res) ? 0 : res) * sign;
- }
-
- function positiveMomentsDifference(base, other) {
- var res = {};
-
- res.months = other.month() - base.month() +
- (other.year() - base.year()) * 12;
- if (base.clone().add(res.months, 'M').isAfter(other)) {
- --res.months;
- }
-
- res.milliseconds = +other - +(base.clone().add(res.months, 'M'));
-
- return res;
- }
-
- function momentsDifference(base, other) {
- var res;
- if (!(base.isValid() && other.isValid())) {
- return {milliseconds: 0, months: 0};
- }
-
- other = cloneWithOffset(other, base);
- if (base.isBefore(other)) {
- res = positiveMomentsDifference(base, other);
- } else {
- res = positiveMomentsDifference(other, base);
- res.milliseconds = -res.milliseconds;
- res.months = -res.months;
- }
-
- return res;
- }
-
- // TODO: remove 'name' arg after deprecation is removed
- function createAdder(direction, name) {
- return function (val, period) {
- var dur, tmp;
- //invert the arguments, but complain about it
- if (period !== null && !isNaN(+period)) {
- deprecateSimple(name, 'moment().' + name + '(period, number) is deprecated. Please use moment().' + name + '(number, period). ' +
- 'See http://momentjs.com/guides/#/warnings/add-inverted-param/ for more info.');
- tmp = val; val = period; period = tmp;
- }
-
- val = typeof val === 'string' ? +val : val;
- dur = createDuration(val, period);
- addSubtract(this, dur, direction);
- return this;
- };
- }
-
- function addSubtract (mom, duration, isAdding, updateOffset) {
- var milliseconds = duration._milliseconds,
- days = absRound(duration._days),
- months = absRound(duration._months);
-
- if (!mom.isValid()) {
- // No op
- return;
- }
-
- updateOffset = updateOffset == null ? true : updateOffset;
-
- if (months) {
- setMonth(mom, get(mom, 'Month') + months * isAdding);
- }
- if (days) {
- set$1(mom, 'Date', get(mom, 'Date') + days * isAdding);
- }
- if (milliseconds) {
- mom._d.setTime(mom._d.valueOf() + milliseconds * isAdding);
- }
- if (updateOffset) {
- hooks.updateOffset(mom, days || months);
- }
- }
-
- var add = createAdder(1, 'add');
- var subtract = createAdder(-1, 'subtract');
-
- function getCalendarFormat(myMoment, now) {
- var diff = myMoment.diff(now, 'days', true);
- return diff < -6 ? 'sameElse' :
- diff < -1 ? 'lastWeek' :
- diff < 0 ? 'lastDay' :
- diff < 1 ? 'sameDay' :
- diff < 2 ? 'nextDay' :
- diff < 7 ? 'nextWeek' : 'sameElse';
- }
-
- function calendar$1 (time, formats) {
- // We want to compare the start of today, vs this.
- // Getting start-of-today depends on whether we're local/utc/offset or not.
- var now = time || createLocal(),
- sod = cloneWithOffset(now, this).startOf('day'),
- format = hooks.calendarFormat(this, sod) || 'sameElse';
-
- var output = formats && (isFunction(formats[format]) ? formats[format].call(this, now) : formats[format]);
-
- return this.format(output || this.localeData().calendar(format, this, createLocal(now)));
- }
-
- function clone () {
- return new Moment(this);
- }
-
- function isAfter (input, units) {
- var localInput = isMoment(input) ? input : createLocal(input);
- if (!(this.isValid() && localInput.isValid())) {
- return false;
- }
- units = normalizeUnits(units) || 'millisecond';
- if (units === 'millisecond') {
- return this.valueOf() > localInput.valueOf();
- } else {
- return localInput.valueOf() < this.clone().startOf(units).valueOf();
- }
- }
-
- function isBefore (input, units) {
- var localInput = isMoment(input) ? input : createLocal(input);
- if (!(this.isValid() && localInput.isValid())) {
- return false;
- }
- units = normalizeUnits(units) || 'millisecond';
- if (units === 'millisecond') {
- return this.valueOf() < localInput.valueOf();
- } else {
- return this.clone().endOf(units).valueOf() < localInput.valueOf();
- }
- }
-
- function isBetween (from, to, units, inclusivity) {
- var localFrom = isMoment(from) ? from : createLocal(from),
- localTo = isMoment(to) ? to : createLocal(to);
- if (!(this.isValid() && localFrom.isValid() && localTo.isValid())) {
- return false;
- }
- inclusivity = inclusivity || '()';
- return (inclusivity[0] === '(' ? this.isAfter(localFrom, units) : !this.isBefore(localFrom, units)) &&
- (inclusivity[1] === ')' ? this.isBefore(localTo, units) : !this.isAfter(localTo, units));
- }
-
- function isSame (input, units) {
- var localInput = isMoment(input) ? input : createLocal(input),
- inputMs;
- if (!(this.isValid() && localInput.isValid())) {
- return false;
- }
- units = normalizeUnits(units) || 'millisecond';
- if (units === 'millisecond') {
- return this.valueOf() === localInput.valueOf();
- } else {
- inputMs = localInput.valueOf();
- return this.clone().startOf(units).valueOf() <= inputMs && inputMs <= this.clone().endOf(units).valueOf();
- }
- }
-
- function isSameOrAfter (input, units) {
- return this.isSame(input, units) || this.isAfter(input, units);
- }
-
- function isSameOrBefore (input, units) {
- return this.isSame(input, units) || this.isBefore(input, units);
- }
-
- function diff (input, units, asFloat) {
- var that,
- zoneDelta,
- output;
-
- if (!this.isValid()) {
- return NaN;
- }
-
- that = cloneWithOffset(input, this);
-
- if (!that.isValid()) {
- return NaN;
- }
-
- zoneDelta = (that.utcOffset() - this.utcOffset()) * 6e4;
-
- units = normalizeUnits(units);
-
- switch (units) {
- case 'year': output = monthDiff(this, that) / 12; break;
- case 'month': output = monthDiff(this, that); break;
- case 'quarter': output = monthDiff(this, that) / 3; break;
- case 'second': output = (this - that) / 1e3; break; // 1000
- case 'minute': output = (this - that) / 6e4; break; // 1000 * 60
- case 'hour': output = (this - that) / 36e5; break; // 1000 * 60 * 60
- case 'day': output = (this - that - zoneDelta) / 864e5; break; // 1000 * 60 * 60 * 24, negate dst
- case 'week': output = (this - that - zoneDelta) / 6048e5; break; // 1000 * 60 * 60 * 24 * 7, negate dst
- default: output = this - that;
- }
-
- return asFloat ? output : absFloor(output);
- }
-
- function monthDiff (a, b) {
- // difference in months
- var wholeMonthDiff = ((b.year() - a.year()) * 12) + (b.month() - a.month()),
- // b is in (anchor - 1 month, anchor + 1 month)
- anchor = a.clone().add(wholeMonthDiff, 'months'),
- anchor2, adjust;
-
- if (b - anchor < 0) {
- anchor2 = a.clone().add(wholeMonthDiff - 1, 'months');
- // linear across the month
- adjust = (b - anchor) / (anchor - anchor2);
- } else {
- anchor2 = a.clone().add(wholeMonthDiff + 1, 'months');
- // linear across the month
- adjust = (b - anchor) / (anchor2 - anchor);
- }
-
- //check for negative zero, return zero if negative zero
- return -(wholeMonthDiff + adjust) || 0;
- }
-
- hooks.defaultFormat = 'YYYY-MM-DDTHH:mm:ssZ';
- hooks.defaultFormatUtc = 'YYYY-MM-DDTHH:mm:ss[Z]';
-
- function toString () {
- return this.clone().locale('en').format('ddd MMM DD YYYY HH:mm:ss [GMT]ZZ');
- }
-
- function toISOString(keepOffset) {
- if (!this.isValid()) {
- return null;
- }
- var utc = keepOffset !== true;
- var m = utc ? this.clone().utc() : this;
- if (m.year() < 0 || m.year() > 9999) {
- return formatMoment(m, utc ? 'YYYYYY-MM-DD[T]HH:mm:ss.SSS[Z]' : 'YYYYYY-MM-DD[T]HH:mm:ss.SSSZ');
- }
- if (isFunction(Date.prototype.toISOString)) {
- // native implementation is ~50x faster, use it when we can
- if (utc) {
- return this.toDate().toISOString();
- } else {
- return new Date(this.valueOf() + this.utcOffset() * 60 * 1000).toISOString().replace('Z', formatMoment(m, 'Z'));
- }
- }
- return formatMoment(m, utc ? 'YYYY-MM-DD[T]HH:mm:ss.SSS[Z]' : 'YYYY-MM-DD[T]HH:mm:ss.SSSZ');
- }
-
- /**
- * Return a human readable representation of a moment that can
- * also be evaluated to get a new moment which is the same
- *
- * @link https://nodejs.org/dist/latest/docs/api/util.html#util_custom_inspect_function_on_objects
- */
- function inspect () {
- if (!this.isValid()) {
- return 'moment.invalid(/* ' + this._i + ' */)';
- }
- var func = 'moment';
- var zone = '';
- if (!this.isLocal()) {
- func = this.utcOffset() === 0 ? 'moment.utc' : 'moment.parseZone';
- zone = 'Z';
- }
- var prefix = '[' + func + '("]';
- var year = (0 <= this.year() && this.year() <= 9999) ? 'YYYY' : 'YYYYYY';
- var datetime = '-MM-DD[T]HH:mm:ss.SSS';
- var suffix = zone + '[")]';
-
- return this.format(prefix + year + datetime + suffix);
- }
-
- function format (inputString) {
- if (!inputString) {
- inputString = this.isUtc() ? hooks.defaultFormatUtc : hooks.defaultFormat;
- }
- var output = formatMoment(this, inputString);
- return this.localeData().postformat(output);
- }
-
- function from (time, withoutSuffix) {
- if (this.isValid() &&
- ((isMoment(time) && time.isValid()) ||
- createLocal(time).isValid())) {
- return createDuration({to: this, from: time}).locale(this.locale()).humanize(!withoutSuffix);
- } else {
- return this.localeData().invalidDate();
- }
- }
-
- function fromNow (withoutSuffix) {
- return this.from(createLocal(), withoutSuffix);
- }
-
- function to (time, withoutSuffix) {
- if (this.isValid() &&
- ((isMoment(time) && time.isValid()) ||
- createLocal(time).isValid())) {
- return createDuration({from: this, to: time}).locale(this.locale()).humanize(!withoutSuffix);
- } else {
- return this.localeData().invalidDate();
- }
- }
-
- function toNow (withoutSuffix) {
- return this.to(createLocal(), withoutSuffix);
- }
-
- // If passed a locale key, it will set the locale for this
- // instance. Otherwise, it will return the locale configuration
- // variables for this instance.
- function locale (key) {
- var newLocaleData;
-
- if (key === undefined) {
- return this._locale._abbr;
- } else {
- newLocaleData = getLocale(key);
- if (newLocaleData != null) {
- this._locale = newLocaleData;
- }
- return this;
- }
- }
-
- var lang = deprecate(
- 'moment().lang() is deprecated. Instead, use moment().localeData() to get the language configuration. Use moment().locale() to change languages.',
- function (key) {
- if (key === undefined) {
- return this.localeData();
- } else {
- return this.locale(key);
- }
- }
- );
-
- function localeData () {
- return this._locale;
- }
-
- var MS_PER_SECOND = 1000;
- var MS_PER_MINUTE = 60 * MS_PER_SECOND;
- var MS_PER_HOUR = 60 * MS_PER_MINUTE;
- var MS_PER_400_YEARS = (365 * 400 + 97) * 24 * MS_PER_HOUR;
-
- // actual modulo - handles negative numbers (for dates before 1970):
- function mod$1(dividend, divisor) {
- return (dividend % divisor + divisor) % divisor;
- }
-
- function localStartOfDate(y, m, d) {
- // the date constructor remaps years 0-99 to 1900-1999
- if (y < 100 && y >= 0) {
- // preserve leap years using a full 400 year cycle, then reset
- return new Date(y + 400, m, d) - MS_PER_400_YEARS;
- } else {
- return new Date(y, m, d).valueOf();
- }
- }
-
- function utcStartOfDate(y, m, d) {
- // Date.UTC remaps years 0-99 to 1900-1999
- if (y < 100 && y >= 0) {
- // preserve leap years using a full 400 year cycle, then reset
- return Date.UTC(y + 400, m, d) - MS_PER_400_YEARS;
- } else {
- return Date.UTC(y, m, d);
- }
- }
-
- function startOf (units) {
- var time;
- units = normalizeUnits(units);
- if (units === undefined || units === 'millisecond' || !this.isValid()) {
- return this;
- }
-
- var startOfDate = this._isUTC ? utcStartOfDate : localStartOfDate;
-
- switch (units) {
- case 'year':
- time = startOfDate(this.year(), 0, 1);
- break;
- case 'quarter':
- time = startOfDate(this.year(), this.month() - this.month() % 3, 1);
- break;
- case 'month':
- time = startOfDate(this.year(), this.month(), 1);
- break;
- case 'week':
- time = startOfDate(this.year(), this.month(), this.date() - this.weekday());
- break;
- case 'isoWeek':
- time = startOfDate(this.year(), this.month(), this.date() - (this.isoWeekday() - 1));
- break;
- case 'day':
- case 'date':
- time = startOfDate(this.year(), this.month(), this.date());
- break;
- case 'hour':
- time = this._d.valueOf();
- time -= mod$1(time + (this._isUTC ? 0 : this.utcOffset() * MS_PER_MINUTE), MS_PER_HOUR);
- break;
- case 'minute':
- time = this._d.valueOf();
- time -= mod$1(time, MS_PER_MINUTE);
- break;
- case 'second':
- time = this._d.valueOf();
- time -= mod$1(time, MS_PER_SECOND);
- break;
- }
-
- this._d.setTime(time);
- hooks.updateOffset(this, true);
- return this;
- }
-
- function endOf (units) {
- var time;
- units = normalizeUnits(units);
- if (units === undefined || units === 'millisecond' || !this.isValid()) {
- return this;
- }
-
- var startOfDate = this._isUTC ? utcStartOfDate : localStartOfDate;
-
- switch (units) {
- case 'year':
- time = startOfDate(this.year() + 1, 0, 1) - 1;
- break;
- case 'quarter':
- time = startOfDate(this.year(), this.month() - this.month() % 3 + 3, 1) - 1;
- break;
- case 'month':
- time = startOfDate(this.year(), this.month() + 1, 1) - 1;
- break;
- case 'week':
- time = startOfDate(this.year(), this.month(), this.date() - this.weekday() + 7) - 1;
- break;
- case 'isoWeek':
- time = startOfDate(this.year(), this.month(), this.date() - (this.isoWeekday() - 1) + 7) - 1;
- break;
- case 'day':
- case 'date':
- time = startOfDate(this.year(), this.month(), this.date() + 1) - 1;
- break;
- case 'hour':
- time = this._d.valueOf();
- time += MS_PER_HOUR - mod$1(time + (this._isUTC ? 0 : this.utcOffset() * MS_PER_MINUTE), MS_PER_HOUR) - 1;
- break;
- case 'minute':
- time = this._d.valueOf();
- time += MS_PER_MINUTE - mod$1(time, MS_PER_MINUTE) - 1;
- break;
- case 'second':
- time = this._d.valueOf();
- time += MS_PER_SECOND - mod$1(time, MS_PER_SECOND) - 1;
- break;
- }
-
- this._d.setTime(time);
- hooks.updateOffset(this, true);
- return this;
- }
-
- function valueOf () {
- return this._d.valueOf() - ((this._offset || 0) * 60000);
- }
-
- function unix () {
- return Math.floor(this.valueOf() / 1000);
- }
-
- function toDate () {
- return new Date(this.valueOf());
- }
-
- function toArray () {
- var m = this;
- return [m.year(), m.month(), m.date(), m.hour(), m.minute(), m.second(), m.millisecond()];
- }
-
- function toObject () {
- var m = this;
- return {
- years: m.year(),
- months: m.month(),
- date: m.date(),
- hours: m.hours(),
- minutes: m.minutes(),
- seconds: m.seconds(),
- milliseconds: m.milliseconds()
- };
- }
-
- function toJSON () {
- // new Date(NaN).toJSON() === null
- return this.isValid() ? this.toISOString() : null;
- }
-
- function isValid$2 () {
- return isValid(this);
- }
-
- function parsingFlags () {
- return extend({}, getParsingFlags(this));
- }
-
- function invalidAt () {
- return getParsingFlags(this).overflow;
- }
-
- function creationData() {
- return {
- input: this._i,
- format: this._f,
- locale: this._locale,
- isUTC: this._isUTC,
- strict: this._strict
- };
- }
-
- // FORMATTING
-
- addFormatToken(0, ['gg', 2], 0, function () {
- return this.weekYear() % 100;
- });
-
- addFormatToken(0, ['GG', 2], 0, function () {
- return this.isoWeekYear() % 100;
- });
-
- function addWeekYearFormatToken (token, getter) {
- addFormatToken(0, [token, token.length], 0, getter);
- }
-
- addWeekYearFormatToken('gggg', 'weekYear');
- addWeekYearFormatToken('ggggg', 'weekYear');
- addWeekYearFormatToken('GGGG', 'isoWeekYear');
- addWeekYearFormatToken('GGGGG', 'isoWeekYear');
-
- // ALIASES
-
- addUnitAlias('weekYear', 'gg');
- addUnitAlias('isoWeekYear', 'GG');
-
- // PRIORITY
-
- addUnitPriority('weekYear', 1);
- addUnitPriority('isoWeekYear', 1);
-
-
- // PARSING
-
- addRegexToken('G', matchSigned);
- addRegexToken('g', matchSigned);
- addRegexToken('GG', match1to2, match2);
- addRegexToken('gg', match1to2, match2);
- addRegexToken('GGGG', match1to4, match4);
- addRegexToken('gggg', match1to4, match4);
- addRegexToken('GGGGG', match1to6, match6);
- addRegexToken('ggggg', match1to6, match6);
-
- addWeekParseToken(['gggg', 'ggggg', 'GGGG', 'GGGGG'], function (input, week, config, token) {
- week[token.substr(0, 2)] = toInt(input);
- });
-
- addWeekParseToken(['gg', 'GG'], function (input, week, config, token) {
- week[token] = hooks.parseTwoDigitYear(input);
- });
-
- // MOMENTS
-
- function getSetWeekYear (input) {
- return getSetWeekYearHelper.call(this,
- input,
- this.week(),
- this.weekday(),
- this.localeData()._week.dow,
- this.localeData()._week.doy);
- }
-
- function getSetISOWeekYear (input) {
- return getSetWeekYearHelper.call(this,
- input, this.isoWeek(), this.isoWeekday(), 1, 4);
- }
-
- function getISOWeeksInYear () {
- return weeksInYear(this.year(), 1, 4);
- }
-
- function getWeeksInYear () {
- var weekInfo = this.localeData()._week;
- return weeksInYear(this.year(), weekInfo.dow, weekInfo.doy);
- }
-
- function getSetWeekYearHelper(input, week, weekday, dow, doy) {
- var weeksTarget;
- if (input == null) {
- return weekOfYear(this, dow, doy).year;
- } else {
- weeksTarget = weeksInYear(input, dow, doy);
- if (week > weeksTarget) {
- week = weeksTarget;
- }
- return setWeekAll.call(this, input, week, weekday, dow, doy);
- }
- }
-
- function setWeekAll(weekYear, week, weekday, dow, doy) {
- var dayOfYearData = dayOfYearFromWeeks(weekYear, week, weekday, dow, doy),
- date = createUTCDate(dayOfYearData.year, 0, dayOfYearData.dayOfYear);
-
- this.year(date.getUTCFullYear());
- this.month(date.getUTCMonth());
- this.date(date.getUTCDate());
- return this;
- }
-
- // FORMATTING
-
- addFormatToken('Q', 0, 'Qo', 'quarter');
-
- // ALIASES
-
- addUnitAlias('quarter', 'Q');
-
- // PRIORITY
-
- addUnitPriority('quarter', 7);
-
- // PARSING
-
- addRegexToken('Q', match1);
- addParseToken('Q', function (input, array) {
- array[MONTH] = (toInt(input) - 1) * 3;
- });
-
- // MOMENTS
-
- function getSetQuarter (input) {
- return input == null ? Math.ceil((this.month() + 1) / 3) : this.month((input - 1) * 3 + this.month() % 3);
- }
-
- // FORMATTING
-
- addFormatToken('D', ['DD', 2], 'Do', 'date');
-
- // ALIASES
-
- addUnitAlias('date', 'D');
-
- // PRIORITY
- addUnitPriority('date', 9);
-
- // PARSING
-
- addRegexToken('D', match1to2);
- addRegexToken('DD', match1to2, match2);
- addRegexToken('Do', function (isStrict, locale) {
- // TODO: Remove "ordinalParse" fallback in next major release.
- return isStrict ?
- (locale._dayOfMonthOrdinalParse || locale._ordinalParse) :
- locale._dayOfMonthOrdinalParseLenient;
- });
-
- addParseToken(['D', 'DD'], DATE);
- addParseToken('Do', function (input, array) {
- array[DATE] = toInt(input.match(match1to2)[0]);
- });
-
- // MOMENTS
-
- var getSetDayOfMonth = makeGetSet('Date', true);
-
- // FORMATTING
-
- addFormatToken('DDD', ['DDDD', 3], 'DDDo', 'dayOfYear');
-
- // ALIASES
-
- addUnitAlias('dayOfYear', 'DDD');
-
- // PRIORITY
- addUnitPriority('dayOfYear', 4);
-
- // PARSING
-
- addRegexToken('DDD', match1to3);
- addRegexToken('DDDD', match3);
- addParseToken(['DDD', 'DDDD'], function (input, array, config) {
- config._dayOfYear = toInt(input);
- });
-
- // HELPERS
-
- // MOMENTS
-
- function getSetDayOfYear (input) {
- var dayOfYear = Math.round((this.clone().startOf('day') - this.clone().startOf('year')) / 864e5) + 1;
- return input == null ? dayOfYear : this.add((input - dayOfYear), 'd');
- }
-
- // FORMATTING
-
- addFormatToken('m', ['mm', 2], 0, 'minute');
-
- // ALIASES
-
- addUnitAlias('minute', 'm');
-
- // PRIORITY
-
- addUnitPriority('minute', 14);
-
- // PARSING
-
- addRegexToken('m', match1to2);
- addRegexToken('mm', match1to2, match2);
- addParseToken(['m', 'mm'], MINUTE);
-
- // MOMENTS
-
- var getSetMinute = makeGetSet('Minutes', false);
-
- // FORMATTING
-
- addFormatToken('s', ['ss', 2], 0, 'second');
-
- // ALIASES
-
- addUnitAlias('second', 's');
-
- // PRIORITY
-
- addUnitPriority('second', 15);
-
- // PARSING
-
- addRegexToken('s', match1to2);
- addRegexToken('ss', match1to2, match2);
- addParseToken(['s', 'ss'], SECOND);
-
- // MOMENTS
-
- var getSetSecond = makeGetSet('Seconds', false);
-
- // FORMATTING
-
- addFormatToken('S', 0, 0, function () {
- return ~~(this.millisecond() / 100);
- });
-
- addFormatToken(0, ['SS', 2], 0, function () {
- return ~~(this.millisecond() / 10);
- });
-
- addFormatToken(0, ['SSS', 3], 0, 'millisecond');
- addFormatToken(0, ['SSSS', 4], 0, function () {
- return this.millisecond() * 10;
- });
- addFormatToken(0, ['SSSSS', 5], 0, function () {
- return this.millisecond() * 100;
- });
- addFormatToken(0, ['SSSSSS', 6], 0, function () {
- return this.millisecond() * 1000;
- });
- addFormatToken(0, ['SSSSSSS', 7], 0, function () {
- return this.millisecond() * 10000;
- });
- addFormatToken(0, ['SSSSSSSS', 8], 0, function () {
- return this.millisecond() * 100000;
- });
- addFormatToken(0, ['SSSSSSSSS', 9], 0, function () {
- return this.millisecond() * 1000000;
- });
-
-
- // ALIASES
-
- addUnitAlias('millisecond', 'ms');
-
- // PRIORITY
-
- addUnitPriority('millisecond', 16);
-
- // PARSING
-
- addRegexToken('S', match1to3, match1);
- addRegexToken('SS', match1to3, match2);
- addRegexToken('SSS', match1to3, match3);
-
- var token;
- for (token = 'SSSS'; token.length <= 9; token += 'S') {
- addRegexToken(token, matchUnsigned);
- }
-
- function parseMs(input, array) {
- array[MILLISECOND] = toInt(('0.' + input) * 1000);
- }
-
- for (token = 'S'; token.length <= 9; token += 'S') {
- addParseToken(token, parseMs);
- }
- // MOMENTS
-
- var getSetMillisecond = makeGetSet('Milliseconds', false);
-
- // FORMATTING
-
- addFormatToken('z', 0, 0, 'zoneAbbr');
- addFormatToken('zz', 0, 0, 'zoneName');
-
- // MOMENTS
-
- function getZoneAbbr () {
- return this._isUTC ? 'UTC' : '';
- }
-
- function getZoneName () {
- return this._isUTC ? 'Coordinated Universal Time' : '';
- }
-
- var proto = Moment.prototype;
-
- proto.add = add;
- proto.calendar = calendar$1;
- proto.clone = clone;
- proto.diff = diff;
- proto.endOf = endOf;
- proto.format = format;
- proto.from = from;
- proto.fromNow = fromNow;
- proto.to = to;
- proto.toNow = toNow;
- proto.get = stringGet;
- proto.invalidAt = invalidAt;
- proto.isAfter = isAfter;
- proto.isBefore = isBefore;
- proto.isBetween = isBetween;
- proto.isSame = isSame;
- proto.isSameOrAfter = isSameOrAfter;
- proto.isSameOrBefore = isSameOrBefore;
- proto.isValid = isValid$2;
- proto.lang = lang;
- proto.locale = locale;
- proto.localeData = localeData;
- proto.max = prototypeMax;
- proto.min = prototypeMin;
- proto.parsingFlags = parsingFlags;
- proto.set = stringSet;
- proto.startOf = startOf;
- proto.subtract = subtract;
- proto.toArray = toArray;
- proto.toObject = toObject;
- proto.toDate = toDate;
- proto.toISOString = toISOString;
- proto.inspect = inspect;
- proto.toJSON = toJSON;
- proto.toString = toString;
- proto.unix = unix;
- proto.valueOf = valueOf;
- proto.creationData = creationData;
- proto.year = getSetYear;
- proto.isLeapYear = getIsLeapYear;
- proto.weekYear = getSetWeekYear;
- proto.isoWeekYear = getSetISOWeekYear;
- proto.quarter = proto.quarters = getSetQuarter;
- proto.month = getSetMonth;
- proto.daysInMonth = getDaysInMonth;
- proto.week = proto.weeks = getSetWeek;
- proto.isoWeek = proto.isoWeeks = getSetISOWeek;
- proto.weeksInYear = getWeeksInYear;
- proto.isoWeeksInYear = getISOWeeksInYear;
- proto.date = getSetDayOfMonth;
- proto.day = proto.days = getSetDayOfWeek;
- proto.weekday = getSetLocaleDayOfWeek;
- proto.isoWeekday = getSetISODayOfWeek;
- proto.dayOfYear = getSetDayOfYear;
- proto.hour = proto.hours = getSetHour;
- proto.minute = proto.minutes = getSetMinute;
- proto.second = proto.seconds = getSetSecond;
- proto.millisecond = proto.milliseconds = getSetMillisecond;
- proto.utcOffset = getSetOffset;
- proto.utc = setOffsetToUTC;
- proto.local = setOffsetToLocal;
- proto.parseZone = setOffsetToParsedOffset;
- proto.hasAlignedHourOffset = hasAlignedHourOffset;
- proto.isDST = isDaylightSavingTime;
- proto.isLocal = isLocal;
- proto.isUtcOffset = isUtcOffset;
- proto.isUtc = isUtc;
- proto.isUTC = isUtc;
- proto.zoneAbbr = getZoneAbbr;
- proto.zoneName = getZoneName;
- proto.dates = deprecate('dates accessor is deprecated. Use date instead.', getSetDayOfMonth);
- proto.months = deprecate('months accessor is deprecated. Use month instead', getSetMonth);
- proto.years = deprecate('years accessor is deprecated. Use year instead', getSetYear);
- proto.zone = deprecate('moment().zone is deprecated, use moment().utcOffset instead. http://momentjs.com/guides/#/warnings/zone/', getSetZone);
- proto.isDSTShifted = deprecate('isDSTShifted is deprecated. See http://momentjs.com/guides/#/warnings/dst-shifted/ for more information', isDaylightSavingTimeShifted);
-
- function createUnix (input) {
- return createLocal(input * 1000);
- }
-
- function createInZone () {
- return createLocal.apply(null, arguments).parseZone();
- }
-
- function preParsePostFormat (string) {
- return string;
- }
-
- var proto$1 = Locale.prototype;
-
- proto$1.calendar = calendar;
- proto$1.longDateFormat = longDateFormat;
- proto$1.invalidDate = invalidDate;
- proto$1.ordinal = ordinal;
- proto$1.preparse = preParsePostFormat;
- proto$1.postformat = preParsePostFormat;
- proto$1.relativeTime = relativeTime;
- proto$1.pastFuture = pastFuture;
- proto$1.set = set;
-
- proto$1.months = localeMonths;
- proto$1.monthsShort = localeMonthsShort;
- proto$1.monthsParse = localeMonthsParse;
- proto$1.monthsRegex = monthsRegex;
- proto$1.monthsShortRegex = monthsShortRegex;
- proto$1.week = localeWeek;
- proto$1.firstDayOfYear = localeFirstDayOfYear;
- proto$1.firstDayOfWeek = localeFirstDayOfWeek;
-
- proto$1.weekdays = localeWeekdays;
- proto$1.weekdaysMin = localeWeekdaysMin;
- proto$1.weekdaysShort = localeWeekdaysShort;
- proto$1.weekdaysParse = localeWeekdaysParse;
-
- proto$1.weekdaysRegex = weekdaysRegex;
- proto$1.weekdaysShortRegex = weekdaysShortRegex;
- proto$1.weekdaysMinRegex = weekdaysMinRegex;
-
- proto$1.isPM = localeIsPM;
- proto$1.meridiem = localeMeridiem;
-
- function get$1 (format, index, field, setter) {
- var locale = getLocale();
- var utc = createUTC().set(setter, index);
- return locale[field](utc, format);
- }
-
- function listMonthsImpl (format, index, field) {
- if (isNumber(format)) {
- index = format;
- format = undefined;
- }
-
- format = format || '';
-
- if (index != null) {
- return get$1(format, index, field, 'month');
- }
-
- var i;
- var out = [];
- for (i = 0; i < 12; i++) {
- out[i] = get$1(format, i, field, 'month');
- }
- return out;
- }
-
- // ()
- // (5)
- // (fmt, 5)
- // (fmt)
- // (true)
- // (true, 5)
- // (true, fmt, 5)
- // (true, fmt)
- function listWeekdaysImpl (localeSorted, format, index, field) {
- if (typeof localeSorted === 'boolean') {
- if (isNumber(format)) {
- index = format;
- format = undefined;
- }
-
- format = format || '';
- } else {
- format = localeSorted;
- index = format;
- localeSorted = false;
-
- if (isNumber(format)) {
- index = format;
- format = undefined;
- }
-
- format = format || '';
- }
-
- var locale = getLocale(),
- shift = localeSorted ? locale._week.dow : 0;
-
- if (index != null) {
- return get$1(format, (index + shift) % 7, field, 'day');
- }
-
- var i;
- var out = [];
- for (i = 0; i < 7; i++) {
- out[i] = get$1(format, (i + shift) % 7, field, 'day');
- }
- return out;
- }
-
- function listMonths (format, index) {
- return listMonthsImpl(format, index, 'months');
- }
-
- function listMonthsShort (format, index) {
- return listMonthsImpl(format, index, 'monthsShort');
- }
-
- function listWeekdays (localeSorted, format, index) {
- return listWeekdaysImpl(localeSorted, format, index, 'weekdays');
- }
-
- function listWeekdaysShort (localeSorted, format, index) {
- return listWeekdaysImpl(localeSorted, format, index, 'weekdaysShort');
- }
-
- function listWeekdaysMin (localeSorted, format, index) {
- return listWeekdaysImpl(localeSorted, format, index, 'weekdaysMin');
- }
-
- getSetGlobalLocale('en', {
- dayOfMonthOrdinalParse: /\d{1,2}(th|st|nd|rd)/,
- ordinal : function (number) {
- var b = number % 10,
- output = (toInt(number % 100 / 10) === 1) ? 'th' :
- (b === 1) ? 'st' :
- (b === 2) ? 'nd' :
- (b === 3) ? 'rd' : 'th';
- return number + output;
- }
- });
-
- // Side effect imports
-
- hooks.lang = deprecate('moment.lang is deprecated. Use moment.locale instead.', getSetGlobalLocale);
- hooks.langData = deprecate('moment.langData is deprecated. Use moment.localeData instead.', getLocale);
-
- var mathAbs = Math.abs;
-
- function abs () {
- var data = this._data;
-
- this._milliseconds = mathAbs(this._milliseconds);
- this._days = mathAbs(this._days);
- this._months = mathAbs(this._months);
-
- data.milliseconds = mathAbs(data.milliseconds);
- data.seconds = mathAbs(data.seconds);
- data.minutes = mathAbs(data.minutes);
- data.hours = mathAbs(data.hours);
- data.months = mathAbs(data.months);
- data.years = mathAbs(data.years);
-
- return this;
- }
-
- function addSubtract$1 (duration, input, value, direction) {
- var other = createDuration(input, value);
-
- duration._milliseconds += direction * other._milliseconds;
- duration._days += direction * other._days;
- duration._months += direction * other._months;
-
- return duration._bubble();
- }
-
- // supports only 2.0-style add(1, 's') or add(duration)
- function add$1 (input, value) {
- return addSubtract$1(this, input, value, 1);
- }
-
- // supports only 2.0-style subtract(1, 's') or subtract(duration)
- function subtract$1 (input, value) {
- return addSubtract$1(this, input, value, -1);
- }
-
- function absCeil (number) {
- if (number < 0) {
- return Math.floor(number);
- } else {
- return Math.ceil(number);
- }
- }
-
- function bubble () {
- var milliseconds = this._milliseconds;
- var days = this._days;
- var months = this._months;
- var data = this._data;
- var seconds, minutes, hours, years, monthsFromDays;
-
- // if we have a mix of positive and negative values, bubble down first
- // check: https://github.com/moment/moment/issues/2166
- if (!((milliseconds >= 0 && days >= 0 && months >= 0) ||
- (milliseconds <= 0 && days <= 0 && months <= 0))) {
- milliseconds += absCeil(monthsToDays(months) + days) * 864e5;
- days = 0;
- months = 0;
- }
-
- // The following code bubbles up values, see the tests for
- // examples of what that means.
- data.milliseconds = milliseconds % 1000;
-
- seconds = absFloor(milliseconds / 1000);
- data.seconds = seconds % 60;
-
- minutes = absFloor(seconds / 60);
- data.minutes = minutes % 60;
-
- hours = absFloor(minutes / 60);
- data.hours = hours % 24;
-
- days += absFloor(hours / 24);
-
- // convert days to months
- monthsFromDays = absFloor(daysToMonths(days));
- months += monthsFromDays;
- days -= absCeil(monthsToDays(monthsFromDays));
-
- // 12 months -> 1 year
- years = absFloor(months / 12);
- months %= 12;
-
- data.days = days;
- data.months = months;
- data.years = years;
-
- return this;
- }
-
- function daysToMonths (days) {
- // 400 years have 146097 days (taking into account leap year rules)
- // 400 years have 12 months === 4800
- return days * 4800 / 146097;
- }
-
- function monthsToDays (months) {
- // the reverse of daysToMonths
- return months * 146097 / 4800;
- }
-
- function as (units) {
- if (!this.isValid()) {
- return NaN;
- }
- var days;
- var months;
- var milliseconds = this._milliseconds;
-
- units = normalizeUnits(units);
-
- if (units === 'month' || units === 'quarter' || units === 'year') {
- days = this._days + milliseconds / 864e5;
- months = this._months + daysToMonths(days);
- switch (units) {
- case 'month': return months;
- case 'quarter': return months / 3;
- case 'year': return months / 12;
- }
- } else {
- // handle milliseconds separately because of floating point math errors (issue #1867)
- days = this._days + Math.round(monthsToDays(this._months));
- switch (units) {
- case 'week' : return days / 7 + milliseconds / 6048e5;
- case 'day' : return days + milliseconds / 864e5;
- case 'hour' : return days * 24 + milliseconds / 36e5;
- case 'minute' : return days * 1440 + milliseconds / 6e4;
- case 'second' : return days * 86400 + milliseconds / 1000;
- // Math.floor prevents floating point math errors here
- case 'millisecond': return Math.floor(days * 864e5) + milliseconds;
- default: throw new Error('Unknown unit ' + units);
- }
- }
- }
-
- // TODO: Use this.as('ms')?
- function valueOf$1 () {
- if (!this.isValid()) {
- return NaN;
- }
- return (
- this._milliseconds +
- this._days * 864e5 +
- (this._months % 12) * 2592e6 +
- toInt(this._months / 12) * 31536e6
- );
- }
-
- function makeAs (alias) {
- return function () {
- return this.as(alias);
- };
- }
-
- var asMilliseconds = makeAs('ms');
- var asSeconds = makeAs('s');
- var asMinutes = makeAs('m');
- var asHours = makeAs('h');
- var asDays = makeAs('d');
- var asWeeks = makeAs('w');
- var asMonths = makeAs('M');
- var asQuarters = makeAs('Q');
- var asYears = makeAs('y');
-
- function clone$1 () {
- return createDuration(this);
- }
-
- function get$2 (units) {
- units = normalizeUnits(units);
- return this.isValid() ? this[units + 's']() : NaN;
- }
-
- function makeGetter(name) {
- return function () {
- return this.isValid() ? this._data[name] : NaN;
- };
- }
-
- var milliseconds = makeGetter('milliseconds');
- var seconds = makeGetter('seconds');
- var minutes = makeGetter('minutes');
- var hours = makeGetter('hours');
- var days = makeGetter('days');
- var months = makeGetter('months');
- var years = makeGetter('years');
-
- function weeks () {
- return absFloor(this.days() / 7);
- }
-
- var round = Math.round;
- var thresholds = {
- ss: 44, // a few seconds to seconds
- s : 45, // seconds to minute
- m : 45, // minutes to hour
- h : 22, // hours to day
- d : 26, // days to month
- M : 11 // months to year
- };
-
- // helper function for moment.fn.from, moment.fn.fromNow, and moment.duration.fn.humanize
- function substituteTimeAgo(string, number, withoutSuffix, isFuture, locale) {
- return locale.relativeTime(number || 1, !!withoutSuffix, string, isFuture);
- }
-
- function relativeTime$1 (posNegDuration, withoutSuffix, locale) {
- var duration = createDuration(posNegDuration).abs();
- var seconds = round(duration.as('s'));
- var minutes = round(duration.as('m'));
- var hours = round(duration.as('h'));
- var days = round(duration.as('d'));
- var months = round(duration.as('M'));
- var years = round(duration.as('y'));
-
- var a = seconds <= thresholds.ss && ['s', seconds] ||
- seconds < thresholds.s && ['ss', seconds] ||
- minutes <= 1 && ['m'] ||
- minutes < thresholds.m && ['mm', minutes] ||
- hours <= 1 && ['h'] ||
- hours < thresholds.h && ['hh', hours] ||
- days <= 1 && ['d'] ||
- days < thresholds.d && ['dd', days] ||
- months <= 1 && ['M'] ||
- months < thresholds.M && ['MM', months] ||
- years <= 1 && ['y'] || ['yy', years];
-
- a[2] = withoutSuffix;
- a[3] = +posNegDuration > 0;
- a[4] = locale;
- return substituteTimeAgo.apply(null, a);
- }
-
- // This function allows you to set the rounding function for relative time strings
- function getSetRelativeTimeRounding (roundingFunction) {
- if (roundingFunction === undefined) {
- return round;
- }
- if (typeof(roundingFunction) === 'function') {
- round = roundingFunction;
- return true;
- }
- return false;
- }
-
- // This function allows you to set a threshold for relative time strings
- function getSetRelativeTimeThreshold (threshold, limit) {
- if (thresholds[threshold] === undefined) {
- return false;
- }
- if (limit === undefined) {
- return thresholds[threshold];
- }
- thresholds[threshold] = limit;
- if (threshold === 's') {
- thresholds.ss = limit - 1;
- }
- return true;
- }
-
- function humanize (withSuffix) {
- if (!this.isValid()) {
- return this.localeData().invalidDate();
- }
-
- var locale = this.localeData();
- var output = relativeTime$1(this, !withSuffix, locale);
-
- if (withSuffix) {
- output = locale.pastFuture(+this, output);
- }
-
- return locale.postformat(output);
- }
-
- var abs$1 = Math.abs;
-
- function sign(x) {
- return ((x > 0) - (x < 0)) || +x;
- }
-
- function toISOString$1() {
- // for ISO strings we do not use the normal bubbling rules:
- // * milliseconds bubble up until they become hours
- // * days do not bubble at all
- // * months bubble up until they become years
- // This is because there is no context-free conversion between hours and days
- // (think of clock changes)
- // and also not between days and months (28-31 days per month)
- if (!this.isValid()) {
- return this.localeData().invalidDate();
- }
-
- var seconds = abs$1(this._milliseconds) / 1000;
- var days = abs$1(this._days);
- var months = abs$1(this._months);
- var minutes, hours, years;
-
- // 3600 seconds -> 60 minutes -> 1 hour
- minutes = absFloor(seconds / 60);
- hours = absFloor(minutes / 60);
- seconds %= 60;
- minutes %= 60;
-
- // 12 months -> 1 year
- years = absFloor(months / 12);
- months %= 12;
-
-
- // inspired by https://github.com/dordille/moment-isoduration/blob/master/moment.isoduration.js
- var Y = years;
- var M = months;
- var D = days;
- var h = hours;
- var m = minutes;
- var s = seconds ? seconds.toFixed(3).replace(/\.?0+$/, '') : '';
- var total = this.asSeconds();
-
- if (!total) {
- // this is the same as C#'s (Noda) and python (isodate)...
- // but not other JS (goog.date)
- return 'P0D';
- }
-
- var totalSign = total < 0 ? '-' : '';
- var ymSign = sign(this._months) !== sign(total) ? '-' : '';
- var daysSign = sign(this._days) !== sign(total) ? '-' : '';
- var hmsSign = sign(this._milliseconds) !== sign(total) ? '-' : '';
-
- return totalSign + 'P' +
- (Y ? ymSign + Y + 'Y' : '') +
- (M ? ymSign + M + 'M' : '') +
- (D ? daysSign + D + 'D' : '') +
- ((h || m || s) ? 'T' : '') +
- (h ? hmsSign + h + 'H' : '') +
- (m ? hmsSign + m + 'M' : '') +
- (s ? hmsSign + s + 'S' : '');
- }
-
- var proto$2 = Duration.prototype;
-
- proto$2.isValid = isValid$1;
- proto$2.abs = abs;
- proto$2.add = add$1;
- proto$2.subtract = subtract$1;
- proto$2.as = as;
- proto$2.asMilliseconds = asMilliseconds;
- proto$2.asSeconds = asSeconds;
- proto$2.asMinutes = asMinutes;
- proto$2.asHours = asHours;
- proto$2.asDays = asDays;
- proto$2.asWeeks = asWeeks;
- proto$2.asMonths = asMonths;
- proto$2.asQuarters = asQuarters;
- proto$2.asYears = asYears;
- proto$2.valueOf = valueOf$1;
- proto$2._bubble = bubble;
- proto$2.clone = clone$1;
- proto$2.get = get$2;
- proto$2.milliseconds = milliseconds;
- proto$2.seconds = seconds;
- proto$2.minutes = minutes;
- proto$2.hours = hours;
- proto$2.days = days;
- proto$2.weeks = weeks;
- proto$2.months = months;
- proto$2.years = years;
- proto$2.humanize = humanize;
- proto$2.toISOString = toISOString$1;
- proto$2.toString = toISOString$1;
- proto$2.toJSON = toISOString$1;
- proto$2.locale = locale;
- proto$2.localeData = localeData;
-
- proto$2.toIsoString = deprecate('toIsoString() is deprecated. Please use toISOString() instead (notice the capitals)', toISOString$1);
- proto$2.lang = lang;
-
- // Side effect imports
-
- // FORMATTING
-
- addFormatToken('X', 0, 0, 'unix');
- addFormatToken('x', 0, 0, 'valueOf');
-
- // PARSING
-
- addRegexToken('x', matchSigned);
- addRegexToken('X', matchTimestamp);
- addParseToken('X', function (input, array, config) {
- config._d = new Date(parseFloat(input, 10) * 1000);
- });
- addParseToken('x', function (input, array, config) {
- config._d = new Date(toInt(input));
- });
-
- // Side effect imports
-
-
- hooks.version = '2.24.0';
-
- setHookCallback(createLocal);
-
- hooks.fn = proto;
- hooks.min = min;
- hooks.max = max;
- hooks.now = now;
- hooks.utc = createUTC;
- hooks.unix = createUnix;
- hooks.months = listMonths;
- hooks.isDate = isDate;
- hooks.locale = getSetGlobalLocale;
- hooks.invalid = createInvalid;
- hooks.duration = createDuration;
- hooks.isMoment = isMoment;
- hooks.weekdays = listWeekdays;
- hooks.parseZone = createInZone;
- hooks.localeData = getLocale;
- hooks.isDuration = isDuration;
- hooks.monthsShort = listMonthsShort;
- hooks.weekdaysMin = listWeekdaysMin;
- hooks.defineLocale = defineLocale;
- hooks.updateLocale = updateLocale;
- hooks.locales = listLocales;
- hooks.weekdaysShort = listWeekdaysShort;
- hooks.normalizeUnits = normalizeUnits;
- hooks.relativeTimeRounding = getSetRelativeTimeRounding;
- hooks.relativeTimeThreshold = getSetRelativeTimeThreshold;
- hooks.calendarFormat = getCalendarFormat;
- hooks.prototype = proto;
-
- // currently HTML5 input type only supports 24-hour formats
- hooks.HTML5_FMT = {
- DATETIME_LOCAL: 'YYYY-MM-DDTHH:mm', //
- DATETIME_LOCAL_SECONDS: 'YYYY-MM-DDTHH:mm:ss', //
- DATETIME_LOCAL_MS: 'YYYY-MM-DDTHH:mm:ss.SSS', //
- DATE: 'YYYY-MM-DD', //
- TIME: 'HH:mm', //
- TIME_SECONDS: 'HH:mm:ss', //
- TIME_MS: 'HH:mm:ss.SSS', //
- WEEK: 'GGGG-[W]WW', //
- MONTH: 'YYYY-MM' //
- };
-
- return hooks;
-
-})));
-});
-
-var FORMATS = {
- datetime: 'MMM D, YYYY, h:mm:ss a',
- millisecond: 'h:mm:ss.SSS a',
- second: 'h:mm:ss a',
- minute: 'h:mm a',
- hour: 'hA',
- day: 'MMM D',
- week: 'll',
- month: 'MMM YYYY',
- quarter: '[Q]Q - YYYY',
- year: 'YYYY'
-};
-
-core_adapters._date.override(typeof moment === 'function' ? {
- _id: 'moment', // DEBUG ONLY
-
- formats: function() {
- return FORMATS;
- },
-
- parse: function(value, format) {
- if (typeof value === 'string' && typeof format === 'string') {
- value = moment(value, format);
- } else if (!(value instanceof moment)) {
- value = moment(value);
- }
- return value.isValid() ? value.valueOf() : null;
- },
-
- format: function(time, format) {
- return moment(time).format(format);
- },
-
- add: function(time, amount, unit) {
- return moment(time).add(amount, unit).valueOf();
- },
-
- diff: function(max, min, unit) {
- return moment.duration(moment(max).diff(moment(min))).as(unit);
- },
-
- startOf: function(time, unit, weekday) {
- time = moment(time);
- if (unit === 'isoWeek') {
- return time.isoWeekday(weekday).valueOf();
- }
- return time.startOf(unit).valueOf();
- },
-
- endOf: function(time, unit) {
- return moment(time).endOf(unit).valueOf();
- },
-
- // DEPRECATIONS
-
- /**
- * Provided for backward compatibility with scale.getValueForPixel().
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- * @private
- */
- _create: function(time) {
- return moment(time);
- },
-} : {});
-
-core_defaults._set('global', {
- plugins: {
- filler: {
- propagate: true
- }
- }
-});
-
-var mappers = {
- dataset: function(source) {
- var index = source.fill;
- var chart = source.chart;
- var meta = chart.getDatasetMeta(index);
- var visible = meta && chart.isDatasetVisible(index);
- var points = (visible && meta.dataset._children) || [];
- var length = points.length || 0;
-
- return !length ? null : function(point, i) {
- return (i < length && points[i]._view) || null;
- };
- },
-
- boundary: function(source) {
- var boundary = source.boundary;
- var x = boundary ? boundary.x : null;
- var y = boundary ? boundary.y : null;
-
- return function(point) {
- return {
- x: x === null ? point.x : x,
- y: y === null ? point.y : y,
- };
- };
- }
-};
-
-// @todo if (fill[0] === '#')
-function decodeFill(el, index, count) {
- var model = el._model || {};
- var fill = model.fill;
- var target;
-
- if (fill === undefined) {
- fill = !!model.backgroundColor;
- }
-
- if (fill === false || fill === null) {
- return false;
- }
-
- if (fill === true) {
- return 'origin';
- }
-
- target = parseFloat(fill, 10);
- if (isFinite(target) && Math.floor(target) === target) {
- if (fill[0] === '-' || fill[0] === '+') {
- target = index + target;
- }
-
- if (target === index || target < 0 || target >= count) {
- return false;
- }
-
- return target;
- }
-
- switch (fill) {
- // compatibility
- case 'bottom':
- return 'start';
- case 'top':
- return 'end';
- case 'zero':
- return 'origin';
- // supported boundaries
- case 'origin':
- case 'start':
- case 'end':
- return fill;
- // invalid fill values
- default:
- return false;
- }
-}
-
-function computeBoundary(source) {
- var model = source.el._model || {};
- var scale = source.el._scale || {};
- var fill = source.fill;
- var target = null;
- var horizontal;
-
- if (isFinite(fill)) {
- return null;
- }
-
- // Backward compatibility: until v3, we still need to support boundary values set on
- // the model (scaleTop, scaleBottom and scaleZero) because some external plugins and
- // controllers might still use it (e.g. the Smith chart).
-
- if (fill === 'start') {
- target = model.scaleBottom === undefined ? scale.bottom : model.scaleBottom;
- } else if (fill === 'end') {
- target = model.scaleTop === undefined ? scale.top : model.scaleTop;
- } else if (model.scaleZero !== undefined) {
- target = model.scaleZero;
- } else if (scale.getBasePosition) {
- target = scale.getBasePosition();
- } else if (scale.getBasePixel) {
- target = scale.getBasePixel();
- }
-
- if (target !== undefined && target !== null) {
- if (target.x !== undefined && target.y !== undefined) {
- return target;
- }
-
- if (helpers$1.isFinite(target)) {
- horizontal = scale.isHorizontal();
- return {
- x: horizontal ? target : null,
- y: horizontal ? null : target
- };
- }
- }
-
- return null;
-}
-
-function resolveTarget(sources, index, propagate) {
- var source = sources[index];
- var fill = source.fill;
- var visited = [index];
- var target;
-
- if (!propagate) {
- return fill;
- }
-
- while (fill !== false && visited.indexOf(fill) === -1) {
- if (!isFinite(fill)) {
- return fill;
- }
-
- target = sources[fill];
- if (!target) {
- return false;
- }
-
- if (target.visible) {
- return fill;
- }
-
- visited.push(fill);
- fill = target.fill;
- }
-
- return false;
-}
-
-function createMapper(source) {
- var fill = source.fill;
- var type = 'dataset';
-
- if (fill === false) {
- return null;
- }
-
- if (!isFinite(fill)) {
- type = 'boundary';
- }
-
- return mappers[type](source);
-}
-
-function isDrawable(point) {
- return point && !point.skip;
-}
-
-function drawArea(ctx, curve0, curve1, len0, len1) {
- var i;
-
- if (!len0 || !len1) {
- return;
- }
-
- // building first area curve (normal)
- ctx.moveTo(curve0[0].x, curve0[0].y);
- for (i = 1; i < len0; ++i) {
- helpers$1.canvas.lineTo(ctx, curve0[i - 1], curve0[i]);
- }
-
- // joining the two area curves
- ctx.lineTo(curve1[len1 - 1].x, curve1[len1 - 1].y);
-
- // building opposite area curve (reverse)
- for (i = len1 - 1; i > 0; --i) {
- helpers$1.canvas.lineTo(ctx, curve1[i], curve1[i - 1], true);
- }
-}
-
-function doFill(ctx, points, mapper, view, color, loop) {
- var count = points.length;
- var span = view.spanGaps;
- var curve0 = [];
- var curve1 = [];
- var len0 = 0;
- var len1 = 0;
- var i, ilen, index, p0, p1, d0, d1;
-
- ctx.beginPath();
-
- for (i = 0, ilen = (count + !!loop); i < ilen; ++i) {
- index = i % count;
- p0 = points[index]._view;
- p1 = mapper(p0, index, view);
- d0 = isDrawable(p0);
- d1 = isDrawable(p1);
-
- if (d0 && d1) {
- len0 = curve0.push(p0);
- len1 = curve1.push(p1);
- } else if (len0 && len1) {
- if (!span) {
- drawArea(ctx, curve0, curve1, len0, len1);
- len0 = len1 = 0;
- curve0 = [];
- curve1 = [];
- } else {
- if (d0) {
- curve0.push(p0);
- }
- if (d1) {
- curve1.push(p1);
- }
- }
- }
- }
-
- drawArea(ctx, curve0, curve1, len0, len1);
-
- ctx.closePath();
- ctx.fillStyle = color;
- ctx.fill();
-}
-
-var plugin_filler = {
- id: 'filler',
-
- afterDatasetsUpdate: function(chart, options) {
- var count = (chart.data.datasets || []).length;
- var propagate = options.propagate;
- var sources = [];
- var meta, i, el, source;
-
- for (i = 0; i < count; ++i) {
- meta = chart.getDatasetMeta(i);
- el = meta.dataset;
- source = null;
-
- if (el && el._model && el instanceof elements.Line) {
- source = {
- visible: chart.isDatasetVisible(i),
- fill: decodeFill(el, i, count),
- chart: chart,
- el: el
- };
- }
-
- meta.$filler = source;
- sources.push(source);
- }
-
- for (i = 0; i < count; ++i) {
- source = sources[i];
- if (!source) {
- continue;
- }
-
- source.fill = resolveTarget(sources, i, propagate);
- source.boundary = computeBoundary(source);
- source.mapper = createMapper(source);
- }
- },
-
- beforeDatasetDraw: function(chart, args) {
- var meta = args.meta.$filler;
- if (!meta) {
- return;
- }
-
- var ctx = chart.ctx;
- var el = meta.el;
- var view = el._view;
- var points = el._children || [];
- var mapper = meta.mapper;
- var color = view.backgroundColor || core_defaults.global.defaultColor;
-
- if (mapper && color && points.length) {
- helpers$1.canvas.clipArea(ctx, chart.chartArea);
- doFill(ctx, points, mapper, view, color, el._loop);
- helpers$1.canvas.unclipArea(ctx);
- }
- }
-};
-
-var noop$1 = helpers$1.noop;
-var valueOrDefault$d = helpers$1.valueOrDefault;
-
-core_defaults._set('global', {
- legend: {
- display: true,
- position: 'top',
- fullWidth: true,
- reverse: false,
- weight: 1000,
-
- // a callback that will handle
- onClick: function(e, legendItem) {
- var index = legendItem.datasetIndex;
- var ci = this.chart;
- var meta = ci.getDatasetMeta(index);
-
- // See controller.isDatasetVisible comment
- meta.hidden = meta.hidden === null ? !ci.data.datasets[index].hidden : null;
-
- // We hid a dataset ... rerender the chart
- ci.update();
- },
-
- onHover: null,
- onLeave: null,
-
- labels: {
- boxWidth: 40,
- padding: 10,
- // Generates labels shown in the legend
- // Valid properties to return:
- // text : text to display
- // fillStyle : fill of coloured box
- // strokeStyle: stroke of coloured box
- // hidden : if this legend item refers to a hidden item
- // lineCap : cap style for line
- // lineDash
- // lineDashOffset :
- // lineJoin :
- // lineWidth :
- generateLabels: function(chart) {
- var data = chart.data;
- return helpers$1.isArray(data.datasets) ? data.datasets.map(function(dataset, i) {
- return {
- text: dataset.label,
- fillStyle: (!helpers$1.isArray(dataset.backgroundColor) ? dataset.backgroundColor : dataset.backgroundColor[0]),
- hidden: !chart.isDatasetVisible(i),
- lineCap: dataset.borderCapStyle,
- lineDash: dataset.borderDash,
- lineDashOffset: dataset.borderDashOffset,
- lineJoin: dataset.borderJoinStyle,
- lineWidth: dataset.borderWidth,
- strokeStyle: dataset.borderColor,
- pointStyle: dataset.pointStyle,
-
- // Below is extra data used for toggling the datasets
- datasetIndex: i
- };
- }, this) : [];
- }
- }
- },
-
- legendCallback: function(chart) {
- var text = [];
- text.push('
');
- for (var i = 0; i < chart.data.datasets.length; i++) {
- text.push(' ');
- if (chart.data.datasets[i].label) {
- text.push(chart.data.datasets[i].label);
- }
- text.push(' ');
- }
- text.push(' ');
- return text.join('');
- }
-});
-
-/**
- * Helper function to get the box width based on the usePointStyle option
- * @param {object} labelopts - the label options on the legend
- * @param {number} fontSize - the label font size
- * @return {number} width of the color box area
- */
-function getBoxWidth(labelOpts, fontSize) {
- return labelOpts.usePointStyle && labelOpts.boxWidth > fontSize ?
- fontSize :
- labelOpts.boxWidth;
-}
-
-/**
- * IMPORTANT: this class is exposed publicly as Chart.Legend, backward compatibility required!
- */
-var Legend = core_element.extend({
-
- initialize: function(config) {
- helpers$1.extend(this, config);
-
- // Contains hit boxes for each dataset (in dataset order)
- this.legendHitBoxes = [];
-
- /**
- * @private
- */
- this._hoveredItem = null;
-
- // Are we in doughnut mode which has a different data type
- this.doughnutMode = false;
- },
-
- // These methods are ordered by lifecycle. Utilities then follow.
- // Any function defined here is inherited by all legend types.
- // Any function can be extended by the legend type
-
- beforeUpdate: noop$1,
- update: function(maxWidth, maxHeight, margins) {
- var me = this;
-
- // Update Lifecycle - Probably don't want to ever extend or overwrite this function ;)
- me.beforeUpdate();
-
- // Absorb the master measurements
- me.maxWidth = maxWidth;
- me.maxHeight = maxHeight;
- me.margins = margins;
-
- // Dimensions
- me.beforeSetDimensions();
- me.setDimensions();
- me.afterSetDimensions();
- // Labels
- me.beforeBuildLabels();
- me.buildLabels();
- me.afterBuildLabels();
-
- // Fit
- me.beforeFit();
- me.fit();
- me.afterFit();
- //
- me.afterUpdate();
-
- return me.minSize;
- },
- afterUpdate: noop$1,
-
- //
-
- beforeSetDimensions: noop$1,
- setDimensions: function() {
- var me = this;
- // Set the unconstrained dimension before label rotation
- if (me.isHorizontal()) {
- // Reset position before calculating rotation
- me.width = me.maxWidth;
- me.left = 0;
- me.right = me.width;
- } else {
- me.height = me.maxHeight;
-
- // Reset position before calculating rotation
- me.top = 0;
- me.bottom = me.height;
- }
-
- // Reset padding
- me.paddingLeft = 0;
- me.paddingTop = 0;
- me.paddingRight = 0;
- me.paddingBottom = 0;
-
- // Reset minSize
- me.minSize = {
- width: 0,
- height: 0
- };
- },
- afterSetDimensions: noop$1,
-
- //
-
- beforeBuildLabels: noop$1,
- buildLabels: function() {
- var me = this;
- var labelOpts = me.options.labels || {};
- var legendItems = helpers$1.callback(labelOpts.generateLabels, [me.chart], me) || [];
-
- if (labelOpts.filter) {
- legendItems = legendItems.filter(function(item) {
- return labelOpts.filter(item, me.chart.data);
- });
- }
-
- if (me.options.reverse) {
- legendItems.reverse();
- }
-
- me.legendItems = legendItems;
- },
- afterBuildLabels: noop$1,
-
- //
-
- beforeFit: noop$1,
- fit: function() {
- var me = this;
- var opts = me.options;
- var labelOpts = opts.labels;
- var display = opts.display;
-
- var ctx = me.ctx;
-
- var labelFont = helpers$1.options._parseFont(labelOpts);
- var fontSize = labelFont.size;
-
- // Reset hit boxes
- var hitboxes = me.legendHitBoxes = [];
-
- var minSize = me.minSize;
- var isHorizontal = me.isHorizontal();
-
- if (isHorizontal) {
- minSize.width = me.maxWidth; // fill all the width
- minSize.height = display ? 10 : 0;
- } else {
- minSize.width = display ? 10 : 0;
- minSize.height = me.maxHeight; // fill all the height
- }
-
- // Increase sizes here
- if (display) {
- ctx.font = labelFont.string;
-
- if (isHorizontal) {
- // Labels
-
- // Width of each line of legend boxes. Labels wrap onto multiple lines when there are too many to fit on one
- var lineWidths = me.lineWidths = [0];
- var totalHeight = 0;
-
- ctx.textAlign = 'left';
- ctx.textBaseline = 'top';
-
- helpers$1.each(me.legendItems, function(legendItem, i) {
- var boxWidth = getBoxWidth(labelOpts, fontSize);
- var width = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
-
- if (i === 0 || lineWidths[lineWidths.length - 1] + width + labelOpts.padding > minSize.width) {
- totalHeight += fontSize + labelOpts.padding;
- lineWidths[lineWidths.length - (i > 0 ? 0 : 1)] = labelOpts.padding;
- }
-
- // Store the hitbox width and height here. Final position will be updated in `draw`
- hitboxes[i] = {
- left: 0,
- top: 0,
- width: width,
- height: fontSize
- };
-
- lineWidths[lineWidths.length - 1] += width + labelOpts.padding;
- });
-
- minSize.height += totalHeight;
-
- } else {
- var vPadding = labelOpts.padding;
- var columnWidths = me.columnWidths = [];
- var totalWidth = labelOpts.padding;
- var currentColWidth = 0;
- var currentColHeight = 0;
- var itemHeight = fontSize + vPadding;
-
- helpers$1.each(me.legendItems, function(legendItem, i) {
- var boxWidth = getBoxWidth(labelOpts, fontSize);
- var itemWidth = boxWidth + (fontSize / 2) + ctx.measureText(legendItem.text).width;
-
- // If too tall, go to new column
- if (i > 0 && currentColHeight + itemHeight > minSize.height - vPadding) {
- totalWidth += currentColWidth + labelOpts.padding;
- columnWidths.push(currentColWidth); // previous column width
-
- currentColWidth = 0;
- currentColHeight = 0;
- }
-
- // Get max width
- currentColWidth = Math.max(currentColWidth, itemWidth);
- currentColHeight += itemHeight;
-
- // Store the hitbox width and height here. Final position will be updated in `draw`
- hitboxes[i] = {
- left: 0,
- top: 0,
- width: itemWidth,
- height: fontSize
- };
- });
-
- totalWidth += currentColWidth;
- columnWidths.push(currentColWidth);
- minSize.width += totalWidth;
- }
- }
-
- me.width = minSize.width;
- me.height = minSize.height;
- },
- afterFit: noop$1,
-
- // Shared Methods
- isHorizontal: function() {
- return this.options.position === 'top' || this.options.position === 'bottom';
- },
-
- // Actually draw the legend on the canvas
- draw: function() {
- var me = this;
- var opts = me.options;
- var labelOpts = opts.labels;
- var globalDefaults = core_defaults.global;
- var defaultColor = globalDefaults.defaultColor;
- var lineDefault = globalDefaults.elements.line;
- var legendWidth = me.width;
- var lineWidths = me.lineWidths;
-
- if (opts.display) {
- var ctx = me.ctx;
- var fontColor = valueOrDefault$d(labelOpts.fontColor, globalDefaults.defaultFontColor);
- var labelFont = helpers$1.options._parseFont(labelOpts);
- var fontSize = labelFont.size;
- var cursor;
-
- // Canvas setup
- ctx.textAlign = 'left';
- ctx.textBaseline = 'middle';
- ctx.lineWidth = 0.5;
- ctx.strokeStyle = fontColor; // for strikethrough effect
- ctx.fillStyle = fontColor; // render in correct colour
- ctx.font = labelFont.string;
-
- var boxWidth = getBoxWidth(labelOpts, fontSize);
- var hitboxes = me.legendHitBoxes;
-
- // current position
- var drawLegendBox = function(x, y, legendItem) {
- if (isNaN(boxWidth) || boxWidth <= 0) {
- return;
- }
-
- // Set the ctx for the box
- ctx.save();
-
- var lineWidth = valueOrDefault$d(legendItem.lineWidth, lineDefault.borderWidth);
- ctx.fillStyle = valueOrDefault$d(legendItem.fillStyle, defaultColor);
- ctx.lineCap = valueOrDefault$d(legendItem.lineCap, lineDefault.borderCapStyle);
- ctx.lineDashOffset = valueOrDefault$d(legendItem.lineDashOffset, lineDefault.borderDashOffset);
- ctx.lineJoin = valueOrDefault$d(legendItem.lineJoin, lineDefault.borderJoinStyle);
- ctx.lineWidth = lineWidth;
- ctx.strokeStyle = valueOrDefault$d(legendItem.strokeStyle, defaultColor);
-
- if (ctx.setLineDash) {
- // IE 9 and 10 do not support line dash
- ctx.setLineDash(valueOrDefault$d(legendItem.lineDash, lineDefault.borderDash));
- }
-
- if (opts.labels && opts.labels.usePointStyle) {
- // Recalculate x and y for drawPoint() because its expecting
- // x and y to be center of figure (instead of top left)
- var radius = boxWidth * Math.SQRT2 / 2;
- var centerX = x + boxWidth / 2;
- var centerY = y + fontSize / 2;
-
- // Draw pointStyle as legend symbol
- helpers$1.canvas.drawPoint(ctx, legendItem.pointStyle, radius, centerX, centerY);
- } else {
- // Draw box as legend symbol
- if (lineWidth !== 0) {
- ctx.strokeRect(x, y, boxWidth, fontSize);
- }
- ctx.fillRect(x, y, boxWidth, fontSize);
- }
-
- ctx.restore();
- };
- var fillText = function(x, y, legendItem, textWidth) {
- var halfFontSize = fontSize / 2;
- var xLeft = boxWidth + halfFontSize + x;
- var yMiddle = y + halfFontSize;
-
- ctx.fillText(legendItem.text, xLeft, yMiddle);
-
- if (legendItem.hidden) {
- // Strikethrough the text if hidden
- ctx.beginPath();
- ctx.lineWidth = 2;
- ctx.moveTo(xLeft, yMiddle);
- ctx.lineTo(xLeft + textWidth, yMiddle);
- ctx.stroke();
- }
- };
-
- // Horizontal
- var isHorizontal = me.isHorizontal();
- if (isHorizontal) {
- cursor = {
- x: me.left + ((legendWidth - lineWidths[0]) / 2) + labelOpts.padding,
- y: me.top + labelOpts.padding,
- line: 0
- };
- } else {
- cursor = {
- x: me.left + labelOpts.padding,
- y: me.top + labelOpts.padding,
- line: 0
- };
- }
-
- var itemHeight = fontSize + labelOpts.padding;
- helpers$1.each(me.legendItems, function(legendItem, i) {
- var textWidth = ctx.measureText(legendItem.text).width;
- var width = boxWidth + (fontSize / 2) + textWidth;
- var x = cursor.x;
- var y = cursor.y;
-
- // Use (me.left + me.minSize.width) and (me.top + me.minSize.height)
- // instead of me.right and me.bottom because me.width and me.height
- // may have been changed since me.minSize was calculated
- if (isHorizontal) {
- if (i > 0 && x + width + labelOpts.padding > me.left + me.minSize.width) {
- y = cursor.y += itemHeight;
- cursor.line++;
- x = cursor.x = me.left + ((legendWidth - lineWidths[cursor.line]) / 2) + labelOpts.padding;
- }
- } else if (i > 0 && y + itemHeight > me.top + me.minSize.height) {
- x = cursor.x = x + me.columnWidths[cursor.line] + labelOpts.padding;
- y = cursor.y = me.top + labelOpts.padding;
- cursor.line++;
- }
-
- drawLegendBox(x, y, legendItem);
-
- hitboxes[i].left = x;
- hitboxes[i].top = y;
-
- // Fill the actual label
- fillText(x, y, legendItem, textWidth);
-
- if (isHorizontal) {
- cursor.x += width + labelOpts.padding;
- } else {
- cursor.y += itemHeight;
- }
-
- });
- }
- },
-
- /**
- * @private
- */
- _getLegendItemAt: function(x, y) {
- var me = this;
- var i, hitBox, lh;
-
- if (x >= me.left && x <= me.right && y >= me.top && y <= me.bottom) {
- // See if we are touching one of the dataset boxes
- lh = me.legendHitBoxes;
- for (i = 0; i < lh.length; ++i) {
- hitBox = lh[i];
-
- if (x >= hitBox.left && x <= hitBox.left + hitBox.width && y >= hitBox.top && y <= hitBox.top + hitBox.height) {
- // Touching an element
- return me.legendItems[i];
- }
- }
- }
-
- return null;
- },
-
- /**
- * Handle an event
- * @private
- * @param {IEvent} event - The event to handle
- */
- handleEvent: function(e) {
- var me = this;
- var opts = me.options;
- var type = e.type === 'mouseup' ? 'click' : e.type;
- var hoveredItem;
-
- if (type === 'mousemove') {
- if (!opts.onHover && !opts.onLeave) {
- return;
- }
- } else if (type === 'click') {
- if (!opts.onClick) {
- return;
- }
- } else {
- return;
- }
-
- // Chart event already has relative position in it
- hoveredItem = me._getLegendItemAt(e.x, e.y);
-
- if (type === 'click') {
- if (hoveredItem && opts.onClick) {
- // use e.native for backwards compatibility
- opts.onClick.call(me, e.native, hoveredItem);
- }
- } else {
- if (opts.onLeave && hoveredItem !== me._hoveredItem) {
- if (me._hoveredItem) {
- opts.onLeave.call(me, e.native, me._hoveredItem);
- }
- me._hoveredItem = hoveredItem;
- }
-
- if (opts.onHover && hoveredItem) {
- // use e.native for backwards compatibility
- opts.onHover.call(me, e.native, hoveredItem);
- }
- }
- }
-});
-
-function createNewLegendAndAttach(chart, legendOpts) {
- var legend = new Legend({
- ctx: chart.ctx,
- options: legendOpts,
- chart: chart
- });
-
- core_layouts.configure(chart, legend, legendOpts);
- core_layouts.addBox(chart, legend);
- chart.legend = legend;
-}
-
-var plugin_legend = {
- id: 'legend',
-
- /**
- * Backward compatibility: since 2.1.5, the legend is registered as a plugin, making
- * Chart.Legend obsolete. To avoid a breaking change, we export the Legend as part of
- * the plugin, which one will be re-exposed in the chart.js file.
- * https://github.com/chartjs/Chart.js/pull/2640
- * @private
- */
- _element: Legend,
-
- beforeInit: function(chart) {
- var legendOpts = chart.options.legend;
-
- if (legendOpts) {
- createNewLegendAndAttach(chart, legendOpts);
- }
- },
-
- beforeUpdate: function(chart) {
- var legendOpts = chart.options.legend;
- var legend = chart.legend;
-
- if (legendOpts) {
- helpers$1.mergeIf(legendOpts, core_defaults.global.legend);
-
- if (legend) {
- core_layouts.configure(chart, legend, legendOpts);
- legend.options = legendOpts;
- } else {
- createNewLegendAndAttach(chart, legendOpts);
- }
- } else if (legend) {
- core_layouts.removeBox(chart, legend);
- delete chart.legend;
- }
- },
-
- afterEvent: function(chart, e) {
- var legend = chart.legend;
- if (legend) {
- legend.handleEvent(e);
- }
- }
-};
-
-var noop$2 = helpers$1.noop;
-
-core_defaults._set('global', {
- title: {
- display: false,
- fontStyle: 'bold',
- fullWidth: true,
- padding: 10,
- position: 'top',
- text: '',
- weight: 2000 // by default greater than legend (1000) to be above
- }
-});
-
-/**
- * IMPORTANT: this class is exposed publicly as Chart.Legend, backward compatibility required!
- */
-var Title = core_element.extend({
- initialize: function(config) {
- var me = this;
- helpers$1.extend(me, config);
-
- // Contains hit boxes for each dataset (in dataset order)
- me.legendHitBoxes = [];
- },
-
- // These methods are ordered by lifecycle. Utilities then follow.
-
- beforeUpdate: noop$2,
- update: function(maxWidth, maxHeight, margins) {
- var me = this;
-
- // Update Lifecycle - Probably don't want to ever extend or overwrite this function ;)
- me.beforeUpdate();
-
- // Absorb the master measurements
- me.maxWidth = maxWidth;
- me.maxHeight = maxHeight;
- me.margins = margins;
-
- // Dimensions
- me.beforeSetDimensions();
- me.setDimensions();
- me.afterSetDimensions();
- // Labels
- me.beforeBuildLabels();
- me.buildLabels();
- me.afterBuildLabels();
-
- // Fit
- me.beforeFit();
- me.fit();
- me.afterFit();
- //
- me.afterUpdate();
-
- return me.minSize;
-
- },
- afterUpdate: noop$2,
-
- //
-
- beforeSetDimensions: noop$2,
- setDimensions: function() {
- var me = this;
- // Set the unconstrained dimension before label rotation
- if (me.isHorizontal()) {
- // Reset position before calculating rotation
- me.width = me.maxWidth;
- me.left = 0;
- me.right = me.width;
- } else {
- me.height = me.maxHeight;
-
- // Reset position before calculating rotation
- me.top = 0;
- me.bottom = me.height;
- }
-
- // Reset padding
- me.paddingLeft = 0;
- me.paddingTop = 0;
- me.paddingRight = 0;
- me.paddingBottom = 0;
-
- // Reset minSize
- me.minSize = {
- width: 0,
- height: 0
- };
- },
- afterSetDimensions: noop$2,
-
- //
-
- beforeBuildLabels: noop$2,
- buildLabels: noop$2,
- afterBuildLabels: noop$2,
-
- //
-
- beforeFit: noop$2,
- fit: function() {
- var me = this;
- var opts = me.options;
- var display = opts.display;
- var minSize = me.minSize;
- var lineCount = helpers$1.isArray(opts.text) ? opts.text.length : 1;
- var fontOpts = helpers$1.options._parseFont(opts);
- var textSize = display ? (lineCount * fontOpts.lineHeight) + (opts.padding * 2) : 0;
-
- if (me.isHorizontal()) {
- minSize.width = me.maxWidth; // fill all the width
- minSize.height = textSize;
- } else {
- minSize.width = textSize;
- minSize.height = me.maxHeight; // fill all the height
- }
-
- me.width = minSize.width;
- me.height = minSize.height;
-
- },
- afterFit: noop$2,
-
- // Shared Methods
- isHorizontal: function() {
- var pos = this.options.position;
- return pos === 'top' || pos === 'bottom';
- },
-
- // Actually draw the title block on the canvas
- draw: function() {
- var me = this;
- var ctx = me.ctx;
- var opts = me.options;
-
- if (opts.display) {
- var fontOpts = helpers$1.options._parseFont(opts);
- var lineHeight = fontOpts.lineHeight;
- var offset = lineHeight / 2 + opts.padding;
- var rotation = 0;
- var top = me.top;
- var left = me.left;
- var bottom = me.bottom;
- var right = me.right;
- var maxWidth, titleX, titleY;
-
- ctx.fillStyle = helpers$1.valueOrDefault(opts.fontColor, core_defaults.global.defaultFontColor); // render in correct colour
- ctx.font = fontOpts.string;
-
- // Horizontal
- if (me.isHorizontal()) {
- titleX = left + ((right - left) / 2); // midpoint of the width
- titleY = top + offset;
- maxWidth = right - left;
- } else {
- titleX = opts.position === 'left' ? left + offset : right - offset;
- titleY = top + ((bottom - top) / 2);
- maxWidth = bottom - top;
- rotation = Math.PI * (opts.position === 'left' ? -0.5 : 0.5);
- }
-
- ctx.save();
- ctx.translate(titleX, titleY);
- ctx.rotate(rotation);
- ctx.textAlign = 'center';
- ctx.textBaseline = 'middle';
-
- var text = opts.text;
- if (helpers$1.isArray(text)) {
- var y = 0;
- for (var i = 0; i < text.length; ++i) {
- ctx.fillText(text[i], 0, y, maxWidth);
- y += lineHeight;
- }
- } else {
- ctx.fillText(text, 0, 0, maxWidth);
- }
-
- ctx.restore();
- }
- }
-});
-
-function createNewTitleBlockAndAttach(chart, titleOpts) {
- var title = new Title({
- ctx: chart.ctx,
- options: titleOpts,
- chart: chart
- });
-
- core_layouts.configure(chart, title, titleOpts);
- core_layouts.addBox(chart, title);
- chart.titleBlock = title;
-}
-
-var plugin_title = {
- id: 'title',
-
- /**
- * Backward compatibility: since 2.1.5, the title is registered as a plugin, making
- * Chart.Title obsolete. To avoid a breaking change, we export the Title as part of
- * the plugin, which one will be re-exposed in the chart.js file.
- * https://github.com/chartjs/Chart.js/pull/2640
- * @private
- */
- _element: Title,
-
- beforeInit: function(chart) {
- var titleOpts = chart.options.title;
-
- if (titleOpts) {
- createNewTitleBlockAndAttach(chart, titleOpts);
- }
- },
-
- beforeUpdate: function(chart) {
- var titleOpts = chart.options.title;
- var titleBlock = chart.titleBlock;
-
- if (titleOpts) {
- helpers$1.mergeIf(titleOpts, core_defaults.global.title);
-
- if (titleBlock) {
- core_layouts.configure(chart, titleBlock, titleOpts);
- titleBlock.options = titleOpts;
- } else {
- createNewTitleBlockAndAttach(chart, titleOpts);
- }
- } else if (titleBlock) {
- core_layouts.removeBox(chart, titleBlock);
- delete chart.titleBlock;
- }
- }
-};
-
-var plugins = {};
-var filler = plugin_filler;
-var legend = plugin_legend;
-var title = plugin_title;
-plugins.filler = filler;
-plugins.legend = legend;
-plugins.title = title;
-
-/**
- * @namespace Chart
- */
-
-
-core_controller.helpers = helpers$1;
-
-// @todo dispatch these helpers into appropriated helpers/helpers.* file and write unit tests!
-core_helpers(core_controller);
-
-core_controller._adapters = core_adapters;
-core_controller.Animation = core_animation;
-core_controller.animationService = core_animations;
-core_controller.controllers = controllers;
-core_controller.DatasetController = core_datasetController;
-core_controller.defaults = core_defaults;
-core_controller.Element = core_element;
-core_controller.elements = elements;
-core_controller.Interaction = core_interaction;
-core_controller.layouts = core_layouts;
-core_controller.platform = platform;
-core_controller.plugins = core_plugins;
-core_controller.Scale = core_scale;
-core_controller.scaleService = core_scaleService;
-core_controller.Ticks = core_ticks;
-core_controller.Tooltip = core_tooltip;
-
-// Register built-in scales
-
-core_controller.helpers.each(scales, function(scale, type) {
- core_controller.scaleService.registerScaleType(type, scale, scale._defaults);
-});
-
-// Load to register built-in adapters (as side effects)
-
-
-// Loading built-in plugins
-
-for (var k in plugins) {
- if (plugins.hasOwnProperty(k)) {
- core_controller.plugins.register(plugins[k]);
- }
-}
-
-core_controller.platform.initialize();
-
-var src = core_controller;
-if (typeof window !== 'undefined') {
- window.Chart = core_controller;
-}
-
-// DEPRECATIONS
-
-/**
- * Provided for backward compatibility, not available anymore
- * @namespace Chart.Chart
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- * @private
- */
-core_controller.Chart = core_controller;
-
-/**
- * Provided for backward compatibility, not available anymore
- * @namespace Chart.Legend
- * @deprecated since version 2.1.5
- * @todo remove at version 3
- * @private
- */
-core_controller.Legend = plugins.legend._element;
-
-/**
- * Provided for backward compatibility, not available anymore
- * @namespace Chart.Title
- * @deprecated since version 2.1.5
- * @todo remove at version 3
- * @private
- */
-core_controller.Title = plugins.title._element;
-
-/**
- * Provided for backward compatibility, use Chart.plugins instead
- * @namespace Chart.pluginService
- * @deprecated since version 2.1.5
- * @todo remove at version 3
- * @private
- */
-core_controller.pluginService = core_controller.plugins;
-
-/**
- * Provided for backward compatibility, inheriting from Chart.PlugingBase has no
- * effect, instead simply create/register plugins via plain JavaScript objects.
- * @interface Chart.PluginBase
- * @deprecated since version 2.5.0
- * @todo remove at version 3
- * @private
- */
-core_controller.PluginBase = core_controller.Element.extend({});
-
-/**
- * Provided for backward compatibility, use Chart.helpers.canvas instead.
- * @namespace Chart.canvasHelpers
- * @deprecated since version 2.6.0
- * @todo remove at version 3
- * @private
- */
-core_controller.canvasHelpers = core_controller.helpers.canvas;
-
-/**
- * Provided for backward compatibility, use Chart.layouts instead.
- * @namespace Chart.layoutService
- * @deprecated since version 2.7.3
- * @todo remove at version 3
- * @private
- */
-core_controller.layoutService = core_controller.layouts;
-
-/**
- * Provided for backward compatibility, not available anymore.
- * @namespace Chart.LinearScaleBase
- * @deprecated since version 2.8
- * @todo remove at version 3
- * @private
- */
-core_controller.LinearScaleBase = scale_linearbase;
-
-/**
- * Provided for backward compatibility, instead we should create a new Chart
- * by setting the type in the config (`new Chart(id, {type: '{chart-type}'}`).
- * @deprecated since version 2.8.0
- * @todo remove at version 3
- */
-core_controller.helpers.each(
- [
- 'Bar',
- 'Bubble',
- 'Doughnut',
- 'Line',
- 'PolarArea',
- 'Radar',
- 'Scatter'
- ],
- function(klass) {
- core_controller[klass] = function(ctx, cfg) {
- return new core_controller(ctx, core_controller.helpers.merge(cfg || {}, {
- type: klass.charAt(0).toLowerCase() + klass.slice(1)
- }));
- };
- }
-);
-
-return src;
-
-})));
diff --git a/activity_dashboard_mngmnt/static/src/js/lib/columnHeatmap.js b/activity_dashboard_mngmnt/static/src/js/lib/columnHeatmap.js
deleted file mode 100644
index 9faf9a4f2..000000000
--- a/activity_dashboard_mngmnt/static/src/js/lib/columnHeatmap.js
+++ /dev/null
@@ -1,114 +0,0 @@
-(function($) {
- $.columnHeatmap = {
- name: 'columnHeatmap',
- version: '1.0',
- release: '2020-06-15',
- author: 'Paulo Kramer',
- site: 'https://www.paulokramer.com',
- documentation: 'https://github.com/PauloAK/jQuery-columnHeatMap'
- };
-
- $.fn.columnHeatmap = function(options) {
- var settings = $.extend({
- columns: [], // 0 is the first column
- contrast: true, // Change text color to white on stronger background colors
- inverse: false, // By default, higher are red and lower are green, if this options is enabled, the logic are inversed
- animated: true, // Animated background-color and text color transition
- animationSpeed: .1, // Speed of transition animation in seconds
- fn_parseValue: null, // Custom function to parse cell value
- colorStartPoint: 0 // HSL color start point
- }, options);
-
- try {
- if (!this.is('table'))
- throw 'Selected element isn\'t a table';
-
- if (settings.columns.length == 0)
- throw 'You need to specify the columns';
-
- if (settings.colorStartPoint < 0 || settings.colorStartPoint > 360)
- throw `colorStartPoint need to be beetween 0 and 360, current: ${settings.colorStartPoint}`;
-
- let $table = this;
- let rows = $table.find('tbody tr');
- let data = [];
-
- $.each(settings.columns, (loop, col) => {
- rows.each((key, row) => {
- if (key == 0) {
- data[col.toString()] = new Array;
- data[col.toString()]['values'] = new Array;
- data[col.toString()]['tds'] = new Array;
- }
-
- let td = $(row).find('td')[col];
- data[col.toString()]['tds'].push(td);
-
-
-
- if (typeof settings.fn_parseValue == "function") {
- let value = fn_parseValue($(td).text());
- if (typeof value == "undefined") {
- throw 'None value returned in fn_parseValue';
- } else {
- data[col.toString()]['values'].push(value);
- }
- } else {
- // Get only numbers from the cell, (with float points)
- let numbers = $(td).text().match(/[\d|\-|.|,]+/)[0];
-
- data[col.toString()]['values'].push(parseFloat(numbers));
- }
- });
- });
-
- data = data.filter((value) => { return value; });
-
- $.each(data, (key, col) => {
- if (!col || !col['values'])
- return;
-
- data[key]['min'] = null;
- data[key]['max'] = null;
-
- data[key]['min'] = col['values'].reduce(function(a, b) {
- return Math.min(a, b);
- });
-
- data[key]['max'] = col['values'].reduce(function(a, b) {
- return Math.max(a, b);
- });
- });
-
- $.each(data, (key, col) => {
- $.each(col['values'], (key, value) => {
- let colorGenerated = colorGenerator(value, col['min'], col['max']);
-
- if (settings.animated) {
- $(col['tds'][key]).css('transition', `background-color ${settings.animationSpeed}s linear, color ${settings.animationSpeed}s linear`);
- }
-
- $(col['tds'][key]).css('background-color', colorGenerated.color);
-
- if (colorGenerated.perc > 70 && settings.contrast) {
- $(col['tds'][key]).css('color', '#fff');
- }
- });
- });
-
- function colorGenerator(value, min, max) {
- var perc = (100 * (value - min)) / (max - min);
-
- if (settings.inverse)
- perc = 100 - perc;
-
- var hsl = Math.abs((perc - 100) * -1) + settings.colorStartPoint;
-
- return { color: 'hsl(' + hsl + ', 70%, 65%)', perc: perc };
- }
- } catch (error) {
- console.error(`[${$.columnHeatmap.name}::Error] ${error}`);
- return;
- }
- };
-}(jQuery));
\ No newline at end of file
diff --git a/activity_dashboard_mngmnt/static/src/js/lib/columnHeatmap.min.js b/activity_dashboard_mngmnt/static/src/js/lib/columnHeatmap.min.js
deleted file mode 100644
index 129ddbdbf..000000000
--- a/activity_dashboard_mngmnt/static/src/js/lib/columnHeatmap.min.js
+++ /dev/null
@@ -1 +0,0 @@
-!function(t){t.columnHeatmap={name:"columnHeatmap",version:"1.0",release:"2020-06-15",author:"Paulo Kramer",site:"https://www.paulokramer.com",documentation:"https://github.com/PauloAK/jQuery-columnHeatMap"},t.fn.columnHeatmap=function(e){var n=t.extend({columns:[],contrast:!0,inverse:!1,animated:!0,animationSpeed:.1,fn_parseValue:null,colorStartPoint:0},e);try{if(!this.is("table"))throw"Selected element isn't a table";if(0==n.columns.length)throw"You need to specify the columns";if(n.colorStartPoint<0||n.colorStartPoint>360)throw`colorStartPoint need to be beetween 0 and 360, current: ${n.colorStartPoint}`;let e=this.find("tbody tr"),a=[];t.each(n.columns,(o,r)=>{e.each((e,o)=>{0==e&&(a[r.toString()]=new Array,a[r.toString()].values=new Array,a[r.toString()].tds=new Array);let l=t(o).find("td")[r];if(a[r.toString()].tds.push(l),"function"==typeof n.fn_parseValue){let e=fn_parseValue(t(l).text());if(void 0===e)throw"None value returned in fn_parseValue";a[r.toString()].values.push(e)}else{let e=t(l).text().match(/[\d|\-|.|,]+/)[0];a[r.toString()].values.push(parseFloat(e))}})}),a=a.filter(t=>t),t.each(a,(t,e)=>{e&&e.values&&(a[t].min=null,a[t].max=null,a[t].min=e.values.reduce(function(t,e){return Math.min(t,e)}),a[t].max=e.values.reduce(function(t,e){return Math.max(t,e)}))}),t.each(a,(e,a)=>{t.each(a.values,(e,o)=>{let r=function(t,e,a){var o=100*(t-e)/(a-e);n.inverse&&(o=100-o);return{color:"hsl("+(Math.abs(-1*(o-100))+n.colorStartPoint)+", 70%, 65%)",perc:o}}(o,a.min,a.max);n.animated&&t(a.tds[e]).css("transition",`background-color ${n.animationSpeed}s linear, color ${n.animationSpeed}s linear`),t(a.tds[e]).css("background-color",r.color),r.perc>70&&n.contrast&&t(a.tds[e]).css("color","#fff")})})}catch(e){return void console.error(`[${t.columnHeatmap.name}::Error] ${e}`)}}}(jQuery);
diff --git a/activity_dashboard_mngmnt/static/src/js/lib/d3.min.js b/activity_dashboard_mngmnt/static/src/js/lib/d3.min.js
deleted file mode 100644
index 213a10816..000000000
--- a/activity_dashboard_mngmnt/static/src/js/lib/d3.min.js
+++ /dev/null
@@ -1,7828 +0,0 @@
-! function() {
- function n(n) {
- return n && (n.ownerDocument || n.document).documentElement
- }
-
- function t(n) {
- return n && n.ownerDocument ? n.ownerDocument.defaultView : n
- }
-
- function e(n, t) {
- return t > n ? -1 : n > t ? 1 : n >= t ? 0 : 0 / 0
- }
-
- function r(n) {
- return null === n ? 0 / 0 : +n
- }
-
- function u(n) {
- return !isNaN(n)
- }
-
- function i(n) {
- return {
- left: function(t, e, r, u) {
- for (arguments.length < 3 && (r = 0), arguments.length < 4 && (u = t.length); u > r;) {
- var i = r + u >>> 1;
- n(t[i], e) < 0 ? r = i + 1 : u = i
- }
- return r
- },
- right: function(t, e, r, u) {
- for (arguments.length < 3 && (r = 0), arguments.length < 4 && (u = t.length); u > r;) {
- var i = r + u >>> 1;
- n(t[i], e) > 0 ? u = i : r = i + 1
- }
- return r
- }
- }
- }
-
- function o(n) {
- return n.length
- }
-
- function a(n) {
- for (var t = 1; n * t % 1;) t *= 10;
- return t
- }
-
- function c(n, t) {
- for (var e in t) Object.defineProperty(n.prototype, e, {
- value: t[e],
- enumerable: !1
- })
- }
-
- function l() {
- this._ = Object.create(null)
- }
-
- function s(n) {
- return (n += "") === pa || n[0] === va ? va + n : n
- }
-
- function f(n) {
- return (n += "")[0] === va ? n.slice(1) : n
- }
-
- function h(n) {
- return s(n) in this._
- }
-
- function g(n) {
- return (n = s(n)) in this._ && delete this._[n]
- }
-
- function p() {
- var n = [];
- for (var t in this._) n.push(f(t));
- return n
- }
-
- function v() {
- var n = 0;
- for (var t in this._) ++n;
- return n
- }
-
- function d() {
- for (var n in this._) return !1;
- return !0
- }
-
- function m() {
- this._ = Object.create(null)
- }
-
- function y(n) {
- return n
- }
-
- function M(n, t, e) {
- return function() {
- var r = e.apply(t, arguments);
- return r === t ? n : r
- }
- }
-
- function x(n, t) {
- if (t in n) return t;
- t = t.charAt(0).toUpperCase() + t.slice(1);
- for (var e = 0, r = da.length; r > e; ++e) {
- var u = da[e] + t;
- if (u in n) return u
- }
- }
-
- function b() {}
-
- function _() {}
-
- function w(n) {
- function t() {
- for (var t, r = e, u = -1, i = r.length; ++u < i;)(t = r[u].on) && t.apply(this, arguments);
- return n
- }
- var e = [],
- r = new l;
- return t.on = function(t, u) {
- var i, o = r.get(t);
- return arguments.length < 2 ? o && o.on : (o && (o.on = null, e = e.slice(0, i = e.indexOf(o)).concat(e.slice(i + 1)), r.remove(t)), u && e.push(r.set(t, {
- on: u
- })), n)
- }, t
- }
-
- function S() {
- ta.event.preventDefault()
- }
-
- function k() {
- for (var n, t = ta.event; n = t.sourceEvent;) t = n;
- return t
- }
-
- function E(n) {
- for (var t = new _, e = 0, r = arguments.length; ++e < r;) t[arguments[e]] = w(t);
- return t.of = function(e, r) {
- return function(u) {
- try {
- var i = u.sourceEvent = ta.event;
- u.target = n, ta.event = u, t[u.type].apply(e, r)
- } finally {
- ta.event = i
- }
- }
- }, t
- }
-
- function A(n) {
- return ya(n, _a), n
- }
-
- function N(n) {
- return "function" == typeof n ? n : function() {
- return Ma(n, this)
- }
- }
-
- function C(n) {
- return "function" == typeof n ? n : function() {
- return xa(n, this)
- }
- }
-
- function z(n, t) {
- function e() {
- this.removeAttribute(n)
- }
-
- function r() {
- this.removeAttributeNS(n.space, n.local)
- }
-
- function u() {
- this.setAttribute(n, t)
- }
-
- function i() {
- this.setAttributeNS(n.space, n.local, t)
- }
-
- function o() {
- var e = t.apply(this, arguments);
- null == e ? this.removeAttribute(n) : this.setAttribute(n, e)
- }
-
- function a() {
- var e = t.apply(this, arguments);
- null == e ? this.removeAttributeNS(n.space, n.local) : this.setAttributeNS(n.space, n.local, e)
- }
- return n = ta.ns.qualify(n), null == t ? n.local ? r : e : "function" == typeof t ? n.local ? a : o : n.local ? i : u
- }
-
- function q(n) {
- return n.trim().replace(/\s+/g, " ")
- }
-
- function L(n) {
- return new RegExp("(?:^|\\s+)" + ta.requote(n) + "(?:\\s+|$)", "g")
- }
-
- function T(n) {
- return (n + "").trim().split(/^|\s+/)
- }
-
- function R(n, t) {
- function e() {
- for (var e = -1; ++e < u;) n[e](this, t)
- }
-
- function r() {
- for (var e = -1, r = t.apply(this, arguments); ++e < u;) n[e](this, r)
- }
- n = T(n).map(D);
- var u = n.length;
- return "function" == typeof t ? r : e
- }
-
- function D(n) {
- var t = L(n);
- return function(e, r) {
- if (u = e.classList) return r ? u.add(n) : u.remove(n);
- var u = e.getAttribute("class") || "";
- r ? (t.lastIndex = 0, t.test(u) || e.setAttribute("class", q(u + " " + n))) : e.setAttribute("class", q(u.replace(t, " ")))
- }
- }
-
- function P(n, t, e) {
- function r() {
- this.style.removeProperty(n)
- }
-
- function u() {
- this.style.setProperty(n, t, e)
- }
-
- function i() {
- var r = t.apply(this, arguments);
- null == r ? this.style.removeProperty(n) : this.style.setProperty(n, r, e)
- }
- return null == t ? r : "function" == typeof t ? i : u
- }
-
- function U(n, t) {
- function e() {
- delete this[n]
- }
-
- function r() {
- this[n] = t
- }
-
- function u() {
- var e = t.apply(this, arguments);
- null == e ? delete this[n] : this[n] = e
- }
- return null == t ? e : "function" == typeof t ? u : r
- }
-
- function j(n) {
- function t() {
- var t = this.ownerDocument,
- e = this.namespaceURI;
- return e ? t.createElementNS(e, n) : t.createElement(n)
- }
-
- function e() {
- return this.ownerDocument.createElementNS(n.space, n.local)
- }
- return "function" == typeof n ? n : (n = ta.ns.qualify(n)).local ? e : t
- }
-
- function F() {
- var n = this.parentNode;
- n && n.removeChild(this)
- }
-
- function H(n) {
- return {
- __data__: n
- }
- }
-
- function O(n) {
- return function() {
- return ba(this, n)
- }
- }
-
- function I(n) {
- return arguments.length || (n = e),
- function(t, e) {
- return t && e ? n(t.__data__, e.__data__) : !t - !e
- }
- }
-
- function Y(n, t) {
- for (var e = 0, r = n.length; r > e; e++)
- for (var u, i = n[e], o = 0, a = i.length; a > o; o++)(u = i[o]) && t(u, o, e);
- return n
- }
-
- function Z(n) {
- return ya(n, Sa), n
- }
-
- function V(n) {
- var t, e;
- return function(r, u, i) {
- var o, a = n[i].update,
- c = a.length;
- for (i != e && (e = i, t = 0), u >= t && (t = u + 1); !(o = a[t]) && ++t < c;);
- return o
- }
- }
-
- function X(n, t, e) {
- function r() {
- var t = this[o];
- t && (this.removeEventListener(n, t, t.$), delete this[o])
- }
-
- function u() {
- var u = c(t, ra(arguments));
- r.call(this), this.addEventListener(n, this[o] = u, u.$ = e), u._ = t
- }
-
- function i() {
- var t, e = new RegExp("^__on([^.]+)" + ta.requote(n) + "$");
- for (var r in this)
- if (t = r.match(e)) {
- var u = this[r];
- this.removeEventListener(t[1], u, u.$), delete this[r]
- }
- }
- var o = "__on" + n,
- a = n.indexOf("."),
- c = $;
- a > 0 && (n = n.slice(0, a));
- var l = ka.get(n);
- return l && (n = l, c = B), a ? t ? u : r : t ? b : i
- }
-
- function $(n, t) {
- return function(e) {
- var r = ta.event;
- ta.event = e, t[0] = this.__data__;
- try {
- n.apply(this, t)
- } finally {
- ta.event = r
- }
- }
- }
-
- function B(n, t) {
- var e = $(n, t);
- return function(n) {
- var t = this,
- r = n.relatedTarget;
- r && (r === t || 8 & r.compareDocumentPosition(t)) || e.call(t, n)
- }
- }
-
- function W(e) {
- var r = ".dragsuppress-" + ++Aa,
- u = "click" + r,
- i = ta.select(t(e)).on("touchmove" + r, S).on("dragstart" + r, S).on("selectstart" + r, S);
- if (null == Ea && (Ea = "onselectstart" in e ? !1 : x(e.style, "userSelect")), Ea) {
- var o = n(e).style,
- a = o[Ea];
- o[Ea] = "none"
- }
- return function(n) {
- if (i.on(r, null), Ea && (o[Ea] = a), n) {
- var t = function() {
- i.on(u, null)
- };
- i.on(u, function() {
- S(), t()
- }, !0), setTimeout(t, 0)
- }
- }
- }
-
- function J(n, e) {
- e.changedTouches && (e = e.changedTouches[0]);
- var r = n.ownerSVGElement || n;
- if (r.createSVGPoint) {
- var u = r.createSVGPoint();
- if (0 > Na) {
- var i = t(n);
- if (i.scrollX || i.scrollY) {
- r = ta.select("body").append("svg").style({
- position: "absolute",
- top: 0,
- left: 0,
- margin: 0,
- padding: 0,
- border: "none"
- }, "important");
- var o = r[0][0].getScreenCTM();
- Na = !(o.f || o.e), r.remove()
- }
- }
- return Na ? (u.x = e.pageX, u.y = e.pageY) : (u.x = e.clientX, u.y = e.clientY), u = u.matrixTransform(n.getScreenCTM().inverse()), [u.x, u.y]
- }
- var a = n.getBoundingClientRect();
- return [e.clientX - a.left - n.clientLeft, e.clientY - a.top - n.clientTop]
- }
-
- function G() {
- return ta.event.changedTouches[0].identifier
- }
-
- function K(n) {
- return n > 0 ? 1 : 0 > n ? -1 : 0
- }
-
- function Q(n, t, e) {
- return (t[0] - n[0]) * (e[1] - n[1]) - (t[1] - n[1]) * (e[0] - n[0])
- }
-
- function nt(n) {
- return n > 1 ? 0 : -1 > n ? qa : Math.acos(n)
- }
-
- function tt(n) {
- return n > 1 ? Ra : -1 > n ? -Ra : Math.asin(n)
- }
-
- function et(n) {
- return ((n = Math.exp(n)) - 1 / n) / 2
- }
-
- function rt(n) {
- return ((n = Math.exp(n)) + 1 / n) / 2
- }
-
- function ut(n) {
- return ((n = Math.exp(2 * n)) - 1) / (n + 1)
- }
-
- function it(n) {
- return (n = Math.sin(n / 2)) * n
- }
-
- function ot() {}
-
- function at(n, t, e) {
- return this instanceof at ? (this.h = +n, this.s = +t, void(this.l = +e)) : arguments.length < 2 ? n instanceof at ? new at(n.h, n.s, n.l) : bt("" + n, _t, at) : new at(n, t, e)
- }
-
- function ct(n, t, e) {
- function r(n) {
- return n > 360 ? n -= 360 : 0 > n && (n += 360), 60 > n ? i + (o - i) * n / 60 : 180 > n ? o : 240 > n ? i + (o - i) * (240 - n) / 60 : i
- }
-
- function u(n) {
- return Math.round(255 * r(n))
- }
- var i, o;
- return n = isNaN(n) ? 0 : (n %= 360) < 0 ? n + 360 : n, t = isNaN(t) ? 0 : 0 > t ? 0 : t > 1 ? 1 : t, e = 0 > e ? 0 : e > 1 ? 1 : e, o = .5 >= e ? e * (1 + t) : e + t - e * t, i = 2 * e - o, new mt(u(n + 120), u(n), u(n - 120))
- }
-
- function lt(n, t, e) {
- return this instanceof lt ? (this.h = +n, this.c = +t, void(this.l = +e)) : arguments.length < 2 ? n instanceof lt ? new lt(n.h, n.c, n.l) : n instanceof ft ? gt(n.l, n.a, n.b) : gt((n = wt((n = ta.rgb(n)).r, n.g, n.b)).l, n.a, n.b) : new lt(n, t, e)
- }
-
- function st(n, t, e) {
- return isNaN(n) && (n = 0), isNaN(t) && (t = 0), new ft(e, Math.cos(n *= Da) * t, Math.sin(n) * t)
- }
-
- function ft(n, t, e) {
- return this instanceof ft ? (this.l = +n, this.a = +t, void(this.b = +e)) : arguments.length < 2 ? n instanceof ft ? new ft(n.l, n.a, n.b) : n instanceof lt ? st(n.h, n.c, n.l) : wt((n = mt(n)).r, n.g, n.b) : new ft(n, t, e)
- }
-
- function ht(n, t, e) {
- var r = (n + 16) / 116,
- u = r + t / 500,
- i = r - e / 200;
- return u = pt(u) * Xa, r = pt(r) * $a, i = pt(i) * Ba, new mt(dt(3.2404542 * u - 1.5371385 * r - .4985314 * i), dt(-.969266 * u + 1.8760108 * r + .041556 * i), dt(.0556434 * u - .2040259 * r + 1.0572252 * i))
- }
-
- function gt(n, t, e) {
- return n > 0 ? new lt(Math.atan2(e, t) * Pa, Math.sqrt(t * t + e * e), n) : new lt(0 / 0, 0 / 0, n)
- }
-
- function pt(n) {
- return n > .206893034 ? n * n * n : (n - 4 / 29) / 7.787037
- }
-
- function vt(n) {
- return n > .008856 ? Math.pow(n, 1 / 3) : 7.787037 * n + 4 / 29
- }
-
- function dt(n) {
- return Math.round(255 * (.00304 >= n ? 12.92 * n : 1.055 * Math.pow(n, 1 / 2.4) - .055))
- }
-
- function mt(n, t, e) {
- return this instanceof mt ? (this.r = ~~n, this.g = ~~t, void(this.b = ~~e)) : arguments.length < 2 ? n instanceof mt ? new mt(n.r, n.g, n.b) : bt("" + n, mt, ct) : new mt(n, t, e)
- }
-
- function yt(n) {
- return new mt(n >> 16, n >> 8 & 255, 255 & n)
- }
-
- function Mt(n) {
- return yt(n) + ""
- }
-
- function xt(n) {
- return 16 > n ? "0" + Math.max(0, n).toString(16) : Math.min(255, n).toString(16)
- }
-
- function bt(n, t, e) {
- var r, u, i, o = 0,
- a = 0,
- c = 0;
- if (r = /([a-z]+)\((.*)\)/i.exec(n)) switch (u = r[2].split(","), r[1]) {
- case "hsl":
- return e(parseFloat(u[0]), parseFloat(u[1]) / 100, parseFloat(u[2]) / 100);
- case "rgb":
- return t(kt(u[0]), kt(u[1]), kt(u[2]))
- }
- return (i = Ga.get(n.toLowerCase())) ? t(i.r, i.g, i.b) : (null == n || "#" !== n.charAt(0) || isNaN(i = parseInt(n.slice(1), 16)) || (4 === n.length ? (o = (3840 & i) >> 4, o = o >> 4 | o, a = 240 & i, a = a >> 4 | a, c = 15 & i, c = c << 4 | c) : 7 === n.length && (o = (16711680 & i) >> 16, a = (65280 & i) >> 8, c = 255 & i)), t(o, a, c))
- }
-
- function _t(n, t, e) {
- var r, u, i = Math.min(n /= 255, t /= 255, e /= 255),
- o = Math.max(n, t, e),
- a = o - i,
- c = (o + i) / 2;
- return a ? (u = .5 > c ? a / (o + i) : a / (2 - o - i), r = n == o ? (t - e) / a + (e > t ? 6 : 0) : t == o ? (e - n) / a + 2 : (n - t) / a + 4, r *= 60) : (r = 0 / 0, u = c > 0 && 1 > c ? 0 : r), new at(r, u, c)
- }
-
- function wt(n, t, e) {
- n = St(n), t = St(t), e = St(e);
- var r = vt((.4124564 * n + .3575761 * t + .1804375 * e) / Xa),
- u = vt((.2126729 * n + .7151522 * t + .072175 * e) / $a),
- i = vt((.0193339 * n + .119192 * t + .9503041 * e) / Ba);
- return ft(116 * u - 16, 500 * (r - u), 200 * (u - i))
- }
-
- function St(n) {
- return (n /= 255) <= .04045 ? n / 12.92 : Math.pow((n + .055) / 1.055, 2.4)
- }
-
- function kt(n) {
- var t = parseFloat(n);
- return "%" === n.charAt(n.length - 1) ? Math.round(2.55 * t) : t
- }
-
- function Et(n) {
- return "function" == typeof n ? n : function() {
- return n
- }
- }
-
- function At(n) {
- return function(t, e, r) {
- return 2 === arguments.length && "function" == typeof e && (r = e, e = null), Nt(t, e, n, r)
- }
- }
-
- function Nt(n, t, e, r) {
- function u() {
- var n, t = c.status;
- if (!t && zt(c) || t >= 200 && 300 > t || 304 === t) {
- try {
- n = e.call(i, c)
- } catch (r) {
- return void o.error.call(i, r)
- }
- o.load.call(i, n)
- } else o.error.call(i, c)
- }
- var i = {},
- o = ta.dispatch("beforesend", "progress", "load", "error"),
- a = {},
- c = new XMLHttpRequest,
- l = null;
- return !this.XDomainRequest || "withCredentials" in c || !/^(http(s)?:)?\/\//.test(n) || (c = new XDomainRequest), "onload" in c ? c.onload = c.onerror = u : c.onreadystatechange = function() {
- c.readyState > 3 && u()
- }, c.onprogress = function(n) {
- var t = ta.event;
- ta.event = n;
- try {
- o.progress.call(i, c)
- } finally {
- ta.event = t
- }
- }, i.header = function(n, t) {
- return n = (n + "").toLowerCase(), arguments.length < 2 ? a[n] : (null == t ? delete a[n] : a[n] = t + "", i)
- }, i.mimeType = function(n) {
- return arguments.length ? (t = null == n ? null : n + "", i) : t
- }, i.responseType = function(n) {
- return arguments.length ? (l = n, i) : l
- }, i.response = function(n) {
- return e = n, i
- }, ["get", "post"].forEach(function(n) {
- i[n] = function() {
- return i.send.apply(i, [n].concat(ra(arguments)))
- }
- }), i.send = function(e, r, u) {
- if (2 === arguments.length && "function" == typeof r && (u = r, r = null), c.open(e, n, !0), null == t || "accept" in a || (a.accept = t + ",*/*"), c.setRequestHeader)
- for (var s in a) c.setRequestHeader(s, a[s]);
- return null != t && c.overrideMimeType && c.overrideMimeType(t), null != l && (c.responseType = l), null != u && i.on("error", u).on("load", function(n) {
- u(null, n)
- }), o.beforesend.call(i, c), c.send(null == r ? null : r), i
- }, i.abort = function() {
- return c.abort(), i
- }, ta.rebind(i, o, "on"), null == r ? i : i.get(Ct(r))
- }
-
- function Ct(n) {
- return 1 === n.length ? function(t, e) {
- n(null == t ? e : null)
- } : n
- }
-
- function zt(n) {
- var t = n.responseType;
- return t && "text" !== t ? n.response : n.responseText
- }
-
- function qt() {
- var n = Lt(),
- t = Tt() - n;
- t > 24 ? (isFinite(t) && (clearTimeout(tc), tc = setTimeout(qt, t)), nc = 0) : (nc = 1, rc(qt))
- }
-
- function Lt() {
- var n = Date.now();
- for (ec = Ka; ec;) n >= ec.t && (ec.f = ec.c(n - ec.t)), ec = ec.n;
- return n
- }
-
- function Tt() {
- for (var n, t = Ka, e = 1 / 0; t;) t.f ? t = n ? n.n = t.n : Ka = t.n : (t.t < e && (e = t.t), t = (n = t).n);
- return Qa = n, e
- }
-
- function Rt(n, t) {
- return t - (n ? Math.ceil(Math.log(n) / Math.LN10) : 1)
- }
-
- function Dt(n, t) {
- var e = Math.pow(10, 3 * ga(8 - t));
- return {
- scale: t > 8 ? function(n) {
- return n / e
- } : function(n) {
- return n * e
- },
- symbol: n
- }
- }
-
- function Pt(n) {
- var t = n.decimal,
- e = n.thousands,
- r = n.grouping,
- u = n.currency,
- i = r && e ? function(n, t) {
- for (var u = n.length, i = [], o = 0, a = r[0], c = 0; u > 0 && a > 0 && (c + a + 1 > t && (a = Math.max(1, t - c)), i.push(n.substring(u -= a, u + a)), !((c += a + 1) > t));) a = r[o = (o + 1) % r.length];
- return i.reverse().join(e)
- } : y;
- return function(n) {
- var e = ic.exec(n),
- r = e[1] || " ",
- o = e[2] || ">",
- a = e[3] || "-",
- c = e[4] || "",
- l = e[5],
- s = +e[6],
- f = e[7],
- h = e[8],
- g = e[9],
- p = 1,
- v = "",
- d = "",
- m = !1,
- y = !0;
- switch (h && (h = +h.substring(1)), (l || "0" === r && "=" === o) && (l = r = "0", o = "="), g) {
- case "n":
- f = !0, g = "g";
- break;
- case "%":
- p = 100, d = "%", g = "f";
- break;
- case "p":
- p = 100, d = "%", g = "r";
- break;
- case "b":
- case "o":
- case "x":
- case "X":
- "#" === c && (v = "0" + g.toLowerCase());
- case "c":
- y = !1;
- case "d":
- m = !0, h = 0;
- break;
- case "s":
- p = -1, g = "r"
- }
- "$" === c && (v = u[0], d = u[1]), "r" != g || h || (g = "g"), null != h && ("g" == g ? h = Math.max(1, Math.min(21, h)) : ("e" == g || "f" == g) && (h = Math.max(0, Math.min(20, h)))), g = oc.get(g) || Ut;
- var M = l && f;
- return function(n) {
- var e = d;
- if (m && n % 1) return "";
- var u = 0 > n || 0 === n && 0 > 1 / n ? (n = -n, "-") : "-" === a ? "" : a;
- if (0 > p) {
- var c = ta.formatPrefix(n, h);
- n = c.scale(n), e = c.symbol + d
- } else n *= p;
- n = g(n, h);
- var x, b, _ = n.lastIndexOf(".");
- if (0 > _) {
- var w = y ? n.lastIndexOf("e") : -1;
- 0 > w ? (x = n, b = "") : (x = n.substring(0, w), b = n.substring(w))
- } else x = n.substring(0, _), b = t + n.substring(_ + 1);
- !l && f && (x = i(x, 1 / 0));
- var S = v.length + x.length + b.length + (M ? 0 : u.length),
- k = s > S ? new Array(S = s - S + 1).join(r) : "";
- return M && (x = i(k + x, k.length ? s - b.length : 1 / 0)), u += v, n = x + b, ("<" === o ? u + n + k : ">" === o ? k + u + n : "^" === o ? k.substring(0, S >>= 1) + u + n + k.substring(S) : u + (M ? n : k + n)) + e
- }
- }
- }
-
- function Ut(n) {
- return n + ""
- }
-
- function jt() {
- this._ = new Date(arguments.length > 1 ? Date.UTC.apply(this, arguments) : arguments[0])
- }
-
- function Ft(n, t, e) {
- function r(t) {
- var e = n(t),
- r = i(e, 1);
- return r - t > t - e ? e : r
- }
-
- function u(e) {
- return t(e = n(new cc(e - 1)), 1), e
- }
-
- function i(n, e) {
- return t(n = new cc(+n), e), n
- }
-
- function o(n, r, i) {
- var o = u(n),
- a = [];
- if (i > 1)
- for (; r > o;) e(o) % i || a.push(new Date(+o)), t(o, 1);
- else
- for (; r > o;) a.push(new Date(+o)), t(o, 1);
- return a
- }
-
- function a(n, t, e) {
- try {
- cc = jt;
- var r = new jt;
- return r._ = n, o(r, t, e)
- } finally {
- cc = Date
- }
- }
- n.floor = n, n.round = r, n.ceil = u, n.offset = i, n.range = o;
- var c = n.utc = Ht(n);
- return c.floor = c, c.round = Ht(r), c.ceil = Ht(u), c.offset = Ht(i), c.range = a, n
- }
-
- function Ht(n) {
- return function(t, e) {
- try {
- cc = jt;
- var r = new jt;
- return r._ = t, n(r, e)._
- } finally {
- cc = Date
- }
- }
- }
-
- function Ot(n) {
- function t(n) {
- function t(t) {
- for (var e, u, i, o = [], a = -1, c = 0; ++a < r;) 37 === n.charCodeAt(a) && (o.push(n.slice(c, a)), null != (u = sc[e = n.charAt(++a)]) && (e = n.charAt(++a)), (i = N[e]) && (e = i(t, null == u ? "e" === e ? " " : "0" : u)), o.push(e), c = a + 1);
- return o.push(n.slice(c, a)), o.join("")
- }
- var r = n.length;
- return t.parse = function(t) {
- var r = {
- y: 1900,
- m: 0,
- d: 1,
- H: 0,
- M: 0,
- S: 0,
- L: 0,
- Z: null
- },
- u = e(r, n, t, 0);
- if (u != t.length) return null;
- "p" in r && (r.H = r.H % 12 + 12 * r.p);
- var i = null != r.Z && cc !== jt,
- o = new(i ? jt : cc);
- return "j" in r ? o.setFullYear(r.y, 0, r.j) : "w" in r && ("W" in r || "U" in r) ? (o.setFullYear(r.y, 0, 1), o.setFullYear(r.y, 0, "W" in r ? (r.w + 6) % 7 + 7 * r.W - (o.getDay() + 5) % 7 : r.w + 7 * r.U - (o.getDay() + 6) % 7)) : o.setFullYear(r.y, r.m, r.d), o.setHours(r.H + (r.Z / 100 | 0), r.M + r.Z % 100, r.S, r.L), i ? o._ : o
- }, t.toString = function() {
- return n
- }, t
- }
-
- function e(n, t, e, r) {
- for (var u, i, o, a = 0, c = t.length, l = e.length; c > a;) {
- if (r >= l) return -1;
- if (u = t.charCodeAt(a++), 37 === u) {
- if (o = t.charAt(a++), i = C[o in sc ? t.charAt(a++) : o], !i || (r = i(n, e, r)) < 0) return -1
- } else if (u != e.charCodeAt(r++)) return -1
- }
- return r
- }
-
- function r(n, t, e) {
- _.lastIndex = 0;
- var r = _.exec(t.slice(e));
- return r ? (n.w = w.get(r[0].toLowerCase()), e + r[0].length) : -1
- }
-
- function u(n, t, e) {
- x.lastIndex = 0;
- var r = x.exec(t.slice(e));
- return r ? (n.w = b.get(r[0].toLowerCase()), e + r[0].length) : -1
- }
-
- function i(n, t, e) {
- E.lastIndex = 0;
- var r = E.exec(t.slice(e));
- return r ? (n.m = A.get(r[0].toLowerCase()), e + r[0].length) : -1
- }
-
- function o(n, t, e) {
- S.lastIndex = 0;
- var r = S.exec(t.slice(e));
- return r ? (n.m = k.get(r[0].toLowerCase()), e + r[0].length) : -1
- }
-
- function a(n, t, r) {
- return e(n, N.c.toString(), t, r)
- }
-
- function c(n, t, r) {
- return e(n, N.x.toString(), t, r)
- }
-
- function l(n, t, r) {
- return e(n, N.X.toString(), t, r)
- }
-
- function s(n, t, e) {
- var r = M.get(t.slice(e, e += 2).toLowerCase());
- return null == r ? -1 : (n.p = r, e)
- }
- var f = n.dateTime,
- h = n.date,
- g = n.time,
- p = n.periods,
- v = n.days,
- d = n.shortDays,
- m = n.months,
- y = n.shortMonths;
- t.utc = function(n) {
- function e(n) {
- try {
- cc = jt;
- var t = new cc;
- return t._ = n, r(t)
- } finally {
- cc = Date
- }
- }
- var r = t(n);
- return e.parse = function(n) {
- try {
- cc = jt;
- var t = r.parse(n);
- return t && t._
- } finally {
- cc = Date
- }
- }, e.toString = r.toString, e
- }, t.multi = t.utc.multi = ae;
- var M = ta.map(),
- x = Yt(v),
- b = Zt(v),
- _ = Yt(d),
- w = Zt(d),
- S = Yt(m),
- k = Zt(m),
- E = Yt(y),
- A = Zt(y);
- p.forEach(function(n, t) {
- M.set(n.toLowerCase(), t)
- });
- var N = {
- a: function(n) {
- return d[n.getDay()]
- },
- A: function(n) {
- return v[n.getDay()]
- },
- b: function(n) {
- return y[n.getMonth()]
- },
- B: function(n) {
- return m[n.getMonth()]
- },
- c: t(f),
- d: function(n, t) {
- return It(n.getDate(), t, 2)
- },
- e: function(n, t) {
- return It(n.getDate(), t, 2)
- },
- H: function(n, t) {
- return It(n.getHours(), t, 2)
- },
- I: function(n, t) {
- return It(n.getHours() % 12 || 12, t, 2)
- },
- j: function(n, t) {
- return It(1 + ac.dayOfYear(n), t, 3)
- },
- L: function(n, t) {
- return It(n.getMilliseconds(), t, 3)
- },
- m: function(n, t) {
- return It(n.getMonth() + 1, t, 2)
- },
- M: function(n, t) {
- return It(n.getMinutes(), t, 2)
- },
- p: function(n) {
- return p[+(n.getHours() >= 12)]
- },
- S: function(n, t) {
- return It(n.getSeconds(), t, 2)
- },
- U: function(n, t) {
- return It(ac.sundayOfYear(n), t, 2)
- },
- w: function(n) {
- return n.getDay()
- },
- W: function(n, t) {
- return It(ac.mondayOfYear(n), t, 2)
- },
- x: t(h),
- X: t(g),
- y: function(n, t) {
- return It(n.getFullYear() % 100, t, 2)
- },
- Y: function(n, t) {
- return It(n.getFullYear() % 1e4, t, 4)
- },
- Z: ie,
- "%": function() {
- return "%"
- }
- },
- C = {
- a: r,
- A: u,
- b: i,
- B: o,
- c: a,
- d: Qt,
- e: Qt,
- H: te,
- I: te,
- j: ne,
- L: ue,
- m: Kt,
- M: ee,
- p: s,
- S: re,
- U: Xt,
- w: Vt,
- W: $t,
- x: c,
- X: l,
- y: Wt,
- Y: Bt,
- Z: Jt,
- "%": oe
- };
- return t
- }
-
- function It(n, t, e) {
- var r = 0 > n ? "-" : "",
- u = (r ? -n : n) + "",
- i = u.length;
- return r + (e > i ? new Array(e - i + 1).join(t) + u : u)
- }
-
- function Yt(n) {
- return new RegExp("^(?:" + n.map(ta.requote).join("|") + ")", "i")
- }
-
- function Zt(n) {
- for (var t = new l, e = -1, r = n.length; ++e < r;) t.set(n[e].toLowerCase(), e);
- return t
- }
-
- function Vt(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 1));
- return r ? (n.w = +r[0], e + r[0].length) : -1
- }
-
- function Xt(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e));
- return r ? (n.U = +r[0], e + r[0].length) : -1
- }
-
- function $t(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e));
- return r ? (n.W = +r[0], e + r[0].length) : -1
- }
-
- function Bt(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 4));
- return r ? (n.y = +r[0], e + r[0].length) : -1
- }
-
- function Wt(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 2));
- return r ? (n.y = Gt(+r[0]), e + r[0].length) : -1
- }
-
- function Jt(n, t, e) {
- return /^[+-]\d{4}$/.test(t = t.slice(e, e + 5)) ? (n.Z = -t, e + 5) : -1
- }
-
- function Gt(n) {
- return n + (n > 68 ? 1900 : 2e3)
- }
-
- function Kt(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 2));
- return r ? (n.m = r[0] - 1, e + r[0].length) : -1
- }
-
- function Qt(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 2));
- return r ? (n.d = +r[0], e + r[0].length) : -1
- }
-
- function ne(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 3));
- return r ? (n.j = +r[0], e + r[0].length) : -1
- }
-
- function te(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 2));
- return r ? (n.H = +r[0], e + r[0].length) : -1
- }
-
- function ee(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 2));
- return r ? (n.M = +r[0], e + r[0].length) : -1
- }
-
- function re(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 2));
- return r ? (n.S = +r[0], e + r[0].length) : -1
- }
-
- function ue(n, t, e) {
- fc.lastIndex = 0;
- var r = fc.exec(t.slice(e, e + 3));
- return r ? (n.L = +r[0], e + r[0].length) : -1
- }
-
- function ie(n) {
- var t = n.getTimezoneOffset(),
- e = t > 0 ? "-" : "+",
- r = ga(t) / 60 | 0,
- u = ga(t) % 60;
- return e + It(r, "0", 2) + It(u, "0", 2)
- }
-
- function oe(n, t, e) {
- hc.lastIndex = 0;
- var r = hc.exec(t.slice(e, e + 1));
- return r ? e + r[0].length : -1
- }
-
- function ae(n) {
- for (var t = n.length, e = -1; ++e < t;) n[e][0] = this(n[e][0]);
- return function(t) {
- for (var e = 0, r = n[e]; !r[1](t);) r = n[++e];
- return r[0](t)
- }
- }
-
- function ce() {}
-
- function le(n, t, e) {
- var r = e.s = n + t,
- u = r - n,
- i = r - u;
- e.t = n - i + (t - u)
- }
-
- function se(n, t) {
- n && dc.hasOwnProperty(n.type) && dc[n.type](n, t)
- }
-
- function fe(n, t, e) {
- var r, u = -1,
- i = n.length - e;
- for (t.lineStart(); ++u < i;) r = n[u], t.point(r[0], r[1], r[2]);
- t.lineEnd()
- }
-
- function he(n, t) {
- var e = -1,
- r = n.length;
- for (t.polygonStart(); ++e < r;) fe(n[e], t, 1);
- t.polygonEnd()
- }
-
- function ge() {
- function n(n, t) {
- n *= Da, t = t * Da / 2 + qa / 4;
- var e = n - r,
- o = e >= 0 ? 1 : -1,
- a = o * e,
- c = Math.cos(t),
- l = Math.sin(t),
- s = i * l,
- f = u * c + s * Math.cos(a),
- h = s * o * Math.sin(a);
- yc.add(Math.atan2(h, f)), r = n, u = c, i = l
- }
- var t, e, r, u, i;
- Mc.point = function(o, a) {
- Mc.point = n, r = (t = o) * Da, u = Math.cos(a = (e = a) * Da / 2 + qa / 4), i = Math.sin(a)
- }, Mc.lineEnd = function() {
- n(t, e)
- }
- }
-
- function pe(n) {
- var t = n[0],
- e = n[1],
- r = Math.cos(e);
- return [r * Math.cos(t), r * Math.sin(t), Math.sin(e)]
- }
-
- function ve(n, t) {
- return n[0] * t[0] + n[1] * t[1] + n[2] * t[2]
- }
-
- function de(n, t) {
- return [n[1] * t[2] - n[2] * t[1], n[2] * t[0] - n[0] * t[2], n[0] * t[1] - n[1] * t[0]]
- }
-
- function me(n, t) {
- n[0] += t[0], n[1] += t[1], n[2] += t[2]
- }
-
- function ye(n, t) {
- return [n[0] * t, n[1] * t, n[2] * t]
- }
-
- function Me(n) {
- var t = Math.sqrt(n[0] * n[0] + n[1] * n[1] + n[2] * n[2]);
- n[0] /= t, n[1] /= t, n[2] /= t
- }
-
- function xe(n) {
- return [Math.atan2(n[1], n[0]), tt(n[2])]
- }
-
- function be(n, t) {
- return ga(n[0] - t[0]) < Ca && ga(n[1] - t[1]) < Ca
- }
-
- function _e(n, t) {
- n *= Da;
- var e = Math.cos(t *= Da);
- we(e * Math.cos(n), e * Math.sin(n), Math.sin(t))
- }
-
- function we(n, t, e) {
- ++xc, _c += (n - _c) / xc, wc += (t - wc) / xc, Sc += (e - Sc) / xc
- }
-
- function Se() {
- function n(n, u) {
- n *= Da;
- var i = Math.cos(u *= Da),
- o = i * Math.cos(n),
- a = i * Math.sin(n),
- c = Math.sin(u),
- l = Math.atan2(Math.sqrt((l = e * c - r * a) * l + (l = r * o - t * c) * l + (l = t * a - e * o) * l), t * o + e * a + r * c);
- bc += l, kc += l * (t + (t = o)), Ec += l * (e + (e = a)), Ac += l * (r + (r = c)), we(t, e, r)
- }
- var t, e, r;
- qc.point = function(u, i) {
- u *= Da;
- var o = Math.cos(i *= Da);
- t = o * Math.cos(u), e = o * Math.sin(u), r = Math.sin(i), qc.point = n, we(t, e, r)
- }
- }
-
- function ke() {
- qc.point = _e
- }
-
- function Ee() {
- function n(n, t) {
- n *= Da;
- var e = Math.cos(t *= Da),
- o = e * Math.cos(n),
- a = e * Math.sin(n),
- c = Math.sin(t),
- l = u * c - i * a,
- s = i * o - r * c,
- f = r * a - u * o,
- h = Math.sqrt(l * l + s * s + f * f),
- g = r * o + u * a + i * c,
- p = h && -nt(g) / h,
- v = Math.atan2(h, g);
- Nc += p * l, Cc += p * s, zc += p * f, bc += v, kc += v * (r + (r = o)), Ec += v * (u + (u = a)), Ac += v * (i + (i = c)), we(r, u, i)
- }
- var t, e, r, u, i;
- qc.point = function(o, a) {
- t = o, e = a, qc.point = n, o *= Da;
- var c = Math.cos(a *= Da);
- r = c * Math.cos(o), u = c * Math.sin(o), i = Math.sin(a), we(r, u, i)
- }, qc.lineEnd = function() {
- n(t, e), qc.lineEnd = ke, qc.point = _e
- }
- }
-
- function Ae(n, t) {
- function e(e, r) {
- return e = n(e, r), t(e[0], e[1])
- }
- return n.invert && t.invert && (e.invert = function(e, r) {
- return e = t.invert(e, r), e && n.invert(e[0], e[1])
- }), e
- }
-
- function Ne() {
- return !0
- }
-
- function Ce(n, t, e, r, u) {
- var i = [],
- o = [];
- if (n.forEach(function(n) {
- if (!((t = n.length - 1) <= 0)) {
- var t, e = n[0],
- r = n[t];
- if (be(e, r)) {
- u.lineStart();
- for (var a = 0; t > a; ++a) u.point((e = n[a])[0], e[1]);
- return void u.lineEnd()
- }
- var c = new qe(e, n, null, !0),
- l = new qe(e, null, c, !1);
- c.o = l, i.push(c), o.push(l), c = new qe(r, n, null, !1), l = new qe(r, null, c, !0), c.o = l, i.push(c), o.push(l)
- }
- }), o.sort(t), ze(i), ze(o), i.length) {
- for (var a = 0, c = e, l = o.length; l > a; ++a) o[a].e = c = !c;
- for (var s, f, h = i[0];;) {
- for (var g = h, p = !0; g.v;)
- if ((g = g.n) === h) return;
- s = g.z, u.lineStart();
- do {
- if (g.v = g.o.v = !0, g.e) {
- if (p)
- for (var a = 0, l = s.length; l > a; ++a) u.point((f = s[a])[0], f[1]);
- else r(g.x, g.n.x, 1, u);
- g = g.n
- } else {
- if (p) {
- s = g.p.z;
- for (var a = s.length - 1; a >= 0; --a) u.point((f = s[a])[0], f[1])
- } else r(g.x, g.p.x, -1, u);
- g = g.p
- }
- g = g.o, s = g.z, p = !p
- } while (!g.v);
- u.lineEnd()
- }
- }
- }
-
- function ze(n) {
- if (t = n.length) {
- for (var t, e, r = 0, u = n[0]; ++r < t;) u.n = e = n[r], e.p = u, u = e;
- u.n = e = n[0], e.p = u
- }
- }
-
- function qe(n, t, e, r) {
- this.x = n, this.z = t, this.o = e, this.e = r, this.v = !1, this.n = this.p = null
- }
-
- function Le(n, t, e, r) {
- return function(u, i) {
- function o(t, e) {
- var r = u(t, e);
- n(t = r[0], e = r[1]) && i.point(t, e)
- }
-
- function a(n, t) {
- var e = u(n, t);
- d.point(e[0], e[1])
- }
-
- function c() {
- y.point = a, d.lineStart()
- }
-
- function l() {
- y.point = o, d.lineEnd()
- }
-
- function s(n, t) {
- v.push([n, t]);
- var e = u(n, t);
- x.point(e[0], e[1])
- }
-
- function f() {
- x.lineStart(), v = []
- }
-
- function h() {
- s(v[0][0], v[0][1]), x.lineEnd();
- var n, t = x.clean(),
- e = M.buffer(),
- r = e.length;
- if (v.pop(), p.push(v), v = null, r)
- if (1 & t) {
- n = e[0];
- var u, r = n.length - 1,
- o = -1;
- if (r > 0) {
- for (b || (i.polygonStart(), b = !0), i.lineStart(); ++o < r;) i.point((u = n[o])[0], u[1]);
- i.lineEnd()
- }
- } else r > 1 && 2 & t && e.push(e.pop().concat(e.shift())), g.push(e.filter(Te))
- }
- var g, p, v, d = t(i),
- m = u.invert(r[0], r[1]),
- y = {
- point: o,
- lineStart: c,
- lineEnd: l,
- polygonStart: function() {
- y.point = s, y.lineStart = f, y.lineEnd = h, g = [], p = []
- },
- polygonEnd: function() {
- y.point = o, y.lineStart = c, y.lineEnd = l, g = ta.merge(g);
- var n = Fe(m, p);
- g.length ? (b || (i.polygonStart(), b = !0), Ce(g, De, n, e, i)) : n && (b || (i.polygonStart(), b = !0), i.lineStart(), e(null, null, 1, i), i.lineEnd()), b && (i.polygonEnd(), b = !1), g = p = null
- },
- sphere: function() {
- i.polygonStart(), i.lineStart(), e(null, null, 1, i), i.lineEnd(), i.polygonEnd()
- }
- },
- M = Re(),
- x = t(M),
- b = !1;
- return y
- }
- }
-
- function Te(n) {
- return n.length > 1
- }
-
- function Re() {
- var n, t = [];
- return {
- lineStart: function() {
- t.push(n = [])
- },
- point: function(t, e) {
- n.push([t, e])
- },
- lineEnd: b,
- buffer: function() {
- var e = t;
- return t = [], n = null, e
- },
- rejoin: function() {
- t.length > 1 && t.push(t.pop().concat(t.shift()))
- }
- }
- }
-
- function De(n, t) {
- return ((n = n.x)[0] < 0 ? n[1] - Ra - Ca : Ra - n[1]) - ((t = t.x)[0] < 0 ? t[1] - Ra - Ca : Ra - t[1])
- }
-
- function Pe(n) {
- var t, e = 0 / 0,
- r = 0 / 0,
- u = 0 / 0;
- return {
- lineStart: function() {
- n.lineStart(), t = 1
- },
- point: function(i, o) {
- var a = i > 0 ? qa : -qa,
- c = ga(i - e);
- ga(c - qa) < Ca ? (n.point(e, r = (r + o) / 2 > 0 ? Ra : -Ra), n.point(u, r), n.lineEnd(), n.lineStart(), n.point(a, r), n.point(i, r), t = 0) : u !== a && c >= qa && (ga(e - u) < Ca && (e -= u * Ca), ga(i - a) < Ca && (i -= a * Ca), r = Ue(e, r, i, o), n.point(u, r), n.lineEnd(), n.lineStart(), n.point(a, r), t = 0), n.point(e = i, r = o), u = a
- },
- lineEnd: function() {
- n.lineEnd(), e = r = 0 / 0
- },
- clean: function() {
- return 2 - t
- }
- }
- }
-
- function Ue(n, t, e, r) {
- var u, i, o = Math.sin(n - e);
- return ga(o) > Ca ? Math.atan((Math.sin(t) * (i = Math.cos(r)) * Math.sin(e) - Math.sin(r) * (u = Math.cos(t)) * Math.sin(n)) / (u * i * o)) : (t + r) / 2
- }
-
- function je(n, t, e, r) {
- var u;
- if (null == n) u = e * Ra, r.point(-qa, u), r.point(0, u), r.point(qa, u), r.point(qa, 0), r.point(qa, -u), r.point(0, -u), r.point(-qa, -u), r.point(-qa, 0), r.point(-qa, u);
- else if (ga(n[0] - t[0]) > Ca) {
- var i = n[0] < t[0] ? qa : -qa;
- u = e * i / 2, r.point(-i, u), r.point(0, u), r.point(i, u)
- } else r.point(t[0], t[1])
- }
-
- function Fe(n, t) {
- var e = n[0],
- r = n[1],
- u = [Math.sin(e), -Math.cos(e), 0],
- i = 0,
- o = 0;
- yc.reset();
- for (var a = 0, c = t.length; c > a; ++a) {
- var l = t[a],
- s = l.length;
- if (s)
- for (var f = l[0], h = f[0], g = f[1] / 2 + qa / 4, p = Math.sin(g), v = Math.cos(g), d = 1;;) {
- d === s && (d = 0), n = l[d];
- var m = n[0],
- y = n[1] / 2 + qa / 4,
- M = Math.sin(y),
- x = Math.cos(y),
- b = m - h,
- _ = b >= 0 ? 1 : -1,
- w = _ * b,
- S = w > qa,
- k = p * M;
- if (yc.add(Math.atan2(k * _ * Math.sin(w), v * x + k * Math.cos(w))), i += S ? b + _ * La : b, S ^ h >= e ^ m >= e) {
- var E = de(pe(f), pe(n));
- Me(E);
- var A = de(u, E);
- Me(A);
- var N = (S ^ b >= 0 ? -1 : 1) * tt(A[2]);
- (r > N || r === N && (E[0] || E[1])) && (o += S ^ b >= 0 ? 1 : -1)
- }
- if (!d++) break;
- h = m, p = M, v = x, f = n
- }
- }
- return (-Ca > i || Ca > i && 0 > yc) ^ 1 & o
- }
-
- function He(n) {
- function t(n, t) {
- return Math.cos(n) * Math.cos(t) > i
- }
-
- function e(n) {
- var e, i, c, l, s;
- return {
- lineStart: function() {
- l = c = !1, s = 1
- },
- point: function(f, h) {
- var g, p = [f, h],
- v = t(f, h),
- d = o ? v ? 0 : u(f, h) : v ? u(f + (0 > f ? qa : -qa), h) : 0;
- if (!e && (l = c = v) && n.lineStart(), v !== c && (g = r(e, p), (be(e, g) || be(p, g)) && (p[0] += Ca, p[1] += Ca, v = t(p[0], p[1]))), v !== c) s = 0, v ? (n.lineStart(), g = r(p, e), n.point(g[0], g[1])) : (g = r(e, p), n.point(g[0], g[1]), n.lineEnd()), e = g;
- else if (a && e && o ^ v) {
- var m;
- d & i || !(m = r(p, e, !0)) || (s = 0, o ? (n.lineStart(), n.point(m[0][0], m[0][1]), n.point(m[1][0], m[1][1]), n.lineEnd()) : (n.point(m[1][0], m[1][1]), n.lineEnd(), n.lineStart(), n.point(m[0][0], m[0][1])))
- }!v || e && be(e, p) || n.point(p[0], p[1]), e = p, c = v, i = d
- },
- lineEnd: function() {
- c && n.lineEnd(), e = null
- },
- clean: function() {
- return s | (l && c) << 1
- }
- }
- }
-
- function r(n, t, e) {
- var r = pe(n),
- u = pe(t),
- o = [1, 0, 0],
- a = de(r, u),
- c = ve(a, a),
- l = a[0],
- s = c - l * l;
- if (!s) return !e && n;
- var f = i * c / s,
- h = -i * l / s,
- g = de(o, a),
- p = ye(o, f),
- v = ye(a, h);
- me(p, v);
- var d = g,
- m = ve(p, d),
- y = ve(d, d),
- M = m * m - y * (ve(p, p) - 1);
- if (!(0 > M)) {
- var x = Math.sqrt(M),
- b = ye(d, (-m - x) / y);
- if (me(b, p), b = xe(b), !e) return b;
- var _, w = n[0],
- S = t[0],
- k = n[1],
- E = t[1];
- w > S && (_ = w, w = S, S = _);
- var A = S - w,
- N = ga(A - qa) < Ca,
- C = N || Ca > A;
- if (!N && k > E && (_ = k, k = E, E = _), C ? N ? k + E > 0 ^ b[1] < (ga(b[0] - w) < Ca ? k : E) : k <= b[1] && b[1] <= E : A > qa ^ (w <= b[0] && b[0] <= S)) {
- var z = ye(d, (-m + x) / y);
- return me(z, p), [b, xe(z)]
- }
- }
- }
-
- function u(t, e) {
- var r = o ? n : qa - n,
- u = 0;
- return -r > t ? u |= 1 : t > r && (u |= 2), -r > e ? u |= 4 : e > r && (u |= 8), u
- }
- var i = Math.cos(n),
- o = i > 0,
- a = ga(i) > Ca,
- c = gr(n, 6 * Da);
- return Le(t, e, c, o ? [0, -n] : [-qa, n - qa])
- }
-
- function Oe(n, t, e, r) {
- return function(u) {
- var i, o = u.a,
- a = u.b,
- c = o.x,
- l = o.y,
- s = a.x,
- f = a.y,
- h = 0,
- g = 1,
- p = s - c,
- v = f - l;
- if (i = n - c, p || !(i > 0)) {
- if (i /= p, 0 > p) {
- if (h > i) return;
- g > i && (g = i)
- } else if (p > 0) {
- if (i > g) return;
- i > h && (h = i)
- }
- if (i = e - c, p || !(0 > i)) {
- if (i /= p, 0 > p) {
- if (i > g) return;
- i > h && (h = i)
- } else if (p > 0) {
- if (h > i) return;
- g > i && (g = i)
- }
- if (i = t - l, v || !(i > 0)) {
- if (i /= v, 0 > v) {
- if (h > i) return;
- g > i && (g = i)
- } else if (v > 0) {
- if (i > g) return;
- i > h && (h = i)
- }
- if (i = r - l, v || !(0 > i)) {
- if (i /= v, 0 > v) {
- if (i > g) return;
- i > h && (h = i)
- } else if (v > 0) {
- if (h > i) return;
- g > i && (g = i)
- }
- return h > 0 && (u.a = {
- x: c + h * p,
- y: l + h * v
- }), 1 > g && (u.b = {
- x: c + g * p,
- y: l + g * v
- }), u
- }
- }
- }
- }
- }
- }
-
- function Ie(n, t, e, r) {
- function u(r, u) {
- return ga(r[0] - n) < Ca ? u > 0 ? 0 : 3 : ga(r[0] - e) < Ca ? u > 0 ? 2 : 1 : ga(r[1] - t) < Ca ? u > 0 ? 1 : 0 : u > 0 ? 3 : 2
- }
-
- function i(n, t) {
- return o(n.x, t.x)
- }
-
- function o(n, t) {
- var e = u(n, 1),
- r = u(t, 1);
- return e !== r ? e - r : 0 === e ? t[1] - n[1] : 1 === e ? n[0] - t[0] : 2 === e ? n[1] - t[1] : t[0] - n[0]
- }
- return function(a) {
- function c(n) {
- for (var t = 0, e = d.length, r = n[1], u = 0; e > u; ++u)
- for (var i, o = 1, a = d[u], c = a.length, l = a[0]; c > o; ++o) i = a[o], l[1] <= r ? i[1] > r && Q(l, i, n) > 0 && ++t : i[1] <= r && Q(l, i, n) < 0 && --t, l = i;
- return 0 !== t
- }
-
- function l(i, a, c, l) {
- var s = 0,
- f = 0;
- if (null == i || (s = u(i, c)) !== (f = u(a, c)) || o(i, a) < 0 ^ c > 0) {
- do l.point(0 === s || 3 === s ? n : e, s > 1 ? r : t); while ((s = (s + c + 4) % 4) !== f)
- } else l.point(a[0], a[1])
- }
-
- function s(u, i) {
- return u >= n && e >= u && i >= t && r >= i
- }
-
- function f(n, t) {
- s(n, t) && a.point(n, t)
- }
-
- function h() {
- C.point = p, d && d.push(m = []), S = !0, w = !1, b = _ = 0 / 0
- }
-
- function g() {
- v && (p(y, M), x && w && A.rejoin(), v.push(A.buffer())), C.point = f, w && a.lineEnd()
- }
-
- function p(n, t) {
- n = Math.max(-Tc, Math.min(Tc, n)), t = Math.max(-Tc, Math.min(Tc, t));
- var e = s(n, t);
- if (d && m.push([n, t]), S) y = n, M = t, x = e, S = !1, e && (a.lineStart(), a.point(n, t));
- else if (e && w) a.point(n, t);
- else {
- var r = {
- a: {
- x: b,
- y: _
- },
- b: {
- x: n,
- y: t
- }
- };
- N(r) ? (w || (a.lineStart(), a.point(r.a.x, r.a.y)), a.point(r.b.x, r.b.y), e || a.lineEnd(), k = !1) : e && (a.lineStart(), a.point(n, t), k = !1)
- }
- b = n, _ = t, w = e
- }
- var v, d, m, y, M, x, b, _, w, S, k, E = a,
- A = Re(),
- N = Oe(n, t, e, r),
- C = {
- point: f,
- lineStart: h,
- lineEnd: g,
- polygonStart: function() {
- a = A, v = [], d = [], k = !0
- },
- polygonEnd: function() {
- a = E, v = ta.merge(v);
- var t = c([n, r]),
- e = k && t,
- u = v.length;
- (e || u) && (a.polygonStart(), e && (a.lineStart(), l(null, null, 1, a), a.lineEnd()), u && Ce(v, i, t, l, a), a.polygonEnd()), v = d = m = null
- }
- };
- return C
- }
- }
-
- function Ye(n) {
- var t = 0,
- e = qa / 3,
- r = ir(n),
- u = r(t, e);
- return u.parallels = function(n) {
- return arguments.length ? r(t = n[0] * qa / 180, e = n[1] * qa / 180) : [t / qa * 180, e / qa * 180]
- }, u
- }
-
- function Ze(n, t) {
- function e(n, t) {
- var e = Math.sqrt(i - 2 * u * Math.sin(t)) / u;
- return [e * Math.sin(n *= u), o - e * Math.cos(n)]
- }
- var r = Math.sin(n),
- u = (r + Math.sin(t)) / 2,
- i = 1 + r * (2 * u - r),
- o = Math.sqrt(i) / u;
- return e.invert = function(n, t) {
- var e = o - t;
- return [Math.atan2(n, e) / u, tt((i - (n * n + e * e) * u * u) / (2 * u))]
- }, e
- }
-
- function Ve() {
- function n(n, t) {
- Dc += u * n - r * t, r = n, u = t
- }
- var t, e, r, u;
- Hc.point = function(i, o) {
- Hc.point = n, t = r = i, e = u = o
- }, Hc.lineEnd = function() {
- n(t, e)
- }
- }
-
- function Xe(n, t) {
- Pc > n && (Pc = n), n > jc && (jc = n), Uc > t && (Uc = t), t > Fc && (Fc = t)
- }
-
- function $e() {
- function n(n, t) {
- o.push("M", n, ",", t, i)
- }
-
- function t(n, t) {
- o.push("M", n, ",", t), a.point = e
- }
-
- function e(n, t) {
- o.push("L", n, ",", t)
- }
-
- function r() {
- a.point = n
- }
-
- function u() {
- o.push("Z")
- }
- var i = Be(4.5),
- o = [],
- a = {
- point: n,
- lineStart: function() {
- a.point = t
- },
- lineEnd: r,
- polygonStart: function() {
- a.lineEnd = u
- },
- polygonEnd: function() {
- a.lineEnd = r, a.point = n
- },
- pointRadius: function(n) {
- return i = Be(n), a
- },
- result: function() {
- if (o.length) {
- var n = o.join("");
- return o = [], n
- }
- }
- };
- return a
- }
-
- function Be(n) {
- return "m0," + n + "a" + n + "," + n + " 0 1,1 0," + -2 * n + "a" + n + "," + n + " 0 1,1 0," + 2 * n + "z"
- }
-
- function We(n, t) {
- _c += n, wc += t, ++Sc
- }
-
- function Je() {
- function n(n, r) {
- var u = n - t,
- i = r - e,
- o = Math.sqrt(u * u + i * i);
- kc += o * (t + n) / 2, Ec += o * (e + r) / 2, Ac += o, We(t = n, e = r)
- }
- var t, e;
- Ic.point = function(r, u) {
- Ic.point = n, We(t = r, e = u)
- }
- }
-
- function Ge() {
- Ic.point = We
- }
-
- function Ke() {
- function n(n, t) {
- var e = n - r,
- i = t - u,
- o = Math.sqrt(e * e + i * i);
- kc += o * (r + n) / 2, Ec += o * (u + t) / 2, Ac += o, o = u * n - r * t, Nc += o * (r + n), Cc += o * (u + t), zc += 3 * o, We(r = n, u = t)
- }
- var t, e, r, u;
- Ic.point = function(i, o) {
- Ic.point = n, We(t = r = i, e = u = o)
- }, Ic.lineEnd = function() {
- n(t, e)
- }
- }
-
- function Qe(n) {
- function t(t, e) {
- n.moveTo(t + o, e), n.arc(t, e, o, 0, La)
- }
-
- function e(t, e) {
- n.moveTo(t, e), a.point = r
- }
-
- function r(t, e) {
- n.lineTo(t, e)
- }
-
- function u() {
- a.point = t
- }
-
- function i() {
- n.closePath()
- }
- var o = 4.5,
- a = {
- point: t,
- lineStart: function() {
- a.point = e
- },
- lineEnd: u,
- polygonStart: function() {
- a.lineEnd = i
- },
- polygonEnd: function() {
- a.lineEnd = u, a.point = t
- },
- pointRadius: function(n) {
- return o = n, a
- },
- result: b
- };
- return a
- }
-
- function nr(n) {
- function t(n) {
- return (a ? r : e)(n)
- }
-
- function e(t) {
- return rr(t, function(e, r) {
- e = n(e, r), t.point(e[0], e[1])
- })
- }
-
- function r(t) {
- function e(e, r) {
- e = n(e, r), t.point(e[0], e[1])
- }
-
- function r() {
- M = 0 / 0, S.point = i, t.lineStart()
- }
-
- function i(e, r) {
- var i = pe([e, r]),
- o = n(e, r);
- u(M, x, y, b, _, w, M = o[0], x = o[1], y = e, b = i[0], _ = i[1], w = i[2], a, t), t.point(M, x)
- }
-
- function o() {
- S.point = e, t.lineEnd()
- }
-
- function c() {
- r(), S.point = l, S.lineEnd = s
- }
-
- function l(n, t) {
- i(f = n, h = t), g = M, p = x, v = b, d = _, m = w, S.point = i
- }
-
- function s() {
- u(M, x, y, b, _, w, g, p, f, v, d, m, a, t), S.lineEnd = o, o()
- }
- var f, h, g, p, v, d, m, y, M, x, b, _, w, S = {
- point: e,
- lineStart: r,
- lineEnd: o,
- polygonStart: function() {
- t.polygonStart(), S.lineStart = c
- },
- polygonEnd: function() {
- t.polygonEnd(), S.lineStart = r
- }
- };
- return S
- }
-
- function u(t, e, r, a, c, l, s, f, h, g, p, v, d, m) {
- var y = s - t,
- M = f - e,
- x = y * y + M * M;
- if (x > 4 * i && d--) {
- var b = a + g,
- _ = c + p,
- w = l + v,
- S = Math.sqrt(b * b + _ * _ + w * w),
- k = Math.asin(w /= S),
- E = ga(ga(w) - 1) < Ca || ga(r - h) < Ca ? (r + h) / 2 : Math.atan2(_, b),
- A = n(E, k),
- N = A[0],
- C = A[1],
- z = N - t,
- q = C - e,
- L = M * z - y * q;
- (L * L / x > i || ga((y * z + M * q) / x - .5) > .3 || o > a * g + c * p + l * v) && (u(t, e, r, a, c, l, N, C, E, b /= S, _ /= S, w, d, m), m.point(N, C), u(N, C, E, b, _, w, s, f, h, g, p, v, d, m))
- }
- }
- var i = .5,
- o = Math.cos(30 * Da),
- a = 16;
- return t.precision = function(n) {
- return arguments.length ? (a = (i = n * n) > 0 && 16, t) : Math.sqrt(i)
- }, t
- }
-
- function tr(n) {
- var t = nr(function(t, e) {
- return n([t * Pa, e * Pa])
- });
- return function(n) {
- return or(t(n))
- }
- }
-
- function er(n) {
- this.stream = n
- }
-
- function rr(n, t) {
- return {
- point: t,
- sphere: function() {
- n.sphere()
- },
- lineStart: function() {
- n.lineStart()
- },
- lineEnd: function() {
- n.lineEnd()
- },
- polygonStart: function() {
- n.polygonStart()
- },
- polygonEnd: function() {
- n.polygonEnd()
- }
- }
- }
-
- function ur(n) {
- return ir(function() {
- return n
- })()
- }
-
- function ir(n) {
- function t(n) {
- return n = a(n[0] * Da, n[1] * Da), [n[0] * h + c, l - n[1] * h]
- }
-
- function e(n) {
- return n = a.invert((n[0] - c) / h, (l - n[1]) / h), n && [n[0] * Pa, n[1] * Pa]
- }
-
- function r() {
- a = Ae(o = lr(m, M, x), i);
- var n = i(v, d);
- return c = g - n[0] * h, l = p + n[1] * h, u()
- }
-
- function u() {
- return s && (s.valid = !1, s = null), t
- }
- var i, o, a, c, l, s, f = nr(function(n, t) {
- return n = i(n, t), [n[0] * h + c, l - n[1] * h]
- }),
- h = 150,
- g = 480,
- p = 250,
- v = 0,
- d = 0,
- m = 0,
- M = 0,
- x = 0,
- b = Lc,
- _ = y,
- w = null,
- S = null;
- return t.stream = function(n) {
- return s && (s.valid = !1), s = or(b(o, f(_(n)))), s.valid = !0, s
- }, t.clipAngle = function(n) {
- return arguments.length ? (b = null == n ? (w = n, Lc) : He((w = +n) * Da), u()) : w
- }, t.clipExtent = function(n) {
- return arguments.length ? (S = n, _ = n ? Ie(n[0][0], n[0][1], n[1][0], n[1][1]) : y, u()) : S
- }, t.scale = function(n) {
- return arguments.length ? (h = +n, r()) : h
- }, t.translate = function(n) {
- return arguments.length ? (g = +n[0], p = +n[1], r()) : [g, p]
- }, t.center = function(n) {
- return arguments.length ? (v = n[0] % 360 * Da, d = n[1] % 360 * Da, r()) : [v * Pa, d * Pa]
- }, t.rotate = function(n) {
- return arguments.length ? (m = n[0] % 360 * Da, M = n[1] % 360 * Da, x = n.length > 2 ? n[2] % 360 * Da : 0, r()) : [m * Pa, M * Pa, x * Pa]
- }, ta.rebind(t, f, "precision"),
- function() {
- return i = n.apply(this, arguments), t.invert = i.invert && e, r()
- }
- }
-
- function or(n) {
- return rr(n, function(t, e) {
- n.point(t * Da, e * Da)
- })
- }
-
- function ar(n, t) {
- return [n, t]
- }
-
- function cr(n, t) {
- return [n > qa ? n - La : -qa > n ? n + La : n, t]
- }
-
- function lr(n, t, e) {
- return n ? t || e ? Ae(fr(n), hr(t, e)) : fr(n) : t || e ? hr(t, e) : cr
- }
-
- function sr(n) {
- return function(t, e) {
- return t += n, [t > qa ? t - La : -qa > t ? t + La : t, e]
- }
- }
-
- function fr(n) {
- var t = sr(n);
- return t.invert = sr(-n), t
- }
-
- function hr(n, t) {
- function e(n, t) {
- var e = Math.cos(t),
- a = Math.cos(n) * e,
- c = Math.sin(n) * e,
- l = Math.sin(t),
- s = l * r + a * u;
- return [Math.atan2(c * i - s * o, a * r - l * u), tt(s * i + c * o)]
- }
- var r = Math.cos(n),
- u = Math.sin(n),
- i = Math.cos(t),
- o = Math.sin(t);
- return e.invert = function(n, t) {
- var e = Math.cos(t),
- a = Math.cos(n) * e,
- c = Math.sin(n) * e,
- l = Math.sin(t),
- s = l * i - c * o;
- return [Math.atan2(c * i + l * o, a * r + s * u), tt(s * r - a * u)]
- }, e
- }
-
- function gr(n, t) {
- var e = Math.cos(n),
- r = Math.sin(n);
- return function(u, i, o, a) {
- var c = o * t;
- null != u ? (u = pr(e, u), i = pr(e, i), (o > 0 ? i > u : u > i) && (u += o * La)) : (u = n + o * La, i = n - .5 * c);
- for (var l, s = u; o > 0 ? s > i : i > s; s -= c) a.point((l = xe([e, -r * Math.cos(s), -r * Math.sin(s)]))[0], l[1])
- }
- }
-
- function pr(n, t) {
- var e = pe(t);
- e[0] -= n, Me(e);
- var r = nt(-e[1]);
- return ((-e[2] < 0 ? -r : r) + 2 * Math.PI - Ca) % (2 * Math.PI)
- }
-
- function vr(n, t, e) {
- var r = ta.range(n, t - Ca, e).concat(t);
- return function(n) {
- return r.map(function(t) {
- return [n, t]
- })
- }
- }
-
- function dr(n, t, e) {
- var r = ta.range(n, t - Ca, e).concat(t);
- return function(n) {
- return r.map(function(t) {
- return [t, n]
- })
- }
- }
-
- function mr(n) {
- return n.source
- }
-
- function yr(n) {
- return n.target
- }
-
- function Mr(n, t, e, r) {
- var u = Math.cos(t),
- i = Math.sin(t),
- o = Math.cos(r),
- a = Math.sin(r),
- c = u * Math.cos(n),
- l = u * Math.sin(n),
- s = o * Math.cos(e),
- f = o * Math.sin(e),
- h = 2 * Math.asin(Math.sqrt(it(r - t) + u * o * it(e - n))),
- g = 1 / Math.sin(h),
- p = h ? function(n) {
- var t = Math.sin(n *= h) * g,
- e = Math.sin(h - n) * g,
- r = e * c + t * s,
- u = e * l + t * f,
- o = e * i + t * a;
- return [Math.atan2(u, r) * Pa, Math.atan2(o, Math.sqrt(r * r + u * u)) * Pa]
- } : function() {
- return [n * Pa, t * Pa]
- };
- return p.distance = h, p
- }
-
- function xr() {
- function n(n, u) {
- var i = Math.sin(u *= Da),
- o = Math.cos(u),
- a = ga((n *= Da) - t),
- c = Math.cos(a);
- Yc += Math.atan2(Math.sqrt((a = o * Math.sin(a)) * a + (a = r * i - e * o * c) * a), e * i + r * o * c), t = n, e = i, r = o
- }
- var t, e, r;
- Zc.point = function(u, i) {
- t = u * Da, e = Math.sin(i *= Da), r = Math.cos(i), Zc.point = n
- }, Zc.lineEnd = function() {
- Zc.point = Zc.lineEnd = b
- }
- }
-
- function br(n, t) {
- function e(t, e) {
- var r = Math.cos(t),
- u = Math.cos(e),
- i = n(r * u);
- return [i * u * Math.sin(t), i * Math.sin(e)]
- }
- return e.invert = function(n, e) {
- var r = Math.sqrt(n * n + e * e),
- u = t(r),
- i = Math.sin(u),
- o = Math.cos(u);
- return [Math.atan2(n * i, r * o), Math.asin(r && e * i / r)]
- }, e
- }
-
- function _r(n, t) {
- function e(n, t) {
- o > 0 ? -Ra + Ca > t && (t = -Ra + Ca) : t > Ra - Ca && (t = Ra - Ca);
- var e = o / Math.pow(u(t), i);
- return [e * Math.sin(i * n), o - e * Math.cos(i * n)]
- }
- var r = Math.cos(n),
- u = function(n) {
- return Math.tan(qa / 4 + n / 2)
- },
- i = n === t ? Math.sin(n) : Math.log(r / Math.cos(t)) / Math.log(u(t) / u(n)),
- o = r * Math.pow(u(n), i) / i;
- return i ? (e.invert = function(n, t) {
- var e = o - t,
- r = K(i) * Math.sqrt(n * n + e * e);
- return [Math.atan2(n, e) / i, 2 * Math.atan(Math.pow(o / r, 1 / i)) - Ra]
- }, e) : Sr
- }
-
- function wr(n, t) {
- function e(n, t) {
- var e = i - t;
- return [e * Math.sin(u * n), i - e * Math.cos(u * n)]
- }
- var r = Math.cos(n),
- u = n === t ? Math.sin(n) : (r - Math.cos(t)) / (t - n),
- i = r / u + n;
- return ga(u) < Ca ? ar : (e.invert = function(n, t) {
- var e = i - t;
- return [Math.atan2(n, e) / u, i - K(u) * Math.sqrt(n * n + e * e)]
- }, e)
- }
-
- function Sr(n, t) {
- return [n, Math.log(Math.tan(qa / 4 + t / 2))]
- }
-
- function kr(n) {
- var t, e = ur(n),
- r = e.scale,
- u = e.translate,
- i = e.clipExtent;
- return e.scale = function() {
- var n = r.apply(e, arguments);
- return n === e ? t ? e.clipExtent(null) : e : n
- }, e.translate = function() {
- var n = u.apply(e, arguments);
- return n === e ? t ? e.clipExtent(null) : e : n
- }, e.clipExtent = function(n) {
- var o = i.apply(e, arguments);
- if (o === e) {
- if (t = null == n) {
- var a = qa * r(),
- c = u();
- i([
- [c[0] - a, c[1] - a],
- [c[0] + a, c[1] + a]
- ])
- }
- } else t && (o = null);
- return o
- }, e.clipExtent(null)
- }
-
- function Er(n, t) {
- return [Math.log(Math.tan(qa / 4 + t / 2)), -n]
- }
-
- function Ar(n) {
- return n[0]
- }
-
- function Nr(n) {
- return n[1]
- }
-
- function Cr(n) {
- for (var t = n.length, e = [0, 1], r = 2, u = 2; t > u; u++) {
- for (; r > 1 && Q(n[e[r - 2]], n[e[r - 1]], n[u]) <= 0;) --r;
- e[r++] = u
- }
- return e.slice(0, r)
- }
-
- function zr(n, t) {
- return n[0] - t[0] || n[1] - t[1]
- }
-
- function qr(n, t, e) {
- return (e[0] - t[0]) * (n[1] - t[1]) < (e[1] - t[1]) * (n[0] - t[0])
- }
-
- function Lr(n, t, e, r) {
- var u = n[0],
- i = e[0],
- o = t[0] - u,
- a = r[0] - i,
- c = n[1],
- l = e[1],
- s = t[1] - c,
- f = r[1] - l,
- h = (a * (c - l) - f * (u - i)) / (f * o - a * s);
- return [u + h * o, c + h * s]
- }
-
- function Tr(n) {
- var t = n[0],
- e = n[n.length - 1];
- return !(t[0] - e[0] || t[1] - e[1])
- }
-
- function Rr() {
- tu(this), this.edge = this.site = this.circle = null
- }
-
- function Dr(n) {
- var t = el.pop() || new Rr;
- return t.site = n, t
- }
-
- function Pr(n) {
- Xr(n), Qc.remove(n), el.push(n), tu(n)
- }
-
- function Ur(n) {
- var t = n.circle,
- e = t.x,
- r = t.cy,
- u = {
- x: e,
- y: r
- },
- i = n.P,
- o = n.N,
- a = [n];
- Pr(n);
- for (var c = i; c.circle && ga(e - c.circle.x) < Ca && ga(r - c.circle.cy) < Ca;) i = c.P, a.unshift(c), Pr(c), c = i;
- a.unshift(c), Xr(c);
- for (var l = o; l.circle && ga(e - l.circle.x) < Ca && ga(r - l.circle.cy) < Ca;) o = l.N, a.push(l), Pr(l), l = o;
- a.push(l), Xr(l);
- var s, f = a.length;
- for (s = 1; f > s; ++s) l = a[s], c = a[s - 1], Kr(l.edge, c.site, l.site, u);
- c = a[0], l = a[f - 1], l.edge = Jr(c.site, l.site, null, u), Vr(c), Vr(l)
- }
-
- function jr(n) {
- for (var t, e, r, u, i = n.x, o = n.y, a = Qc._; a;)
- if (r = Fr(a, o) - i, r > Ca) a = a.L;
- else {
- if (u = i - Hr(a, o), !(u > Ca)) {
- r > -Ca ? (t = a.P, e = a) : u > -Ca ? (t = a, e = a.N) : t = e = a;
- break
- }
- if (!a.R) {
- t = a;
- break
- }
- a = a.R
- } var c = Dr(n);
- if (Qc.insert(t, c), t || e) {
- if (t === e) return Xr(t), e = Dr(t.site), Qc.insert(c, e), c.edge = e.edge = Jr(t.site, c.site), Vr(t), void Vr(e);
- if (!e) return void(c.edge = Jr(t.site, c.site));
- Xr(t), Xr(e);
- var l = t.site,
- s = l.x,
- f = l.y,
- h = n.x - s,
- g = n.y - f,
- p = e.site,
- v = p.x - s,
- d = p.y - f,
- m = 2 * (h * d - g * v),
- y = h * h + g * g,
- M = v * v + d * d,
- x = {
- x: (d * y - g * M) / m + s,
- y: (h * M - v * y) / m + f
- };
- Kr(e.edge, l, p, x), c.edge = Jr(l, n, null, x), e.edge = Jr(n, p, null, x), Vr(t), Vr(e)
- }
- }
-
- function Fr(n, t) {
- var e = n.site,
- r = e.x,
- u = e.y,
- i = u - t;
- if (!i) return r;
- var o = n.P;
- if (!o) return -1 / 0;
- e = o.site;
- var a = e.x,
- c = e.y,
- l = c - t;
- if (!l) return a;
- var s = a - r,
- f = 1 / i - 1 / l,
- h = s / l;
- return f ? (-h + Math.sqrt(h * h - 2 * f * (s * s / (-2 * l) - c + l / 2 + u - i / 2))) / f + r : (r + a) / 2
- }
-
- function Hr(n, t) {
- var e = n.N;
- if (e) return Fr(e, t);
- var r = n.site;
- return r.y === t ? r.x : 1 / 0
- }
-
- function Or(n) {
- this.site = n, this.edges = []
- }
-
- function Ir(n) {
- for (var t, e, r, u, i, o, a, c, l, s, f = n[0][0], h = n[1][0], g = n[0][1], p = n[1][1], v = Kc, d = v.length; d--;)
- if (i = v[d], i && i.prepare())
- for (a = i.edges, c = a.length, o = 0; c > o;) s = a[o].end(), r = s.x, u = s.y, l = a[++o % c].start(), t = l.x, e = l.y, (ga(r - t) > Ca || ga(u - e) > Ca) && (a.splice(o, 0, new Qr(Gr(i.site, s, ga(r - f) < Ca && p - u > Ca ? {
- x: f,
- y: ga(t - f) < Ca ? e : p
- } : ga(u - p) < Ca && h - r > Ca ? {
- x: ga(e - p) < Ca ? t : h,
- y: p
- } : ga(r - h) < Ca && u - g > Ca ? {
- x: h,
- y: ga(t - h) < Ca ? e : g
- } : ga(u - g) < Ca && r - f > Ca ? {
- x: ga(e - g) < Ca ? t : f,
- y: g
- } : null), i.site, null)), ++c)
- }
-
- function Yr(n, t) {
- return t.angle - n.angle
- }
-
- function Zr() {
- tu(this), this.x = this.y = this.arc = this.site = this.cy = null
- }
-
- function Vr(n) {
- var t = n.P,
- e = n.N;
- if (t && e) {
- var r = t.site,
- u = n.site,
- i = e.site;
- if (r !== i) {
- var o = u.x,
- a = u.y,
- c = r.x - o,
- l = r.y - a,
- s = i.x - o,
- f = i.y - a,
- h = 2 * (c * f - l * s);
- if (!(h >= -za)) {
- var g = c * c + l * l,
- p = s * s + f * f,
- v = (f * g - l * p) / h,
- d = (c * p - s * g) / h,
- f = d + a,
- m = rl.pop() || new Zr;
- m.arc = n, m.site = u, m.x = v + o, m.y = f + Math.sqrt(v * v + d * d), m.cy = f, n.circle = m;
- for (var y = null, M = tl._; M;)
- if (m.y < M.y || m.y === M.y && m.x <= M.x) {
- if (!M.L) {
- y = M.P;
- break
- }
- M = M.L
- } else {
- if (!M.R) {
- y = M;
- break
- }
- M = M.R
- } tl.insert(y, m), y || (nl = m)
- }
- }
- }
- }
-
- function Xr(n) {
- var t = n.circle;
- t && (t.P || (nl = t.N), tl.remove(t), rl.push(t), tu(t), n.circle = null)
- }
-
- function $r(n) {
- for (var t, e = Gc, r = Oe(n[0][0], n[0][1], n[1][0], n[1][1]), u = e.length; u--;) t = e[u], (!Br(t, n) || !r(t) || ga(t.a.x - t.b.x) < Ca && ga(t.a.y - t.b.y) < Ca) && (t.a = t.b = null, e.splice(u, 1))
- }
-
- function Br(n, t) {
- var e = n.b;
- if (e) return !0;
- var r, u, i = n.a,
- o = t[0][0],
- a = t[1][0],
- c = t[0][1],
- l = t[1][1],
- s = n.l,
- f = n.r,
- h = s.x,
- g = s.y,
- p = f.x,
- v = f.y,
- d = (h + p) / 2,
- m = (g + v) / 2;
- if (v === g) {
- if (o > d || d >= a) return;
- if (h > p) {
- if (i) {
- if (i.y >= l) return
- } else i = {
- x: d,
- y: c
- };
- e = {
- x: d,
- y: l
- }
- } else {
- if (i) {
- if (i.y < c) return
- } else i = {
- x: d,
- y: l
- };
- e = {
- x: d,
- y: c
- }
- }
- } else if (r = (h - p) / (v - g), u = m - r * d, -1 > r || r > 1)
- if (h > p) {
- if (i) {
- if (i.y >= l) return
- } else i = {
- x: (c - u) / r,
- y: c
- };
- e = {
- x: (l - u) / r,
- y: l
- }
- } else {
- if (i) {
- if (i.y < c) return
- } else i = {
- x: (l - u) / r,
- y: l
- };
- e = {
- x: (c - u) / r,
- y: c
- }
- }
- else if (v > g) {
- if (i) {
- if (i.x >= a) return
- } else i = {
- x: o,
- y: r * o + u
- };
- e = {
- x: a,
- y: r * a + u
- }
- } else {
- if (i) {
- if (i.x < o) return
- } else i = {
- x: a,
- y: r * a + u
- };
- e = {
- x: o,
- y: r * o + u
- }
- }
- return n.a = i, n.b = e, !0
- }
-
- function Wr(n, t) {
- this.l = n, this.r = t, this.a = this.b = null
- }
-
- function Jr(n, t, e, r) {
- var u = new Wr(n, t);
- return Gc.push(u), e && Kr(u, n, t, e), r && Kr(u, t, n, r), Kc[n.i].edges.push(new Qr(u, n, t)), Kc[t.i].edges.push(new Qr(u, t, n)), u
- }
-
- function Gr(n, t, e) {
- var r = new Wr(n, null);
- return r.a = t, r.b = e, Gc.push(r), r
- }
-
- function Kr(n, t, e, r) {
- n.a || n.b ? n.l === e ? n.b = r : n.a = r : (n.a = r, n.l = t, n.r = e)
- }
-
- function Qr(n, t, e) {
- var r = n.a,
- u = n.b;
- this.edge = n, this.site = t, this.angle = e ? Math.atan2(e.y - t.y, e.x - t.x) : n.l === t ? Math.atan2(u.x - r.x, r.y - u.y) : Math.atan2(r.x - u.x, u.y - r.y)
- }
-
- function nu() {
- this._ = null
- }
-
- function tu(n) {
- n.U = n.C = n.L = n.R = n.P = n.N = null
- }
-
- function eu(n, t) {
- var e = t,
- r = t.R,
- u = e.U;
- u ? u.L === e ? u.L = r : u.R = r : n._ = r, r.U = u, e.U = r, e.R = r.L, e.R && (e.R.U = e), r.L = e
- }
-
- function ru(n, t) {
- var e = t,
- r = t.L,
- u = e.U;
- u ? u.L === e ? u.L = r : u.R = r : n._ = r, r.U = u, e.U = r, e.L = r.R, e.L && (e.L.U = e), r.R = e
- }
-
- function uu(n) {
- for (; n.L;) n = n.L;
- return n
- }
-
- function iu(n, t) {
- var e, r, u, i = n.sort(ou).pop();
- for (Gc = [], Kc = new Array(n.length), Qc = new nu, tl = new nu;;)
- if (u = nl, i && (!u || i.y < u.y || i.y === u.y && i.x < u.x))(i.x !== e || i.y !== r) && (Kc[i.i] = new Or(i), jr(i), e = i.x, r = i.y), i = n.pop();
- else {
- if (!u) break;
- Ur(u.arc)
- } t && ($r(t), Ir(t));
- var o = {
- cells: Kc,
- edges: Gc
- };
- return Qc = tl = Gc = Kc = null, o
- }
-
- function ou(n, t) {
- return t.y - n.y || t.x - n.x
- }
-
- function au(n, t, e) {
- return (n.x - e.x) * (t.y - n.y) - (n.x - t.x) * (e.y - n.y)
- }
-
- function cu(n) {
- return n.x
- }
-
- function lu(n) {
- return n.y
- }
-
- function su() {
- return {
- leaf: !0,
- nodes: [],
- point: null,
- x: null,
- y: null
- }
- }
-
- function fu(n, t, e, r, u, i) {
- if (!n(t, e, r, u, i)) {
- var o = .5 * (e + u),
- a = .5 * (r + i),
- c = t.nodes;
- c[0] && fu(n, c[0], e, r, o, a), c[1] && fu(n, c[1], o, r, u, a), c[2] && fu(n, c[2], e, a, o, i), c[3] && fu(n, c[3], o, a, u, i)
- }
- }
-
- function hu(n, t, e, r, u, i, o) {
- var a, c = 1 / 0;
- return function l(n, s, f, h, g) {
- if (!(s > i || f > o || r > h || u > g)) {
- if (p = n.point) {
- var p, v = t - n.x,
- d = e - n.y,
- m = v * v + d * d;
- if (c > m) {
- var y = Math.sqrt(c = m);
- r = t - y, u = e - y, i = t + y, o = e + y, a = p
- }
- }
- for (var M = n.nodes, x = .5 * (s + h), b = .5 * (f + g), _ = t >= x, w = e >= b, S = w << 1 | _, k = S + 4; k > S; ++S)
- if (n = M[3 & S]) switch (3 & S) {
- case 0:
- l(n, s, f, x, b);
- break;
- case 1:
- l(n, x, f, h, b);
- break;
- case 2:
- l(n, s, b, x, g);
- break;
- case 3:
- l(n, x, b, h, g)
- }
- }
- }(n, r, u, i, o), a
- }
-
- function gu(n, t) {
- n = ta.rgb(n), t = ta.rgb(t);
- var e = n.r,
- r = n.g,
- u = n.b,
- i = t.r - e,
- o = t.g - r,
- a = t.b - u;
- return function(n) {
- return "#" + xt(Math.round(e + i * n)) + xt(Math.round(r + o * n)) + xt(Math.round(u + a * n))
- }
- }
-
- function pu(n, t) {
- var e, r = {},
- u = {};
- for (e in n) e in t ? r[e] = mu(n[e], t[e]) : u[e] = n[e];
- for (e in t) e in n || (u[e] = t[e]);
- return function(n) {
- for (e in r) u[e] = r[e](n);
- return u
- }
- }
-
- function vu(n, t) {
- return n = +n, t = +t,
- function(e) {
- return n * (1 - e) + t * e
- }
- }
-
- function du(n, t) {
- var e, r, u, i = il.lastIndex = ol.lastIndex = 0,
- o = -1,
- a = [],
- c = [];
- for (n += "", t += "";
- (e = il.exec(n)) && (r = ol.exec(t));)(u = r.index) > i && (u = t.slice(i, u), a[o] ? a[o] += u : a[++o] = u), (e = e[0]) === (r = r[0]) ? a[o] ? a[o] += r : a[++o] = r : (a[++o] = null, c.push({
- i: o,
- x: vu(e, r)
- })), i = ol.lastIndex;
- return i < t.length && (u = t.slice(i), a[o] ? a[o] += u : a[++o] = u), a.length < 2 ? c[0] ? (t = c[0].x, function(n) {
- return t(n) + ""
- }) : function() {
- return t
- } : (t = c.length, function(n) {
- for (var e, r = 0; t > r; ++r) a[(e = c[r]).i] = e.x(n);
- return a.join("")
- })
- }
-
- function mu(n, t) {
- for (var e, r = ta.interpolators.length; --r >= 0 && !(e = ta.interpolators[r](n, t)););
- return e
- }
-
- function yu(n, t) {
- var e, r = [],
- u = [],
- i = n.length,
- o = t.length,
- a = Math.min(n.length, t.length);
- for (e = 0; a > e; ++e) r.push(mu(n[e], t[e]));
- for (; i > e; ++e) u[e] = n[e];
- for (; o > e; ++e) u[e] = t[e];
- return function(n) {
- for (e = 0; a > e; ++e) u[e] = r[e](n);
- return u
- }
- }
-
- function Mu(n) {
- return function(t) {
- return 0 >= t ? 0 : t >= 1 ? 1 : n(t)
- }
- }
-
- function xu(n) {
- return function(t) {
- return 1 - n(1 - t)
- }
- }
-
- function bu(n) {
- return function(t) {
- return .5 * (.5 > t ? n(2 * t) : 2 - n(2 - 2 * t))
- }
- }
-
- function _u(n) {
- return n * n
- }
-
- function wu(n) {
- return n * n * n
- }
-
- function Su(n) {
- if (0 >= n) return 0;
- if (n >= 1) return 1;
- var t = n * n,
- e = t * n;
- return 4 * (.5 > n ? e : 3 * (n - t) + e - .75)
- }
-
- function ku(n) {
- return function(t) {
- return Math.pow(t, n)
- }
- }
-
- function Eu(n) {
- return 1 - Math.cos(n * Ra)
- }
-
- function Au(n) {
- return Math.pow(2, 10 * (n - 1))
- }
-
- function Nu(n) {
- return 1 - Math.sqrt(1 - n * n)
- }
-
- function Cu(n, t) {
- var e;
- return arguments.length < 2 && (t = .45), arguments.length ? e = t / La * Math.asin(1 / n) : (n = 1, e = t / 4),
- function(r) {
- return 1 + n * Math.pow(2, -10 * r) * Math.sin((r - e) * La / t)
- }
- }
-
- function zu(n) {
- return n || (n = 1.70158),
- function(t) {
- return t * t * ((n + 1) * t - n)
- }
- }
-
- function qu(n) {
- return 1 / 2.75 > n ? 7.5625 * n * n : 2 / 2.75 > n ? 7.5625 * (n -= 1.5 / 2.75) * n + .75 : 2.5 / 2.75 > n ? 7.5625 * (n -= 2.25 / 2.75) * n + .9375 : 7.5625 * (n -= 2.625 / 2.75) * n + .984375
- }
-
- function Lu(n, t) {
- n = ta.hcl(n), t = ta.hcl(t);
- var e = n.h,
- r = n.c,
- u = n.l,
- i = t.h - e,
- o = t.c - r,
- a = t.l - u;
- return isNaN(o) && (o = 0, r = isNaN(r) ? t.c : r), isNaN(i) ? (i = 0, e = isNaN(e) ? t.h : e) : i > 180 ? i -= 360 : -180 > i && (i += 360),
- function(n) {
- return st(e + i * n, r + o * n, u + a * n) + ""
- }
- }
-
- function Tu(n, t) {
- n = ta.hsl(n), t = ta.hsl(t);
- var e = n.h,
- r = n.s,
- u = n.l,
- i = t.h - e,
- o = t.s - r,
- a = t.l - u;
- return isNaN(o) && (o = 0, r = isNaN(r) ? t.s : r), isNaN(i) ? (i = 0, e = isNaN(e) ? t.h : e) : i > 180 ? i -= 360 : -180 > i && (i += 360),
- function(n) {
- return ct(e + i * n, r + o * n, u + a * n) + ""
- }
- }
-
- function Ru(n, t) {
- n = ta.lab(n), t = ta.lab(t);
- var e = n.l,
- r = n.a,
- u = n.b,
- i = t.l - e,
- o = t.a - r,
- a = t.b - u;
- return function(n) {
- return ht(e + i * n, r + o * n, u + a * n) + ""
- }
- }
-
- function Du(n, t) {
- return t -= n,
- function(e) {
- return Math.round(n + t * e)
- }
- }
-
- function Pu(n) {
- var t = [n.a, n.b],
- e = [n.c, n.d],
- r = ju(t),
- u = Uu(t, e),
- i = ju(Fu(e, t, -u)) || 0;
- t[0] * e[1] < e[0] * t[1] && (t[0] *= -1, t[1] *= -1, r *= -1, u *= -1), this.rotate = (r ? Math.atan2(t[1], t[0]) : Math.atan2(-e[0], e[1])) * Pa, this.translate = [n.e, n.f], this.scale = [r, i], this.skew = i ? Math.atan2(u, i) * Pa : 0
- }
-
- function Uu(n, t) {
- return n[0] * t[0] + n[1] * t[1]
- }
-
- function ju(n) {
- var t = Math.sqrt(Uu(n, n));
- return t && (n[0] /= t, n[1] /= t), t
- }
-
- function Fu(n, t, e) {
- return n[0] += e * t[0], n[1] += e * t[1], n
- }
-
- function Hu(n, t) {
- var e, r = [],
- u = [],
- i = ta.transform(n),
- o = ta.transform(t),
- a = i.translate,
- c = o.translate,
- l = i.rotate,
- s = o.rotate,
- f = i.skew,
- h = o.skew,
- g = i.scale,
- p = o.scale;
- return a[0] != c[0] || a[1] != c[1] ? (r.push("translate(", null, ",", null, ")"), u.push({
- i: 1,
- x: vu(a[0], c[0])
- }, {
- i: 3,
- x: vu(a[1], c[1])
- })) : r.push(c[0] || c[1] ? "translate(" + c + ")" : ""), l != s ? (l - s > 180 ? s += 360 : s - l > 180 && (l += 360), u.push({
- i: r.push(r.pop() + "rotate(", null, ")") - 2,
- x: vu(l, s)
- })) : s && r.push(r.pop() + "rotate(" + s + ")"), f != h ? u.push({
- i: r.push(r.pop() + "skewX(", null, ")") - 2,
- x: vu(f, h)
- }) : h && r.push(r.pop() + "skewX(" + h + ")"), g[0] != p[0] || g[1] != p[1] ? (e = r.push(r.pop() + "scale(", null, ",", null, ")"), u.push({
- i: e - 4,
- x: vu(g[0], p[0])
- }, {
- i: e - 2,
- x: vu(g[1], p[1])
- })) : (1 != p[0] || 1 != p[1]) && r.push(r.pop() + "scale(" + p + ")"), e = u.length,
- function(n) {
- for (var t, i = -1; ++i < e;) r[(t = u[i]).i] = t.x(n);
- return r.join("")
- }
- }
-
- function Ou(n, t) {
- return t = (t -= n = +n) || 1 / t,
- function(e) {
- return (e - n) / t
- }
- }
-
- function Iu(n, t) {
- return t = (t -= n = +n) || 1 / t,
- function(e) {
- return Math.max(0, Math.min(1, (e - n) / t))
- }
- }
-
- function Yu(n) {
- for (var t = n.source, e = n.target, r = Vu(t, e), u = [t]; t !== r;) t = t.parent, u.push(t);
- for (var i = u.length; e !== r;) u.splice(i, 0, e), e = e.parent;
- return u
- }
-
- function Zu(n) {
- for (var t = [], e = n.parent; null != e;) t.push(n), n = e, e = e.parent;
- return t.push(n), t
- }
-
- function Vu(n, t) {
- if (n === t) return n;
- for (var e = Zu(n), r = Zu(t), u = e.pop(), i = r.pop(), o = null; u === i;) o = u, u = e.pop(), i = r.pop();
- return o
- }
-
- function Xu(n) {
- n.fixed |= 2
- }
-
- function $u(n) {
- n.fixed &= -7
- }
-
- function Bu(n) {
- n.fixed |= 4, n.px = n.x, n.py = n.y
- }
-
- function Wu(n) {
- n.fixed &= -5
- }
-
- function Ju(n, t, e) {
- var r = 0,
- u = 0;
- if (n.charge = 0, !n.leaf)
- for (var i, o = n.nodes, a = o.length, c = -1; ++c < a;) i = o[c], null != i && (Ju(i, t, e), n.charge += i.charge, r += i.charge * i.cx, u += i.charge * i.cy);
- if (n.point) {
- n.leaf || (n.point.x += Math.random() - .5, n.point.y += Math.random() - .5);
- var l = t * e[n.point.index];
- n.charge += n.pointCharge = l, r += l * n.point.x, u += l * n.point.y
- }
- n.cx = r / n.charge, n.cy = u / n.charge
- }
-
- function Gu(n, t) {
- return ta.rebind(n, t, "sort", "children", "value"), n.nodes = n, n.links = ri, n
- }
-
- function Ku(n, t) {
- for (var e = [n]; null != (n = e.pop());)
- if (t(n), (u = n.children) && (r = u.length))
- for (var r, u; --r >= 0;) e.push(u[r])
- }
-
- function Qu(n, t) {
- for (var e = [n], r = []; null != (n = e.pop());)
- if (r.push(n), (i = n.children) && (u = i.length))
- for (var u, i, o = -1; ++o < u;) e.push(i[o]);
- for (; null != (n = r.pop());) t(n)
- }
-
- function ni(n) {
- return n.children
- }
-
- function ti(n) {
- return n.value
- }
-
- function ei(n, t) {
- return t.value - n.value
- }
-
- function ri(n) {
- return ta.merge(n.map(function(n) {
- return (n.children || []).map(function(t) {
- return {
- source: n,
- target: t
- }
- })
- }))
- }
-
- function ui(n) {
- return n.x
- }
-
- function ii(n) {
- return n.y
- }
-
- function oi(n, t, e) {
- n.y0 = t, n.y = e
- }
-
- function ai(n) {
- return ta.range(n.length)
- }
-
- function ci(n) {
- for (var t = -1, e = n[0].length, r = []; ++t < e;) r[t] = 0;
- return r
- }
-
- function li(n) {
- for (var t, e = 1, r = 0, u = n[0][1], i = n.length; i > e; ++e)(t = n[e][1]) > u && (r = e, u = t);
- return r
- }
-
- function si(n) {
- return n.reduce(fi, 0)
- }
-
- function fi(n, t) {
- return n + t[1]
- }
-
- function hi(n, t) {
- return gi(n, Math.ceil(Math.log(t.length) / Math.LN2 + 1))
- }
-
- function gi(n, t) {
- for (var e = -1, r = +n[0], u = (n[1] - r) / t, i = []; ++e <= t;) i[e] = u * e + r;
- return i
- }
-
- function pi(n) {
- return [ta.min(n), ta.max(n)]
- }
-
- function vi(n, t) {
- return n.value - t.value
- }
-
- function di(n, t) {
- var e = n._pack_next;
- n._pack_next = t, t._pack_prev = n, t._pack_next = e, e._pack_prev = t
- }
-
- function mi(n, t) {
- n._pack_next = t, t._pack_prev = n
- }
-
- function yi(n, t) {
- var e = t.x - n.x,
- r = t.y - n.y,
- u = n.r + t.r;
- return .999 * u * u > e * e + r * r
- }
-
- function Mi(n) {
- function t(n) {
- s = Math.min(n.x - n.r, s), f = Math.max(n.x + n.r, f), h = Math.min(n.y - n.r, h), g = Math.max(n.y + n.r, g)
- }
- if ((e = n.children) && (l = e.length)) {
- var e, r, u, i, o, a, c, l, s = 1 / 0,
- f = -1 / 0,
- h = 1 / 0,
- g = -1 / 0;
- if (e.forEach(xi), r = e[0], r.x = -r.r, r.y = 0, t(r), l > 1 && (u = e[1], u.x = u.r, u.y = 0, t(u), l > 2))
- for (i = e[2], wi(r, u, i), t(i), di(r, i), r._pack_prev = i, di(i, u), u = r._pack_next, o = 3; l > o; o++) {
- wi(r, u, i = e[o]);
- var p = 0,
- v = 1,
- d = 1;
- for (a = u._pack_next; a !== u; a = a._pack_next, v++)
- if (yi(a, i)) {
- p = 1;
- break
- } if (1 == p)
- for (c = r._pack_prev; c !== a._pack_prev && !yi(c, i); c = c._pack_prev, d++);
- p ? (d > v || v == d && u.r < r.r ? mi(r, u = a) : mi(r = c, u), o--) : (di(r, i), u = i, t(i))
- }
- var m = (s + f) / 2,
- y = (h + g) / 2,
- M = 0;
- for (o = 0; l > o; o++) i = e[o], i.x -= m, i.y -= y, M = Math.max(M, i.r + Math.sqrt(i.x * i.x + i.y * i.y));
- n.r = M, e.forEach(bi)
- }
- }
-
- function xi(n) {
- n._pack_next = n._pack_prev = n
- }
-
- function bi(n) {
- delete n._pack_next, delete n._pack_prev
- }
-
- function _i(n, t, e, r) {
- var u = n.children;
- if (n.x = t += r * n.x, n.y = e += r * n.y, n.r *= r, u)
- for (var i = -1, o = u.length; ++i < o;) _i(u[i], t, e, r)
- }
-
- function wi(n, t, e) {
- var r = n.r + e.r,
- u = t.x - n.x,
- i = t.y - n.y;
- if (r && (u || i)) {
- var o = t.r + e.r,
- a = u * u + i * i;
- o *= o, r *= r;
- var c = .5 + (r - o) / (2 * a),
- l = Math.sqrt(Math.max(0, 2 * o * (r + a) - (r -= a) * r - o * o)) / (2 * a);
- e.x = n.x + c * u + l * i, e.y = n.y + c * i - l * u
- } else e.x = n.x + r, e.y = n.y
- }
-
- function Si(n, t) {
- return n.parent == t.parent ? 1 : 2
- }
-
- function ki(n) {
- var t = n.children;
- return t.length ? t[0] : n.t
- }
-
- function Ei(n) {
- var t, e = n.children;
- return (t = e.length) ? e[t - 1] : n.t
- }
-
- function Ai(n, t, e) {
- var r = e / (t.i - n.i);
- t.c -= r, t.s += e, n.c += r, t.z += e, t.m += e
- }
-
- function Ni(n) {
- for (var t, e = 0, r = 0, u = n.children, i = u.length; --i >= 0;) t = u[i], t.z += e, t.m += e, e += t.s + (r += t.c)
- }
-
- function Ci(n, t, e) {
- return n.a.parent === t.parent ? n.a : e
- }
-
- function zi(n) {
- return 1 + ta.max(n, function(n) {
- return n.y
- })
- }
-
- function qi(n) {
- return n.reduce(function(n, t) {
- return n + t.x
- }, 0) / n.length
- }
-
- function Li(n) {
- var t = n.children;
- return t && t.length ? Li(t[0]) : n
- }
-
- function Ti(n) {
- var t, e = n.children;
- return e && (t = e.length) ? Ti(e[t - 1]) : n
- }
-
- function Ri(n) {
- return {
- x: n.x,
- y: n.y,
- dx: n.dx,
- dy: n.dy
- }
- }
-
- function Di(n, t) {
- var e = n.x + t[3],
- r = n.y + t[0],
- u = n.dx - t[1] - t[3],
- i = n.dy - t[0] - t[2];
- return 0 > u && (e += u / 2, u = 0), 0 > i && (r += i / 2, i = 0), {
- x: e,
- y: r,
- dx: u,
- dy: i
- }
- }
-
- function Pi(n) {
- var t = n[0],
- e = n[n.length - 1];
- return e > t ? [t, e] : [e, t]
- }
-
- function Ui(n) {
- return n.rangeExtent ? n.rangeExtent() : Pi(n.range())
- }
-
- function ji(n, t, e, r) {
- var u = e(n[0], n[1]),
- i = r(t[0], t[1]);
- return function(n) {
- return i(u(n))
- }
- }
-
- function Fi(n, t) {
- var e, r = 0,
- u = n.length - 1,
- i = n[r],
- o = n[u];
- return i > o && (e = r, r = u, u = e, e = i, i = o, o = e), n[r] = t.floor(i), n[u] = t.ceil(o), n
- }
-
- function Hi(n) {
- return n ? {
- floor: function(t) {
- return Math.floor(t / n) * n
- },
- ceil: function(t) {
- return Math.ceil(t / n) * n
- }
- } : ml
- }
-
- function Oi(n, t, e, r) {
- var u = [],
- i = [],
- o = 0,
- a = Math.min(n.length, t.length) - 1;
- for (n[a] < n[0] && (n = n.slice().reverse(), t = t.slice().reverse()); ++o <= a;) u.push(e(n[o - 1], n[o])), i.push(r(t[o - 1], t[o]));
- return function(t) {
- var e = ta.bisect(n, t, 1, a) - 1;
- return i[e](u[e](t))
- }
- }
-
- function Ii(n, t, e, r) {
- function u() {
- var u = Math.min(n.length, t.length) > 2 ? Oi : ji,
- c = r ? Iu : Ou;
- return o = u(n, t, c, e), a = u(t, n, c, mu), i
- }
-
- function i(n) {
- return o(n)
- }
- var o, a;
- return i.invert = function(n) {
- return a(n)
- }, i.domain = function(t) {
- return arguments.length ? (n = t.map(Number), u()) : n
- }, i.range = function(n) {
- return arguments.length ? (t = n, u()) : t
- }, i.rangeRound = function(n) {
- return i.range(n).interpolate(Du)
- }, i.clamp = function(n) {
- return arguments.length ? (r = n, u()) : r
- }, i.interpolate = function(n) {
- return arguments.length ? (e = n, u()) : e
- }, i.ticks = function(t) {
- return Xi(n, t)
- }, i.tickFormat = function(t, e) {
- return $i(n, t, e)
- }, i.nice = function(t) {
- return Zi(n, t), u()
- }, i.copy = function() {
- return Ii(n, t, e, r)
- }, u()
- }
-
- function Yi(n, t) {
- return ta.rebind(n, t, "range", "rangeRound", "interpolate", "clamp")
- }
-
- function Zi(n, t) {
- return Fi(n, Hi(Vi(n, t)[2]))
- }
-
- function Vi(n, t) {
- null == t && (t = 10);
- var e = Pi(n),
- r = e[1] - e[0],
- u = Math.pow(10, Math.floor(Math.log(r / t) / Math.LN10)),
- i = t / r * u;
- return .15 >= i ? u *= 10 : .35 >= i ? u *= 5 : .75 >= i && (u *= 2), e[0] = Math.ceil(e[0] / u) * u, e[1] = Math.floor(e[1] / u) * u + .5 * u, e[2] = u, e
- }
-
- function Xi(n, t) {
- return ta.range.apply(ta, Vi(n, t))
- }
-
- function $i(n, t, e) {
- var r = Vi(n, t);
- if (e) {
- var u = ic.exec(e);
- if (u.shift(), "s" === u[8]) {
- var i = ta.formatPrefix(Math.max(ga(r[0]), ga(r[1])));
- return u[7] || (u[7] = "." + Bi(i.scale(r[2]))), u[8] = "f", e = ta.format(u.join("")),
- function(n) {
- return e(i.scale(n)) + i.symbol
- }
- }
- u[7] || (u[7] = "." + Wi(u[8], r)), e = u.join("")
- } else e = ",." + Bi(r[2]) + "f";
- return ta.format(e)
- }
-
- function Bi(n) {
- return -Math.floor(Math.log(n) / Math.LN10 + .01)
- }
-
- function Wi(n, t) {
- var e = Bi(t[2]);
- return n in yl ? Math.abs(e - Bi(Math.max(ga(t[0]), ga(t[1])))) + +("e" !== n) : e - 2 * ("%" === n)
- }
-
- function Ji(n, t, e, r) {
- function u(n) {
- return (e ? Math.log(0 > n ? 0 : n) : -Math.log(n > 0 ? 0 : -n)) / Math.log(t)
- }
-
- function i(n) {
- return e ? Math.pow(t, n) : -Math.pow(t, -n)
- }
-
- function o(t) {
- return n(u(t))
- }
- return o.invert = function(t) {
- return i(n.invert(t))
- }, o.domain = function(t) {
- return arguments.length ? (e = t[0] >= 0, n.domain((r = t.map(Number)).map(u)), o) : r
- }, o.base = function(e) {
- return arguments.length ? (t = +e, n.domain(r.map(u)), o) : t
- }, o.nice = function() {
- var t = Fi(r.map(u), e ? Math : xl);
- return n.domain(t), r = t.map(i), o
- }, o.ticks = function() {
- var n = Pi(r),
- o = [],
- a = n[0],
- c = n[1],
- l = Math.floor(u(a)),
- s = Math.ceil(u(c)),
- f = t % 1 ? 2 : t;
- if (isFinite(s - l)) {
- if (e) {
- for (; s > l; l++)
- for (var h = 1; f > h; h++) o.push(i(l) * h);
- o.push(i(l))
- } else
- for (o.push(i(l)); l++ < s;)
- for (var h = f - 1; h > 0; h--) o.push(i(l) * h);
- for (l = 0; o[l] < a; l++);
- for (s = o.length; o[s - 1] > c; s--);
- o = o.slice(l, s)
- }
- return o
- }, o.tickFormat = function(n, t) {
- if (!arguments.length) return Ml;
- arguments.length < 2 ? t = Ml : "function" != typeof t && (t = ta.format(t));
- var r, a = Math.max(.1, n / o.ticks().length),
- c = e ? (r = 1e-12, Math.ceil) : (r = -1e-12, Math.floor);
- return function(n) {
- return n / i(c(u(n) + r)) <= a ? t(n) : ""
- }
- }, o.copy = function() {
- return Ji(n.copy(), t, e, r)
- }, Yi(o, n)
- }
-
- function Gi(n, t, e) {
- function r(t) {
- return n(u(t))
- }
- var u = Ki(t),
- i = Ki(1 / t);
- return r.invert = function(t) {
- return i(n.invert(t))
- }, r.domain = function(t) {
- return arguments.length ? (n.domain((e = t.map(Number)).map(u)), r) : e
- }, r.ticks = function(n) {
- return Xi(e, n)
- }, r.tickFormat = function(n, t) {
- return $i(e, n, t)
- }, r.nice = function(n) {
- return r.domain(Zi(e, n))
- }, r.exponent = function(o) {
- return arguments.length ? (u = Ki(t = o), i = Ki(1 / t), n.domain(e.map(u)), r) : t
- }, r.copy = function() {
- return Gi(n.copy(), t, e)
- }, Yi(r, n)
- }
-
- function Ki(n) {
- return function(t) {
- return 0 > t ? -Math.pow(-t, n) : Math.pow(t, n)
- }
- }
-
- function Qi(n, t) {
- function e(e) {
- return i[((u.get(e) || ("range" === t.t ? u.set(e, n.push(e)) : 0 / 0)) - 1) % i.length]
- }
-
- function r(t, e) {
- return ta.range(n.length).map(function(n) {
- return t + e * n
- })
- }
- var u, i, o;
- return e.domain = function(r) {
- if (!arguments.length) return n;
- n = [], u = new l;
- for (var i, o = -1, a = r.length; ++o < a;) u.has(i = r[o]) || u.set(i, n.push(i));
- return e[t.t].apply(e, t.a)
- }, e.range = function(n) {
- return arguments.length ? (i = n, o = 0, t = {
- t: "range",
- a: arguments
- }, e) : i
- }, e.rangePoints = function(u, a) {
- arguments.length < 2 && (a = 0);
- var c = u[0],
- l = u[1],
- s = n.length < 2 ? (c = (c + l) / 2, 0) : (l - c) / (n.length - 1 + a);
- return i = r(c + s * a / 2, s), o = 0, t = {
- t: "rangePoints",
- a: arguments
- }, e
- }, e.rangeRoundPoints = function(u, a) {
- arguments.length < 2 && (a = 0);
- var c = u[0],
- l = u[1],
- s = n.length < 2 ? (c = l = Math.round((c + l) / 2), 0) : (l - c) / (n.length - 1 + a) | 0;
- return i = r(c + Math.round(s * a / 2 + (l - c - (n.length - 1 + a) * s) / 2), s), o = 0, t = {
- t: "rangeRoundPoints",
- a: arguments
- }, e
- }, e.rangeBands = function(u, a, c) {
- arguments.length < 2 && (a = 0), arguments.length < 3 && (c = a);
- var l = u[1] < u[0],
- s = u[l - 0],
- f = u[1 - l],
- h = (f - s) / (n.length - a + 2 * c);
- return i = r(s + h * c, h), l && i.reverse(), o = h * (1 - a), t = {
- t: "rangeBands",
- a: arguments
- }, e
- }, e.rangeRoundBands = function(u, a, c) {
- arguments.length < 2 && (a = 0), arguments.length < 3 && (c = a);
- var l = u[1] < u[0],
- s = u[l - 0],
- f = u[1 - l],
- h = Math.floor((f - s) / (n.length - a + 2 * c));
- return i = r(s + Math.round((f - s - (n.length - a) * h) / 2), h), l && i.reverse(), o = Math.round(h * (1 - a)), t = {
- t: "rangeRoundBands",
- a: arguments
- }, e
- }, e.rangeBand = function() {
- return o
- }, e.rangeExtent = function() {
- return Pi(t.a[0])
- }, e.copy = function() {
- return Qi(n, t)
- }, e.domain(n)
- }
-
- function no(n, t) {
- function i() {
- var e = 0,
- r = t.length;
- for (a = []; ++e < r;) a[e - 1] = ta.quantile(n, e / r);
- return o
- }
-
- function o(n) {
- return isNaN(n = +n) ? void 0 : t[ta.bisect(a, n)]
- }
- var a;
- return o.domain = function(t) {
- return arguments.length ? (n = t.map(r).filter(u).sort(e), i()) : n
- }, o.range = function(n) {
- return arguments.length ? (t = n, i()) : t
- }, o.quantiles = function() {
- return a
- }, o.invertExtent = function(e) {
- return e = t.indexOf(e), 0 > e ? [0 / 0, 0 / 0] : [e > 0 ? a[e - 1] : n[0], e < a.length ? a[e] : n[n.length - 1]]
- }, o.copy = function() {
- return no(n, t)
- }, i()
- }
-
- function to(n, t, e) {
- function r(t) {
- return e[Math.max(0, Math.min(o, Math.floor(i * (t - n))))]
- }
-
- function u() {
- return i = e.length / (t - n), o = e.length - 1, r
- }
- var i, o;
- return r.domain = function(e) {
- return arguments.length ? (n = +e[0], t = +e[e.length - 1], u()) : [n, t]
- }, r.range = function(n) {
- return arguments.length ? (e = n, u()) : e
- }, r.invertExtent = function(t) {
- return t = e.indexOf(t), t = 0 > t ? 0 / 0 : t / i + n, [t, t + 1 / i]
- }, r.copy = function() {
- return to(n, t, e)
- }, u()
- }
-
- function eo(n, t) {
- function e(e) {
- return e >= e ? t[ta.bisect(n, e)] : void 0
- }
- return e.domain = function(t) {
- return arguments.length ? (n = t, e) : n
- }, e.range = function(n) {
- return arguments.length ? (t = n, e) : t
- }, e.invertExtent = function(e) {
- return e = t.indexOf(e), [n[e - 1], n[e]]
- }, e.copy = function() {
- return eo(n, t)
- }, e
- }
-
- function ro(n) {
- function t(n) {
- return +n
- }
- return t.invert = t, t.domain = t.range = function(e) {
- return arguments.length ? (n = e.map(t), t) : n
- }, t.ticks = function(t) {
- return Xi(n, t)
- }, t.tickFormat = function(t, e) {
- return $i(n, t, e)
- }, t.copy = function() {
- return ro(n)
- }, t
- }
-
- function uo() {
- return 0
- }
-
- function io(n) {
- return n.innerRadius
- }
-
- function oo(n) {
- return n.outerRadius
- }
-
- function ao(n) {
- return n.startAngle
- }
-
- function co(n) {
- return n.endAngle
- }
-
- function lo(n) {
- return n && n.padAngle
- }
-
- function so(n, t, e, r) {
- return (n - e) * t - (t - r) * n > 0 ? 0 : 1
- }
-
- function fo(n, t, e, r, u) {
- var i = n[0] - t[0],
- o = n[1] - t[1],
- a = (u ? r : -r) / Math.sqrt(i * i + o * o),
- c = a * o,
- l = -a * i,
- s = n[0] + c,
- f = n[1] + l,
- h = t[0] + c,
- g = t[1] + l,
- p = (s + h) / 2,
- v = (f + g) / 2,
- d = h - s,
- m = g - f,
- y = d * d + m * m,
- M = e - r,
- x = s * g - h * f,
- b = (0 > m ? -1 : 1) * Math.sqrt(M * M * y - x * x),
- _ = (x * m - d * b) / y,
- w = (-x * d - m * b) / y,
- S = (x * m + d * b) / y,
- k = (-x * d + m * b) / y,
- E = _ - p,
- A = w - v,
- N = S - p,
- C = k - v;
- return E * E + A * A > N * N + C * C && (_ = S, w = k), [
- [_ - c, w - l],
- [_ * e / M, w * e / M]
- ]
- }
-
- function ho(n) {
- function t(t) {
- function o() {
- l.push("M", i(n(s), a))
- }
- for (var c, l = [], s = [], f = -1, h = t.length, g = Et(e), p = Et(r); ++f < h;) u.call(this, c = t[f], f) ? s.push([+g.call(this, c, f), +p.call(this, c, f)]) : s.length && (o(), s = []);
- return s.length && o(), l.length ? l.join("") : null
- }
- var e = Ar,
- r = Nr,
- u = Ne,
- i = go,
- o = i.key,
- a = .7;
- return t.x = function(n) {
- return arguments.length ? (e = n, t) : e
- }, t.y = function(n) {
- return arguments.length ? (r = n, t) : r
- }, t.defined = function(n) {
- return arguments.length ? (u = n, t) : u
- }, t.interpolate = function(n) {
- return arguments.length ? (o = "function" == typeof n ? i = n : (i = El.get(n) || go).key, t) : o
- }, t.tension = function(n) {
- return arguments.length ? (a = n, t) : a
- }, t
- }
-
- function go(n) {
- return n.join("L")
- }
-
- function po(n) {
- return go(n) + "Z"
- }
-
- function vo(n) {
- for (var t = 0, e = n.length, r = n[0], u = [r[0], ",", r[1]]; ++t < e;) u.push("H", (r[0] + (r = n[t])[0]) / 2, "V", r[1]);
- return e > 1 && u.push("H", r[0]), u.join("")
- }
-
- function mo(n) {
- for (var t = 0, e = n.length, r = n[0], u = [r[0], ",", r[1]]; ++t < e;) u.push("V", (r = n[t])[1], "H", r[0]);
- return u.join("")
- }
-
- function yo(n) {
- for (var t = 0, e = n.length, r = n[0], u = [r[0], ",", r[1]]; ++t < e;) u.push("H", (r = n[t])[0], "V", r[1]);
- return u.join("")
- }
-
- function Mo(n, t) {
- return n.length < 4 ? go(n) : n[1] + _o(n.slice(1, -1), wo(n, t))
- }
-
- function xo(n, t) {
- return n.length < 3 ? go(n) : n[0] + _o((n.push(n[0]), n), wo([n[n.length - 2]].concat(n, [n[1]]), t))
- }
-
- function bo(n, t) {
- return n.length < 3 ? go(n) : n[0] + _o(n, wo(n, t))
- }
-
- function _o(n, t) {
- if (t.length < 1 || n.length != t.length && n.length != t.length + 2) return go(n);
- var e = n.length != t.length,
- r = "",
- u = n[0],
- i = n[1],
- o = t[0],
- a = o,
- c = 1;
- if (e && (r += "Q" + (i[0] - 2 * o[0] / 3) + "," + (i[1] - 2 * o[1] / 3) + "," + i[0] + "," + i[1], u = n[1], c = 2), t.length > 1) {
- a = t[1], i = n[c], c++, r += "C" + (u[0] + o[0]) + "," + (u[1] + o[1]) + "," + (i[0] - a[0]) + "," + (i[1] - a[1]) + "," + i[0] + "," + i[1];
- for (var l = 2; l < t.length; l++, c++) i = n[c], a = t[l], r += "S" + (i[0] - a[0]) + "," + (i[1] - a[1]) + "," + i[0] + "," + i[1]
- }
- if (e) {
- var s = n[c];
- r += "Q" + (i[0] + 2 * a[0] / 3) + "," + (i[1] + 2 * a[1] / 3) + "," + s[0] + "," + s[1]
- }
- return r
- }
-
- function wo(n, t) {
- for (var e, r = [], u = (1 - t) / 2, i = n[0], o = n[1], a = 1, c = n.length; ++a < c;) e = i, i = o, o = n[a], r.push([u * (o[0] - e[0]), u * (o[1] - e[1])]);
- return r
- }
-
- function So(n) {
- if (n.length < 3) return go(n);
- var t = 1,
- e = n.length,
- r = n[0],
- u = r[0],
- i = r[1],
- o = [u, u, u, (r = n[1])[0]],
- a = [i, i, i, r[1]],
- c = [u, ",", i, "L", No(Cl, o), ",", No(Cl, a)];
- for (n.push(n[e - 1]); ++t <= e;) r = n[t], o.shift(), o.push(r[0]), a.shift(), a.push(r[1]), Co(c, o, a);
- return n.pop(), c.push("L", r), c.join("")
- }
-
- function ko(n) {
- if (n.length < 4) return go(n);
- for (var t, e = [], r = -1, u = n.length, i = [0], o = [0]; ++r < 3;) t = n[r], i.push(t[0]), o.push(t[1]);
- for (e.push(No(Cl, i) + "," + No(Cl, o)), --r; ++r < u;) t = n[r], i.shift(), i.push(t[0]), o.shift(), o.push(t[1]), Co(e, i, o);
- return e.join("")
- }
-
- function Eo(n) {
- for (var t, e, r = -1, u = n.length, i = u + 4, o = [], a = []; ++r < 4;) e = n[r % u], o.push(e[0]), a.push(e[1]);
- for (t = [No(Cl, o), ",", No(Cl, a)], --r; ++r < i;) e = n[r % u], o.shift(), o.push(e[0]), a.shift(), a.push(e[1]), Co(t, o, a);
- return t.join("")
- }
-
- function Ao(n, t) {
- var e = n.length - 1;
- if (e)
- for (var r, u, i = n[0][0], o = n[0][1], a = n[e][0] - i, c = n[e][1] - o, l = -1; ++l <= e;) r = n[l], u = l / e, r[0] = t * r[0] + (1 - t) * (i + u * a), r[1] = t * r[1] + (1 - t) * (o + u * c);
- return So(n)
- }
-
- function No(n, t) {
- return n[0] * t[0] + n[1] * t[1] + n[2] * t[2] + n[3] * t[3]
- }
-
- function Co(n, t, e) {
- n.push("C", No(Al, t), ",", No(Al, e), ",", No(Nl, t), ",", No(Nl, e), ",", No(Cl, t), ",", No(Cl, e))
- }
-
- function zo(n, t) {
- return (t[1] - n[1]) / (t[0] - n[0])
- }
-
- function qo(n) {
- for (var t = 0, e = n.length - 1, r = [], u = n[0], i = n[1], o = r[0] = zo(u, i); ++t < e;) r[t] = (o + (o = zo(u = i, i = n[t + 1]))) / 2;
- return r[t] = o, r
- }
-
- function Lo(n) {
- for (var t, e, r, u, i = [], o = qo(n), a = -1, c = n.length - 1; ++a < c;) t = zo(n[a], n[a + 1]), ga(t) < Ca ? o[a] = o[a + 1] = 0 : (e = o[a] / t, r = o[a + 1] / t, u = e * e + r * r, u > 9 && (u = 3 * t / Math.sqrt(u), o[a] = u * e, o[a + 1] = u * r));
- for (a = -1; ++a <= c;) u = (n[Math.min(c, a + 1)][0] - n[Math.max(0, a - 1)][0]) / (6 * (1 + o[a] * o[a])), i.push([u || 0, o[a] * u || 0]);
- return i
- }
-
- function To(n) {
- return n.length < 3 ? go(n) : n[0] + _o(n, Lo(n))
- }
-
- function Ro(n) {
- for (var t, e, r, u = -1, i = n.length; ++u < i;) t = n[u], e = t[0], r = t[1] - Ra, t[0] = e * Math.cos(r), t[1] = e * Math.sin(r);
- return n
- }
-
- function Do(n) {
- function t(t) {
- function c() {
- v.push("M", a(n(m), f), s, l(n(d.reverse()), f), "Z")
- }
- for (var h, g, p, v = [], d = [], m = [], y = -1, M = t.length, x = Et(e), b = Et(u), _ = e === r ? function() {
- return g
- } : Et(r), w = u === i ? function() {
- return p
- } : Et(i); ++y < M;) o.call(this, h = t[y], y) ? (d.push([g = +x.call(this, h, y), p = +b.call(this, h, y)]), m.push([+_.call(this, h, y), +w.call(this, h, y)])) : d.length && (c(), d = [], m = []);
- return d.length && c(), v.length ? v.join("") : null
- }
- var e = Ar,
- r = Ar,
- u = 0,
- i = Nr,
- o = Ne,
- a = go,
- c = a.key,
- l = a,
- s = "L",
- f = .7;
- return t.x = function(n) {
- return arguments.length ? (e = r = n, t) : r
- }, t.x0 = function(n) {
- return arguments.length ? (e = n, t) : e
- }, t.x1 = function(n) {
- return arguments.length ? (r = n, t) : r
- }, t.y = function(n) {
- return arguments.length ? (u = i = n, t) : i
- }, t.y0 = function(n) {
- return arguments.length ? (u = n, t) : u
- }, t.y1 = function(n) {
- return arguments.length ? (i = n, t) : i
- }, t.defined = function(n) {
- return arguments.length ? (o = n, t) : o
- }, t.interpolate = function(n) {
- return arguments.length ? (c = "function" == typeof n ? a = n : (a = El.get(n) || go).key, l = a.reverse || a, s = a.closed ? "M" : "L", t) : c
- }, t.tension = function(n) {
- return arguments.length ? (f = n, t) : f
- }, t
- }
-
- function Po(n) {
- return n.radius
- }
-
- function Uo(n) {
- return [n.x, n.y]
- }
-
- function jo(n) {
- return function() {
- var t = n.apply(this, arguments),
- e = t[0],
- r = t[1] - Ra;
- return [e * Math.cos(r), e * Math.sin(r)]
- }
- }
-
- function Fo() {
- return 64
- }
-
- function Ho() {
- return "circle"
- }
-
- function Oo(n) {
- var t = Math.sqrt(n / qa);
- return "M0," + t + "A" + t + "," + t + " 0 1,1 0," + -t + "A" + t + "," + t + " 0 1,1 0," + t + "Z"
- }
-
- function Io(n) {
- return function() {
- var t, e;
- (t = this[n]) && (e = t[t.active]) && (--t.count ? delete t[t.active] : delete this[n], t.active += .5, e.event && e.event.interrupt.call(this, this.__data__, e.index))
- }
- }
-
- function Yo(n, t, e) {
- return ya(n, Pl), n.namespace = t, n.id = e, n
- }
-
- function Zo(n, t, e, r) {
- var u = n.id,
- i = n.namespace;
- return Y(n, "function" == typeof e ? function(n, o, a) {
- n[i][u].tween.set(t, r(e.call(n, n.__data__, o, a)))
- } : (e = r(e), function(n) {
- n[i][u].tween.set(t, e)
- }))
- }
-
- function Vo(n) {
- return null == n && (n = ""),
- function() {
- this.textContent = n
- }
- }
-
- function Xo(n) {
- return null == n ? "__transition__" : "__transition_" + n + "__"
- }
-
- function $o(n, t, e, r, u) {
- var i = n[e] || (n[e] = {
- active: 0,
- count: 0
- }),
- o = i[r];
- if (!o) {
- var a = u.time;
- o = i[r] = {
- tween: new l,
- time: a,
- delay: u.delay,
- duration: u.duration,
- ease: u.ease,
- index: t
- }, u = null, ++i.count, ta.timer(function(u) {
- function c(e) {
- if (i.active > r) return s();
- var u = i[i.active];
- u && (--i.count, delete i[i.active], u.event && u.event.interrupt.call(n, n.__data__, u.index)), i.active = r, o.event && o.event.start.call(n, n.__data__, t), o.tween.forEach(function(e, r) {
- (r = r.call(n, n.__data__, t)) && v.push(r)
- }), h = o.ease, f = o.duration, ta.timer(function() {
- return p.c = l(e || 1) ? Ne : l, 1
- }, 0, a)
- }
-
- function l(e) {
- if (i.active !== r) return 1;
- for (var u = e / f, a = h(u), c = v.length; c > 0;) v[--c].call(n, a);
- return u >= 1 ? (o.event && o.event.end.call(n, n.__data__, t), s()) : void 0
- }
-
- function s() {
- return --i.count ? delete i[r] : delete n[e], 1
- }
- var f, h, g = o.delay,
- p = ec,
- v = [];
- return p.t = g + a, u >= g ? c(u - g) : void(p.c = c)
- }, 0, a)
- }
- }
-
- function Bo(n, t, e) {
- n.attr("transform", function(n) {
- var r = t(n);
- return "translate(" + (isFinite(r) ? r : e(n)) + ",0)"
- })
- }
-
- function Wo(n, t, e) {
- n.attr("transform", function(n) {
- var r = t(n);
- return "translate(0," + (isFinite(r) ? r : e(n)) + ")"
- })
- }
-
- function Jo(n) {
- return n.toISOString()
- }
-
- function Go(n, t, e) {
- function r(t) {
- return n(t)
- }
-
- function u(n, e) {
- var r = n[1] - n[0],
- u = r / e,
- i = ta.bisect(Vl, u);
- return i == Vl.length ? [t.year, Vi(n.map(function(n) {
- return n / 31536e6
- }), e)[2]] : i ? t[u / Vl[i - 1] < Vl[i] / u ? i - 1 : i] : [Bl, Vi(n, e)[2]]
- }
- return r.invert = function(t) {
- return Ko(n.invert(t))
- }, r.domain = function(t) {
- return arguments.length ? (n.domain(t), r) : n.domain().map(Ko)
- }, r.nice = function(n, t) {
- function e(e) {
- return !isNaN(e) && !n.range(e, Ko(+e + 1), t).length
- }
- var i = r.domain(),
- o = Pi(i),
- a = null == n ? u(o, 10) : "number" == typeof n && u(o, n);
- return a && (n = a[0], t = a[1]), r.domain(Fi(i, t > 1 ? {
- floor: function(t) {
- for (; e(t = n.floor(t));) t = Ko(t - 1);
- return t
- },
- ceil: function(t) {
- for (; e(t = n.ceil(t));) t = Ko(+t + 1);
- return t
- }
- } : n))
- }, r.ticks = function(n, t) {
- var e = Pi(r.domain()),
- i = null == n ? u(e, 10) : "number" == typeof n ? u(e, n) : !n.range && [{
- range: n
- }, t];
- return i && (n = i[0], t = i[1]), n.range(e[0], Ko(+e[1] + 1), 1 > t ? 1 : t)
- }, r.tickFormat = function() {
- return e
- }, r.copy = function() {
- return Go(n.copy(), t, e)
- }, Yi(r, n)
- }
-
- function Ko(n) {
- return new Date(n)
- }
-
- function Qo(n) {
- return JSON.parse(n.responseText)
- }
-
- function na(n) {
- var t = ua.createRange();
- return t.selectNode(ua.body), t.createContextualFragment(n.responseText)
- }
- var ta = {
- version: "3.5.4"
- },
- ea = [].slice,
- ra = function(n) {
- return ea.call(n)
- },
- ua = this.document;
- if (ua) try {
- ra(ua.documentElement.childNodes)[0].nodeType
- } catch (ia) {
- ra = function(n) {
- for (var t = n.length, e = new Array(t); t--;) e[t] = n[t];
- return e
- }
- }
- if (Date.now || (Date.now = function() {
- return +new Date
- }), ua) try {
- ua.createElement("DIV").style.setProperty("opacity", 0, "")
- } catch (oa) {
- var aa = this.Element.prototype,
- ca = aa.setAttribute,
- la = aa.setAttributeNS,
- sa = this.CSSStyleDeclaration.prototype,
- fa = sa.setProperty;
- aa.setAttribute = function(n, t) {
- ca.call(this, n, t + "")
- }, aa.setAttributeNS = function(n, t, e) {
- la.call(this, n, t, e + "")
- }, sa.setProperty = function(n, t, e) {
- fa.call(this, n, t + "", e)
- }
- }
- ta.ascending = e, ta.descending = function(n, t) {
- return n > t ? -1 : t > n ? 1 : t >= n ? 0 : 0 / 0
- }, ta.min = function(n, t) {
- var e, r, u = -1,
- i = n.length;
- if (1 === arguments.length) {
- for (; ++u < i;)
- if (null != (r = n[u]) && r >= r) {
- e = r;
- break
- } for (; ++u < i;) null != (r = n[u]) && e > r && (e = r)
- } else {
- for (; ++u < i;)
- if (null != (r = t.call(n, n[u], u)) && r >= r) {
- e = r;
- break
- } for (; ++u < i;) null != (r = t.call(n, n[u], u)) && e > r && (e = r)
- }
- return e
- }, ta.max = function(n, t) {
- var e, r, u = -1,
- i = n.length;
- if (1 === arguments.length) {
- for (; ++u < i;)
- if (null != (r = n[u]) && r >= r) {
- e = r;
- break
- } for (; ++u < i;) null != (r = n[u]) && r > e && (e = r)
- } else {
- for (; ++u < i;)
- if (null != (r = t.call(n, n[u], u)) && r >= r) {
- e = r;
- break
- } for (; ++u < i;) null != (r = t.call(n, n[u], u)) && r > e && (e = r)
- }
- return e
- }, ta.extent = function(n, t) {
- var e, r, u, i = -1,
- o = n.length;
- if (1 === arguments.length) {
- for (; ++i < o;)
- if (null != (r = n[i]) && r >= r) {
- e = u = r;
- break
- } for (; ++i < o;) null != (r = n[i]) && (e > r && (e = r), r > u && (u = r))
- } else {
- for (; ++i < o;)
- if (null != (r = t.call(n, n[i], i)) && r >= r) {
- e = u = r;
- break
- } for (; ++i < o;) null != (r = t.call(n, n[i], i)) && (e > r && (e = r), r > u && (u = r))
- }
- return [e, u]
- }, ta.sum = function(n, t) {
- var e, r = 0,
- i = n.length,
- o = -1;
- if (1 === arguments.length)
- for (; ++o < i;) u(e = +n[o]) && (r += e);
- else
- for (; ++o < i;) u(e = +t.call(n, n[o], o)) && (r += e);
- return r
- }, ta.mean = function(n, t) {
- var e, i = 0,
- o = n.length,
- a = -1,
- c = o;
- if (1 === arguments.length)
- for (; ++a < o;) u(e = r(n[a])) ? i += e : --c;
- else
- for (; ++a < o;) u(e = r(t.call(n, n[a], a))) ? i += e : --c;
- return c ? i / c : void 0
- }, ta.quantile = function(n, t) {
- var e = (n.length - 1) * t + 1,
- r = Math.floor(e),
- u = +n[r - 1],
- i = e - r;
- return i ? u + i * (n[r] - u) : u
- }, ta.median = function(n, t) {
- var i, o = [],
- a = n.length,
- c = -1;
- if (1 === arguments.length)
- for (; ++c < a;) u(i = r(n[c])) && o.push(i);
- else
- for (; ++c < a;) u(i = r(t.call(n, n[c], c))) && o.push(i);
- return o.length ? ta.quantile(o.sort(e), .5) : void 0
- }, ta.variance = function(n, t) {
- var e, i, o = n.length,
- a = 0,
- c = 0,
- l = -1,
- s = 0;
- if (1 === arguments.length)
- for (; ++l < o;) u(e = r(n[l])) && (i = e - a, a += i / ++s, c += i * (e - a));
- else
- for (; ++l < o;) u(e = r(t.call(n, n[l], l))) && (i = e - a, a += i / ++s, c += i * (e - a));
- return s > 1 ? c / (s - 1) : void 0
- }, ta.deviation = function() {
- var n = ta.variance.apply(this, arguments);
- return n ? Math.sqrt(n) : n
- };
- var ha = i(e);
- ta.bisectLeft = ha.left, ta.bisect = ta.bisectRight = ha.right, ta.bisector = function(n) {
- return i(1 === n.length ? function(t, r) {
- return e(n(t), r)
- } : n)
- }, ta.shuffle = function(n, t, e) {
- (i = arguments.length) < 3 && (e = n.length, 2 > i && (t = 0));
- for (var r, u, i = e - t; i;) u = Math.random() * i-- | 0, r = n[i + t], n[i + t] = n[u + t], n[u + t] = r;
- return n
- }, ta.permute = function(n, t) {
- for (var e = t.length, r = new Array(e); e--;) r[e] = n[t[e]];
- return r
- }, ta.pairs = function(n) {
- for (var t, e = 0, r = n.length - 1, u = n[0], i = new Array(0 > r ? 0 : r); r > e;) i[e] = [t = u, u = n[++e]];
- return i
- }, ta.zip = function() {
- if (!(r = arguments.length)) return [];
- for (var n = -1, t = ta.min(arguments, o), e = new Array(t); ++n < t;)
- for (var r, u = -1, i = e[n] = new Array(r); ++u < r;) i[u] = arguments[u][n];
- return e
- }, ta.transpose = function(n) {
- return ta.zip.apply(ta, n)
- }, ta.keys = function(n) {
- var t = [];
- for (var e in n) t.push(e);
- return t
- }, ta.values = function(n) {
- var t = [];
- for (var e in n) t.push(n[e]);
- return t
- }, ta.entries = function(n) {
- var t = [];
- for (var e in n) t.push({
- key: e,
- value: n[e]
- });
- return t
- }, ta.merge = function(n) {
- for (var t, e, r, u = n.length, i = -1, o = 0; ++i < u;) o += n[i].length;
- for (e = new Array(o); --u >= 0;)
- for (r = n[u], t = r.length; --t >= 0;) e[--o] = r[t];
- return e
- };
- var ga = Math.abs;
- ta.range = function(n, t, e) {
- if (arguments.length < 3 && (e = 1, arguments.length < 2 && (t = n, n = 0)), (t - n) / e === 1 / 0) throw new Error("infinite range");
- var r, u = [],
- i = a(ga(e)),
- o = -1;
- if (n *= i, t *= i, e *= i, 0 > e)
- for (;
- (r = n + e * ++o) > t;) u.push(r / i);
- else
- for (;
- (r = n + e * ++o) < t;) u.push(r / i);
- return u
- }, ta.map = function(n, t) {
- var e = new l;
- if (n instanceof l) n.forEach(function(n, t) {
- e.set(n, t)
- });
- else if (Array.isArray(n)) {
- var r, u = -1,
- i = n.length;
- if (1 === arguments.length)
- for (; ++u < i;) e.set(u, n[u]);
- else
- for (; ++u < i;) e.set(t.call(n, r = n[u], u), r)
- } else
- for (var o in n) e.set(o, n[o]);
- return e
- };
- var pa = "__proto__",
- va = "\x00";
- c(l, {
- has: h,
- get: function(n) {
- return this._[s(n)]
- },
- set: function(n, t) {
- return this._[s(n)] = t
- },
- remove: g,
- keys: p,
- values: function() {
- var n = [];
- for (var t in this._) n.push(this._[t]);
- return n
- },
- entries: function() {
- var n = [];
- for (var t in this._) n.push({
- key: f(t),
- value: this._[t]
- });
- return n
- },
- size: v,
- empty: d,
- forEach: function(n) {
- for (var t in this._) n.call(this, f(t), this._[t])
- }
- }), ta.nest = function() {
- function n(t, o, a) {
- if (a >= i.length) return r ? r.call(u, o) : e ? o.sort(e) : o;
- for (var c, s, f, h, g = -1, p = o.length, v = i[a++], d = new l; ++g < p;)(h = d.get(c = v(s = o[g]))) ? h.push(s) : d.set(c, [s]);
- return t ? (s = t(), f = function(e, r) {
- s.set(e, n(t, r, a))
- }) : (s = {}, f = function(e, r) {
- s[e] = n(t, r, a)
- }), d.forEach(f), s
- }
-
- function t(n, e) {
- if (e >= i.length) return n;
- var r = [],
- u = o[e++];
- return n.forEach(function(n, u) {
- r.push({
- key: n,
- values: t(u, e)
- })
- }), u ? r.sort(function(n, t) {
- return u(n.key, t.key)
- }) : r
- }
- var e, r, u = {},
- i = [],
- o = [];
- return u.map = function(t, e) {
- return n(e, t, 0)
- }, u.entries = function(e) {
- return t(n(ta.map, e, 0), 0)
- }, u.key = function(n) {
- return i.push(n), u
- }, u.sortKeys = function(n) {
- return o[i.length - 1] = n, u
- }, u.sortValues = function(n) {
- return e = n, u
- }, u.rollup = function(n) {
- return r = n, u
- }, u
- }, ta.set = function(n) {
- var t = new m;
- if (n)
- for (var e = 0, r = n.length; r > e; ++e) t.add(n[e]);
- return t
- }, c(m, {
- has: h,
- add: function(n) {
- return this._[s(n += "")] = !0, n
- },
- remove: g,
- values: p,
- size: v,
- empty: d,
- forEach: function(n) {
- for (var t in this._) n.call(this, f(t))
- }
- }), ta.behavior = {}, ta.rebind = function(n, t) {
- for (var e, r = 1, u = arguments.length; ++r < u;) n[e = arguments[r]] = M(n, t, t[e]);
- return n
- };
- var da = ["webkit", "ms", "moz", "Moz", "o", "O"];
- ta.dispatch = function() {
- for (var n = new _, t = -1, e = arguments.length; ++t < e;) n[arguments[t]] = w(n);
- return n
- }, _.prototype.on = function(n, t) {
- var e = n.indexOf("."),
- r = "";
- if (e >= 0 && (r = n.slice(e + 1), n = n.slice(0, e)), n) return arguments.length < 2 ? this[n].on(r) : this[n].on(r, t);
- if (2 === arguments.length) {
- if (null == t)
- for (n in this) this.hasOwnProperty(n) && this[n].on(r, null);
- return this
- }
- }, ta.event = null, ta.requote = function(n) {
- return n.replace(ma, "\\$&")
- };
- var ma = /[\\\^\$\*\+\?\|\[\]\(\)\.\{\}]/g,
- ya = {}.__proto__ ? function(n, t) {
- n.__proto__ = t
- } : function(n, t) {
- for (var e in t) n[e] = t[e]
- },
- Ma = function(n, t) {
- return t.querySelector(n)
- },
- xa = function(n, t) {
- return t.querySelectorAll(n)
- },
- ba = function(n, t) {
- var e = n.matches || n[x(n, "matchesSelector")];
- return (ba = function(n, t) {
- return e.call(n, t)
- })(n, t)
- };
- "function" == typeof Sizzle && (Ma = function(n, t) {
- return Sizzle(n, t)[0] || null
- }, xa = Sizzle, ba = Sizzle.matchesSelector), ta.selection = function() {
- return ta.select(ua.documentElement)
- };
- var _a = ta.selection.prototype = [];
- _a.select = function(n) {
- var t, e, r, u, i = [];
- n = N(n);
- for (var o = -1, a = this.length; ++o < a;) {
- i.push(t = []), t.parentNode = (r = this[o]).parentNode;
- for (var c = -1, l = r.length; ++c < l;)(u = r[c]) ? (t.push(e = n.call(u, u.__data__, c, o)), e && "__data__" in u && (e.__data__ = u.__data__)) : t.push(null)
- }
- return A(i)
- }, _a.selectAll = function(n) {
- var t, e, r = [];
- n = C(n);
- for (var u = -1, i = this.length; ++u < i;)
- for (var o = this[u], a = -1, c = o.length; ++a < c;)(e = o[a]) && (r.push(t = ra(n.call(e, e.__data__, a, u))), t.parentNode = e);
- return A(r)
- };
- var wa = {
- svg: "http://www.w3.org/2000/svg",
- xhtml: "http://www.w3.org/1999/xhtml",
- xlink: "http://www.w3.org/1999/xlink",
- xml: "http://www.w3.org/XML/1998/namespace",
- xmlns: "http://www.w3.org/2000/xmlns/"
- };
- ta.ns = {
- prefix: wa,
- qualify: function(n) {
- var t = n.indexOf(":"),
- e = n;
- return t >= 0 && (e = n.slice(0, t), n = n.slice(t + 1)), wa.hasOwnProperty(e) ? {
- space: wa[e],
- local: n
- } : n
- }
- }, _a.attr = function(n, t) {
- if (arguments.length < 2) {
- if ("string" == typeof n) {
- var e = this.node();
- return n = ta.ns.qualify(n), n.local ? e.getAttributeNS(n.space, n.local) : e.getAttribute(n)
- }
- for (t in n) this.each(z(t, n[t]));
- return this
- }
- return this.each(z(n, t))
- }, _a.classed = function(n, t) {
- if (arguments.length < 2) {
- if ("string" == typeof n) {
- var e = this.node(),
- r = (n = T(n)).length,
- u = -1;
- if (t = e.classList) {
- for (; ++u < r;)
- if (!t.contains(n[u])) return !1
- } else
- for (t = e.getAttribute("class"); ++u < r;)
- if (!L(n[u]).test(t)) return !1;
- return !0
- }
- for (t in n) this.each(R(t, n[t]));
- return this
- }
- return this.each(R(n, t))
- }, _a.style = function(n, e, r) {
- var u = arguments.length;
- if (3 > u) {
- if ("string" != typeof n) {
- 2 > u && (e = "");
- for (r in n) this.each(P(r, n[r], e));
- return this
- }
- if (2 > u) {
- var i = this.node();
- return t(i).getComputedStyle(i, null).getPropertyValue(n)
- }
- r = ""
- }
- return this.each(P(n, e, r))
- }, _a.property = function(n, t) {
- if (arguments.length < 2) {
- if ("string" == typeof n) return this.node()[n];
- for (t in n) this.each(U(t, n[t]));
- return this
- }
- return this.each(U(n, t))
- }, _a.text = function(n) {
- return arguments.length ? this.each("function" == typeof n ? function() {
- var t = n.apply(this, arguments);
- this.textContent = null == t ? "" : t
- } : null == n ? function() {
- this.textContent = ""
- } : function() {
- this.textContent = n
- }) : this.node().textContent
- }, _a.html = function(n) {
- return arguments.length ? this.each("function" == typeof n ? function() {
- var t = n.apply(this, arguments);
- this.innerHTML = null == t ? "" : t
- } : null == n ? function() {
- this.innerHTML = ""
- } : function() {
- this.innerHTML = n
- }) : this.node().innerHTML
- }, _a.append = function(n) {
- return n = j(n), this.select(function() {
- return this.appendChild(n.apply(this, arguments))
- })
- }, _a.insert = function(n, t) {
- return n = j(n), t = N(t), this.select(function() {
- return this.insertBefore(n.apply(this, arguments), t.apply(this, arguments) || null)
- })
- }, _a.remove = function() {
- return this.each(F)
- }, _a.data = function(n, t) {
- function e(n, e) {
- var r, u, i, o = n.length,
- f = e.length,
- h = Math.min(o, f),
- g = new Array(f),
- p = new Array(f),
- v = new Array(o);
- if (t) {
- var d, m = new l,
- y = new Array(o);
- for (r = -1; ++r < o;) m.has(d = t.call(u = n[r], u.__data__, r)) ? v[r] = u : m.set(d, u), y[r] = d;
- for (r = -1; ++r < f;)(u = m.get(d = t.call(e, i = e[r], r))) ? u !== !0 && (g[r] = u, u.__data__ = i) : p[r] = H(i), m.set(d, !0);
- for (r = -1; ++r < o;) m.get(y[r]) !== !0 && (v[r] = n[r])
- } else {
- for (r = -1; ++r < h;) u = n[r], i = e[r], u ? (u.__data__ = i, g[r] = u) : p[r] = H(i);
- for (; f > r; ++r) p[r] = H(e[r]);
- for (; o > r; ++r) v[r] = n[r]
- }
- p.update = g, p.parentNode = g.parentNode = v.parentNode = n.parentNode, a.push(p), c.push(g), s.push(v)
- }
- var r, u, i = -1,
- o = this.length;
- if (!arguments.length) {
- for (n = new Array(o = (r = this[0]).length); ++i < o;)(u = r[i]) && (n[i] = u.__data__);
- return n
- }
- var a = Z([]),
- c = A([]),
- s = A([]);
- if ("function" == typeof n)
- for (; ++i < o;) e(r = this[i], n.call(r, r.parentNode.__data__, i));
- else
- for (; ++i < o;) e(r = this[i], n);
- return c.enter = function() {
- return a
- }, c.exit = function() {
- return s
- }, c
- }, _a.datum = function(n) {
- return arguments.length ? this.property("__data__", n) : this.property("__data__")
- }, _a.filter = function(n) {
- var t, e, r, u = [];
- "function" != typeof n && (n = O(n));
- for (var i = 0, o = this.length; o > i; i++) {
- u.push(t = []), t.parentNode = (e = this[i]).parentNode;
- for (var a = 0, c = e.length; c > a; a++)(r = e[a]) && n.call(r, r.__data__, a, i) && t.push(r)
- }
- return A(u)
- }, _a.order = function() {
- for (var n = -1, t = this.length; ++n < t;)
- for (var e, r = this[n], u = r.length - 1, i = r[u]; --u >= 0;)(e = r[u]) && (i && i !== e.nextSibling && i.parentNode.insertBefore(e, i), i = e);
- return this
- }, _a.sort = function(n) {
- n = I.apply(this, arguments);
- for (var t = -1, e = this.length; ++t < e;) this[t].sort(n);
- return this.order()
- }, _a.each = function(n) {
- return Y(this, function(t, e, r) {
- n.call(t, t.__data__, e, r)
- })
- }, _a.call = function(n) {
- var t = ra(arguments);
- return n.apply(t[0] = this, t), this
- }, _a.empty = function() {
- return !this.node()
- }, _a.node = function() {
- for (var n = 0, t = this.length; t > n; n++)
- for (var e = this[n], r = 0, u = e.length; u > r; r++) {
- var i = e[r];
- if (i) return i
- }
- return null
- }, _a.size = function() {
- var n = 0;
- return Y(this, function() {
- ++n
- }), n
- };
- var Sa = [];
- ta.selection.enter = Z, ta.selection.enter.prototype = Sa, Sa.append = _a.append, Sa.empty = _a.empty, Sa.node = _a.node, Sa.call = _a.call, Sa.size = _a.size, Sa.select = function(n) {
- for (var t, e, r, u, i, o = [], a = -1, c = this.length; ++a < c;) {
- r = (u = this[a]).update, o.push(t = []), t.parentNode = u.parentNode;
- for (var l = -1, s = u.length; ++l < s;)(i = u[l]) ? (t.push(r[l] = e = n.call(u.parentNode, i.__data__, l, a)), e.__data__ = i.__data__) : t.push(null)
- }
- return A(o)
- }, Sa.insert = function(n, t) {
- return arguments.length < 2 && (t = V(this)), _a.insert.call(this, n, t)
- }, ta.select = function(t) {
- var e;
- return "string" == typeof t ? (e = [Ma(t, ua)], e.parentNode = ua.documentElement) : (e = [t], e.parentNode = n(t)), A([e])
- }, ta.selectAll = function(n) {
- var t;
- return "string" == typeof n ? (t = ra(xa(n, ua)), t.parentNode = ua.documentElement) : (t = n, t.parentNode = null), A([t])
- }, _a.on = function(n, t, e) {
- var r = arguments.length;
- if (3 > r) {
- if ("string" != typeof n) {
- 2 > r && (t = !1);
- for (e in n) this.each(X(e, n[e], t));
- return this
- }
- if (2 > r) return (r = this.node()["__on" + n]) && r._;
- e = !1
- }
- return this.each(X(n, t, e))
- };
- var ka = ta.map({
- mouseenter: "mouseover",
- mouseleave: "mouseout"
- });
- ua && ka.forEach(function(n) {
- "on" + n in ua && ka.remove(n)
- });
- var Ea, Aa = 0;
- ta.mouse = function(n) {
- return J(n, k())
- };
- var Na = this.navigator && /WebKit/.test(this.navigator.userAgent) ? -1 : 0;
- ta.touch = function(n, t, e) {
- if (arguments.length < 3 && (e = t, t = k().changedTouches), t)
- for (var r, u = 0, i = t.length; i > u; ++u)
- if ((r = t[u]).identifier === e) return J(n, r)
- }, ta.behavior.drag = function() {
- function n() {
- this.on("mousedown.drag", i).on("touchstart.drag", o)
- }
-
- function e(n, t, e, i, o) {
- return function() {
- function a() {
- var n, e, r = t(h, v);
- r && (n = r[0] - M[0], e = r[1] - M[1], p |= n | e, M = r, g({
- type: "drag",
- x: r[0] + l[0],
- y: r[1] + l[1],
- dx: n,
- dy: e
- }))
- }
-
- function c() {
- t(h, v) && (m.on(i + d, null).on(o + d, null), y(p && ta.event.target === f), g({
- type: "dragend"
- }))
- }
- var l, s = this,
- f = ta.event.target,
- h = s.parentNode,
- g = r.of(s, arguments),
- p = 0,
- v = n(),
- d = ".drag" + (null == v ? "" : "-" + v),
- m = ta.select(e(f)).on(i + d, a).on(o + d, c),
- y = W(f),
- M = t(h, v);
- u ? (l = u.apply(s, arguments), l = [l.x - M[0], l.y - M[1]]) : l = [0, 0], g({
- type: "dragstart"
- })
- }
- }
- var r = E(n, "drag", "dragstart", "dragend"),
- u = null,
- i = e(b, ta.mouse, t, "mousemove", "mouseup"),
- o = e(G, ta.touch, y, "touchmove", "touchend");
- return n.origin = function(t) {
- return arguments.length ? (u = t, n) : u
- }, ta.rebind(n, r, "on")
- }, ta.touches = function(n, t) {
- return arguments.length < 2 && (t = k().touches), t ? ra(t).map(function(t) {
- var e = J(n, t);
- return e.identifier = t.identifier, e
- }) : []
- };
- var Ca = 1e-6,
- za = Ca * Ca,
- qa = Math.PI,
- La = 2 * qa,
- Ta = La - Ca,
- Ra = qa / 2,
- Da = qa / 180,
- Pa = 180 / qa,
- Ua = Math.SQRT2,
- ja = 2,
- Fa = 4;
- ta.interpolateZoom = function(n, t) {
- function e(n) {
- var t = n * y;
- if (m) {
- var e = rt(v),
- o = i / (ja * h) * (e * ut(Ua * t + v) - et(v));
- return [r + o * l, u + o * s, i * e / rt(Ua * t + v)]
- }
- return [r + n * l, u + n * s, i * Math.exp(Ua * t)]
- }
- var r = n[0],
- u = n[1],
- i = n[2],
- o = t[0],
- a = t[1],
- c = t[2],
- l = o - r,
- s = a - u,
- f = l * l + s * s,
- h = Math.sqrt(f),
- g = (c * c - i * i + Fa * f) / (2 * i * ja * h),
- p = (c * c - i * i - Fa * f) / (2 * c * ja * h),
- v = Math.log(Math.sqrt(g * g + 1) - g),
- d = Math.log(Math.sqrt(p * p + 1) - p),
- m = d - v,
- y = (m || Math.log(c / i)) / Ua;
- return e.duration = 1e3 * y, e
- }, ta.behavior.zoom = function() {
- function n(n) {
- n.on(q, f).on(Oa + ".zoom", g).on("dblclick.zoom", p).on(R, h)
- }
-
- function e(n) {
- return [(n[0] - k.x) / k.k, (n[1] - k.y) / k.k]
- }
-
- function r(n) {
- return [n[0] * k.k + k.x, n[1] * k.k + k.y]
- }
-
- function u(n) {
- k.k = Math.max(N[0], Math.min(N[1], n))
- }
-
- function i(n, t) {
- t = r(t), k.x += n[0] - t[0], k.y += n[1] - t[1]
- }
-
- function o(t, e, r, o) {
- t.__chart__ = {
- x: k.x,
- y: k.y,
- k: k.k
- }, u(Math.pow(2, o)), i(d = e, r), t = ta.select(t), C > 0 && (t = t.transition().duration(C)), t.call(n.event)
- }
-
- function a() {
- b && b.domain(x.range().map(function(n) {
- return (n - k.x) / k.k
- }).map(x.invert)), w && w.domain(_.range().map(function(n) {
- return (n - k.y) / k.k
- }).map(_.invert))
- }
-
- function c(n) {
- z++ || n({
- type: "zoomstart"
- })
- }
-
- function l(n) {
- a(), n({
- type: "zoom",
- scale: k.k,
- translate: [k.x, k.y]
- })
- }
-
- function s(n) {
- --z || n({
- type: "zoomend"
- }), d = null
- }
-
- function f() {
- function n() {
- f = 1, i(ta.mouse(u), g), l(a)
- }
-
- function r() {
- h.on(L, null).on(T, null), p(f && ta.event.target === o), s(a)
- }
- var u = this,
- o = ta.event.target,
- a = D.of(u, arguments),
- f = 0,
- h = ta.select(t(u)).on(L, n).on(T, r),
- g = e(ta.mouse(u)),
- p = W(u);
- Dl.call(u), c(a)
- }
-
- function h() {
- function n() {
- var n = ta.touches(p);
- return g = k.k, n.forEach(function(n) {
- n.identifier in d && (d[n.identifier] = e(n))
- }), n
- }
-
- function t() {
- var t = ta.event.target;
- ta.select(t).on(x, r).on(b, a), _.push(t);
- for (var e = ta.event.changedTouches, u = 0, i = e.length; i > u; ++u) d[e[u].identifier] = null;
- var c = n(),
- l = Date.now();
- if (1 === c.length) {
- if (500 > l - M) {
- var s = c[0];
- o(p, s, d[s.identifier], Math.floor(Math.log(k.k) / Math.LN2) + 1), S()
- }
- M = l
- } else if (c.length > 1) {
- var s = c[0],
- f = c[1],
- h = s[0] - f[0],
- g = s[1] - f[1];
- m = h * h + g * g
- }
- }
-
- function r() {
- var n, t, e, r, o = ta.touches(p);
- Dl.call(p);
- for (var a = 0, c = o.length; c > a; ++a, r = null)
- if (e = o[a], r = d[e.identifier]) {
- if (t) break;
- n = e, t = r
- } if (r) {
- var s = (s = e[0] - n[0]) * s + (s = e[1] - n[1]) * s,
- f = m && Math.sqrt(s / m);
- n = [(n[0] + e[0]) / 2, (n[1] + e[1]) / 2], t = [(t[0] + r[0]) / 2, (t[1] + r[1]) / 2], u(f * g)
- }
- M = null, i(n, t), l(v)
- }
-
- function a() {
- if (ta.event.touches.length) {
- for (var t = ta.event.changedTouches, e = 0, r = t.length; r > e; ++e) delete d[t[e].identifier];
- for (var u in d) return void n()
- }
- ta.selectAll(_).on(y, null), w.on(q, f).on(R, h), E(), s(v)
- }
- var g, p = this,
- v = D.of(p, arguments),
- d = {},
- m = 0,
- y = ".zoom-" + ta.event.changedTouches[0].identifier,
- x = "touchmove" + y,
- b = "touchend" + y,
- _ = [],
- w = ta.select(p),
- E = W(p);
- t(), c(v), w.on(q, null).on(R, t)
- }
-
- function g() {
- var n = D.of(this, arguments);
- y ? clearTimeout(y) : (v = e(d = m || ta.mouse(this)), Dl.call(this), c(n)), y = setTimeout(function() {
- y = null, s(n)
- }, 50), S(), u(Math.pow(2, .002 * Ha()) * k.k), i(d, v), l(n)
- }
-
- function p() {
- var n = ta.mouse(this),
- t = Math.log(k.k) / Math.LN2;
- o(this, n, e(n), ta.event.shiftKey ? Math.ceil(t) - 1 : Math.floor(t) + 1)
- }
- var v, d, m, y, M, x, b, _, w, k = {
- x: 0,
- y: 0,
- k: 1
- },
- A = [960, 500],
- N = Ia,
- C = 250,
- z = 0,
- q = "mousedown.zoom",
- L = "mousemove.zoom",
- T = "mouseup.zoom",
- R = "touchstart.zoom",
- D = E(n, "zoomstart", "zoom", "zoomend");
- return Oa || (Oa = "onwheel" in ua ? (Ha = function() {
- return -ta.event.deltaY * (ta.event.deltaMode ? 120 : 1)
- }, "wheel") : "onmousewheel" in ua ? (Ha = function() {
- return ta.event.wheelDelta
- }, "mousewheel") : (Ha = function() {
- return -ta.event.detail
- }, "MozMousePixelScroll")), n.event = function(n) {
- n.each(function() {
- var n = D.of(this, arguments),
- t = k;
- Tl ? ta.select(this).transition().each("start.zoom", function() {
- k = this.__chart__ || {
- x: 0,
- y: 0,
- k: 1
- }, c(n)
- }).tween("zoom:zoom", function() {
- var e = A[0],
- r = A[1],
- u = d ? d[0] : e / 2,
- i = d ? d[1] : r / 2,
- o = ta.interpolateZoom([(u - k.x) / k.k, (i - k.y) / k.k, e / k.k], [(u - t.x) / t.k, (i - t.y) / t.k, e / t.k]);
- return function(t) {
- var r = o(t),
- a = e / r[2];
- this.__chart__ = k = {
- x: u - r[0] * a,
- y: i - r[1] * a,
- k: a
- }, l(n)
- }
- }).each("interrupt.zoom", function() {
- s(n)
- }).each("end.zoom", function() {
- s(n)
- }) : (this.__chart__ = k, c(n), l(n), s(n))
- })
- }, n.translate = function(t) {
- return arguments.length ? (k = {
- x: +t[0],
- y: +t[1],
- k: k.k
- }, a(), n) : [k.x, k.y]
- }, n.scale = function(t) {
- return arguments.length ? (k = {
- x: k.x,
- y: k.y,
- k: +t
- }, a(), n) : k.k
- }, n.scaleExtent = function(t) {
- return arguments.length ? (N = null == t ? Ia : [+t[0], +t[1]], n) : N
- }, n.center = function(t) {
- return arguments.length ? (m = t && [+t[0], +t[1]], n) : m
- }, n.size = function(t) {
- return arguments.length ? (A = t && [+t[0], +t[1]], n) : A
- }, n.duration = function(t) {
- return arguments.length ? (C = +t, n) : C
- }, n.x = function(t) {
- return arguments.length ? (b = t, x = t.copy(), k = {
- x: 0,
- y: 0,
- k: 1
- }, n) : b
- }, n.y = function(t) {
- return arguments.length ? (w = t, _ = t.copy(), k = {
- x: 0,
- y: 0,
- k: 1
- }, n) : w
- }, ta.rebind(n, D, "on")
- };
- var Ha, Oa, Ia = [0, 1 / 0];
- ta.color = ot, ot.prototype.toString = function() {
- return this.rgb() + ""
- }, ta.hsl = at;
- var Ya = at.prototype = new ot;
- Ya.brighter = function(n) {
- return n = Math.pow(.7, arguments.length ? n : 1), new at(this.h, this.s, this.l / n)
- }, Ya.darker = function(n) {
- return n = Math.pow(.7, arguments.length ? n : 1), new at(this.h, this.s, n * this.l)
- }, Ya.rgb = function() {
- return ct(this.h, this.s, this.l)
- }, ta.hcl = lt;
- var Za = lt.prototype = new ot;
- Za.brighter = function(n) {
- return new lt(this.h, this.c, Math.min(100, this.l + Va * (arguments.length ? n : 1)))
- }, Za.darker = function(n) {
- return new lt(this.h, this.c, Math.max(0, this.l - Va * (arguments.length ? n : 1)))
- }, Za.rgb = function() {
- return st(this.h, this.c, this.l).rgb()
- }, ta.lab = ft;
- var Va = 18,
- Xa = .95047,
- $a = 1,
- Ba = 1.08883,
- Wa = ft.prototype = new ot;
- Wa.brighter = function(n) {
- return new ft(Math.min(100, this.l + Va * (arguments.length ? n : 1)), this.a, this.b)
- }, Wa.darker = function(n) {
- return new ft(Math.max(0, this.l - Va * (arguments.length ? n : 1)), this.a, this.b)
- }, Wa.rgb = function() {
- return ht(this.l, this.a, this.b)
- }, ta.rgb = mt;
- var Ja = mt.prototype = new ot;
- Ja.brighter = function(n) {
- n = Math.pow(.7, arguments.length ? n : 1);
- var t = this.r,
- e = this.g,
- r = this.b,
- u = 30;
- return t || e || r ? (t && u > t && (t = u), e && u > e && (e = u), r && u > r && (r = u), new mt(Math.min(255, t / n), Math.min(255, e / n), Math.min(255, r / n))) : new mt(u, u, u)
- }, Ja.darker = function(n) {
- return n = Math.pow(.7, arguments.length ? n : 1), new mt(n * this.r, n * this.g, n * this.b)
- }, Ja.hsl = function() {
- return _t(this.r, this.g, this.b)
- }, Ja.toString = function() {
- return "#" + xt(this.r) + xt(this.g) + xt(this.b)
- };
- var Ga = ta.map({
- aliceblue: 15792383,
- antiquewhite: 16444375,
- aqua: 65535,
- aquamarine: 8388564,
- azure: 15794175,
- beige: 16119260,
- bisque: 16770244,
- black: 0,
- blanchedalmond: 16772045,
- blue: 255,
- blueviolet: 9055202,
- brown: 10824234,
- burlywood: 14596231,
- cadetblue: 6266528,
- chartreuse: 8388352,
- chocolate: 13789470,
- coral: 16744272,
- cornflowerblue: 6591981,
- cornsilk: 16775388,
- crimson: 14423100,
- cyan: 65535,
- darkblue: 139,
- darkcyan: 35723,
- darkgoldenrod: 12092939,
- darkgray: 11119017,
- darkgreen: 25600,
- darkgrey: 11119017,
- darkkhaki: 12433259,
- darkmagenta: 9109643,
- darkolivegreen: 5597999,
- darkorange: 16747520,
- darkorchid: 10040012,
- darkred: 9109504,
- darksalmon: 15308410,
- darkseagreen: 9419919,
- darkslateblue: 4734347,
- darkslategray: 3100495,
- darkslategrey: 3100495,
- darkturquoise: 52945,
- darkviolet: 9699539,
- deeppink: 16716947,
- deepskyblue: 49151,
- dimgray: 6908265,
- dimgrey: 6908265,
- dodgerblue: 2003199,
- firebrick: 11674146,
- floralwhite: 16775920,
- forestgreen: 2263842,
- fuchsia: 16711935,
- gainsboro: 14474460,
- ghostwhite: 16316671,
- gold: 16766720,
- goldenrod: 14329120,
- gray: 8421504,
- green: 32768,
- greenyellow: 11403055,
- grey: 8421504,
- honeydew: 15794160,
- hotpink: 16738740,
- indianred: 13458524,
- indigo: 4915330,
- ivory: 16777200,
- khaki: 15787660,
- lavender: 15132410,
- lavenderblush: 16773365,
- lawngreen: 8190976,
- lemonchiffon: 16775885,
- lightblue: 11393254,
- lightcoral: 15761536,
- lightcyan: 14745599,
- lightgoldenrodyellow: 16448210,
- lightgray: 13882323,
- lightgreen: 9498256,
- lightgrey: 13882323,
- lightpink: 16758465,
- lightsalmon: 16752762,
- lightseagreen: 2142890,
- lightskyblue: 8900346,
- lightslategray: 7833753,
- lightslategrey: 7833753,
- lightsteelblue: 11584734,
- lightyellow: 16777184,
- lime: 65280,
- limegreen: 3329330,
- linen: 16445670,
- magenta: 16711935,
- maroon: 8388608,
- mediumaquamarine: 6737322,
- mediumblue: 205,
- mediumorchid: 12211667,
- mediumpurple: 9662683,
- mediumseagreen: 3978097,
- mediumslateblue: 8087790,
- mediumspringgreen: 64154,
- mediumturquoise: 4772300,
- mediumvioletred: 13047173,
- midnightblue: 1644912,
- mintcream: 16121850,
- mistyrose: 16770273,
- moccasin: 16770229,
- navajowhite: 16768685,
- navy: 128,
- oldlace: 16643558,
- olive: 8421376,
- olivedrab: 7048739,
- orange: 16753920,
- orangered: 16729344,
- orchid: 14315734,
- palegoldenrod: 15657130,
- palegreen: 10025880,
- paleturquoise: 11529966,
- palevioletred: 14381203,
- papayawhip: 16773077,
- peachpuff: 16767673,
- peru: 13468991,
- pink: 16761035,
- plum: 14524637,
- powderblue: 11591910,
- purple: 8388736,
- rebeccapurple: 6697881,
- red: 16711680,
- rosybrown: 12357519,
- royalblue: 4286945,
- saddlebrown: 9127187,
- salmon: 16416882,
- sandybrown: 16032864,
- seagreen: 3050327,
- seashell: 16774638,
- sienna: 10506797,
- silver: 12632256,
- skyblue: 8900331,
- slateblue: 6970061,
- slategray: 7372944,
- slategrey: 7372944,
- snow: 16775930,
- springgreen: 65407,
- steelblue: 4620980,
- tan: 13808780,
- teal: 32896,
- thistle: 14204888,
- tomato: 16737095,
- turquoise: 4251856,
- violet: 15631086,
- wheat: 16113331,
- white: 16777215,
- whitesmoke: 16119285,
- yellow: 16776960,
- yellowgreen: 10145074
- });
- Ga.forEach(function(n, t) {
- Ga.set(n, yt(t))
- }), ta.functor = Et, ta.xhr = At(y), ta.dsv = function(n, t) {
- function e(n, e, i) {
- arguments.length < 3 && (i = e, e = null);
- var o = Nt(n, t, null == e ? r : u(e), i);
- return o.row = function(n) {
- return arguments.length ? o.response(null == (e = n) ? r : u(n)) : e
- }, o
- }
-
- function r(n) {
- return e.parse(n.responseText)
- }
-
- function u(n) {
- return function(t) {
- return e.parse(t.responseText, n)
- }
- }
-
- function i(t) {
- return t.map(o).join(n)
- }
-
- function o(n) {
- return a.test(n) ? '"' + n.replace(/\"/g, '""') + '"' : n
- }
- var a = new RegExp('["' + n + "\n]"),
- c = n.charCodeAt(0);
- return e.parse = function(n, t) {
- var r;
- return e.parseRows(n, function(n, e) {
- if (r) return r(n, e - 1);
- var u = new Function("d", "return {" + n.map(function(n, t) {
- return JSON.stringify(n) + ": d[" + t + "]"
- }).join(",") + "}");
- r = t ? function(n, e) {
- return t(u(n), e)
- } : u
- })
- }, e.parseRows = function(n, t) {
- function e() {
- if (s >= l) return o;
- if (u) return u = !1, i;
- var t = s;
- if (34 === n.charCodeAt(t)) {
- for (var e = t; e++ < l;)
- if (34 === n.charCodeAt(e)) {
- if (34 !== n.charCodeAt(e + 1)) break;
- ++e
- } s = e + 2;
- var r = n.charCodeAt(e + 1);
- return 13 === r ? (u = !0, 10 === n.charCodeAt(e + 2) && ++s) : 10 === r && (u = !0), n.slice(t + 1, e).replace(/""/g, '"')
- }
- for (; l > s;) {
- var r = n.charCodeAt(s++),
- a = 1;
- if (10 === r) u = !0;
- else if (13 === r) u = !0, 10 === n.charCodeAt(s) && (++s, ++a);
- else if (r !== c) continue;
- return n.slice(t, s - a)
- }
- return n.slice(t)
- }
- for (var r, u, i = {}, o = {}, a = [], l = n.length, s = 0, f = 0;
- (r = e()) !== o;) {
- for (var h = []; r !== i && r !== o;) h.push(r), r = e();
- t && null == (h = t(h, f++)) || a.push(h)
- }
- return a
- }, e.format = function(t) {
- if (Array.isArray(t[0])) return e.formatRows(t);
- var r = new m,
- u = [];
- return t.forEach(function(n) {
- for (var t in n) r.has(t) || u.push(r.add(t))
- }), [u.map(o).join(n)].concat(t.map(function(t) {
- return u.map(function(n) {
- return o(t[n])
- }).join(n)
- })).join("\n")
- }, e.formatRows = function(n) {
- return n.map(i).join("\n")
- }, e
- }, ta.csv = ta.dsv(",", "text/csv"), ta.tsv = ta.dsv(" ", "text/tab-separated-values");
- var Ka, Qa, nc, tc, ec, rc = this[x(this, "requestAnimationFrame")] || function(n) {
- setTimeout(n, 17)
- };
- ta.timer = function(n, t, e) {
- var r = arguments.length;
- 2 > r && (t = 0), 3 > r && (e = Date.now());
- var u = e + t,
- i = {
- c: n,
- t: u,
- f: !1,
- n: null
- };
- Qa ? Qa.n = i : Ka = i, Qa = i, nc || (tc = clearTimeout(tc), nc = 1, rc(qt))
- }, ta.timer.flush = function() {
- Lt(), Tt()
- }, ta.round = function(n, t) {
- return t ? Math.round(n * (t = Math.pow(10, t))) / t : Math.round(n)
- };
- var uc = ["y", "z", "a", "f", "p", "n", "\xb5", "m", "", "k", "M", "G", "T", "P", "E", "Z", "Y"].map(Dt);
- ta.formatPrefix = function(n, t) {
- var e = 0;
- return n && (0 > n && (n *= -1), t && (n = ta.round(n, Rt(n, t))), e = 1 + Math.floor(1e-12 + Math.log(n) / Math.LN10), e = Math.max(-24, Math.min(24, 3 * Math.floor((e - 1) / 3)))), uc[8 + e / 3]
- };
- var ic = /(?:([^{])?([<>=^]))?([+\- ])?([$#])?(0)?(\d+)?(,)?(\.-?\d+)?([a-z%])?/i,
- oc = ta.map({
- b: function(n) {
- return n.toString(2)
- },
- c: function(n) {
- return String.fromCharCode(n)
- },
- o: function(n) {
- return n.toString(8)
- },
- x: function(n) {
- return n.toString(16)
- },
- X: function(n) {
- return n.toString(16).toUpperCase()
- },
- g: function(n, t) {
- return n.toPrecision(t)
- },
- e: function(n, t) {
- return n.toExponential(t)
- },
- f: function(n, t) {
- return n.toFixed(t)
- },
- r: function(n, t) {
- return (n = ta.round(n, Rt(n, t))).toFixed(Math.max(0, Math.min(20, Rt(n * (1 + 1e-15), t))))
- }
- }),
- ac = ta.time = {},
- cc = Date;
- jt.prototype = {
- getDate: function() {
- return this._.getUTCDate()
- },
- getDay: function() {
- return this._.getUTCDay()
- },
- getFullYear: function() {
- return this._.getUTCFullYear()
- },
- getHours: function() {
- return this._.getUTCHours()
- },
- getMilliseconds: function() {
- return this._.getUTCMilliseconds()
- },
- getMinutes: function() {
- return this._.getUTCMinutes()
- },
- getMonth: function() {
- return this._.getUTCMonth()
- },
- getSeconds: function() {
- return this._.getUTCSeconds()
- },
- getTime: function() {
- return this._.getTime()
- },
- getTimezoneOffset: function() {
- return 0
- },
- valueOf: function() {
- return this._.valueOf()
- },
- setDate: function() {
- lc.setUTCDate.apply(this._, arguments)
- },
- setDay: function() {
- lc.setUTCDay.apply(this._, arguments)
- },
- setFullYear: function() {
- lc.setUTCFullYear.apply(this._, arguments)
- },
- setHours: function() {
- lc.setUTCHours.apply(this._, arguments)
- },
- setMilliseconds: function() {
- lc.setUTCMilliseconds.apply(this._, arguments)
- },
- setMinutes: function() {
- lc.setUTCMinutes.apply(this._, arguments)
- },
- setMonth: function() {
- lc.setUTCMonth.apply(this._, arguments)
- },
- setSeconds: function() {
- lc.setUTCSeconds.apply(this._, arguments)
- },
- setTime: function() {
- lc.setTime.apply(this._, arguments)
- }
- };
- var lc = Date.prototype;
- ac.year = Ft(function(n) {
- return n = ac.day(n), n.setMonth(0, 1), n
- }, function(n, t) {
- n.setFullYear(n.getFullYear() + t)
- }, function(n) {
- return n.getFullYear()
- }), ac.years = ac.year.range, ac.years.utc = ac.year.utc.range, ac.day = Ft(function(n) {
- var t = new cc(2e3, 0);
- return t.setFullYear(n.getFullYear(), n.getMonth(), n.getDate()), t
- }, function(n, t) {
- n.setDate(n.getDate() + t)
- }, function(n) {
- return n.getDate() - 1
- }), ac.days = ac.day.range, ac.days.utc = ac.day.utc.range, ac.dayOfYear = function(n) {
- var t = ac.year(n);
- return Math.floor((n - t - 6e4 * (n.getTimezoneOffset() - t.getTimezoneOffset())) / 864e5)
- }, ["sunday", "monday", "tuesday", "wednesday", "thursday", "friday", "saturday"].forEach(function(n, t) {
- t = 7 - t;
- var e = ac[n] = Ft(function(n) {
- return (n = ac.day(n)).setDate(n.getDate() - (n.getDay() + t) % 7), n
- }, function(n, t) {
- n.setDate(n.getDate() + 7 * Math.floor(t))
- }, function(n) {
- var e = ac.year(n).getDay();
- return Math.floor((ac.dayOfYear(n) + (e + t) % 7) / 7) - (e !== t)
- });
- ac[n + "s"] = e.range, ac[n + "s"].utc = e.utc.range, ac[n + "OfYear"] = function(n) {
- var e = ac.year(n).getDay();
- return Math.floor((ac.dayOfYear(n) + (e + t) % 7) / 7)
- }
- }), ac.week = ac.sunday, ac.weeks = ac.sunday.range, ac.weeks.utc = ac.sunday.utc.range, ac.weekOfYear = ac.sundayOfYear;
- var sc = {
- "-": "",
- _: " ",
- 0: "0"
- },
- fc = /^\s*\d+/,
- hc = /^%/;
- ta.locale = function(n) {
- return {
- numberFormat: Pt(n),
- timeFormat: Ot(n)
- }
- };
- var gc = ta.locale({
- decimal: ".",
- thousands: ",",
- grouping: [3],
- currency: ["$", ""],
- dateTime: "%a %b %e %X %Y",
- date: "%m/%d/%Y",
- time: "%H:%M:%S",
- periods: ["AM", "PM"],
- days: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"],
- shortDays: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
- months: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
- shortMonths: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"]
- });
- ta.format = gc.numberFormat, ta.geo = {}, ce.prototype = {
- s: 0,
- t: 0,
- add: function(n) {
- le(n, this.t, pc), le(pc.s, this.s, this), this.s ? this.t += pc.t : this.s = pc.t
- },
- reset: function() {
- this.s = this.t = 0
- },
- valueOf: function() {
- return this.s
- }
- };
- var pc = new ce;
- ta.geo.stream = function(n, t) {
- n && vc.hasOwnProperty(n.type) ? vc[n.type](n, t) : se(n, t)
- };
- var vc = {
- Feature: function(n, t) {
- se(n.geometry, t)
- },
- FeatureCollection: function(n, t) {
- for (var e = n.features, r = -1, u = e.length; ++r < u;) se(e[r].geometry, t)
- }
- },
- dc = {
- Sphere: function(n, t) {
- t.sphere()
- },
- Point: function(n, t) {
- n = n.coordinates, t.point(n[0], n[1], n[2])
- },
- MultiPoint: function(n, t) {
- for (var e = n.coordinates, r = -1, u = e.length; ++r < u;) n = e[r], t.point(n[0], n[1], n[2])
- },
- LineString: function(n, t) {
- fe(n.coordinates, t, 0)
- },
- MultiLineString: function(n, t) {
- for (var e = n.coordinates, r = -1, u = e.length; ++r < u;) fe(e[r], t, 0)
- },
- Polygon: function(n, t) {
- he(n.coordinates, t)
- },
- MultiPolygon: function(n, t) {
- for (var e = n.coordinates, r = -1, u = e.length; ++r < u;) he(e[r], t)
- },
- GeometryCollection: function(n, t) {
- for (var e = n.geometries, r = -1, u = e.length; ++r < u;) se(e[r], t)
- }
- };
- ta.geo.area = function(n) {
- return mc = 0, ta.geo.stream(n, Mc), mc
- };
- var mc, yc = new ce,
- Mc = {
- sphere: function() {
- mc += 4 * qa
- },
- point: b,
- lineStart: b,
- lineEnd: b,
- polygonStart: function() {
- yc.reset(), Mc.lineStart = ge
- },
- polygonEnd: function() {
- var n = 2 * yc;
- mc += 0 > n ? 4 * qa + n : n, Mc.lineStart = Mc.lineEnd = Mc.point = b
- }
- };
- ta.geo.bounds = function() {
- function n(n, t) {
- M.push(x = [s = n, h = n]), f > t && (f = t), t > g && (g = t)
- }
-
- function t(t, e) {
- var r = pe([t * Da, e * Da]);
- if (m) {
- var u = de(m, r),
- i = [u[1], -u[0], 0],
- o = de(i, u);
- Me(o), o = xe(o);
- var c = t - p,
- l = c > 0 ? 1 : -1,
- v = o[0] * Pa * l,
- d = ga(c) > 180;
- if (d ^ (v > l * p && l * t > v)) {
- var y = o[1] * Pa;
- y > g && (g = y)
- } else if (v = (v + 360) % 360 - 180, d ^ (v > l * p && l * t > v)) {
- var y = -o[1] * Pa;
- f > y && (f = y)
- } else f > e && (f = e), e > g && (g = e);
- d ? p > t ? a(s, t) > a(s, h) && (h = t) : a(t, h) > a(s, h) && (s = t) : h >= s ? (s > t && (s = t), t > h && (h = t)) : t > p ? a(s, t) > a(s, h) && (h = t) : a(t, h) > a(s, h) && (s = t)
- } else n(t, e);
- m = r, p = t
- }
-
- function e() {
- b.point = t
- }
-
- function r() {
- x[0] = s, x[1] = h, b.point = n, m = null
- }
-
- function u(n, e) {
- if (m) {
- var r = n - p;
- y += ga(r) > 180 ? r + (r > 0 ? 360 : -360) : r
- } else v = n, d = e;
- Mc.point(n, e), t(n, e)
- }
-
- function i() {
- Mc.lineStart()
- }
-
- function o() {
- u(v, d), Mc.lineEnd(), ga(y) > Ca && (s = -(h = 180)), x[0] = s, x[1] = h, m = null
- }
-
- function a(n, t) {
- return (t -= n) < 0 ? t + 360 : t
- }
-
- function c(n, t) {
- return n[0] - t[0]
- }
-
- function l(n, t) {
- return t[0] <= t[1] ? t[0] <= n && n <= t[1] : n < t[0] || t[1] < n
- }
- var s, f, h, g, p, v, d, m, y, M, x, b = {
- point: n,
- lineStart: e,
- lineEnd: r,
- polygonStart: function() {
- b.point = u, b.lineStart = i, b.lineEnd = o, y = 0, Mc.polygonStart()
- },
- polygonEnd: function() {
- Mc.polygonEnd(), b.point = n, b.lineStart = e, b.lineEnd = r, 0 > yc ? (s = -(h = 180), f = -(g = 90)) : y > Ca ? g = 90 : -Ca > y && (f = -90), x[0] = s, x[1] = h
- }
- };
- return function(n) {
- g = h = -(s = f = 1 / 0), M = [], ta.geo.stream(n, b);
- var t = M.length;
- if (t) {
- M.sort(c);
- for (var e, r = 1, u = M[0], i = [u]; t > r; ++r) e = M[r], l(e[0], u) || l(e[1], u) ? (a(u[0], e[1]) > a(u[0], u[1]) && (u[1] = e[1]), a(e[0], u[1]) > a(u[0], u[1]) && (u[0] = e[0])) : i.push(u = e);
- for (var o, e, p = -1 / 0, t = i.length - 1, r = 0, u = i[t]; t >= r; u = e, ++r) e = i[r], (o = a(u[1], e[0])) > p && (p = o, s = e[0], h = u[1])
- }
- return M = x = null, 1 / 0 === s || 1 / 0 === f ? [
- [0 / 0, 0 / 0],
- [0 / 0, 0 / 0]
- ] : [
- [s, f],
- [h, g]
- ]
- }
- }(), ta.geo.centroid = function(n) {
- xc = bc = _c = wc = Sc = kc = Ec = Ac = Nc = Cc = zc = 0, ta.geo.stream(n, qc);
- var t = Nc,
- e = Cc,
- r = zc,
- u = t * t + e * e + r * r;
- return za > u && (t = kc, e = Ec, r = Ac, Ca > bc && (t = _c, e = wc, r = Sc), u = t * t + e * e + r * r, za > u) ? [0 / 0, 0 / 0] : [Math.atan2(e, t) * Pa, tt(r / Math.sqrt(u)) * Pa]
- };
- var xc, bc, _c, wc, Sc, kc, Ec, Ac, Nc, Cc, zc, qc = {
- sphere: b,
- point: _e,
- lineStart: Se,
- lineEnd: ke,
- polygonStart: function() {
- qc.lineStart = Ee
- },
- polygonEnd: function() {
- qc.lineStart = Se
- }
- },
- Lc = Le(Ne, Pe, je, [-qa, -qa / 2]),
- Tc = 1e9;
- ta.geo.clipExtent = function() {
- var n, t, e, r, u, i, o = {
- stream: function(n) {
- return u && (u.valid = !1), u = i(n), u.valid = !0, u
- },
- extent: function(a) {
- return arguments.length ? (i = Ie(n = +a[0][0], t = +a[0][1], e = +a[1][0], r = +a[1][1]), u && (u.valid = !1, u = null), o) : [
- [n, t],
- [e, r]
- ]
- }
- };
- return o.extent([
- [0, 0],
- [960, 500]
- ])
- }, (ta.geo.conicEqualArea = function() {
- return Ye(Ze)
- }).raw = Ze, ta.geo.albers = function() {
- return ta.geo.conicEqualArea().rotate([96, 0]).center([-.6, 38.7]).parallels([29.5, 45.5]).scale(1070)
- }, ta.geo.albersUsa = function() {
- function n(n) {
- var i = n[0],
- o = n[1];
- return t = null, e(i, o), t || (r(i, o), t) || u(i, o), t
- }
- var t, e, r, u, i = ta.geo.albers(),
- o = ta.geo.conicEqualArea().rotate([154, 0]).center([-2, 58.5]).parallels([55, 65]),
- a = ta.geo.conicEqualArea().rotate([157, 0]).center([-3, 19.9]).parallels([8, 18]),
- c = {
- point: function(n, e) {
- t = [n, e]
- }
- };
- return n.invert = function(n) {
- var t = i.scale(),
- e = i.translate(),
- r = (n[0] - e[0]) / t,
- u = (n[1] - e[1]) / t;
- return (u >= .12 && .234 > u && r >= -.425 && -.214 > r ? o : u >= .166 && .234 > u && r >= -.214 && -.115 > r ? a : i).invert(n)
- }, n.stream = function(n) {
- var t = i.stream(n),
- e = o.stream(n),
- r = a.stream(n);
- return {
- point: function(n, u) {
- t.point(n, u), e.point(n, u), r.point(n, u)
- },
- sphere: function() {
- t.sphere(), e.sphere(), r.sphere()
- },
- lineStart: function() {
- t.lineStart(), e.lineStart(), r.lineStart()
- },
- lineEnd: function() {
- t.lineEnd(), e.lineEnd(), r.lineEnd()
- },
- polygonStart: function() {
- t.polygonStart(), e.polygonStart(), r.polygonStart()
- },
- polygonEnd: function() {
- t.polygonEnd(), e.polygonEnd(), r.polygonEnd()
- }
- }
- }, n.precision = function(t) {
- return arguments.length ? (i.precision(t), o.precision(t), a.precision(t), n) : i.precision()
- }, n.scale = function(t) {
- return arguments.length ? (i.scale(t), o.scale(.35 * t), a.scale(t), n.translate(i.translate())) : i.scale()
- }, n.translate = function(t) {
- if (!arguments.length) return i.translate();
- var l = i.scale(),
- s = +t[0],
- f = +t[1];
- return e = i.translate(t).clipExtent([
- [s - .455 * l, f - .238 * l],
- [s + .455 * l, f + .238 * l]
- ]).stream(c).point, r = o.translate([s - .307 * l, f + .201 * l]).clipExtent([
- [s - .425 * l + Ca, f + .12 * l + Ca],
- [s - .214 * l - Ca, f + .234 * l - Ca]
- ]).stream(c).point, u = a.translate([s - .205 * l, f + .212 * l]).clipExtent([
- [s - .214 * l + Ca, f + .166 * l + Ca],
- [s - .115 * l - Ca, f + .234 * l - Ca]
- ]).stream(c).point, n
- }, n.scale(1070)
- };
- var Rc, Dc, Pc, Uc, jc, Fc, Hc = {
- point: b,
- lineStart: b,
- lineEnd: b,
- polygonStart: function() {
- Dc = 0, Hc.lineStart = Ve
- },
- polygonEnd: function() {
- Hc.lineStart = Hc.lineEnd = Hc.point = b, Rc += ga(Dc / 2)
- }
- },
- Oc = {
- point: Xe,
- lineStart: b,
- lineEnd: b,
- polygonStart: b,
- polygonEnd: b
- },
- Ic = {
- point: We,
- lineStart: Je,
- lineEnd: Ge,
- polygonStart: function() {
- Ic.lineStart = Ke
- },
- polygonEnd: function() {
- Ic.point = We, Ic.lineStart = Je, Ic.lineEnd = Ge
- }
- };
- ta.geo.path = function() {
- function n(n) {
- return n && ("function" == typeof a && i.pointRadius(+a.apply(this, arguments)), o && o.valid || (o = u(i)), ta.geo.stream(n, o)), i.result()
- }
-
- function t() {
- return o = null, n
- }
- var e, r, u, i, o, a = 4.5;
- return n.area = function(n) {
- return Rc = 0, ta.geo.stream(n, u(Hc)), Rc
- }, n.centroid = function(n) {
- return _c = wc = Sc = kc = Ec = Ac = Nc = Cc = zc = 0, ta.geo.stream(n, u(Ic)), zc ? [Nc / zc, Cc / zc] : Ac ? [kc / Ac, Ec / Ac] : Sc ? [_c / Sc, wc / Sc] : [0 / 0, 0 / 0]
- }, n.bounds = function(n) {
- return jc = Fc = -(Pc = Uc = 1 / 0), ta.geo.stream(n, u(Oc)), [
- [Pc, Uc],
- [jc, Fc]
- ]
- }, n.projection = function(n) {
- return arguments.length ? (u = (e = n) ? n.stream || tr(n) : y, t()) : e
- }, n.context = function(n) {
- return arguments.length ? (i = null == (r = n) ? new $e : new Qe(n), "function" != typeof a && i.pointRadius(a), t()) : r
- }, n.pointRadius = function(t) {
- return arguments.length ? (a = "function" == typeof t ? t : (i.pointRadius(+t), +t), n) : a
- }, n.projection(ta.geo.albersUsa()).context(null)
- }, ta.geo.transform = function(n) {
- return {
- stream: function(t) {
- var e = new er(t);
- for (var r in n) e[r] = n[r];
- return e
- }
- }
- }, er.prototype = {
- point: function(n, t) {
- this.stream.point(n, t)
- },
- sphere: function() {
- this.stream.sphere()
- },
- lineStart: function() {
- this.stream.lineStart()
- },
- lineEnd: function() {
- this.stream.lineEnd()
- },
- polygonStart: function() {
- this.stream.polygonStart()
- },
- polygonEnd: function() {
- this.stream.polygonEnd()
- }
- }, ta.geo.projection = ur, ta.geo.projectionMutator = ir, (ta.geo.equirectangular = function() {
- return ur(ar)
- }).raw = ar.invert = ar, ta.geo.rotation = function(n) {
- function t(t) {
- return t = n(t[0] * Da, t[1] * Da), t[0] *= Pa, t[1] *= Pa, t
- }
- return n = lr(n[0] % 360 * Da, n[1] * Da, n.length > 2 ? n[2] * Da : 0), t.invert = function(t) {
- return t = n.invert(t[0] * Da, t[1] * Da), t[0] *= Pa, t[1] *= Pa, t
- }, t
- }, cr.invert = ar, ta.geo.circle = function() {
- function n() {
- var n = "function" == typeof r ? r.apply(this, arguments) : r,
- t = lr(-n[0] * Da, -n[1] * Da, 0).invert,
- u = [];
- return e(null, null, 1, {
- point: function(n, e) {
- u.push(n = t(n, e)), n[0] *= Pa, n[1] *= Pa
- }
- }), {
- type: "Polygon",
- coordinates: [u]
- }
- }
- var t, e, r = [0, 0],
- u = 6;
- return n.origin = function(t) {
- return arguments.length ? (r = t, n) : r
- }, n.angle = function(r) {
- return arguments.length ? (e = gr((t = +r) * Da, u * Da), n) : t
- }, n.precision = function(r) {
- return arguments.length ? (e = gr(t * Da, (u = +r) * Da), n) : u
- }, n.angle(90)
- }, ta.geo.distance = function(n, t) {
- var e, r = (t[0] - n[0]) * Da,
- u = n[1] * Da,
- i = t[1] * Da,
- o = Math.sin(r),
- a = Math.cos(r),
- c = Math.sin(u),
- l = Math.cos(u),
- s = Math.sin(i),
- f = Math.cos(i);
- return Math.atan2(Math.sqrt((e = f * o) * e + (e = l * s - c * f * a) * e), c * s + l * f * a)
- }, ta.geo.graticule = function() {
- function n() {
- return {
- type: "MultiLineString",
- coordinates: t()
- }
- }
-
- function t() {
- return ta.range(Math.ceil(i / d) * d, u, d).map(h).concat(ta.range(Math.ceil(l / m) * m, c, m).map(g)).concat(ta.range(Math.ceil(r / p) * p, e, p).filter(function(n) {
- return ga(n % d) > Ca
- }).map(s)).concat(ta.range(Math.ceil(a / v) * v, o, v).filter(function(n) {
- return ga(n % m) > Ca
- }).map(f))
- }
- var e, r, u, i, o, a, c, l, s, f, h, g, p = 10,
- v = p,
- d = 90,
- m = 360,
- y = 2.5;
- return n.lines = function() {
- return t().map(function(n) {
- return {
- type: "LineString",
- coordinates: n
- }
- })
- }, n.outline = function() {
- return {
- type: "Polygon",
- coordinates: [h(i).concat(g(c).slice(1), h(u).reverse().slice(1), g(l).reverse().slice(1))]
- }
- }, n.extent = function(t) {
- return arguments.length ? n.majorExtent(t).minorExtent(t) : n.minorExtent()
- }, n.majorExtent = function(t) {
- return arguments.length ? (i = +t[0][0], u = +t[1][0], l = +t[0][1], c = +t[1][1], i > u && (t = i, i = u, u = t), l > c && (t = l, l = c, c = t), n.precision(y)) : [
- [i, l],
- [u, c]
- ]
- }, n.minorExtent = function(t) {
- return arguments.length ? (r = +t[0][0], e = +t[1][0], a = +t[0][1], o = +t[1][1], r > e && (t = r, r = e, e = t), a > o && (t = a, a = o, o = t), n.precision(y)) : [
- [r, a],
- [e, o]
- ]
- }, n.step = function(t) {
- return arguments.length ? n.majorStep(t).minorStep(t) : n.minorStep()
- }, n.majorStep = function(t) {
- return arguments.length ? (d = +t[0], m = +t[1], n) : [d, m]
- }, n.minorStep = function(t) {
- return arguments.length ? (p = +t[0], v = +t[1], n) : [p, v]
- }, n.precision = function(t) {
- return arguments.length ? (y = +t, s = vr(a, o, 90), f = dr(r, e, y), h = vr(l, c, 90), g = dr(i, u, y), n) : y
- }, n.majorExtent([
- [-180, -90 + Ca],
- [180, 90 - Ca]
- ]).minorExtent([
- [-180, -80 - Ca],
- [180, 80 + Ca]
- ])
- }, ta.geo.greatArc = function() {
- function n() {
- return {
- type: "LineString",
- coordinates: [t || r.apply(this, arguments), e || u.apply(this, arguments)]
- }
- }
- var t, e, r = mr,
- u = yr;
- return n.distance = function() {
- return ta.geo.distance(t || r.apply(this, arguments), e || u.apply(this, arguments))
- }, n.source = function(e) {
- return arguments.length ? (r = e, t = "function" == typeof e ? null : e, n) : r
- }, n.target = function(t) {
- return arguments.length ? (u = t, e = "function" == typeof t ? null : t, n) : u
- }, n.precision = function() {
- return arguments.length ? n : 0
- }, n
- }, ta.geo.interpolate = function(n, t) {
- return Mr(n[0] * Da, n[1] * Da, t[0] * Da, t[1] * Da)
- }, ta.geo.length = function(n) {
- return Yc = 0, ta.geo.stream(n, Zc), Yc
- };
- var Yc, Zc = {
- sphere: b,
- point: b,
- lineStart: xr,
- lineEnd: b,
- polygonStart: b,
- polygonEnd: b
- },
- Vc = br(function(n) {
- return Math.sqrt(2 / (1 + n))
- }, function(n) {
- return 2 * Math.asin(n / 2)
- });
- (ta.geo.azimuthalEqualArea = function() {
- return ur(Vc)
- }).raw = Vc;
- var Xc = br(function(n) {
- var t = Math.acos(n);
- return t && t / Math.sin(t)
- }, y);
- (ta.geo.azimuthalEquidistant = function() {
- return ur(Xc)
- }).raw = Xc, (ta.geo.conicConformal = function() {
- return Ye(_r)
- }).raw = _r, (ta.geo.conicEquidistant = function() {
- return Ye(wr)
- }).raw = wr;
- var $c = br(function(n) {
- return 1 / n
- }, Math.atan);
- (ta.geo.gnomonic = function() {
- return ur($c)
- }).raw = $c, Sr.invert = function(n, t) {
- return [n, 2 * Math.atan(Math.exp(t)) - Ra]
- }, (ta.geo.mercator = function() {
- return kr(Sr)
- }).raw = Sr;
- var Bc = br(function() {
- return 1
- }, Math.asin);
- (ta.geo.orthographic = function() {
- return ur(Bc)
- }).raw = Bc;
- var Wc = br(function(n) {
- return 1 / (1 + n)
- }, function(n) {
- return 2 * Math.atan(n)
- });
- (ta.geo.stereographic = function() {
- return ur(Wc)
- }).raw = Wc, Er.invert = function(n, t) {
- return [-t, 2 * Math.atan(Math.exp(n)) - Ra]
- }, (ta.geo.transverseMercator = function() {
- var n = kr(Er),
- t = n.center,
- e = n.rotate;
- return n.center = function(n) {
- return n ? t([-n[1], n[0]]) : (n = t(), [n[1], -n[0]])
- }, n.rotate = function(n) {
- return n ? e([n[0], n[1], n.length > 2 ? n[2] + 90 : 90]) : (n = e(), [n[0], n[1], n[2] - 90])
- }, e([0, 0, 90])
- }).raw = Er, ta.geom = {}, ta.geom.hull = function(n) {
- function t(n) {
- if (n.length < 3) return [];
- var t, u = Et(e),
- i = Et(r),
- o = n.length,
- a = [],
- c = [];
- for (t = 0; o > t; t++) a.push([+u.call(this, n[t], t), +i.call(this, n[t], t), t]);
- for (a.sort(zr), t = 0; o > t; t++) c.push([a[t][0], -a[t][1]]);
- var l = Cr(a),
- s = Cr(c),
- f = s[0] === l[0],
- h = s[s.length - 1] === l[l.length - 1],
- g = [];
- for (t = l.length - 1; t >= 0; --t) g.push(n[a[l[t]][2]]);
- for (t = +f; t < s.length - h; ++t) g.push(n[a[s[t]][2]]);
- return g
- }
- var e = Ar,
- r = Nr;
- return arguments.length ? t(n) : (t.x = function(n) {
- return arguments.length ? (e = n, t) : e
- }, t.y = function(n) {
- return arguments.length ? (r = n, t) : r
- }, t)
- }, ta.geom.polygon = function(n) {
- return ya(n, Jc), n
- };
- var Jc = ta.geom.polygon.prototype = [];
- Jc.area = function() {
- for (var n, t = -1, e = this.length, r = this[e - 1], u = 0; ++t < e;) n = r, r = this[t], u += n[1] * r[0] - n[0] * r[1];
- return .5 * u
- }, Jc.centroid = function(n) {
- var t, e, r = -1,
- u = this.length,
- i = 0,
- o = 0,
- a = this[u - 1];
- for (arguments.length || (n = -1 / (6 * this.area())); ++r < u;) t = a, a = this[r], e = t[0] * a[1] - a[0] * t[1], i += (t[0] + a[0]) * e, o += (t[1] + a[1]) * e;
- return [i * n, o * n]
- }, Jc.clip = function(n) {
- for (var t, e, r, u, i, o, a = Tr(n), c = -1, l = this.length - Tr(this), s = this[l - 1]; ++c < l;) {
- for (t = n.slice(), n.length = 0, u = this[c], i = t[(r = t.length - a) - 1], e = -1; ++e < r;) o = t[e], qr(o, s, u) ? (qr(i, s, u) || n.push(Lr(i, o, s, u)), n.push(o)) : qr(i, s, u) && n.push(Lr(i, o, s, u)), i = o;
- a && n.push(n[0]), s = u
- }
- return n
- };
- var Gc, Kc, Qc, nl, tl, el = [],
- rl = [];
- Or.prototype.prepare = function() {
- for (var n, t = this.edges, e = t.length; e--;) n = t[e].edge, n.b && n.a || t.splice(e, 1);
- return t.sort(Yr), t.length
- }, Qr.prototype = {
- start: function() {
- return this.edge.l === this.site ? this.edge.a : this.edge.b
- },
- end: function() {
- return this.edge.l === this.site ? this.edge.b : this.edge.a
- }
- }, nu.prototype = {
- insert: function(n, t) {
- var e, r, u;
- if (n) {
- if (t.P = n, t.N = n.N, n.N && (n.N.P = t), n.N = t, n.R) {
- for (n = n.R; n.L;) n = n.L;
- n.L = t
- } else n.R = t;
- e = n
- } else this._ ? (n = uu(this._), t.P = null, t.N = n, n.P = n.L = t, e = n) : (t.P = t.N = null, this._ = t, e = null);
- for (t.L = t.R = null, t.U = e, t.C = !0, n = t; e && e.C;) r = e.U, e === r.L ? (u = r.R, u && u.C ? (e.C = u.C = !1, r.C = !0, n = r) : (n === e.R && (eu(this, e), n = e, e = n.U), e.C = !1, r.C = !0, ru(this, r))) : (u = r.L, u && u.C ? (e.C = u.C = !1, r.C = !0, n = r) : (n === e.L && (ru(this, e), n = e, e = n.U), e.C = !1, r.C = !0, eu(this, r))), e = n.U;
- this._.C = !1
- },
- remove: function(n) {
- n.N && (n.N.P = n.P), n.P && (n.P.N = n.N), n.N = n.P = null;
- var t, e, r, u = n.U,
- i = n.L,
- o = n.R;
- if (e = i ? o ? uu(o) : i : o, u ? u.L === n ? u.L = e : u.R = e : this._ = e, i && o ? (r = e.C, e.C = n.C, e.L = i, i.U = e, e !== o ? (u = e.U, e.U = n.U, n = e.R, u.L = n, e.R = o, o.U = e) : (e.U = u, u = e, n = e.R)) : (r = n.C, n = e), n && (n.U = u), !r) {
- if (n && n.C) return void(n.C = !1);
- do {
- if (n === this._) break;
- if (n === u.L) {
- if (t = u.R, t.C && (t.C = !1, u.C = !0, eu(this, u), t = u.R), t.L && t.L.C || t.R && t.R.C) {
- t.R && t.R.C || (t.L.C = !1, t.C = !0, ru(this, t), t = u.R), t.C = u.C, u.C = t.R.C = !1, eu(this, u), n = this._;
- break
- }
- } else if (t = u.L, t.C && (t.C = !1, u.C = !0, ru(this, u), t = u.L), t.L && t.L.C || t.R && t.R.C) {
- t.L && t.L.C || (t.R.C = !1, t.C = !0, eu(this, t), t = u.L), t.C = u.C, u.C = t.L.C = !1, ru(this, u), n = this._;
- break
- }
- t.C = !0, n = u, u = u.U
- } while (!n.C);
- n && (n.C = !1)
- }
- }
- }, ta.geom.voronoi = function(n) {
- function t(n) {
- var t = new Array(n.length),
- r = a[0][0],
- u = a[0][1],
- i = a[1][0],
- o = a[1][1];
- return iu(e(n), a).cells.forEach(function(e, a) {
- var c = e.edges,
- l = e.site,
- s = t[a] = c.length ? c.map(function(n) {
- var t = n.start();
- return [t.x, t.y]
- }) : l.x >= r && l.x <= i && l.y >= u && l.y <= o ? [
- [r, o],
- [i, o],
- [i, u],
- [r, u]
- ] : [];
- s.point = n[a]
- }), t
- }
-
- function e(n) {
- return n.map(function(n, t) {
- return {
- x: Math.round(i(n, t) / Ca) * Ca,
- y: Math.round(o(n, t) / Ca) * Ca,
- i: t
- }
- })
- }
- var r = Ar,
- u = Nr,
- i = r,
- o = u,
- a = ul;
- return n ? t(n) : (t.links = function(n) {
- return iu(e(n)).edges.filter(function(n) {
- return n.l && n.r
- }).map(function(t) {
- return {
- source: n[t.l.i],
- target: n[t.r.i]
- }
- })
- }, t.triangles = function(n) {
- var t = [];
- return iu(e(n)).cells.forEach(function(e, r) {
- for (var u, i, o = e.site, a = e.edges.sort(Yr), c = -1, l = a.length, s = a[l - 1].edge, f = s.l === o ? s.r : s.l; ++c < l;) u = s, i = f, s = a[c].edge, f = s.l === o ? s.r : s.l, r < i.i && r < f.i && au(o, i, f) < 0 && t.push([n[r], n[i.i], n[f.i]])
- }), t
- }, t.x = function(n) {
- return arguments.length ? (i = Et(r = n), t) : r
- }, t.y = function(n) {
- return arguments.length ? (o = Et(u = n), t) : u
- }, t.clipExtent = function(n) {
- return arguments.length ? (a = null == n ? ul : n, t) : a === ul ? null : a
- }, t.size = function(n) {
- return arguments.length ? t.clipExtent(n && [
- [0, 0], n
- ]) : a === ul ? null : a && a[1]
- }, t)
- };
- var ul = [
- [-1e6, -1e6],
- [1e6, 1e6]
- ];
- ta.geom.delaunay = function(n) {
- return ta.geom.voronoi().triangles(n)
- }, ta.geom.quadtree = function(n, t, e, r, u) {
- function i(n) {
- function i(n, t, e, r, u, i, o, a) {
- if (!isNaN(e) && !isNaN(r))
- if (n.leaf) {
- var c = n.x,
- s = n.y;
- if (null != c)
- if (ga(c - e) + ga(s - r) < .01) l(n, t, e, r, u, i, o, a);
- else {
- var f = n.point;
- n.x = n.y = n.point = null, l(n, f, c, s, u, i, o, a), l(n, t, e, r, u, i, o, a)
- }
- else n.x = e, n.y = r, n.point = t
- } else l(n, t, e, r, u, i, o, a)
- }
-
- function l(n, t, e, r, u, o, a, c) {
- var l = .5 * (u + a),
- s = .5 * (o + c),
- f = e >= l,
- h = r >= s,
- g = h << 1 | f;
- n.leaf = !1, n = n.nodes[g] || (n.nodes[g] = su()), f ? u = l : a = l, h ? o = s : c = s, i(n, t, e, r, u, o, a, c)
- }
- var s, f, h, g, p, v, d, m, y, M = Et(a),
- x = Et(c);
- if (null != t) v = t, d = e, m = r, y = u;
- else if (m = y = -(v = d = 1 / 0), f = [], h = [], p = n.length, o)
- for (g = 0; p > g; ++g) s = n[g], s.x < v && (v = s.x), s.y < d && (d = s.y), s.x > m && (m = s.x), s.y > y && (y = s.y), f.push(s.x), h.push(s.y);
- else
- for (g = 0; p > g; ++g) {
- var b = +M(s = n[g], g),
- _ = +x(s, g);
- v > b && (v = b), d > _ && (d = _), b > m && (m = b), _ > y && (y = _), f.push(b), h.push(_)
- }
- var w = m - v,
- S = y - d;
- w > S ? y = d + w : m = v + S;
- var k = su();
- if (k.add = function(n) {
- i(k, n, +M(n, ++g), +x(n, g), v, d, m, y)
- }, k.visit = function(n) {
- fu(n, k, v, d, m, y)
- }, k.find = function(n) {
- return hu(k, n[0], n[1], v, d, m, y)
- }, g = -1, null == t) {
- for (; ++g < p;) i(k, n[g], f[g], h[g], v, d, m, y);
- --g
- } else n.forEach(k.add);
- return f = h = n = s = null, k
- }
- var o, a = Ar,
- c = Nr;
- return (o = arguments.length) ? (a = cu, c = lu, 3 === o && (u = e, r = t, e = t = 0), i(n)) : (i.x = function(n) {
- return arguments.length ? (a = n, i) : a
- }, i.y = function(n) {
- return arguments.length ? (c = n, i) : c
- }, i.extent = function(n) {
- return arguments.length ? (null == n ? t = e = r = u = null : (t = +n[0][0], e = +n[0][1], r = +n[1][0], u = +n[1][1]), i) : null == t ? null : [
- [t, e],
- [r, u]
- ]
- }, i.size = function(n) {
- return arguments.length ? (null == n ? t = e = r = u = null : (t = e = 0, r = +n[0], u = +n[1]), i) : null == t ? null : [r - t, u - e]
- }, i)
- }, ta.interpolateRgb = gu, ta.interpolateObject = pu, ta.interpolateNumber = vu, ta.interpolateString = du;
- var il = /[-+]?(?:\d+\.?\d*|\.?\d+)(?:[eE][-+]?\d+)?/g,
- ol = new RegExp(il.source, "g");
- ta.interpolate = mu, ta.interpolators = [function(n, t) {
- var e = typeof t;
- return ("string" === e ? Ga.has(t) || /^(#|rgb\(|hsl\()/.test(t) ? gu : du : t instanceof ot ? gu : Array.isArray(t) ? yu : "object" === e && isNaN(t) ? pu : vu)(n, t)
- }], ta.interpolateArray = yu;
- var al = function() {
- return y
- },
- cl = ta.map({
- linear: al,
- poly: ku,
- quad: function() {
- return _u
- },
- cubic: function() {
- return wu
- },
- sin: function() {
- return Eu
- },
- exp: function() {
- return Au
- },
- circle: function() {
- return Nu
- },
- elastic: Cu,
- back: zu,
- bounce: function() {
- return qu
- }
- }),
- ll = ta.map({
- "in": y,
- out: xu,
- "in-out": bu,
- "out-in": function(n) {
- return bu(xu(n))
- }
- });
- ta.ease = function(n) {
- var t = n.indexOf("-"),
- e = t >= 0 ? n.slice(0, t) : n,
- r = t >= 0 ? n.slice(t + 1) : "in";
- return e = cl.get(e) || al, r = ll.get(r) || y, Mu(r(e.apply(null, ea.call(arguments, 1))))
- }, ta.interpolateHcl = Lu, ta.interpolateHsl = Tu, ta.interpolateLab = Ru, ta.interpolateRound = Du, ta.transform = function(n) {
- var t = ua.createElementNS(ta.ns.prefix.svg, "g");
- return (ta.transform = function(n) {
- if (null != n) {
- t.setAttribute("transform", n);
- var e = t.transform.baseVal.consolidate()
- }
- return new Pu(e ? e.matrix : sl)
- })(n)
- }, Pu.prototype.toString = function() {
- return "translate(" + this.translate + ")rotate(" + this.rotate + ")skewX(" + this.skew + ")scale(" + this.scale + ")"
- };
- var sl = {
- a: 1,
- b: 0,
- c: 0,
- d: 1,
- e: 0,
- f: 0
- };
- ta.interpolateTransform = Hu, ta.layout = {}, ta.layout.bundle = function() {
- return function(n) {
- for (var t = [], e = -1, r = n.length; ++e < r;) t.push(Yu(n[e]));
- return t
- }
- }, ta.layout.chord = function() {
- function n() {
- var n, l, f, h, g, p = {},
- v = [],
- d = ta.range(i),
- m = [];
- for (e = [], r = [], n = 0, h = -1; ++h < i;) {
- for (l = 0, g = -1; ++g < i;) l += u[h][g];
- v.push(l), m.push(ta.range(i)), n += l
- }
- for (o && d.sort(function(n, t) {
- return o(v[n], v[t])
- }), a && m.forEach(function(n, t) {
- n.sort(function(n, e) {
- return a(u[t][n], u[t][e])
- })
- }), n = (La - s * i) / n, l = 0, h = -1; ++h < i;) {
- for (f = l, g = -1; ++g < i;) {
- var y = d[h],
- M = m[y][g],
- x = u[y][M],
- b = l,
- _ = l += x * n;
- p[y + "-" + M] = {
- index: y,
- subindex: M,
- startAngle: b,
- endAngle: _,
- value: x
- }
- }
- r[y] = {
- index: y,
- startAngle: f,
- endAngle: l,
- value: (l - f) / n
- }, l += s
- }
- for (h = -1; ++h < i;)
- for (g = h - 1; ++g < i;) {
- var w = p[h + "-" + g],
- S = p[g + "-" + h];
- (w.value || S.value) && e.push(w.value < S.value ? {
- source: S,
- target: w
- } : {
- source: w,
- target: S
- })
- }
- c && t()
- }
-
- function t() {
- e.sort(function(n, t) {
- return c((n.source.value + n.target.value) / 2, (t.source.value + t.target.value) / 2)
- })
- }
- var e, r, u, i, o, a, c, l = {},
- s = 0;
- return l.matrix = function(n) {
- return arguments.length ? (i = (u = n) && u.length, e = r = null, l) : u
- }, l.padding = function(n) {
- return arguments.length ? (s = n, e = r = null, l) : s
- }, l.sortGroups = function(n) {
- return arguments.length ? (o = n, e = r = null, l) : o
- }, l.sortSubgroups = function(n) {
- return arguments.length ? (a = n, e = null, l) : a
- }, l.sortChords = function(n) {
- return arguments.length ? (c = n, e && t(), l) : c
- }, l.chords = function() {
- return e || n(), e
- }, l.groups = function() {
- return r || n(), r
- }, l
- }, ta.layout.force = function() {
- function n(n) {
- return function(t, e, r, u) {
- if (t.point !== n) {
- var i = t.cx - n.x,
- o = t.cy - n.y,
- a = u - e,
- c = i * i + o * o;
- if (c > a * a / d) {
- if (p > c) {
- var l = t.charge / c;
- n.px -= i * l, n.py -= o * l
- }
- return !0
- }
- if (t.point && c && p > c) {
- var l = t.pointCharge / c;
- n.px -= i * l, n.py -= o * l
- }
- }
- return !t.charge
- }
- }
-
- function t(n) {
- n.px = ta.event.x, n.py = ta.event.y, a.resume()
- }
- var e, r, u, i, o, a = {},
- c = ta.dispatch("start", "tick", "end"),
- l = [1, 1],
- s = .9,
- f = fl,
- h = hl,
- g = -30,
- p = gl,
- v = .1,
- d = .64,
- m = [],
- M = [];
- return a.tick = function() {
- if ((r *= .99) < .005) return c.end({
- type: "end",
- alpha: r = 0
- }), !0;
- var t, e, a, f, h, p, d, y, x, b = m.length,
- _ = M.length;
- for (e = 0; _ > e; ++e) a = M[e], f = a.source, h = a.target, y = h.x - f.x, x = h.y - f.y, (p = y * y + x * x) && (p = r * i[e] * ((p = Math.sqrt(p)) - u[e]) / p, y *= p, x *= p, h.x -= y * (d = f.weight / (h.weight + f.weight)), h.y -= x * d, f.x += y * (d = 1 - d), f.y += x * d);
- if ((d = r * v) && (y = l[0] / 2, x = l[1] / 2, e = -1, d))
- for (; ++e < b;) a = m[e], a.x += (y - a.x) * d, a.y += (x - a.y) * d;
- if (g)
- for (Ju(t = ta.geom.quadtree(m), r, o), e = -1; ++e < b;)(a = m[e]).fixed || t.visit(n(a));
- for (e = -1; ++e < b;) a = m[e], a.fixed ? (a.x = a.px, a.y = a.py) : (a.x -= (a.px - (a.px = a.x)) * s, a.y -= (a.py - (a.py = a.y)) * s);
- c.tick({
- type: "tick",
- alpha: r
- })
- }, a.nodes = function(n) {
- return arguments.length ? (m = n, a) : m
- }, a.links = function(n) {
- return arguments.length ? (M = n, a) : M
- }, a.size = function(n) {
- return arguments.length ? (l = n, a) : l
- }, a.linkDistance = function(n) {
- return arguments.length ? (f = "function" == typeof n ? n : +n, a) : f
- }, a.distance = a.linkDistance, a.linkStrength = function(n) {
- return arguments.length ? (h = "function" == typeof n ? n : +n, a) : h
- }, a.friction = function(n) {
- return arguments.length ? (s = +n, a) : s
- }, a.charge = function(n) {
- return arguments.length ? (g = "function" == typeof n ? n : +n, a) : g
- }, a.chargeDistance = function(n) {
- return arguments.length ? (p = n * n, a) : Math.sqrt(p)
- }, a.gravity = function(n) {
- return arguments.length ? (v = +n, a) : v
- }, a.theta = function(n) {
- return arguments.length ? (d = n * n, a) : Math.sqrt(d)
- }, a.alpha = function(n) {
- return arguments.length ? (n = +n, r ? r = n > 0 ? n : 0 : n > 0 && (c.start({
- type: "start",
- alpha: r = n
- }), ta.timer(a.tick)), a) : r
- }, a.start = function() {
- function n(n, r) {
- if (!e) {
- for (e = new Array(c), a = 0; c > a; ++a) e[a] = [];
- for (a = 0; s > a; ++a) {
- var u = M[a];
- e[u.source.index].push(u.target), e[u.target.index].push(u.source)
- }
- }
- for (var i, o = e[t], a = -1, l = o.length; ++a < l;)
- if (!isNaN(i = o[a][n])) return i;
- return Math.random() * r
- }
- var t, e, r, c = m.length,
- s = M.length,
- p = l[0],
- v = l[1];
- for (t = 0; c > t; ++t)(r = m[t]).index = t, r.weight = 0;
- for (t = 0; s > t; ++t) r = M[t], "number" == typeof r.source && (r.source = m[r.source]), "number" == typeof r.target && (r.target = m[r.target]), ++r.source.weight, ++r.target.weight;
- for (t = 0; c > t; ++t) r = m[t], isNaN(r.x) && (r.x = n("x", p)), isNaN(r.y) && (r.y = n("y", v)), isNaN(r.px) && (r.px = r.x), isNaN(r.py) && (r.py = r.y);
- if (u = [], "function" == typeof f)
- for (t = 0; s > t; ++t) u[t] = +f.call(this, M[t], t);
- else
- for (t = 0; s > t; ++t) u[t] = f;
- if (i = [], "function" == typeof h)
- for (t = 0; s > t; ++t) i[t] = +h.call(this, M[t], t);
- else
- for (t = 0; s > t; ++t) i[t] = h;
- if (o = [], "function" == typeof g)
- for (t = 0; c > t; ++t) o[t] = +g.call(this, m[t], t);
- else
- for (t = 0; c > t; ++t) o[t] = g;
- return a.resume()
- }, a.resume = function() {
- return a.alpha(.1)
- }, a.stop = function() {
- return a.alpha(0)
- }, a.drag = function() {
- return e || (e = ta.behavior.drag().origin(y).on("dragstart.force", Xu).on("drag.force", t).on("dragend.force", $u)), arguments.length ? void this.on("mouseover.force", Bu).on("mouseout.force", Wu).call(e) : e
- }, ta.rebind(a, c, "on")
- };
- var fl = 20,
- hl = 1,
- gl = 1 / 0;
- ta.layout.hierarchy = function() {
- function n(u) {
- var i, o = [u],
- a = [];
- for (u.depth = 0; null != (i = o.pop());)
- if (a.push(i), (l = e.call(n, i, i.depth)) && (c = l.length)) {
- for (var c, l, s; --c >= 0;) o.push(s = l[c]), s.parent = i, s.depth = i.depth + 1;
- r && (i.value = 0), i.children = l
- } else r && (i.value = +r.call(n, i, i.depth) || 0), delete i.children;
- return Qu(u, function(n) {
- var e, u;
- t && (e = n.children) && e.sort(t), r && (u = n.parent) && (u.value += n.value)
- }), a
- }
- var t = ei,
- e = ni,
- r = ti;
- return n.sort = function(e) {
- return arguments.length ? (t = e, n) : t
- }, n.children = function(t) {
- return arguments.length ? (e = t, n) : e
- }, n.value = function(t) {
- return arguments.length ? (r = t, n) : r
- }, n.revalue = function(t) {
- return r && (Ku(t, function(n) {
- n.children && (n.value = 0)
- }), Qu(t, function(t) {
- var e;
- t.children || (t.value = +r.call(n, t, t.depth) || 0), (e = t.parent) && (e.value += t.value)
- })), t
- }, n
- }, ta.layout.partition = function() {
- function n(t, e, r, u) {
- var i = t.children;
- if (t.x = e, t.y = t.depth * u, t.dx = r, t.dy = u, i && (o = i.length)) {
- var o, a, c, l = -1;
- for (r = t.value ? r / t.value : 0; ++l < o;) n(a = i[l], e, c = a.value * r, u), e += c
- }
- }
-
- function t(n) {
- var e = n.children,
- r = 0;
- if (e && (u = e.length))
- for (var u, i = -1; ++i < u;) r = Math.max(r, t(e[i]));
- return 1 + r
- }
-
- function e(e, i) {
- var o = r.call(this, e, i);
- return n(o[0], 0, u[0], u[1] / t(o[0])), o
- }
- var r = ta.layout.hierarchy(),
- u = [1, 1];
- return e.size = function(n) {
- return arguments.length ? (u = n, e) : u
- }, Gu(e, r)
- }, ta.layout.pie = function() {
- function n(o) {
- var a, c = o.length,
- l = o.map(function(e, r) {
- return +t.call(n, e, r)
- }),
- s = +("function" == typeof r ? r.apply(this, arguments) : r),
- f = ("function" == typeof u ? u.apply(this, arguments) : u) - s,
- h = Math.min(Math.abs(f) / c, +("function" == typeof i ? i.apply(this, arguments) : i)),
- g = h * (0 > f ? -1 : 1),
- p = (f - c * g) / ta.sum(l),
- v = ta.range(c),
- d = [];
- return null != e && v.sort(e === pl ? function(n, t) {
- return l[t] - l[n]
- } : function(n, t) {
- return e(o[n], o[t])
- }), v.forEach(function(n) {
- d[n] = {
- data: o[n],
- value: a = l[n],
- startAngle: s,
- endAngle: s += a * p + g,
- padAngle: h
- }
- }), d
- }
- var t = Number,
- e = pl,
- r = 0,
- u = La,
- i = 0;
- return n.value = function(e) {
- return arguments.length ? (t = e, n) : t
- }, n.sort = function(t) {
- return arguments.length ? (e = t, n) : e
- }, n.startAngle = function(t) {
- return arguments.length ? (r = t, n) : r
- }, n.endAngle = function(t) {
- return arguments.length ? (u = t, n) : u
- }, n.padAngle = function(t) {
- return arguments.length ? (i = t, n) : i
- }, n
- };
- var pl = {};
- ta.layout.stack = function() {
- function n(a, c) {
- if (!(h = a.length)) return a;
- var l = a.map(function(e, r) {
- return t.call(n, e, r)
- }),
- s = l.map(function(t) {
- return t.map(function(t, e) {
- return [i.call(n, t, e), o.call(n, t, e)]
- })
- }),
- f = e.call(n, s, c);
- l = ta.permute(l, f), s = ta.permute(s, f);
- var h, g, p, v, d = r.call(n, s, c),
- m = l[0].length;
- for (p = 0; m > p; ++p)
- for (u.call(n, l[0][p], v = d[p], s[0][p][1]), g = 1; h > g; ++g) u.call(n, l[g][p], v += s[g - 1][p][1], s[g][p][1]);
- return a
- }
- var t = y,
- e = ai,
- r = ci,
- u = oi,
- i = ui,
- o = ii;
- return n.values = function(e) {
- return arguments.length ? (t = e, n) : t
- }, n.order = function(t) {
- return arguments.length ? (e = "function" == typeof t ? t : vl.get(t) || ai, n) : e
- }, n.offset = function(t) {
- return arguments.length ? (r = "function" == typeof t ? t : dl.get(t) || ci, n) : r
- }, n.x = function(t) {
- return arguments.length ? (i = t, n) : i
- }, n.y = function(t) {
- return arguments.length ? (o = t, n) : o
- }, n.out = function(t) {
- return arguments.length ? (u = t, n) : u
- }, n
- };
- var vl = ta.map({
- "inside-out": function(n) {
- var t, e, r = n.length,
- u = n.map(li),
- i = n.map(si),
- o = ta.range(r).sort(function(n, t) {
- return u[n] - u[t]
- }),
- a = 0,
- c = 0,
- l = [],
- s = [];
- for (t = 0; r > t; ++t) e = o[t], c > a ? (a += i[e], l.push(e)) : (c += i[e], s.push(e));
- return s.reverse().concat(l)
- },
- reverse: function(n) {
- return ta.range(n.length).reverse()
- },
- "default": ai
- }),
- dl = ta.map({
- silhouette: function(n) {
- var t, e, r, u = n.length,
- i = n[0].length,
- o = [],
- a = 0,
- c = [];
- for (e = 0; i > e; ++e) {
- for (t = 0, r = 0; u > t; t++) r += n[t][e][1];
- r > a && (a = r), o.push(r)
- }
- for (e = 0; i > e; ++e) c[e] = (a - o[e]) / 2;
- return c
- },
- wiggle: function(n) {
- var t, e, r, u, i, o, a, c, l, s = n.length,
- f = n[0],
- h = f.length,
- g = [];
- for (g[0] = c = l = 0, e = 1; h > e; ++e) {
- for (t = 0, u = 0; s > t; ++t) u += n[t][e][1];
- for (t = 0, i = 0, a = f[e][0] - f[e - 1][0]; s > t; ++t) {
- for (r = 0, o = (n[t][e][1] - n[t][e - 1][1]) / (2 * a); t > r; ++r) o += (n[r][e][1] - n[r][e - 1][1]) / a;
- i += o * n[t][e][1]
- }
- g[e] = c -= u ? i / u * a : 0, l > c && (l = c)
- }
- for (e = 0; h > e; ++e) g[e] -= l;
- return g
- },
- expand: function(n) {
- var t, e, r, u = n.length,
- i = n[0].length,
- o = 1 / u,
- a = [];
- for (e = 0; i > e; ++e) {
- for (t = 0, r = 0; u > t; t++) r += n[t][e][1];
- if (r)
- for (t = 0; u > t; t++) n[t][e][1] /= r;
- else
- for (t = 0; u > t; t++) n[t][e][1] = o
- }
- for (e = 0; i > e; ++e) a[e] = 0;
- return a
- },
- zero: ci
- });
- ta.layout.histogram = function() {
- function n(n, i) {
- for (var o, a, c = [], l = n.map(e, this), s = r.call(this, l, i), f = u.call(this, s, l, i), i = -1, h = l.length, g = f.length - 1, p = t ? 1 : 1 / h; ++i < g;) o = c[i] = [], o.dx = f[i + 1] - (o.x = f[i]), o.y = 0;
- if (g > 0)
- for (i = -1; ++i < h;) a = l[i], a >= s[0] && a <= s[1] && (o = c[ta.bisect(f, a, 1, g) - 1], o.y += p, o.push(n[i]));
- return c
- }
- var t = !0,
- e = Number,
- r = pi,
- u = hi;
- return n.value = function(t) {
- return arguments.length ? (e = t, n) : e
- }, n.range = function(t) {
- return arguments.length ? (r = Et(t), n) : r
- }, n.bins = function(t) {
- return arguments.length ? (u = "number" == typeof t ? function(n) {
- return gi(n, t)
- } : Et(t), n) : u
- }, n.frequency = function(e) {
- return arguments.length ? (t = !!e, n) : t
- }, n
- }, ta.layout.pack = function() {
- function n(n, i) {
- var o = e.call(this, n, i),
- a = o[0],
- c = u[0],
- l = u[1],
- s = null == t ? Math.sqrt : "function" == typeof t ? t : function() {
- return t
- };
- if (a.x = a.y = 0, Qu(a, function(n) {
- n.r = +s(n.value)
- }), Qu(a, Mi), r) {
- var f = r * (t ? 1 : Math.max(2 * a.r / c, 2 * a.r / l)) / 2;
- Qu(a, function(n) {
- n.r += f
- }), Qu(a, Mi), Qu(a, function(n) {
- n.r -= f
- })
- }
- return _i(a, c / 2, l / 2, t ? 1 : 1 / Math.max(2 * a.r / c, 2 * a.r / l)), o
- }
- var t, e = ta.layout.hierarchy().sort(vi),
- r = 0,
- u = [1, 1];
- return n.size = function(t) {
- return arguments.length ? (u = t, n) : u
- }, n.radius = function(e) {
- return arguments.length ? (t = null == e || "function" == typeof e ? e : +e, n) : t
- }, n.padding = function(t) {
- return arguments.length ? (r = +t, n) : r
- }, Gu(n, e)
- }, ta.layout.tree = function() {
- function n(n, u) {
- var s = o.call(this, n, u),
- f = s[0],
- h = t(f);
- if (Qu(h, e), h.parent.m = -h.z, Ku(h, r), l) Ku(f, i);
- else {
- var g = f,
- p = f,
- v = f;
- Ku(f, function(n) {
- n.x < g.x && (g = n), n.x > p.x && (p = n), n.depth > v.depth && (v = n)
- });
- var d = a(g, p) / 2 - g.x,
- m = c[0] / (p.x + a(p, g) / 2 + d),
- y = c[1] / (v.depth || 1);
- Ku(f, function(n) {
- n.x = (n.x + d) * m, n.y = n.depth * y
- })
- }
- return s
- }
-
- function t(n) {
- for (var t, e = {
- A: null,
- children: [n]
- }, r = [e]; null != (t = r.pop());)
- for (var u, i = t.children, o = 0, a = i.length; a > o; ++o) r.push((i[o] = u = {
- _: i[o],
- parent: t,
- children: (u = i[o].children) && u.slice() || [],
- A: null,
- a: null,
- z: 0,
- m: 0,
- c: 0,
- s: 0,
- t: null,
- i: o
- }).a = u);
- return e.children[0]
- }
-
- function e(n) {
- var t = n.children,
- e = n.parent.children,
- r = n.i ? e[n.i - 1] : null;
- if (t.length) {
- Ni(n);
- var i = (t[0].z + t[t.length - 1].z) / 2;
- r ? (n.z = r.z + a(n._, r._), n.m = n.z - i) : n.z = i
- } else r && (n.z = r.z + a(n._, r._));
- n.parent.A = u(n, r, n.parent.A || e[0])
- }
-
- function r(n) {
- n._.x = n.z + n.parent.m, n.m += n.parent.m
- }
-
- function u(n, t, e) {
- if (t) {
- for (var r, u = n, i = n, o = t, c = u.parent.children[0], l = u.m, s = i.m, f = o.m, h = c.m; o = Ei(o), u = ki(u), o && u;) c = ki(c), i = Ei(i), i.a = n, r = o.z + f - u.z - l + a(o._, u._), r > 0 && (Ai(Ci(o, n, e), n, r), l += r, s += r), f += o.m, l += u.m, h += c.m, s += i.m;
- o && !Ei(i) && (i.t = o, i.m += f - s), u && !ki(c) && (c.t = u, c.m += l - h, e = n)
- }
- return e
- }
-
- function i(n) {
- n.x *= c[0], n.y = n.depth * c[1]
- }
- var o = ta.layout.hierarchy().sort(null).value(null),
- a = Si,
- c = [1, 1],
- l = null;
- return n.separation = function(t) {
- return arguments.length ? (a = t, n) : a
- }, n.size = function(t) {
- return arguments.length ? (l = null == (c = t) ? i : null, n) : l ? null : c
- }, n.nodeSize = function(t) {
- return arguments.length ? (l = null == (c = t) ? null : i, n) : l ? c : null
- }, Gu(n, o)
- }, ta.layout.cluster = function() {
- function n(n, i) {
- var o, a = t.call(this, n, i),
- c = a[0],
- l = 0;
- Qu(c, function(n) {
- var t = n.children;
- t && t.length ? (n.x = qi(t), n.y = zi(t)) : (n.x = o ? l += e(n, o) : 0, n.y = 0, o = n)
- });
- var s = Li(c),
- f = Ti(c),
- h = s.x - e(s, f) / 2,
- g = f.x + e(f, s) / 2;
- return Qu(c, u ? function(n) {
- n.x = (n.x - c.x) * r[0], n.y = (c.y - n.y) * r[1]
- } : function(n) {
- n.x = (n.x - h) / (g - h) * r[0], n.y = (1 - (c.y ? n.y / c.y : 1)) * r[1]
- }), a
- }
- var t = ta.layout.hierarchy().sort(null).value(null),
- e = Si,
- r = [1, 1],
- u = !1;
- return n.separation = function(t) {
- return arguments.length ? (e = t, n) : e
- }, n.size = function(t) {
- return arguments.length ? (u = null == (r = t), n) : u ? null : r
- }, n.nodeSize = function(t) {
- return arguments.length ? (u = null != (r = t), n) : u ? r : null
- }, Gu(n, t)
- }, ta.layout.treemap = function() {
- function n(n, t) {
- for (var e, r, u = -1, i = n.length; ++u < i;) r = (e = n[u]).value * (0 > t ? 0 : t), e.area = isNaN(r) || 0 >= r ? 0 : r
- }
-
- function t(e) {
- var i = e.children;
- if (i && i.length) {
- var o, a, c, l = f(e),
- s = [],
- h = i.slice(),
- p = 1 / 0,
- v = "slice" === g ? l.dx : "dice" === g ? l.dy : "slice-dice" === g ? 1 & e.depth ? l.dy : l.dx : Math.min(l.dx, l.dy);
- for (n(h, l.dx * l.dy / e.value), s.area = 0;
- (c = h.length) > 0;) s.push(o = h[c - 1]), s.area += o.area, "squarify" !== g || (a = r(s, v)) <= p ? (h.pop(), p = a) : (s.area -= s.pop().area, u(s, v, l, !1), v = Math.min(l.dx, l.dy), s.length = s.area = 0, p = 1 / 0);
- s.length && (u(s, v, l, !0), s.length = s.area = 0), i.forEach(t)
- }
- }
-
- function e(t) {
- var r = t.children;
- if (r && r.length) {
- var i, o = f(t),
- a = r.slice(),
- c = [];
- for (n(a, o.dx * o.dy / t.value), c.area = 0; i = a.pop();) c.push(i), c.area += i.area, null != i.z && (u(c, i.z ? o.dx : o.dy, o, !a.length), c.length = c.area = 0);
- r.forEach(e)
- }
- }
-
- function r(n, t) {
- for (var e, r = n.area, u = 0, i = 1 / 0, o = -1, a = n.length; ++o < a;)(e = n[o].area) && (i > e && (i = e), e > u && (u = e));
- return r *= r, t *= t, r ? Math.max(t * u * p / r, r / (t * i * p)) : 1 / 0
- }
-
- function u(n, t, e, r) {
- var u, i = -1,
- o = n.length,
- a = e.x,
- l = e.y,
- s = t ? c(n.area / t) : 0;
- if (t == e.dx) {
- for ((r || s > e.dy) && (s = e.dy); ++i < o;) u = n[i], u.x = a, u.y = l, u.dy = s, a += u.dx = Math.min(e.x + e.dx - a, s ? c(u.area / s) : 0);
- u.z = !0, u.dx += e.x + e.dx - a, e.y += s, e.dy -= s
- } else {
- for ((r || s > e.dx) && (s = e.dx); ++i < o;) u = n[i], u.x = a, u.y = l, u.dx = s, l += u.dy = Math.min(e.y + e.dy - l, s ? c(u.area / s) : 0);
- u.z = !1, u.dy += e.y + e.dy - l, e.x += s, e.dx -= s
- }
- }
-
- function i(r) {
- var u = o || a(r),
- i = u[0];
- return i.x = 0, i.y = 0, i.dx = l[0], i.dy = l[1], o && a.revalue(i), n([i], i.dx * i.dy / i.value), (o ? e : t)(i), h && (o = u), u
- }
- var o, a = ta.layout.hierarchy(),
- c = Math.round,
- l = [1, 1],
- s = null,
- f = Ri,
- h = !1,
- g = "squarify",
- p = .5 * (1 + Math.sqrt(5));
- return i.size = function(n) {
- return arguments.length ? (l = n, i) : l
- }, i.padding = function(n) {
- function t(t) {
- var e = n.call(i, t, t.depth);
- return null == e ? Ri(t) : Di(t, "number" == typeof e ? [e, e, e, e] : e)
- }
-
- function e(t) {
- return Di(t, n)
- }
- if (!arguments.length) return s;
- var r;
- return f = null == (s = n) ? Ri : "function" == (r = typeof n) ? t : "number" === r ? (n = [n, n, n, n], e) : e, i
- }, i.round = function(n) {
- return arguments.length ? (c = n ? Math.round : Number, i) : c != Number
- }, i.sticky = function(n) {
- return arguments.length ? (h = n, o = null, i) : h
- }, i.ratio = function(n) {
- return arguments.length ? (p = n, i) : p
- }, i.mode = function(n) {
- return arguments.length ? (g = n + "", i) : g
- }, Gu(i, a)
- }, ta.random = {
- normal: function(n, t) {
- var e = arguments.length;
- return 2 > e && (t = 1), 1 > e && (n = 0),
- function() {
- var e, r, u;
- do e = 2 * Math.random() - 1, r = 2 * Math.random() - 1, u = e * e + r * r; while (!u || u > 1);
- return n + t * e * Math.sqrt(-2 * Math.log(u) / u)
- }
- },
- logNormal: function() {
- var n = ta.random.normal.apply(ta, arguments);
- return function() {
- return Math.exp(n())
- }
- },
- bates: function(n) {
- var t = ta.random.irwinHall(n);
- return function() {
- return t() / n
- }
- },
- irwinHall: function(n) {
- return function() {
- for (var t = 0, e = 0; n > e; e++) t += Math.random();
- return t
- }
- }
- }, ta.scale = {};
- var ml = {
- floor: y,
- ceil: y
- };
- ta.scale.linear = function() {
- return Ii([0, 1], [0, 1], mu, !1)
- };
- var yl = {
- s: 1,
- g: 1,
- p: 1,
- r: 1,
- e: 1
- };
- ta.scale.log = function() {
- return Ji(ta.scale.linear().domain([0, 1]), 10, !0, [1, 10])
- };
- var Ml = ta.format(".0e"),
- xl = {
- floor: function(n) {
- return -Math.ceil(-n)
- },
- ceil: function(n) {
- return -Math.floor(-n)
- }
- };
- ta.scale.pow = function() {
- return Gi(ta.scale.linear(), 1, [0, 1])
- }, ta.scale.sqrt = function() {
- return ta.scale.pow().exponent(.5)
- }, ta.scale.ordinal = function() {
- return Qi([], {
- t: "range",
- a: [
- []
- ]
- })
- }, ta.scale.category10 = function() {
- return ta.scale.ordinal().range(bl)
- }, ta.scale.category20 = function() {
- return ta.scale.ordinal().range(_l)
- }, ta.scale.category20b = function() {
- return ta.scale.ordinal().range(wl)
- }, ta.scale.category20c = function() {
- return ta.scale.ordinal().range(Sl)
- };
- var bl = [2062260, 16744206, 2924588, 14034728, 9725885, 9197131, 14907330, 8355711, 12369186, 1556175].map(Mt),
- _l = [2062260, 11454440, 16744206, 16759672, 2924588, 10018698, 14034728, 16750742, 9725885, 12955861, 9197131, 12885140, 14907330, 16234194, 8355711, 13092807, 12369186, 14408589, 1556175, 10410725].map(Mt),
- wl = [3750777, 5395619, 7040719, 10264286, 6519097, 9216594, 11915115, 13556636, 9202993, 12426809, 15186514, 15190932, 8666169, 11356490, 14049643, 15177372, 8077683, 10834324, 13528509, 14589654].map(Mt),
- Sl = [3244733, 7057110, 10406625, 13032431, 15095053, 16616764, 16625259, 16634018, 3253076, 7652470, 10607003, 13101504, 7695281, 10394312, 12369372, 14342891, 6513507, 9868950, 12434877, 14277081].map(Mt);
- ta.scale.quantile = function() {
- return no([], [])
- }, ta.scale.quantize = function() {
- return to(0, 1, [0, 1])
- }, ta.scale.threshold = function() {
- return eo([.5], [0, 1])
- }, ta.scale.identity = function() {
- return ro([0, 1])
- }, ta.svg = {}, ta.svg.arc = function() {
- function n() {
- var n = Math.max(0, +e.apply(this, arguments)),
- l = Math.max(0, +r.apply(this, arguments)),
- s = o.apply(this, arguments) - Ra,
- f = a.apply(this, arguments) - Ra,
- h = Math.abs(f - s),
- g = s > f ? 0 : 1;
- if (n > l && (p = l, l = n, n = p), h >= Ta) return t(l, g) + (n ? t(n, 1 - g) : "") + "Z";
- var p, v, d, m, y, M, x, b, _, w, S, k, E = 0,
- A = 0,
- N = [];
- if ((m = (+c.apply(this, arguments) || 0) / 2) && (d = i === kl ? Math.sqrt(n * n + l * l) : +i.apply(this, arguments), g || (A *= -1), l && (A = tt(d / l * Math.sin(m))), n && (E = tt(d / n * Math.sin(m)))), l) {
- y = l * Math.cos(s + A), M = l * Math.sin(s + A), x = l * Math.cos(f - A), b = l * Math.sin(f - A);
- var C = Math.abs(f - s - 2 * A) <= qa ? 0 : 1;
- if (A && so(y, M, x, b) === g ^ C) {
- var z = (s + f) / 2;
- y = l * Math.cos(z), M = l * Math.sin(z), x = b = null
- }
- } else y = M = 0;
- if (n) {
- _ = n * Math.cos(f - E), w = n * Math.sin(f - E), S = n * Math.cos(s + E), k = n * Math.sin(s + E);
- var q = Math.abs(s - f + 2 * E) <= qa ? 0 : 1;
- if (E && so(_, w, S, k) === 1 - g ^ q) {
- var L = (s + f) / 2;
- _ = n * Math.cos(L), w = n * Math.sin(L), S = k = null
- }
- } else _ = w = 0;
- if ((p = Math.min(Math.abs(l - n) / 2, +u.apply(this, arguments))) > .001) {
- v = l > n ^ g ? 0 : 1;
- var T = null == S ? [_, w] : null == x ? [y, M] : Lr([y, M], [S, k], [x, b], [_, w]),
- R = y - T[0],
- D = M - T[1],
- P = x - T[0],
- U = b - T[1],
- j = 1 / Math.sin(Math.acos((R * P + D * U) / (Math.sqrt(R * R + D * D) * Math.sqrt(P * P + U * U))) / 2),
- F = Math.sqrt(T[0] * T[0] + T[1] * T[1]);
- if (null != x) {
- var H = Math.min(p, (l - F) / (j + 1)),
- O = fo(null == S ? [_, w] : [S, k], [y, M], l, H, g),
- I = fo([x, b], [_, w], l, H, g);
- p === H ? N.push("M", O[0], "A", H, ",", H, " 0 0,", v, " ", O[1], "A", l, ",", l, " 0 ", 1 - g ^ so(O[1][0], O[1][1], I[1][0], I[1][1]), ",", g, " ", I[1], "A", H, ",", H, " 0 0,", v, " ", I[0]) : N.push("M", O[0], "A", H, ",", H, " 0 1,", v, " ", I[0])
- } else N.push("M", y, ",", M);
- if (null != S) {
- var Y = Math.min(p, (n - F) / (j - 1)),
- Z = fo([y, M], [S, k], n, -Y, g),
- V = fo([_, w], null == x ? [y, M] : [x, b], n, -Y, g);
- p === Y ? N.push("L", V[0], "A", Y, ",", Y, " 0 0,", v, " ", V[1], "A", n, ",", n, " 0 ", g ^ so(V[1][0], V[1][1], Z[1][0], Z[1][1]), ",", 1 - g, " ", Z[1], "A", Y, ",", Y, " 0 0,", v, " ", Z[0]) : N.push("L", V[0], "A", Y, ",", Y, " 0 0,", v, " ", Z[0])
- } else N.push("L", _, ",", w)
- } else N.push("M", y, ",", M), null != x && N.push("A", l, ",", l, " 0 ", C, ",", g, " ", x, ",", b), N.push("L", _, ",", w), null != S && N.push("A", n, ",", n, " 0 ", q, ",", 1 - g, " ", S, ",", k);
- return N.push("Z"), N.join("")
- }
-
- function t(n, t) {
- return "M0," + n + "A" + n + "," + n + " 0 1," + t + " 0," + -n + "A" + n + "," + n + " 0 1," + t + " 0," + n
- }
- var e = io,
- r = oo,
- u = uo,
- i = kl,
- o = ao,
- a = co,
- c = lo;
- return n.innerRadius = function(t) {
- return arguments.length ? (e = Et(t), n) : e
- }, n.outerRadius = function(t) {
- return arguments.length ? (r = Et(t), n) : r
- }, n.cornerRadius = function(t) {
- return arguments.length ? (u = Et(t), n) : u
- }, n.padRadius = function(t) {
- return arguments.length ? (i = t == kl ? kl : Et(t), n) : i
- }, n.startAngle = function(t) {
- return arguments.length ? (o = Et(t), n) : o
- }, n.endAngle = function(t) {
- return arguments.length ? (a = Et(t), n) : a
- }, n.padAngle = function(t) {
- return arguments.length ? (c = Et(t), n) : c
- }, n.centroid = function() {
- var n = (+e.apply(this, arguments) + +r.apply(this, arguments)) / 2,
- t = (+o.apply(this, arguments) + +a.apply(this, arguments)) / 2 - Ra;
- return [Math.cos(t) * n, Math.sin(t) * n]
- }, n
- };
- var kl = "auto";
- ta.svg.line = function() {
- return ho(y)
- };
- var El = ta.map({
- linear: go,
- "linear-closed": po,
- step: vo,
- "step-before": mo,
- "step-after": yo,
- basis: So,
- "basis-open": ko,
- "basis-closed": Eo,
- bundle: Ao,
- cardinal: bo,
- "cardinal-open": Mo,
- "cardinal-closed": xo,
- monotone: To
- });
- El.forEach(function(n, t) {
- t.key = n, t.closed = /-closed$/.test(n)
- });
- var Al = [0, 2 / 3, 1 / 3, 0],
- Nl = [0, 1 / 3, 2 / 3, 0],
- Cl = [0, 1 / 6, 2 / 3, 1 / 6];
- ta.svg.line.radial = function() {
- var n = ho(Ro);
- return n.radius = n.x, delete n.x, n.angle = n.y, delete n.y, n
- }, mo.reverse = yo, yo.reverse = mo, ta.svg.area = function() {
- return Do(y)
- }, ta.svg.area.radial = function() {
- var n = Do(Ro);
- return n.radius = n.x, delete n.x, n.innerRadius = n.x0, delete n.x0, n.outerRadius = n.x1, delete n.x1, n.angle = n.y, delete n.y, n.startAngle = n.y0, delete n.y0, n.endAngle = n.y1, delete n.y1, n
- }, ta.svg.chord = function() {
- function n(n, a) {
- var c = t(this, i, n, a),
- l = t(this, o, n, a);
- return "M" + c.p0 + r(c.r, c.p1, c.a1 - c.a0) + (e(c, l) ? u(c.r, c.p1, c.r, c.p0) : u(c.r, c.p1, l.r, l.p0) + r(l.r, l.p1, l.a1 - l.a0) + u(l.r, l.p1, c.r, c.p0)) + "Z"
- }
-
- function t(n, t, e, r) {
- var u = t.call(n, e, r),
- i = a.call(n, u, r),
- o = c.call(n, u, r) - Ra,
- s = l.call(n, u, r) - Ra;
- return {
- r: i,
- a0: o,
- a1: s,
- p0: [i * Math.cos(o), i * Math.sin(o)],
- p1: [i * Math.cos(s), i * Math.sin(s)]
- }
- }
-
- function e(n, t) {
- return n.a0 == t.a0 && n.a1 == t.a1
- }
-
- function r(n, t, e) {
- return "A" + n + "," + n + " 0 " + +(e > qa) + ",1 " + t
- }
-
- function u(n, t, e, r) {
- return "Q 0,0 " + r
- }
- var i = mr,
- o = yr,
- a = Po,
- c = ao,
- l = co;
- return n.radius = function(t) {
- return arguments.length ? (a = Et(t), n) : a
- }, n.source = function(t) {
- return arguments.length ? (i = Et(t), n) : i
- }, n.target = function(t) {
- return arguments.length ? (o = Et(t), n) : o
- }, n.startAngle = function(t) {
- return arguments.length ? (c = Et(t), n) : c
- }, n.endAngle = function(t) {
- return arguments.length ? (l = Et(t), n) : l
- }, n
- }, ta.svg.diagonal = function() {
- function n(n, u) {
- var i = t.call(this, n, u),
- o = e.call(this, n, u),
- a = (i.y + o.y) / 2,
- c = [i, {
- x: i.x,
- y: a
- }, {
- x: o.x,
- y: a
- }, o];
- return c = c.map(r), "M" + c[0] + "C" + c[1] + " " + c[2] + " " + c[3]
- }
- var t = mr,
- e = yr,
- r = Uo;
- return n.source = function(e) {
- return arguments.length ? (t = Et(e), n) : t
- }, n.target = function(t) {
- return arguments.length ? (e = Et(t), n) : e
- }, n.projection = function(t) {
- return arguments.length ? (r = t, n) : r
- }, n
- }, ta.svg.diagonal.radial = function() {
- var n = ta.svg.diagonal(),
- t = Uo,
- e = n.projection;
- return n.projection = function(n) {
- return arguments.length ? e(jo(t = n)) : t
- }, n
- }, ta.svg.symbol = function() {
- function n(n, r) {
- return (zl.get(t.call(this, n, r)) || Oo)(e.call(this, n, r))
- }
- var t = Ho,
- e = Fo;
- return n.type = function(e) {
- return arguments.length ? (t = Et(e), n) : t
- }, n.size = function(t) {
- return arguments.length ? (e = Et(t), n) : e
- }, n
- };
- var zl = ta.map({
- circle: Oo,
- cross: function(n) {
- var t = Math.sqrt(n / 5) / 2;
- return "M" + -3 * t + "," + -t + "H" + -t + "V" + -3 * t + "H" + t + "V" + -t + "H" + 3 * t + "V" + t + "H" + t + "V" + 3 * t + "H" + -t + "V" + t + "H" + -3 * t + "Z"
- },
- diamond: function(n) {
- var t = Math.sqrt(n / (2 * Ll)),
- e = t * Ll;
- return "M0," + -t + "L" + e + ",0 0," + t + " " + -e + ",0Z"
- },
- square: function(n) {
- var t = Math.sqrt(n) / 2;
- return "M" + -t + "," + -t + "L" + t + "," + -t + " " + t + "," + t + " " + -t + "," + t + "Z"
- },
- "triangle-down": function(n) {
- var t = Math.sqrt(n / ql),
- e = t * ql / 2;
- return "M0," + e + "L" + t + "," + -e + " " + -t + "," + -e + "Z"
- },
- "triangle-up": function(n) {
- var t = Math.sqrt(n / ql),
- e = t * ql / 2;
- return "M0," + -e + "L" + t + "," + e + " " + -t + "," + e + "Z"
- }
- });
- ta.svg.symbolTypes = zl.keys();
- var ql = Math.sqrt(3),
- Ll = Math.tan(30 * Da);
- _a.transition = function(n) {
- for (var t, e, r = Tl || ++Ul, u = Xo(n), i = [], o = Rl || {
- time: Date.now(),
- ease: Su,
- delay: 0,
- duration: 250
- }, a = -1, c = this.length; ++a < c;) {
- i.push(t = []);
- for (var l = this[a], s = -1, f = l.length; ++s < f;)(e = l[s]) && $o(e, s, u, r, o), t.push(e)
- }
- return Yo(i, u, r)
- }, _a.interrupt = function(n) {
- return this.each(null == n ? Dl : Io(Xo(n)))
- };
- var Tl, Rl, Dl = Io(Xo()),
- Pl = [],
- Ul = 0;
- Pl.call = _a.call, Pl.empty = _a.empty, Pl.node = _a.node, Pl.size = _a.size, ta.transition = function(n, t) {
- return n && n.transition ? Tl ? n.transition(t) : n : ta.selection().transition(n)
- }, ta.transition.prototype = Pl, Pl.select = function(n) {
- var t, e, r, u = this.id,
- i = this.namespace,
- o = [];
- n = N(n);
- for (var a = -1, c = this.length; ++a < c;) {
- o.push(t = []);
- for (var l = this[a], s = -1, f = l.length; ++s < f;)(r = l[s]) && (e = n.call(r, r.__data__, s, a)) ? ("__data__" in r && (e.__data__ = r.__data__), $o(e, s, i, u, r[i][u]), t.push(e)) : t.push(null)
- }
- return Yo(o, i, u)
- }, Pl.selectAll = function(n) {
- var t, e, r, u, i, o = this.id,
- a = this.namespace,
- c = [];
- n = C(n);
- for (var l = -1, s = this.length; ++l < s;)
- for (var f = this[l], h = -1, g = f.length; ++h < g;)
- if (r = f[h]) {
- i = r[a][o], e = n.call(r, r.__data__, h, l), c.push(t = []);
- for (var p = -1, v = e.length; ++p < v;)(u = e[p]) && $o(u, p, a, o, i), t.push(u)
- } return Yo(c, a, o)
- }, Pl.filter = function(n) {
- var t, e, r, u = [];
- "function" != typeof n && (n = O(n));
- for (var i = 0, o = this.length; o > i; i++) {
- u.push(t = []);
- for (var e = this[i], a = 0, c = e.length; c > a; a++)(r = e[a]) && n.call(r, r.__data__, a, i) && t.push(r)
- }
- return Yo(u, this.namespace, this.id)
- }, Pl.tween = function(n, t) {
- var e = this.id,
- r = this.namespace;
- return arguments.length < 2 ? this.node()[r][e].tween.get(n) : Y(this, null == t ? function(t) {
- t[r][e].tween.remove(n)
- } : function(u) {
- u[r][e].tween.set(n, t)
- })
- }, Pl.attr = function(n, t) {
- function e() {
- this.removeAttribute(a)
- }
-
- function r() {
- this.removeAttributeNS(a.space, a.local)
- }
-
- function u(n) {
- return null == n ? e : (n += "", function() {
- var t, e = this.getAttribute(a);
- return e !== n && (t = o(e, n), function(n) {
- this.setAttribute(a, t(n))
- })
- })
- }
-
- function i(n) {
- return null == n ? r : (n += "", function() {
- var t, e = this.getAttributeNS(a.space, a.local);
- return e !== n && (t = o(e, n), function(n) {
- this.setAttributeNS(a.space, a.local, t(n))
- })
- })
- }
- if (arguments.length < 2) {
- for (t in n) this.attr(t, n[t]);
- return this
- }
- var o = "transform" == n ? Hu : mu,
- a = ta.ns.qualify(n);
- return Zo(this, "attr." + n, t, a.local ? i : u)
- }, Pl.attrTween = function(n, t) {
- function e(n, e) {
- var r = t.call(this, n, e, this.getAttribute(u));
- return r && function(n) {
- this.setAttribute(u, r(n))
- }
- }
-
- function r(n, e) {
- var r = t.call(this, n, e, this.getAttributeNS(u.space, u.local));
- return r && function(n) {
- this.setAttributeNS(u.space, u.local, r(n))
- }
- }
- var u = ta.ns.qualify(n);
- return this.tween("attr." + n, u.local ? r : e)
- }, Pl.style = function(n, e, r) {
- function u() {
- this.style.removeProperty(n)
- }
-
- function i(e) {
- return null == e ? u : (e += "", function() {
- var u, i = t(this).getComputedStyle(this, null).getPropertyValue(n);
- return i !== e && (u = mu(i, e), function(t) {
- this.style.setProperty(n, u(t), r)
- })
- })
- }
- var o = arguments.length;
- if (3 > o) {
- if ("string" != typeof n) {
- 2 > o && (e = "");
- for (r in n) this.style(r, n[r], e);
- return this
- }
- r = ""
- }
- return Zo(this, "style." + n, e, i)
- }, Pl.styleTween = function(n, e, r) {
- function u(u, i) {
- var o = e.call(this, u, i, t(this).getComputedStyle(this, null).getPropertyValue(n));
- return o && function(t) {
- this.style.setProperty(n, o(t), r)
- }
- }
- return arguments.length < 3 && (r = ""), this.tween("style." + n, u)
- }, Pl.text = function(n) {
- return Zo(this, "text", n, Vo)
- }, Pl.remove = function() {
- var n = this.namespace;
- return this.each("end.transition", function() {
- var t;
- this[n].count < 2 && (t = this.parentNode) && t.removeChild(this)
- })
- }, Pl.ease = function(n) {
- var t = this.id,
- e = this.namespace;
- return arguments.length < 1 ? this.node()[e][t].ease : ("function" != typeof n && (n = ta.ease.apply(ta, arguments)), Y(this, function(r) {
- r[e][t].ease = n
- }))
- }, Pl.delay = function(n) {
- var t = this.id,
- e = this.namespace;
- return arguments.length < 1 ? this.node()[e][t].delay : Y(this, "function" == typeof n ? function(r, u, i) {
- r[e][t].delay = +n.call(r, r.__data__, u, i)
- } : (n = +n, function(r) {
- r[e][t].delay = n
- }))
- }, Pl.duration = function(n) {
- var t = this.id,
- e = this.namespace;
- return arguments.length < 1 ? this.node()[e][t].duration : Y(this, "function" == typeof n ? function(r, u, i) {
- r[e][t].duration = Math.max(1, n.call(r, r.__data__, u, i))
- } : (n = Math.max(1, n), function(r) {
- r[e][t].duration = n
- }))
- }, Pl.each = function(n, t) {
- var e = this.id,
- r = this.namespace;
- if (arguments.length < 2) {
- var u = Rl,
- i = Tl;
- try {
- Tl = e, Y(this, function(t, u, i) {
- Rl = t[r][e], n.call(t, t.__data__, u, i)
- })
- } finally {
- Rl = u, Tl = i
- }
- } else Y(this, function(u) {
- var i = u[r][e];
- (i.event || (i.event = ta.dispatch("start", "end", "interrupt"))).on(n, t)
- });
- return this
- }, Pl.transition = function() {
- for (var n, t, e, r, u = this.id, i = ++Ul, o = this.namespace, a = [], c = 0, l = this.length; l > c; c++) {
- a.push(n = []);
- for (var t = this[c], s = 0, f = t.length; f > s; s++)(e = t[s]) && (r = e[o][u], $o(e, s, o, i, {
- time: r.time,
- ease: r.ease,
- delay: r.delay + r.duration,
- duration: r.duration
- })), n.push(e)
- }
- return Yo(a, o, i)
- }, ta.svg.axis = function() {
- function n(n) {
- n.each(function() {
- var n, l = ta.select(this),
- s = this.__chart__ || e,
- f = this.__chart__ = e.copy(),
- h = null == c ? f.ticks ? f.ticks.apply(f, a) : f.domain() : c,
- g = null == t ? f.tickFormat ? f.tickFormat.apply(f, a) : y : t,
- p = l.selectAll(".tick").data(h, f),
- v = p.enter().insert("g", ".domain").attr("class", "tick").style("opacity", Ca),
- d = ta.transition(p.exit()).style("opacity", Ca).remove(),
- m = ta.transition(p.order()).style("opacity", 1),
- M = Math.max(u, 0) + o,
- x = Ui(f),
- b = l.selectAll(".domain").data([0]),
- _ = (b.enter().append("path").attr("class", "domain"), ta.transition(b));
- v.append("line"), v.append("text");
- var w, S, k, E, A = v.select("line"),
- N = m.select("line"),
- C = p.select("text").text(g),
- z = v.select("text"),
- q = m.select("text"),
- L = "top" === r || "left" === r ? -1 : 1;
- if ("bottom" === r || "top" === r ? (n = Bo, w = "x", k = "y", S = "x2", E = "y2", C.attr("dy", 0 > L ? "0em" : ".71em").style("text-anchor", "middle"), _.attr("d", "M" + x[0] + "," + L * i + "V0H" + x[1] + "V" + L * i)) : (n = Wo, w = "y", k = "x", S = "y2", E = "x2", C.attr("dy", ".32em").style("text-anchor", 0 > L ? "end" : "start"), _.attr("d", "M" + L * i + "," + x[0] + "H0V" + x[1] + "H" + L * i)), A.attr(E, L * u), z.attr(k, L * M), N.attr(S, 0).attr(E, L * u), q.attr(w, 0).attr(k, L * M), f.rangeBand) {
- var T = f,
- R = T.rangeBand() / 2;
- s = f = function(n) {
- return T(n) + R
- }
- } else s.rangeBand ? s = f : d.call(n, f, s);
- v.call(n, s, f), m.call(n, f, f)
- })
- }
- var t, e = ta.scale.linear(),
- r = jl,
- u = 6,
- i = 6,
- o = 3,
- a = [10],
- c = null;
- return n.scale = function(t) {
- return arguments.length ? (e = t, n) : e
- }, n.orient = function(t) {
- return arguments.length ? (r = t in Fl ? t + "" : jl, n) : r
- }, n.ticks = function() {
- return arguments.length ? (a = arguments, n) : a
- }, n.tickValues = function(t) {
- return arguments.length ? (c = t, n) : c
- }, n.tickFormat = function(e) {
- return arguments.length ? (t = e, n) : t
- }, n.tickSize = function(t) {
- var e = arguments.length;
- return e ? (u = +t, i = +arguments[e - 1], n) : u
- }, n.innerTickSize = function(t) {
- return arguments.length ? (u = +t, n) : u
- }, n.outerTickSize = function(t) {
- return arguments.length ? (i = +t, n) : i
- }, n.tickPadding = function(t) {
- return arguments.length ? (o = +t, n) : o
- }, n.tickSubdivide = function() {
- return arguments.length && n
- }, n
- };
- var jl = "bottom",
- Fl = {
- top: 1,
- right: 1,
- bottom: 1,
- left: 1
- };
- ta.svg.brush = function() {
- function n(t) {
- t.each(function() {
- var t = ta.select(this).style("pointer-events", "all").style("-webkit-tap-highlight-color", "rgba(0,0,0,0)").on("mousedown.brush", i).on("touchstart.brush", i),
- o = t.selectAll(".background").data([0]);
- o.enter().append("rect").attr("class", "background").style("visibility", "hidden").style("cursor", "crosshair"), t.selectAll(".extent").data([0]).enter().append("rect").attr("class", "extent").style("cursor", "move");
- var a = t.selectAll(".resize").data(v, y);
- a.exit().remove(), a.enter().append("g").attr("class", function(n) {
- return "resize " + n
- }).style("cursor", function(n) {
- return Hl[n]
- }).append("rect").attr("x", function(n) {
- return /[ew]$/.test(n) ? -3 : null
- }).attr("y", function(n) {
- return /^[ns]/.test(n) ? -3 : null
- }).attr("width", 6).attr("height", 6).style("visibility", "hidden"), a.style("display", n.empty() ? "none" : null);
- var c, f = ta.transition(t),
- h = ta.transition(o);
- l && (c = Ui(l), h.attr("x", c[0]).attr("width", c[1] - c[0]), r(f)), s && (c = Ui(s), h.attr("y", c[0]).attr("height", c[1] - c[0]), u(f)), e(f)
- })
- }
-
- function e(n) {
- n.selectAll(".resize").attr("transform", function(n) {
- return "translate(" + f[+/e$/.test(n)] + "," + h[+/^s/.test(n)] + ")"
- })
- }
-
- function r(n) {
- n.select(".extent").attr("x", f[0]), n.selectAll(".extent,.n>rect,.s>rect").attr("width", f[1] - f[0])
- }
-
- function u(n) {
- n.select(".extent").attr("y", h[0]), n.selectAll(".extent,.e>rect,.w>rect").attr("height", h[1] - h[0])
- }
-
- function i() {
- function i() {
- 32 == ta.event.keyCode && (C || (M = null, q[0] -= f[1], q[1] -= h[1], C = 2), S())
- }
-
- function v() {
- 32 == ta.event.keyCode && 2 == C && (q[0] += f[1], q[1] += h[1], C = 0, S())
- }
-
- function d() {
- var n = ta.mouse(b),
- t = !1;
- x && (n[0] += x[0], n[1] += x[1]), C || (ta.event.altKey ? (M || (M = [(f[0] + f[1]) / 2, (h[0] + h[1]) / 2]), q[0] = f[+(n[0] < M[0])], q[1] = h[+(n[1] < M[1])]) : M = null), A && m(n, l, 0) && (r(k), t = !0), N && m(n, s, 1) && (u(k), t = !0), t && (e(k), w({
- type: "brush",
- mode: C ? "move" : "resize"
- }))
- }
-
- function m(n, t, e) {
- var r, u, i = Ui(t),
- c = i[0],
- l = i[1],
- s = q[e],
- v = e ? h : f,
- d = v[1] - v[0];
- return C && (c -= s, l -= d + s), r = (e ? p : g) ? Math.max(c, Math.min(l, n[e])) : n[e], C ? u = (r += s) + d : (M && (s = Math.max(c, Math.min(l, 2 * M[e] - r))), r > s ? (u = r, r = s) : u = s), v[0] != r || v[1] != u ? (e ? a = null : o = null, v[0] = r, v[1] = u, !0) : void 0
- }
-
- function y() {
- d(), k.style("pointer-events", "all").selectAll(".resize").style("display", n.empty() ? "none" : null), ta.select("body").style("cursor", null), L.on("mousemove.brush", null).on("mouseup.brush", null).on("touchmove.brush", null).on("touchend.brush", null).on("keydown.brush", null).on("keyup.brush", null), z(), w({
- type: "brushend"
- })
- }
- var M, x, b = this,
- _ = ta.select(ta.event.target),
- w = c.of(b, arguments),
- k = ta.select(b),
- E = _.datum(),
- A = !/^(n|s)$/.test(E) && l,
- N = !/^(e|w)$/.test(E) && s,
- C = _.classed("extent"),
- z = W(b),
- q = ta.mouse(b),
- L = ta.select(t(b)).on("keydown.brush", i).on("keyup.brush", v);
- if (ta.event.changedTouches ? L.on("touchmove.brush", d).on("touchend.brush", y) : L.on("mousemove.brush", d).on("mouseup.brush", y), k.interrupt().selectAll("*").interrupt(), C) q[0] = f[0] - q[0], q[1] = h[0] - q[1];
- else if (E) {
- var T = +/w$/.test(E),
- R = +/^n/.test(E);
- x = [f[1 - T] - q[0], h[1 - R] - q[1]], q[0] = f[T], q[1] = h[R]
- } else ta.event.altKey && (M = q.slice());
- k.style("pointer-events", "none").selectAll(".resize").style("display", null), ta.select("body").style("cursor", _.style("cursor")), w({
- type: "brushstart"
- }), d()
- }
- var o, a, c = E(n, "brushstart", "brush", "brushend"),
- l = null,
- s = null,
- f = [0, 0],
- h = [0, 0],
- g = !0,
- p = !0,
- v = Ol[0];
- return n.event = function(n) {
- n.each(function() {
- var n = c.of(this, arguments),
- t = {
- x: f,
- y: h,
- i: o,
- j: a
- },
- e = this.__chart__ || t;
- this.__chart__ = t, Tl ? ta.select(this).transition().each("start.brush", function() {
- o = e.i, a = e.j, f = e.x, h = e.y, n({
- type: "brushstart"
- })
- }).tween("brush:brush", function() {
- var e = yu(f, t.x),
- r = yu(h, t.y);
- return o = a = null,
- function(u) {
- f = t.x = e(u), h = t.y = r(u), n({
- type: "brush",
- mode: "resize"
- })
- }
- }).each("end.brush", function() {
- o = t.i, a = t.j, n({
- type: "brush",
- mode: "resize"
- }), n({
- type: "brushend"
- })
- }) : (n({
- type: "brushstart"
- }), n({
- type: "brush",
- mode: "resize"
- }), n({
- type: "brushend"
- }))
- })
- }, n.x = function(t) {
- return arguments.length ? (l = t, v = Ol[!l << 1 | !s], n) : l
- }, n.y = function(t) {
- return arguments.length ? (s = t, v = Ol[!l << 1 | !s], n) : s
- }, n.clamp = function(t) {
- return arguments.length ? (l && s ? (g = !!t[0], p = !!t[1]) : l ? g = !!t : s && (p = !!t), n) : l && s ? [g, p] : l ? g : s ? p : null
- }, n.extent = function(t) {
- var e, r, u, i, c;
- return arguments.length ? (l && (e = t[0], r = t[1], s && (e = e[0], r = r[0]), o = [e, r], l.invert && (e = l(e), r = l(r)), e > r && (c = e, e = r, r = c), (e != f[0] || r != f[1]) && (f = [e, r])), s && (u = t[0], i = t[1], l && (u = u[1], i = i[1]), a = [u, i], s.invert && (u = s(u), i = s(i)), u > i && (c = u, u = i, i = c), (u != h[0] || i != h[1]) && (h = [u, i])), n) : (l && (o ? (e = o[0], r = o[1]) : (e = f[0], r = f[1], l.invert && (e = l.invert(e), r = l.invert(r)), e > r && (c = e, e = r, r = c))), s && (a ? (u = a[0], i = a[1]) : (u = h[0], i = h[1], s.invert && (u = s.invert(u), i = s.invert(i)), u > i && (c = u, u = i, i = c))), l && s ? [
- [e, u],
- [r, i]
- ] : l ? [e, r] : s && [u, i])
- }, n.clear = function() {
- return n.empty() || (f = [0, 0], h = [0, 0], o = a = null), n
- }, n.empty = function() {
- return !!l && f[0] == f[1] || !!s && h[0] == h[1]
- }, ta.rebind(n, c, "on")
- };
- var Hl = {
- n: "ns-resize",
- e: "ew-resize",
- s: "ns-resize",
- w: "ew-resize",
- nw: "nwse-resize",
- ne: "nesw-resize",
- se: "nwse-resize",
- sw: "nesw-resize"
- },
- Ol = [
- ["n", "e", "s", "w", "nw", "ne", "se", "sw"],
- ["e", "w"],
- ["n", "s"],
- []
- ],
- Il = ac.format = gc.timeFormat,
- Yl = Il.utc,
- Zl = Yl("%Y-%m-%dT%H:%M:%S.%LZ");
- Il.iso = Date.prototype.toISOString && +new Date("2000-01-01T00:00:00.000Z") ? Jo : Zl, Jo.parse = function(n) {
- var t = new Date(n);
- return isNaN(t) ? null : t
- }, Jo.toString = Zl.toString, ac.second = Ft(function(n) {
- return new cc(1e3 * Math.floor(n / 1e3))
- }, function(n, t) {
- n.setTime(n.getTime() + 1e3 * Math.floor(t))
- }, function(n) {
- return n.getSeconds()
- }), ac.seconds = ac.second.range, ac.seconds.utc = ac.second.utc.range, ac.minute = Ft(function(n) {
- return new cc(6e4 * Math.floor(n / 6e4))
- }, function(n, t) {
- n.setTime(n.getTime() + 6e4 * Math.floor(t))
- }, function(n) {
- return n.getMinutes()
- }), ac.minutes = ac.minute.range, ac.minutes.utc = ac.minute.utc.range, ac.hour = Ft(function(n) {
- var t = n.getTimezoneOffset() / 60;
- return new cc(36e5 * (Math.floor(n / 36e5 - t) + t))
- }, function(n, t) {
- n.setTime(n.getTime() + 36e5 * Math.floor(t))
- }, function(n) {
- return n.getHours()
- }), ac.hours = ac.hour.range, ac.hours.utc = ac.hour.utc.range, ac.month = Ft(function(n) {
- return n = ac.day(n), n.setDate(1), n
- }, function(n, t) {
- n.setMonth(n.getMonth() + t)
- }, function(n) {
- return n.getMonth()
- }), ac.months = ac.month.range, ac.months.utc = ac.month.utc.range;
- var Vl = [1e3, 5e3, 15e3, 3e4, 6e4, 3e5, 9e5, 18e5, 36e5, 108e5, 216e5, 432e5, 864e5, 1728e5, 6048e5, 2592e6, 7776e6, 31536e6],
- Xl = [
- [ac.second, 1],
- [ac.second, 5],
- [ac.second, 15],
- [ac.second, 30],
- [ac.minute, 1],
- [ac.minute, 5],
- [ac.minute, 15],
- [ac.minute, 30],
- [ac.hour, 1],
- [ac.hour, 3],
- [ac.hour, 6],
- [ac.hour, 12],
- [ac.day, 1],
- [ac.day, 2],
- [ac.week, 1],
- [ac.month, 1],
- [ac.month, 3],
- [ac.year, 1]
- ],
- $l = Il.multi([
- [".%L", function(n) {
- return n.getMilliseconds()
- }],
- [":%S", function(n) {
- return n.getSeconds()
- }],
- ["%I:%M", function(n) {
- return n.getMinutes()
- }],
- ["%I %p", function(n) {
- return n.getHours()
- }],
- ["%a %d", function(n) {
- return n.getDay() && 1 != n.getDate()
- }],
- ["%b %d", function(n) {
- return 1 != n.getDate()
- }],
- ["%B", function(n) {
- return n.getMonth()
- }],
- ["%Y", Ne]
- ]),
- Bl = {
- range: function(n, t, e) {
- return ta.range(Math.ceil(n / e) * e, +t, e).map(Ko)
- },
- floor: y,
- ceil: y
- };
- Xl.year = ac.year, ac.scale = function() {
- return Go(ta.scale.linear(), Xl, $l)
- };
- var Wl = Xl.map(function(n) {
- return [n[0].utc, n[1]]
- }),
- Jl = Yl.multi([
- [".%L", function(n) {
- return n.getUTCMilliseconds()
- }],
- [":%S", function(n) {
- return n.getUTCSeconds()
- }],
- ["%I:%M", function(n) {
- return n.getUTCMinutes()
- }],
- ["%I %p", function(n) {
- return n.getUTCHours()
- }],
- ["%a %d", function(n) {
- return n.getUTCDay() && 1 != n.getUTCDate()
- }],
- ["%b %d", function(n) {
- return 1 != n.getUTCDate()
- }],
- ["%B", function(n) {
- return n.getUTCMonth()
- }],
- ["%Y", Ne]
- ]);
- Wl.year = ac.year.utc, ac.scale.utc = function() {
- return Go(ta.scale.linear(), Wl, Jl)
- }, ta.text = At(function(n) {
- return n.responseText
- }), ta.json = function(n, t) {
- return Nt(n, "application/json", Qo, t)
- }, ta.html = function(n, t) {
- return Nt(n, "text/html", na, t)
- }, ta.xml = At(function(n) {
- return n.responseXML
- }), "function" == typeof define && define.amd ? define(ta) : "object" == typeof module && module.exports && (module.exports = ta), this.d3 = ta
-}();
\ No newline at end of file
diff --git a/activity_dashboard_mngmnt/static/src/js/lib/funnel.js b/activity_dashboard_mngmnt/static/src/js/lib/funnel.js
deleted file mode 100644
index ccfa100d2..000000000
--- a/activity_dashboard_mngmnt/static/src/js/lib/funnel.js
+++ /dev/null
@@ -1,5 +0,0 @@
-(function(b){typeof module==="object"&&module.exports?module.exports=b:b(Highcharts)})(function(b){var q=b.getOptions(),w=q.plotOptions,r=b.seriesTypes,G=b.merge,E=function(){},B=b.each,F=b.pick;w.funnel=G(w.pie,{animation:!1,center:["50%","50%"],width:"90%",neckWidth:"30%",height:"100%",neckHeight:"25%",reversed:!1,dataLabels:{connectorWidth:1,connectorColor:"#606060"},size:!0,states:{select:{color:"#C0C0C0",borderColor:"#000000",shadow:!1}}});r.funnel=b.extendClass(r.pie,{type:"funnel",animate:E,
-translate:function(){var a=function(k,a){return/%$/.test(k)?a*parseInt(k,10)/100:parseInt(k,10)},b=0,f=this.chart,c=this.options,g=c.reversed,l=c.ignoreHiddenPoint,h=f.plotWidth,d=f.plotHeight,q=0,f=c.center,i=a(f[0],h),x=a(f[1],d),r=a(c.width,h),m,s,e=a(c.height,d),t=a(c.neckWidth,h),C=a(c.neckHeight,d),u=x-e/2+e-C,a=this.data,y,z,w=c.dataLabels.position==="left"?1:0,A,n,D,p,j,v,o;this.getWidthAt=s=function(k){var a=x-e/2;return k>u||e===C?t:t+(r-t)*(1-(k-a)/(e-C))};this.getX=function(k,a){return i+
-(a?-1:1)*(s(g?d-k:k)/2+c.dataLabels.distance)};this.center=[i,x,e];this.centerX=i;B(a,function(a){if(!l||a.visible!==!1)b+=a.y});B(a,function(a){o=null;z=b?a.y/b:0;n=x-e/2+q*e;j=n+z*e;m=s(n);A=i-m/2;D=A+m;m=s(j);p=i-m/2;v=p+m;n>u?(A=p=i-t/2,D=v=i+t/2):j>u&&(o=j,m=s(u),p=i-m/2,v=p+m,j=u);g&&(n=e-n,j=e-j,o=o?e-o:null);y=["M",A,n,"L",D,n,v,j];o&&y.push(v,o,p,o);y.push(p,j,"Z");a.shapeType="path";a.shapeArgs={d:y};a.percentage=z*100;a.plotX=i;a.plotY=(n+(o||j))/2;a.tooltipPos=[i,a.plotY];a.slice=E;a.half=
-w;if(!l||a.visible!==!1)q+=z})},drawPoints:function(){var a=this,b=a.options,f=a.chart.renderer,c,g,l,h;B(a.data,function(d){c=d.options;h=d.graphic;l=d.shapeArgs;g={fill:d.color,stroke:F(c.borderColor,b.borderColor),"stroke-width":F(c.borderWidth,b.borderWidth)};h?h.attr(g).animate(l):d.graphic=f.path(l).attr(g).add(a.group)})},sortByAngle:function(a){a.sort(function(a,b){return a.plotY-b.plotY})},drawDataLabels:function(){var a=this.data,b=this.options.dataLabels.distance,f,c,g,l=a.length,h,d;for(this.center[2]-=
-2*b;l--;)g=a[l],c=(f=g.half)?1:-1,d=g.plotY,h=this.getX(d,f),g.labelPos=[0,d,h+(b-5)*c,d,h+b*c,d,f?"right":"left",0];r.pie.prototype.drawDataLabels.call(this)}});q.plotOptions.pyramid=b.merge(q.plotOptions.funnel,{neckWidth:"0%",neckHeight:"0%",reversed:!0});b.seriesTypes.pyramid=b.extendClass(b.seriesTypes.funnel,{type:"pyramid"})});
diff --git a/activity_dashboard_mngmnt/static/src/js/lib/highcharts.js b/activity_dashboard_mngmnt/static/src/js/lib/highcharts.js
deleted file mode 100644
index fc26d2d83..000000000
--- a/activity_dashboard_mngmnt/static/src/js/lib/highcharts.js
+++ /dev/null
@@ -1,333 +0,0 @@
-(function(E,X){typeof module==="object"&&module.exports?module.exports=E.document?X(E):X:E.Highcharts=X(E)})(typeof window!=="undefined"?window:this,function(E){function X(a,b){var c="Highcharts error #"+a+": www.highcharts.com/errors/"+a;if(b)throw Error(c);E.console&&console.log(c)}function pb(a,b,c){this.options=b;this.elem=a;this.prop=c}function D(){var a,b=arguments,c,d={},e=function(a,b){var c,d;typeof a!=="object"&&(a={});for(d in b)b.hasOwnProperty(d)&&(c=b[d],a[d]=c&&typeof c==="object"&&
-Object.prototype.toString.call(c)!=="[object Array]"&&d!=="renderTo"&&typeof c.nodeType!=="number"?e(a[d]||{},c):b[d]);return a};b[0]===!0&&(d=b[1],b=Array.prototype.slice.call(b,2));c=b.length;for(a=0;a
-1?h.thousandsSep:""))):e=Qa(f,e)}k.push(e);a=a.slice(c+1);c=(d=!d)?"}":"{"}k.push(a);return k.join("")}function rb(a){return W.pow(10,T(W.log(a)/W.LN10))}function sb(a,b,c,d,e){var f,g=a,c=p(c,1);f=a/c;b||(b=[1,2,2.5,5,10],d===!1&&(c===1?b=[1,2,5,10]:c<=0.1&&(b=[1/c])));for(d=0;d=a||!e&&f<=(b[d]+(b[d+1]||b[d]))/
-2)break;g*=c;return g}function ib(a,b){var c=a.length,d,e;for(e=0;ec&&(c=a[b]);return c}function Sa(a,b){for(var c in a)a[c]&&a[c]!==b&&a[c].destroy&&a[c].destroy(),delete a[c]}function Ta(a){jb||(jb=Z(La));a&&jb.appendChild(a);jb.innerHTML=""}function fa(a,b){return parseFloat(a.toPrecision(b||
-14))}function Ua(a,b){b.renderer.globalAnimation=p(a,b.animation)}function Fb(){var a=N.global,b=a.useUTC,c=b?"getUTC":"get",d=b?"setUTC":"set";qa=a.Date||E.Date;qb=b&&a.timezoneOffset;Za=b&&a.getTimezoneOffset;kb=function(a,c,d,h,i,k){var j;b?(j=qa.UTC.apply(0,arguments),j+=Ya(j)):j=(new qa(a,c,p(d,1),p(h,0),p(i,0),p(k,0))).getTime();return j};tb=c+"Minutes";ub=c+"Hours";vb=c+"Day";$a=c+"Date";ab=c+"Month";bb=c+"FullYear";Gb=d+"Milliseconds";Hb=d+"Seconds";Ib=d+"Minutes";Jb=d+"Hours";wb=d+"Date";
-xb=d+"Month";yb=d+"FullYear"}function ia(a){if(!(this instanceof ia))return new ia(a);this.init(a)}function O(){}function Va(a,b,c,d){this.axis=a;this.pos=b;this.type=c||"";this.isNew=!0;!c&&!d&&this.addLabel()}function Kb(a,b,c,d,e){var f=a.chart.inverted;this.axis=a;this.isNegative=c;this.options=b;this.x=d;this.total=null;this.points={};this.stack=e;this.rightCliff=this.leftCliff=0;this.alignOptions={align:b.align||(f?c?"left":"right":"center"),verticalAlign:b.verticalAlign||(f?"middle":c?"bottom":
-"top"),y:p(b.y,f?4:c?14:-6),x:p(b.x,f?c?-6:6:0)};this.textAlign=b.textAlign||(f?c?"right":"left":"center")}var z,y=E.document,W=Math,A=W.round,T=W.floor,ua=W.ceil,t=W.max,F=W.min,P=W.abs,U=W.cos,$=W.sin,ra=W.PI,ga=ra*2/360,za=E.navigator&&E.navigator.userAgent||"",Lb=E.opera,ya=/(msie|trident|edge)/i.test(za)&&!Lb,lb=y&&y.documentMode===8,mb=!ya&&/AppleWebKit/.test(za),Ma=/Firefox/.test(za),Mb=/(Mobile|Android|Windows Phone)/.test(za),Fa="http://www.w3.org/2000/svg",ca=y&&y.createElementNS&&!!y.createElementNS(Fa,
-"svg").createSVGRect,Qb=Ma&&parseInt(za.split("Firefox/")[1],10)<4,ha=y&&!ca&&!ya&&!!y.createElement("canvas").getContext,cb,db,Nb={},zb=0,jb,N,Qa,G,Aa=function(){},S=[],eb=0,La="div",Rb=/^[0-9]+$/,nb=["plotTop","marginRight","marginBottom","plotLeft"],qa,kb,qb,Za,tb,ub,vb,$a,ab,bb,Gb,Hb,Ib,Jb,wb,xb,yb,I={},B;B=E.Highcharts?X(16,!0):{win:E};B.seriesTypes=I;var Ga=[],ja,sa,o,Na,Ab,Ba,M,V,H,Wa,Oa;pb.prototype={dSetter:function(){var a=this.paths[0],b=this.paths[1],c=[],d=this.now,e=a.length,f;if(d===
-1)c=this.toD;else if(e===b.length&&d<1)for(;e--;)f=parseFloat(a[e]),c[e]=isNaN(f)?a[e]:d*parseFloat(b[e]-f)+f;else c=b;this.elem.attr("d",c)},update:function(){var a=this.elem,b=this.prop,c=this.now,d=this.options.step;if(this[b+"Setter"])this[b+"Setter"]();else a.attr?a.element&&a.attr(b,c):a.style[b]=c+this.unit;d&&d.call(a,c,this)},run:function(a,b,c){var d=this,e=function(a){return e.stopped?!1:d.step(a)},f;this.startTime=+new qa;this.start=a;this.end=b;this.unit=c;this.now=this.start;this.pos=
-0;e.elem=this.elem;if(e()&&Ga.push(e)===1)e.timerId=setInterval(function(){for(f=0;f=f+this.startTime){this.now=this.end;this.pos=1;this.update();a=g[this.prop]=!0;for(h in g)g[h]!==!0&&(a=!1);a&&e&&e.call(c);c=!1}else this.pos=d.easing((b-this.startTime)/f),this.now=this.start+
-(this.end-this.start)*this.pos,this.update(),c=!0;return c},initPath:function(a,b,c){var b=b||"",d=a.shift,e=b.indexOf("C")>-1,f=e?7:3,g,b=b.split(" "),c=[].concat(c),h=a.isArea,i=h?2:1,k=function(a){for(g=a.length;g--;)(a[g]==="M"||a[g]==="L")&&a.splice(g+1,0,a[g+1],a[g+2],a[g+1],a[g+2])};e&&(k(b),k(c));if(d<=c.length/f&&b.length===c.length)for(;d--;)c=c.slice(0,f).concat(c),h&&(c=c.concat(c.slice(c.length-f)));a.shift=0;if(b.length)for(a=c.length;b.length3?g.length%3:0;c=p(c,e.decimalPoint);d=p(d,e.thousandsSep);a=a<0?"-":"";a+=h?g.substr(0,h)+d:"";a+=g.substr(h).replace(/(\d{3})(?=\d)/g,"$1"+d);+b&&(d=Math.abs(i-g+Math.pow(10,-Math.max(b,f)-1)),a+=c+d.toFixed(b).slice(2));
-return a};Math.easeInOutSine=function(a){return-0.5*(Math.cos(Math.PI*a)-1)};ja=function(a,b){var c;if(b==="width")return Math.min(a.offsetWidth,a.scrollWidth)-ja(a,"padding-left")-ja(a,"padding-right");else if(b==="height")return Math.min(a.offsetHeight,a.scrollHeight)-ja(a,"padding-top")-ja(a,"padding-bottom");return(c=E.getComputedStyle(a,void 0))&&C(c.getPropertyValue(b))};sa=function(a,b){return b.indexOf?b.indexOf(a):[].indexOf.call(b,a)};Na=function(a,b){return[].filter.call(a,b)};Ba=function(a,
-b){for(var c=[],d=0,e=a.length;d-1&&(f.splice(h,1),g[b]=f),d(b,c)):(e(),g[b]=[])):(e(),a.hcEvents={})};H=function(a,b,c,d){var e;e=a.hcEvents;var f,g,h,i,c=c||{};if(y.createEvent&&(a.dispatchEvent||a.fireEvent))e=y.createEvent("Events"),e.initEvent(b,!0,!0),e.target=a,u(e,c),a.dispatchEvent?a.dispatchEvent(e):a.fireEvent(b,e);else if(e){e=e[b]||[];f=e.length;h=function(){c.defaultPrevented=!0};for(g=0;g{point.key} ',pointFormat:'\u25cf {series.name}: {point.y} ',shadow:!0,snap:Mb?25:10,style:{color:"#333333",cursor:"default",fontSize:"12px",padding:"8px",pointerEvents:"none",whiteSpace:"nowrap"}},credits:{enabled:!0,text:"Highcharts.com",
-href:"http://www.highcharts.com",position:{align:"right",x:-10,verticalAlign:"bottom",y:-5},style:{cursor:"pointer",color:"#909090",fontSize:"9px"}}};var aa=N.plotOptions,da=aa.line;Fb();ia.prototype={parsers:[{regex:/rgba\(\s*([0-9]{1,3})\s*,\s*([0-9]{1,3})\s*,\s*([0-9]{1,3})\s*,\s*([0-9]?(?:\.[0-9]+)?)\s*\)/,parse:function(a){return[C(a[1]),C(a[2]),C(a[3]),parseFloat(a[4],10)]}},{regex:/#([a-fA-F0-9]{2})([a-fA-F0-9]{2})([a-fA-F0-9]{2})/,parse:function(a){return[C(a[1],16),C(a[2],16),C(a[3],16),
-1]}},{regex:/rgb\(\s*([0-9]{1,3})\s*,\s*([0-9]{1,3})\s*,\s*([0-9]{1,3})\s*\)/,parse:function(a){return[C(a[1]),C(a[2]),C(a[3]),1]}}],init:function(a){var b,c,d,e;if((this.input=a)&&a.stops)this.stops=Ba(a.stops,function(a){return new ia(a[1])});else for(d=this.parsers.length;d--&&!c;)e=this.parsers[d],(b=e.regex.exec(a))&&(c=e.parse(b));this.rgba=c||[]},get:function(a){var b=this.input,c=this.rgba,d;this.stops?(d=D(b),d.stops=[].concat(d.stops),o(this.stops,function(b,c){d.stops[c]=[d.stops[c][0],
-b.get(a)]})):d=c&&!isNaN(c[0])?a==="rgb"||!a&&c[3]===1?"rgb("+c[0]+","+c[1]+","+c[2]+")":a==="a"?c[3]:"rgba("+c.join(",")+")":b;return d},brighten:function(a){var b,c=this.rgba;if(this.stops)o(this.stops,function(b){b.brighten(a)});else if(ma(a)&&a!==0)for(b=0;b<3;b++)c[b]+=C(a*255),c[b]<0&&(c[b]=0),c[b]>255&&(c[b]=255);return this},setOpacity:function(a){this.rgba[3]=a;return this}};O.prototype={opacity:1,textProps:"direction,fontSize,fontWeight,fontFamily,fontStyle,color,lineHeight,width,textDecoration,textOverflow,textShadow".split(","),
-init:function(a,b){this.element=b==="span"?Z(b):y.createElementNS(Fa,b);this.renderer=a},animate:function(a,b,c){b=p(b,this.renderer.globalAnimation,!0);Oa(this);if(b){b=D(b,{});if(c)b.complete=c;Wa(this,a,b)}else this.attr(a,null,c);return this},colorGradient:function(a,b,c){var d=this.renderer,e,f,g,h,i,k,j,l,m,n,r,s=[],p;a.linearGradient?f="linearGradient":a.radialGradient&&(f="radialGradient");if(f){g=a[f];i=d.gradients;j=a.stops;n=c.radialReference;Ia(g)&&(a[f]=g={x1:g[0],y1:g[1],x2:g[2],y2:g[3],
-gradientUnits:"userSpaceOnUse"});f==="radialGradient"&&n&&!q(g.gradientUnits)&&(h=g,g=D(g,d.getRadialAttr(n,h),{gradientUnits:"userSpaceOnUse"}));for(r in g)r!=="id"&&s.push(r,g[r]);for(r in j)s.push(j[r]);s=s.join(",");i[s]?n=i[s].attr("id"):(g.id=n="highcharts-"+zb++,i[s]=k=d.createElement(f).attr(g).add(d.defs),k.radAttr=h,k.stops=[],o(j,function(a){a[1].indexOf("rgba")===0?(e=ia(a[1]),l=e.get("rgb"),m=e.get("a")):(l=a[1],m=1);a=d.createElement("stop").attr({offset:a[0],"stop-color":l,"stop-opacity":m}).add(k);
-k.stops.push(a)}));p="url("+d.url+"#"+n+")";c.setAttribute(b,p);c.gradient=s;a.toString=function(){return p}}},applyTextShadow:function(a){var b=this.element,c,d=a.indexOf("contrast")!==-1,e={},f=this.renderer.forExport,g=f||b.style.textShadow!==z&&!ya;if(d)e.textShadow=a=a.replace(/contrast/g,this.renderer.getContrast(b.style.fill));if(mb||f)e.textRendering="geometricPrecision";g?this.css(e):(this.fakeTS=!0,this.ySetter=this.xSetter,c=[].slice.call(b.getElementsByTagName("tspan")),o(a.split(/\s?,\s?/g),
-function(a){var d=b.firstChild,e,f,a=a.split(" ");e=a[a.length-1];(f=a[a.length-2])&&o(c,function(a,c){var g;c===0&&(a.setAttribute("x",b.getAttribute("x")),c=b.getAttribute("y"),a.setAttribute("y",c||0),c===null&&b.setAttribute("y",0));g=a.cloneNode(1);K(g,{"class":"highcharts-text-shadow",fill:e,stroke:e,"stroke-opacity":1/t(C(f),3),"stroke-width":f,"stroke-linejoin":"round"});b.insertBefore(g,d)})}))},attr:function(a,b,c){var d,e=this.element,f,g=this,h;typeof a==="string"&&b!==z&&(d=a,a={},a[d]=
-b);if(typeof a==="string")g=(this[a+"Getter"]||this._defaultGetter).call(this,a,e);else{for(d in a){b=a[d];h=!1;this.symbolName&&/^(x|y|width|height|r|start|end|innerR|anchorX|anchorY)/.test(d)&&(f||(this.symbolAttr(a),f=!0),h=!0);if(this.rotation&&(d==="x"||d==="y"))this.doTransform=!0;h||(h=this[d+"Setter"]||this._defaultSetter,h.call(this,b,d,e),this.shadows&&/^(width|height|visibility|x|y|d|transform|cx|cy|r)$/.test(d)&&this.updateShadows(d,b,h))}if(this.doTransform)this.updateTransform(),this.doTransform=
-!1}c&&c();return g},updateShadows:function(a,b,c){for(var d=this.shadows,e=d.length;e--;)c.call(null,a==="height"?Math.max(b-(d[e].cutHeight||0),0):a==="d"?this.d:b,a,d[e])},addClass:function(a){var b=this.element,c=K(b,"class")||"";c.indexOf(a)===-1&&K(b,"class",c+" "+a);return this},symbolAttr:function(a){var b=this;o("x,y,r,start,end,width,height,innerR,anchorX,anchorY".split(","),function(c){b[c]=p(a[c],b[c])});b.attr({d:b.renderer.symbols[b.symbolName](b.x,b.y,b.width,b.height,b)})},clip:function(a){return this.attr("clip-path",
-a?"url("+this.renderer.url+"#"+a.id+")":"none")},crisp:function(a){var b,c={},d,e=this.strokeWidth||0;d=A(e)%2/2;a.x=T(a.x||this.x||0)+d;a.y=T(a.y||this.y||0)+d;a.width=T((a.width||this.width||0)-2*d);a.height=T((a.height||this.height||0)-2*d);a.strokeWidth=e;for(b in a)this[b]!==a[b]&&(this[b]=c[b]=a[b]);return c},css:function(a){var b=this.styles,c={},d=this.element,e,f,g="";e=!b;if(a&&a.color)a.fill=a.color;if(b)for(f in a)a[f]!==b[f]&&(c[f]=a[f],e=!0);if(e){e=this.textWidth=a&&a.width&&d.nodeName.toLowerCase()===
-"text"&&C(a.width)||this.textWidth;b&&(a=u(b,c));this.styles=a;e&&(ha||!ca&&this.renderer.forExport)&&delete a.width;if(ya&&!ca)L(this.element,a);else{b=function(a,b){return"-"+b.toLowerCase()};for(f in a)g+=f.replace(/([A-Z])/g,b)+":"+a[f]+";";K(d,"style",g)}e&&this.added&&this.renderer.buildText(this)}return this},on:function(a,b){var c=this,d=c.element;db&&a==="click"?(d.ontouchstart=function(a){c.touchEventFired=qa.now();a.preventDefault();b.call(d,a)},d.onclick=function(a){(za.indexOf("Android")===
--1||qa.now()-(c.touchEventFired||0)>1100)&&b.call(d,a)}):d["on"+a]=b;return this},setRadialReference:function(a){var b=this.renderer.gradients[this.element.gradient];this.element.radialReference=a;b&&b.radAttr&&b.animate(this.renderer.getRadialAttr(a,b.radAttr));return this},translate:function(a,b){return this.attr({translateX:a,translateY:b})},invert:function(){this.inverted=!0;this.updateTransform();return this},updateTransform:function(){var a=this.translateX||0,b=this.translateY||0,c=this.scaleX,
-d=this.scaleY,e=this.inverted,f=this.rotation,g=this.element;e&&(a+=this.attr("width"),b+=this.attr("height"));a=["translate("+a+","+b+")"];e?a.push("rotate(90) scale(-1,1)"):f&&a.push("rotate("+f+" "+(g.getAttribute("x")||0)+" "+(g.getAttribute("y")||0)+")");(q(c)||q(d))&&a.push("scale("+p(c,1)+" "+p(d,1)+")");a.length&&g.setAttribute("transform",a.join(" "))},toFront:function(){var a=this.element;a.parentNode.appendChild(a);return this},align:function(a,b,c){var d,e,f,g,h={};e=this.renderer;f=e.alignedObjects;
-if(a){if(this.alignOptions=a,this.alignByTranslate=b,!c||xa(c))this.alignTo=d=c||"renderer",oa(f,this),f.push(this),c=null}else a=this.alignOptions,b=this.alignByTranslate,d=this.alignTo;c=p(c,e[d],e);d=a.align;e=a.verticalAlign;f=(c.x||0)+(a.x||0);g=(c.y||0)+(a.y||0);if(d==="right"||d==="center")f+=(c.width-(a.width||0))/{right:1,center:2}[d];h[b?"translateX":"x"]=A(f);if(e==="bottom"||e==="middle")g+=(c.height-(a.height||0))/({bottom:1,middle:2}[e]||1);h[b?"translateY":"y"]=A(g);this[this.placed?
-"animate":"attr"](h);this.placed=!0;this.alignAttr=h;return this},getBBox:function(a,b){var c,d=this.renderer,e,f,g,h=this.element,i=this.styles;e=this.textStr;var k,j=h.style,l,m=d.cache,n=d.cacheKeys,r;f=p(b,this.rotation);g=f*ga;e!==z&&(r=["",f||0,i&&i.fontSize,h.style.width].join(","),r=e===""||Rb.test(e)?"num:"+e.toString().length+r:e+r);r&&!a&&(c=m[r]);if(!c){if(h.namespaceURI===Fa||d.forExport){try{l=this.fakeTS&&function(a){o(h.querySelectorAll(".highcharts-text-shadow"),function(b){b.style.display=
-a})},Ma&&j.textShadow?(k=j.textShadow,j.textShadow=""):l&&l("none"),c=h.getBBox?u({},h.getBBox()):{width:h.offsetWidth,height:h.offsetHeight},k?j.textShadow=k:l&&l("")}catch(s){}if(!c||c.width<0)c={width:0,height:0}}else c=this.htmlGetBBox();if(d.isSVG){d=c.width;e=c.height;if(ya&&i&&i.fontSize==="11px"&&e.toPrecision(3)==="16.9")c.height=e=14;if(f)c.width=P(e*$(g))+P(d*U(g)),c.height=P(e*U(g))+P(d*$(g))}if(r){for(;n.length>250;)delete m[n.shift()];m[r]||n.push(r);m[r]=c}}return c},show:function(a){return this.attr({visibility:a?
-"inherit":"visible"})},hide:function(){return this.attr({visibility:"hidden"})},fadeOut:function(a){var b=this;b.animate({opacity:0},{duration:a||150,complete:function(){b.attr({y:-9999})}})},add:function(a){var b=this.renderer,c=this.element,d;if(a)this.parentGroup=a;this.parentInverted=a&&a.inverted;this.textStr!==void 0&&b.buildText(this);this.added=!0;if(!a||a.handleZ||this.zIndex)d=this.zIndexSetter();d||(a?a.element:b.box).appendChild(c);if(this.onAdd)this.onAdd();return this},safeRemoveChild:function(a){var b=
-a.parentNode;b&&b.removeChild(a)},destroy:function(){var a=this,b=a.element||{},c=a.shadows,d=a.renderer.isSVG&&b.nodeName==="SPAN"&&a.parentGroup,e,f;b.onclick=b.onmouseout=b.onmouseover=b.onmousemove=b.point=null;Oa(a);if(a.clipPath)a.clipPath=a.clipPath.destroy();if(a.stops){for(f=0;f]*>/g,"")))},textSetter:function(a){if(a!==this.textStr)delete this.bBox,this.textStr=a,this.added&&this.renderer.buildText(this)},fillSetter:function(a,b,c){typeof a==="string"?c.setAttribute(b,a):a&&this.colorGradient(a,b,c)},visibilitySetter:function(a,b,c){a===
-"inherit"?c.removeAttribute(b):c.setAttribute(b,a)},zIndexSetter:function(a,b){var c=this.renderer,d=this.parentGroup,c=(d||c).element||c.box,e,f,g=this.element,h;e=this.added;var i;q(a)&&(g.setAttribute(b,a),a=+a,this[b]===a&&(e=!1),this[b]=a);if(e){if((a=this.zIndex)&&d)d.handleZ=!0;d=c.childNodes;for(i=0;ia||!q(a)&&q(f)))c.insertBefore(g,e),h=!0;h||c.appendChild(g)}return h},_defaultSetter:function(a,b,c){c.setAttribute(b,a)}};O.prototype.yGetter=
-O.prototype.xGetter;O.prototype.translateXSetter=O.prototype.translateYSetter=O.prototype.rotationSetter=O.prototype.verticalAlignSetter=O.prototype.scaleXSetter=O.prototype.scaleYSetter=function(a,b){this[b]=a;this.doTransform=!0};O.prototype["stroke-widthSetter"]=O.prototype.strokeSetter=function(a,b,c){this[b]=a;if(this.stroke&&this["stroke-width"])this.strokeWidth=this["stroke-width"],O.prototype.fillSetter.call(this,this.stroke,"stroke",c),c.setAttribute("stroke-width",this["stroke-width"]),
-this.hasStroke=!0;else if(b==="stroke-width"&&a===0&&this.hasStroke)c.removeAttribute("stroke"),this.hasStroke=!1};var Ca=function(){this.init.apply(this,arguments)};Ca.prototype={Element:O,init:function(a,b,c,d,e,f){var g,d=this.createElement("svg").attr({version:"1.1"}).css(this.getStyle(d));g=d.element;a.appendChild(g);a.innerHTML.indexOf("xmlns")===-1&&K(g,"xmlns",Fa);this.isSVG=!0;this.box=g;this.boxWrapper=d;this.alignedObjects=[];this.url=(Ma||mb)&&y.getElementsByTagName("base").length?E.location.href.replace(/#.*?$/,
-"").replace(/([\('\)])/g,"\\$1").replace(/ /g,"%20"):"";this.createElement("desc").add().element.appendChild(y.createTextNode("Created with Highcharts 4.2.3"));this.defs=this.createElement("defs").add();this.allowHTML=f;this.forExport=e;this.gradients={};this.cache={};this.cacheKeys=[];this.imgCount=0;this.setSize(b,c,!1);var h;if(Ma&&a.getBoundingClientRect)this.subPixelFix=b=function(){L(a,{left:0,top:0});h=a.getBoundingClientRect();L(a,{left:ua(h.left)-h.left+"px",top:ua(h.top)-h.top+"px"})},b(),
-M(E,"resize",b)},getStyle:function(a){return this.style=u({fontFamily:'"Lucida Grande", "Lucida Sans Unicode", Arial, Helvetica, sans-serif',fontSize:"12px"},a)},isHidden:function(){return!this.boxWrapper.getBBox().width},destroy:function(){var a=this.defs;this.box=null;this.boxWrapper=this.boxWrapper.destroy();Sa(this.gradients||{});this.gradients=null;if(a)this.defs=a.destroy();this.subPixelFix&&V(E,"resize",this.subPixelFix);return this.alignedObjects=null},createElement:function(a){var b=new this.Element;
-b.init(this,a);return b},draw:function(){},getRadialAttr:function(a,b){return{cx:a[0]-a[2]/2+b.cx*a[2],cy:a[1]-a[2]/2+b.cy*a[2],r:b.r*a[2]}},buildText:function(a){for(var b=a.element,c=this,d=c.forExport,e=p(a.textStr,"").toString(),f=e.indexOf("<")!==-1,g=b.childNodes,h,i,k=K(b,"x"),j=a.styles,l=a.textWidth,m=j&&j.lineHeight,n=j&&j.textShadow,r=j&&j.textOverflow==="ellipsis",s=g.length,R=l&&!a.added&&this.box,v=function(a){return m?C(m):c.fontMetrics(/(px|em)$/.test(a&&a.style.fontSize)?a.style.fontSize:
-j&&j.fontSize||c.style.fontSize||12,a).h},x=function(a){return a.replace(/</g,"<").replace(/>/g,">")};s--;)b.removeChild(g[s]);!f&&!n&&!r&&e.indexOf(" ")===-1?b.appendChild(y.createTextNode(x(e))):(h=/<.*style="([^"]+)".*>/,i=/<.*href="(http[^"]+)".*>/,R&&R.appendChild(b),e=f?e.replace(/<(b|strong)>/g,'').replace(/<(i|em)>/g,'').replace(//g," ").split(//g):[e],e[e.length-1]===
-""&&e.pop(),o(e,function(e,f){var g,m=0,e=e.replace(//g," |||");g=e.split("|||");o(g,function(e){if(e!==""||g.length===1){var n={},s=y.createElementNS(Fa,"tspan"),p;h.test(e)&&(p=e.match(h)[1].replace(/(;| |^)color([ :])/,"$1fill$2"),K(s,"style",p));i.test(e)&&!d&&(K(s,"onclick",'location.href="'+e.match(i)[1]+'"'),L(s,{cursor:"pointer"}));e=x(e.replace(/<(.|\n)*?>/g,"")||" ");if(e!==" "){s.appendChild(y.createTextNode(e));if(m)n.dx=0;else if(f&&k!==null)n.x=
-k;K(s,n);b.appendChild(s);!m&&f&&(!ca&&d&&L(s,{display:"block"}),K(s,"dy",v(s)));if(l){for(var n=e.replace(/([^\^])-/g,"$1- ").split(" "),R=g.length>1||f||n.length>1&&j.whiteSpace!=="nowrap",o,w,q,t=[],u=v(s),A=1,z=a.rotation,B=e,D=B.length;(R||r)&&(n.length||t.length);)a.rotation=0,o=a.getBBox(!0),q=o.width,!ca&&c.forExport&&(q=c.measureSpanWidth(s.firstChild.data,a.styles)),o=q>l,w===void 0&&(w=o),r&&w?(D/=2,B===""||!o&&D<0.5?n=[]:(o&&(w=!0),B=e.substring(0,B.length+(o?-1:1)*ua(D)),n=[B+(l>3?"\u2026":
-"")],s.removeChild(s.firstChild))):!o||n.length===1?(n=t,t=[],n.length&&(A++,s=y.createElementNS(Fa,"tspan"),K(s,{dy:u,x:k}),p&&K(s,"style",p),b.appendChild(s)),q>l&&(l=q)):(s.removeChild(s.firstChild),t.unshift(n.pop())),n.length&&s.appendChild(y.createTextNode(n.join(" ").replace(/- /g,"-")));w&&a.attr("title",a.textStr);a.rotation=z}m++}}})}),R&&R.removeChild(b),n&&a.applyTextShadow&&a.applyTextShadow(n))},getContrast:function(a){a=ia(a).rgba;return a[0]+a[1]+a[2]>384?"#000000":"#FFFFFF"},button:function(a,
-b,c,d,e,f,g,h,i){var k=this.label(a,b,c,i,null,null,null,null,"button"),j=0,l,m,n,r,s,p,a={x1:0,y1:0,x2:0,y2:1},e=D({"stroke-width":1,stroke:"#CCCCCC",fill:{linearGradient:a,stops:[[0,"#FEFEFE"],[1,"#F6F6F6"]]},r:2,padding:5,style:{color:"black"}},e);n=e.style;delete e.style;f=D(e,{stroke:"#68A",fill:{linearGradient:a,stops:[[0,"#FFF"],[1,"#ACF"]]}},f);r=f.style;delete f.style;g=D(e,{stroke:"#68A",fill:{linearGradient:a,stops:[[0,"#9BD"],[1,"#CDF"]]}},g);s=g.style;delete g.style;h=D(e,{style:{color:"#CCC"}},
-h);p=h.style;delete h.style;M(k.element,ya?"mouseover":"mouseenter",function(){j!==3&&k.attr(f).css(r)});M(k.element,ya?"mouseout":"mouseleave",function(){j!==3&&(l=[e,f,g][j],m=[n,r,s][j],k.attr(l).css(m))});k.setState=function(a){(k.state=j=a)?a===2?k.attr(g).css(s):a===3&&k.attr(h).css(p):k.attr(e).css(n)};return k.on("click",function(a){j!==3&&d.call(k,a)}).attr(e).css(u({cursor:"default"},n))},crispLine:function(a,b){a[1]===a[4]&&(a[1]=a[4]=A(a[1])-b%2/2);a[2]===a[5]&&(a[2]=a[5]=A(a[2])+b%2/
-2);return a},path:function(a){var b={fill:"none"};Ia(a)?b.d=a:Y(a)&&u(b,a);return this.createElement("path").attr(b)},circle:function(a,b,c){a=Y(a)?a:{x:a,y:b,r:c};b=this.createElement("circle");b.xSetter=b.ySetter=function(a,b,c){c.setAttribute("c"+b,a)};return b.attr(a)},arc:function(a,b,c,d,e,f){if(Y(a))b=a.y,c=a.r,d=a.innerR,e=a.start,f=a.end,a=a.x;a=this.symbol("arc",a||0,b||0,c||0,c||0,{innerR:d||0,start:e||0,end:f||0});a.r=c;return a},rect:function(a,b,c,d,e,f){var e=Y(a)?a.r:e,g=this.createElement("rect"),
-a=Y(a)?a:a===z?{}:{x:a,y:b,width:t(c,0),height:t(d,0)};if(f!==z)g.strokeWidth=f,a=g.crisp(a);if(e)a.r=e;g.rSetter=function(a,b,c){K(c,{rx:a,ry:a})};return g.attr(a)},setSize:function(a,b,c){var d=this.alignedObjects,e=d.length;this.width=a;this.height=b;for(this.boxWrapper[p(c,!0)?"animate":"attr"]({width:a,height:b});e--;)d[e].align()},g:function(a){var b=this.createElement("g");return q(a)?b.attr({"class":"highcharts-"+a}):b},image:function(a,b,c,d,e){var f={preserveAspectRatio:"none"};arguments.length>
-1&&u(f,{x:b,y:c,width:d,height:e});f=this.createElement("image").attr(f);f.element.setAttributeNS?f.element.setAttributeNS("http://www.w3.org/1999/xlink","href",a):f.element.setAttribute("hc-svg-href",a);return f},symbol:function(a,b,c,d,e,f){var g=this,h,i=this.symbols[a],i=i&&i(A(b),A(c),d,e,f),k=/^url\((.*?)\)$/,j,l;if(i)h=this.path(i),u(h,{symbolName:a,x:b,y:c,width:d,height:e}),f&&u(h,f);else if(k.test(a))l=function(a,b){a.element&&(a.attr({width:b[0],height:b[1]}),a.alignByTranslate||a.translate(A((d-
-b[0])/2),A((e-b[1])/2)))},j=a.match(k)[1],a=Nb[j]||f&&f.width&&f.height&&[f.width,f.height],h=this.image(j).attr({x:b,y:c}),h.isImg=!0,a?l(h,a):(h.attr({width:0,height:0}),Z("img",{onload:function(){this.width===0&&(L(this,{position:"absolute",top:"-999em"}),y.body.appendChild(this));l(h,Nb[j]=[this.width,this.height]);this.parentNode&&this.parentNode.removeChild(this);g.imgCount--;if(!g.imgCount)S[g.chartIndex].onload()},src:j})),this.imgCount++;return h},symbols:{circle:function(a,b,c,d){var e=
-0.166*c;return["M",a+c/2,b,"C",a+c+e,b,a+c+e,b+d,a+c/2,b+d,"C",a-e,b+d,a-e,b,a+c/2,b,"Z"]},square:function(a,b,c,d){return["M",a,b,"L",a+c,b,a+c,b+d,a,b+d,"Z"]},triangle:function(a,b,c,d){return["M",a+c/2,b,"L",a+c,b+d,a,b+d,"Z"]},"triangle-down":function(a,b,c,d){return["M",a,b,"L",a+c,b,a+c/2,b+d,"Z"]},diamond:function(a,b,c,d){return["M",a+c/2,b,"L",a+c,b+d/2,a+c/2,b+d,a,b+d/2,"Z"]},arc:function(a,b,c,d,e){var f=e.start,c=e.r||c||d,g=e.end-0.001,d=e.innerR,h=e.open,i=U(f),k=$(f),j=U(g),g=$(g),
-e=e.end-fc&&e>b+g&&eb+g&&ed&&h>a+g&&ha+g&&h j&&/[ \-]/.test(b.textContent||b.innerText))L(b,{width:j+"px",display:"block",whiteSpace:l||"normal"}),this.hasTextWidth=!0;else if(this.hasTextWidth)L(b,{width:"",display:"",whiteSpace:l||"nowrap"}),this.hasTextWidth=!1;this.getSpanCorrection(this.hasTextWidth?
-j:b.offsetWidth,k,h,i,g)}L(b,{left:e+(this.xCorr||0)+"px",top:f+(this.yCorr||0)+"px"});if(mb)k=b.offsetHeight;this.cTT=m}}else this.alignOnAdd=!0},setSpanRotation:function(a,b,c){var d={},e=ya?"-ms-transform":mb?"-webkit-transform":Ma?"MozTransform":Lb?"-o-transform":"";d[e]=d.transform="rotate("+a+"deg)";d[e+(Ma?"Origin":"-origin")]=d.transformOrigin=b*100+"% "+c+"px";L(this.element,d)},getSpanCorrection:function(a,b,c){this.xCorr=-a*c;this.yCorr=-b}});u(Ca.prototype,{html:function(a,b,c){var d=
-this.createElement("span"),e=d.element,f=d.renderer,g=function(a,b){o(["opacity","visibility"],function(c){fb(a,c+"Setter",function(a,c,d,e){a.call(this,c,d,e);b[d]=c})})};d.textSetter=function(a){a!==e.innerHTML&&delete this.bBox;e.innerHTML=this.textStr=a;d.htmlUpdateTransform()};g(d,d.element.style);d.xSetter=d.ySetter=d.alignSetter=d.rotationSetter=function(a,b){b==="align"&&(b="textAlign");d[b]=a;d.htmlUpdateTransform()};d.attr({text:a,x:A(b),y:A(c)}).css({position:"absolute",fontFamily:this.style.fontFamily,
-fontSize:this.style.fontSize});e.style.whiteSpace="nowrap";d.css=d.htmlCss;if(f.isSVG)d.add=function(a){var b,c=f.box.parentNode,j=[];if(this.parentGroup=a){if(b=a.div,!b){for(;a;)j.push(a),a=a.parentGroup;o(j.reverse(),function(a){var d,e=K(a.element,"class");e&&(e={className:e});b=a.div=a.div||Z(La,e,{position:"absolute",left:(a.translateX||0)+"px",top:(a.translateY||0)+"px"},b||c);d=b.style;u(a,{translateXSetter:function(b,c){d.left=b+"px";a[c]=b;a.doTransform=!0},translateYSetter:function(b,c){d.top=
-b+"px";a[c]=b;a.doTransform=!0}});g(a,d)})}}else b=c;b.appendChild(e);d.added=!0;d.alignOnAdd&&d.htmlUpdateTransform();return d};return d}});var J;if(!ca&&!ha){J={init:function(a,b){var c=["<",b,' filled="f" stroked="f"'],d=["position: ","absolute",";"],e=b===La;(b==="shape"||e)&&d.push("left:0;top:0;width:1px;height:1px;");d.push("visibility: ",e?"hidden":"visible");c.push(' style="',d.join(""),'"/>');if(b)c=e||b==="span"||b==="img"?c.join(""):a.prepVML(c),this.element=Z(c);this.renderer=a},add:function(a){var b=
-this.renderer,c=this.element,d=b.box,e=a&&a.inverted,d=a?a.element||a:d;if(a)this.parentGroup=a;e&&b.invertChild(c,d);d.appendChild(c);this.added=!0;this.alignOnAdd&&!this.deferUpdateTransform&&this.updateTransform();if(this.onAdd)this.onAdd();return this},updateTransform:O.prototype.htmlUpdateTransform,setSpanRotation:function(){var a=this.rotation,b=U(a*ga),c=$(a*ga);L(this.element,{filter:a?["progid:DXImageTransform.Microsoft.Matrix(M11=",b,", M12=",-c,", M21=",c,", M22=",b,", sizingMethod='auto expand')"].join(""):
-"none"})},getSpanCorrection:function(a,b,c,d,e){var f=d?U(d*ga):1,g=d?$(d*ga):0,h=p(this.elemHeight,this.element.offsetHeight),i;this.xCorr=f<0&&-a;this.yCorr=g<0&&-h;i=f*g<0;this.xCorr+=g*b*(i?1-c:c);this.yCorr-=f*b*(d?i?c:1-c:1);e&&e!=="left"&&(this.xCorr-=a*c*(f<0?-1:1),d&&(this.yCorr-=h*c*(g<0?-1:1)),L(this.element,{textAlign:e}))},pathToVML:function(a){for(var b=a.length,c=[];b--;)if(ma(a[b]))c[b]=A(a[b]*10)-5;else if(a[b]==="Z")c[b]="x";else if(c[b]=a[b],a.isArc&&(a[b]==="wa"||a[b]==="at"))c[b+
-5]===c[b+7]&&(c[b+7]+=a[b+7]>a[b+5]?1:-1),c[b+6]===c[b+8]&&(c[b+8]+=a[b+8]>a[b+6]?1:-1);return c.join(" ")||"x"},clip:function(a){var b=this,c;a?(c=a.members,oa(c,b),c.push(b),b.destroyClip=function(){oa(c,b)},a=a.getCSS(b)):(b.destroyClip&&b.destroyClip(),a={clip:lb?"inherit":"rect(auto)"});return b.css(a)},css:O.prototype.htmlCss,safeRemoveChild:function(a){a.parentNode&&Ta(a)},destroy:function(){this.destroyClip&&this.destroyClip();return O.prototype.destroy.apply(this)},on:function(a,b){this.element["on"+
-a]=function(){var a=E.event;a.target=a.srcElement;b(a)};return this},cutOffPath:function(a,b){var c,a=a.split(/[ ,]/);c=a.length;if(c===9||c===11)a[c-4]=a[c-2]=C(a[c-2])-10*b;return a.join(" ")},shadow:function(a,b,c){var d=[],e,f=this.element,g=this.renderer,h,i=f.style,k,j=f.path,l,m,n,r;j&&typeof j.value!=="string"&&(j="x");m=j;if(a){n=p(a.width,3);r=(a.opacity||0.15)/n;for(e=1;e<=3;e++){l=n*2+1-2*e;c&&(m=this.cutOffPath(j.value,l+0.5));k=[' '];h=Z(g.prepVML(k),null,{left:C(i.left)+p(a.offsetX,1),top:C(i.top)+p(a.offsetY,1)});if(c)h.cutOff=l+1;k=[' '];Z(g.prepVML(k),null,null,h);b?b.element.appendChild(h):f.parentNode.insertBefore(h,f);d.push(h)}this.shadows=d}return this},updateShadows:Aa,setAttr:function(a,b){lb?this.element[a]=b:this.element.setAttribute(a,b)},classSetter:function(a){this.element.className=a},dashstyleSetter:function(a,
-b,c){(c.getElementsByTagName("stroke")[0]||Z(this.renderer.prepVML([" "]),null,null,c))[b]=a||"solid";this[b]=a},dSetter:function(a,b,c){var d=this.shadows,a=a||[];this.d=a.join&&a.join(" ");c.path=a=this.pathToVML(a);if(d)for(c=d.length;c--;)d[c].path=d[c].cutOff?this.cutOffPath(a,d[c].cutOff):a;this.setAttr(b,a)},fillSetter:function(a,b,c){var d=c.nodeName;if(d==="SPAN")c.style.color=a;else if(d!=="IMG")c.filled=a!=="none",this.setAttr("fillcolor",this.renderer.color(a,c,b,this))},"fill-opacitySetter":function(a,
-b,c){Z(this.renderer.prepVML(["<",b.split("-")[0],' opacity="',a,'"/>']),null,null,c)},opacitySetter:Aa,rotationSetter:function(a,b,c){c=c.style;this[b]=c[b]=a;c.left=-A($(a*ga)+1)+"px";c.top=A(U(a*ga))+"px"},strokeSetter:function(a,b,c){this.setAttr("strokecolor",this.renderer.color(a,c,b,this))},"stroke-widthSetter":function(a,b,c){c.stroked=!!a;this[b]=a;ma(a)&&(a+="px");this.setAttr("strokeweight",a)},titleSetter:function(a,b){this.setAttr(b,a)},visibilitySetter:function(a,b,c){a==="inherit"&&
-(a="visible");this.shadows&&o(this.shadows,function(c){c.style[b]=a});c.nodeName==="DIV"&&(a=a==="hidden"?"-999em":0,lb||(c.style[b]=a?"visible":"hidden"),b="top");c.style[b]=a},xSetter:function(a,b,c){this[b]=a;b==="x"?b="left":b==="y"&&(b="top");this.updateClipping?(this[b]=a,this.updateClipping()):c.style[b]=a},zIndexSetter:function(a,b,c){c.style[b]=a}};J["stroke-opacitySetter"]=J["fill-opacitySetter"];B.VMLElement=J=pa(O,J);J.prototype.ySetter=J.prototype.widthSetter=J.prototype.heightSetter=
-J.prototype.xSetter;var Cb={Element:J,isIE8:za.indexOf("MSIE 8.0")>-1,init:function(a,b,c,d){var e;this.alignedObjects=[];d=this.createElement(La).css(u(this.getStyle(d),{position:"relative"}));e=d.element;a.appendChild(d.element);this.isVML=!0;this.box=e;this.boxWrapper=d;this.gradients={};this.cache={};this.cacheKeys=[];this.imgCount=0;this.setSize(b,c,!1);if(!y.namespaces.hcv){y.namespaces.add("hcv","urn:schemas-microsoft-com:vml");try{y.createStyleSheet().cssText="hcv\\:fill, hcv\\:path, hcv\\:shape, hcv\\:stroke{ behavior:url(#default#VML); display: inline-block; } "}catch(f){y.styleSheets[0].cssText+=
-"hcv\\:fill, hcv\\:path, hcv\\:shape, hcv\\:stroke{ behavior:url(#default#VML); display: inline-block; } "}}},isHidden:function(){return!this.box.offsetWidth},clipRect:function(a,b,c,d){var e=this.createElement(),f=Y(a);return u(e,{members:[],count:0,left:(f?a.x:a)+1,top:(f?a.y:b)+1,width:(f?a.width:c)-1,height:(f?a.height:d)-1,getCSS:function(a){var b=a.element,c=b.nodeName,a=a.inverted,d=this.top-(c==="shape"?b.offsetTop:0),e=this.left,b=e+this.width,f=d+this.height,d={clip:"rect("+A(a?e:d)+"px,"+
-A(a?f:b)+"px,"+A(a?b:f)+"px,"+A(a?d:e)+"px)"};!a&&lb&&c==="DIV"&&u(d,{width:b+"px",height:f+"px"});return d},updateClipping:function(){o(e.members,function(a){a.element&&a.css(e.getCSS(a))})}})},color:function(a,b,c,d){var e=this,f,g=/^rgba/,h,i,k="none";a&&a.linearGradient?i="gradient":a&&a.radialGradient&&(i="pattern");if(i){var j,l,m=a.linearGradient||a.radialGradient,n,r,s,p,v,x="",a=a.stops,w,q=[],ba=function(){h=[' '];Z(e.prepVML(h),null,null,b)};n=a[0];w=a[a.length-1];n[0]>0&&a.unshift([0,n[1]]);w[0]<1&&a.push([1,w[1]]);o(a,function(a,b){g.test(a[1])?(f=ia(a[1]),j=f.get("rgb"),l=f.get("a")):(j=a[1],l=1);q.push(a[0]*100+"% "+j);b?(s=l,p=j):(r=l,v=j)});if(c==="fill")if(i==="gradient")c=m.x1||m[0]||0,a=m.y1||m[1]||0,n=m.x2||m[2]||0,m=m.y2||m[3]||0,x='angle="'+(90-W.atan((m-a)/(n-c))*180/ra)+'"',ba();else{var k=m.r,t=k*2,u=k*2,A=m.cx,B=m.cy,z=b.radialReference,y,k=function(){z&&(y=
-d.getBBox(),A+=(z[0]-y.x)/y.width-0.5,B+=(z[1]-y.y)/y.height-0.5,t*=z[2]/y.width,u*=z[2]/y.height);x='src="'+N.global.VMLRadialGradientURL+'" size="'+t+","+u+'" origin="0.5,0.5" position="'+A+","+B+'" color2="'+v+'" ';ba()};d.added?k():d.onAdd=k;k=p}else k=j}else if(g.test(a)&&b.tagName!=="IMG")f=ia(a),d[c+"-opacitySetter"](f.get("a"),c,b),k=f.get("rgb");else{k=b.getElementsByTagName(c);if(k.length)k[0].opacity=1,k[0].type="solid";k=a}return k},prepVML:function(a){var b=this.isIE8,a=a.join("");b?
-(a=a.replace("/>",' xmlns="urn:schemas-microsoft-com:vml" />'),a=a.indexOf('style="')===-1?a.replace("/>",' style="display:inline-block;behavior:url(#default#VML);" />'):a.replace('style="','style="display:inline-block;behavior:url(#default#VML);')):a=a.replace("<","1&&f.attr({x:b,y:c,width:d,height:e});return f},createElement:function(a){return a==="rect"?this.symbol(a):Ca.prototype.createElement.call(this,a)},invertChild:function(a,b){var c=this,d=b.style,e=a.tagName==="IMG"&&a.style;L(a,{flip:"x",left:C(d.width)-(e?C(e.top):
-1),top:C(d.height)-(e?C(e.left):1),rotation:-90});o(a.childNodes,function(b){c.invertChild(b,a)})},symbols:{arc:function(a,b,c,d,e){var f=e.start,g=e.end,h=e.r||c||d,c=e.innerR,d=U(f),i=$(f),k=U(g),j=$(g);if(g-f===0)return["x"];f=["wa",a-h,b-h,a+h,b+h,a+h*d,b+h*i,a+h*k,b+h*j];e.open&&!c&&f.push("e","M",a,b);f.push("at",a-c,b-c,a+c,b+c,a+c*k,b+c*j,a+c*d,b+c*i,"x","e");f.isArc=!0;return f},circle:function(a,b,c,d,e){e&&(c=d=2*e.r);e&&e.isCircle&&(a-=c/2,b-=d/2);return["wa",a,b,a+c,b+d,a+c,b+d/2,a+c,
-b+d/2,"e"]},rect:function(a,b,c,d,e){return Ca.prototype.symbols[!q(e)||!e.r?"square":"callout"].call(0,a,b,c,d,e)}}};B.VMLRenderer=J=function(){this.init.apply(this,arguments)};J.prototype=D(Ca.prototype,Cb);cb=J}Ca.prototype.measureSpanWidth=function(a,b){var c=y.createElement("span"),d;d=y.createTextNode(a);c.appendChild(d);L(c,b);this.box.appendChild(c);d=c.offsetWidth;Ta(c);return d};var Ob;if(ha)B.CanVGRenderer=J=function(){Fa="http://www.w3.org/1999/xhtml"},J.prototype.symbols={},Ob=function(){function a(){var a=
-b.length,d;for(d=0;d0&&c+i*k>e&&(m=A((d-c)/U(h*ga)));else if(d=c+(1-i)*k,c-i*ke&&(j=e-a.x+j*i,l=-1),j=F(b.slotWidth,j),jj||b.autoRotation&&g.styles.width)m=j;if(m){n.width=
-m;if(!b.options.labels.style.textOverflow)n.textOverflow="ellipsis";g.css(n)}},getPosition:function(a,b,c,d){var e=this.axis,f=e.chart,g=d&&f.oldChartHeight||f.chartHeight;return{x:a?e.translate(b+c,null,null,d)+e.transB:e.left+e.offset+(e.opposite?(d&&f.oldChartWidth||f.chartWidth)-e.right-e.left:0),y:a?g-e.bottom+e.offset-(e.opposite?e.height:0):g-e.translate(b+c,null,null,d)-e.transB}},getLabelPosition:function(a,b,c,d,e,f,g,h){var i=this.axis,k=i.transA,j=i.reversed,l=i.staggerLines,m=i.tickRotCorr||
-{x:0,y:0},n=e.y;q(n)||(n=i.side===2?m.y+8:n=U(c.rotation*ga)*(m.y-c.getBBox(!1,0).height/2));a=a+e.x+m.x-(f&&d?f*k*(j?-1:1):0);b=b+n-(f&&!d?f*k*(j?1:-1):0);l&&(c=g/(h||1)%l,i.opposite&&(c=l-c-1),b+=c*(i.labelOffset/l));return{x:a,y:A(b)}},getMarkPath:function(a,b,c,d,e,f){return f.crispLine(["M",a,b,"L",a+(e?0:-c),b+(e?c:0)],d)},render:function(a,b,c){var d=this.axis,e=d.options,f=d.chart.renderer,g=d.horiz,h=this.type,i=this.label,k=this.pos,j=e.labels,l=this.gridLine,m=h?h+"Grid":"grid",n=h?h+"Tick":
-"tick",r=e[m+"LineWidth"],s=e[m+"LineColor"],o=e[m+"LineDashStyle"],v=e[n+"Length"],m=p(e[n+"Width"],!h&&d.isXAxis?1:0),x=e[n+"Color"],w=e[n+"Position"],n=this.mark,q=j.step,ba=!0,t=d.tickmarkOffset,u=this.getPosition(g,k,t,b),A=u.x,u=u.y,B=g&&A===d.pos+d.len||!g&&u===d.pos?-1:1,c=p(c,1);this.isActive=!0;if(r){k=d.getPlotLinePath(k+t,r*B,b,!0);if(l===z){l={stroke:s,"stroke-width":r};if(o)l.dashstyle=o;if(!h)l.zIndex=1;if(b)l.opacity=0;this.gridLine=l=r?f.path(k).attr(l).add(d.gridGroup):null}if(!b&&
-l&&k)l[this.isNew?"attr":"animate"]({d:k,opacity:c})}if(m&&v)w==="inside"&&(v=-v),d.opposite&&(v=-v),h=this.getMarkPath(A,u,v,m*B,g,f),n?n.animate({d:h,opacity:c}):this.mark=f.path(h).attr({stroke:x,"stroke-width":m,opacity:c}).add(d.axisGroup);if(i&&!isNaN(A))i.xy=u=this.getLabelPosition(A,u,i,g,j,t,a,q),this.isFirst&&!this.isLast&&!p(e.showFirstLabel,1)||this.isLast&&!this.isFirst&&!p(e.showLastLabel,1)?ba=!1:g&&!d.isRadial&&!j.step&&!j.rotation&&!b&&c!==0&&this.handleOverflow(u),q&&a%q&&(ba=!1),
-ba&&!isNaN(u.y)?(u.opacity=c,i[this.isNew?"attr":"animate"](u),this.isNew=!1):i.attr("y",-9999)},destroy:function(){Sa(this,this.axis)}};B.PlotLineOrBand=function(a,b){this.axis=a;if(b)this.options=b,this.id=b.id};B.PlotLineOrBand.prototype={render:function(){var a=this,b=a.axis,c=b.horiz,d=a.options,e=d.label,f=a.label,g=d.width,h=d.to,i=d.from,k=q(i)&&q(h),j=d.value,l=d.dashStyle,m=a.svgElem,n=[],r,s=d.color,o=p(d.zIndex,0),v=d.events,x={},w=b.chart.renderer;b.isLog&&(i=Da(i),h=Da(h),j=Da(j));if(g){if(n=
-b.getPlotLinePath(j,g),x={stroke:s,"stroke-width":g},l)x.dashstyle=l}else if(k){n=b.getPlotBandPath(i,h,d);if(s)x.fill=s;if(d.borderWidth)x.stroke=d.borderColor,x["stroke-width"]=d.borderWidth}else return;x.zIndex=o;if(m)if(n)m.show(),m.animate({d:n});else{if(m.hide(),f)a.label=f=f.destroy()}else if(n&&n.length&&(a.svgElem=m=w.path(n).attr(x).add(),v))for(r in d=function(b){m.on(b,function(c){v[b].apply(a,[c])})},v)d(r);e&&q(e.text)&&n&&n.length&&b.width>0&&b.height>0&&!n.flat?(e=D({align:c&&k&&"center",
-x:c?!k&&4:10,verticalAlign:!c&&k&&"middle",y:c?k?16:10:k?6:-4,rotation:c&&!k&&90},e),this.renderLabel(e,n,k,o)):f&&f.hide();return a},renderLabel:function(a,b,c,d){var e=this.label,f=this.axis.chart.renderer;if(!e)e={align:a.textAlign||a.align,rotation:a.rotation},e.zIndex=d,this.label=e=f.text(a.text,0,0,a.useHTML).attr(e).css(a.style).add();d=[b[1],b[4],c?b[6]:b[1]];b=[b[2],b[5],c?b[7]:b[2]];c=Ra(d);f=Ra(b);e.align(a,!1,{x:c,y:f,width:Ea(d)-c,height:Ea(b)-f});e.show()},destroy:function(){oa(this.axis.plotLinesAndBands,
-this);delete this.axis;Sa(this)}};var ka=B.Axis=function(){this.init.apply(this,arguments)};ka.prototype={defaultOptions:{dateTimeLabelFormats:{millisecond:"%H:%M:%S.%L",second:"%H:%M:%S",minute:"%H:%M",hour:"%H:%M",day:"%e. %b",week:"%e. %b",month:"%b '%y",year:"%Y"},endOnTick:!1,gridLineColor:"#D8D8D8",labels:{enabled:!0,style:{color:"#606060",cursor:"default",fontSize:"11px"},x:0,y:15},lineColor:"#C0D0E0",lineWidth:1,minPadding:0.01,maxPadding:0.01,minorGridLineColor:"#E0E0E0",minorGridLineWidth:1,
-minorTickColor:"#A0A0A0",minorTickLength:2,minorTickPosition:"outside",startOfWeek:1,startOnTick:!1,tickColor:"#C0D0E0",tickLength:10,tickmarkPlacement:"between",tickPixelInterval:100,tickPosition:"outside",title:{align:"middle",style:{color:"#707070"}},type:"linear"},defaultYAxisOptions:{endOnTick:!0,gridLineWidth:1,tickPixelInterval:72,showLastLabel:!0,labels:{x:-8,y:3},lineWidth:0,maxPadding:0.05,minPadding:0.05,startOnTick:!0,title:{rotation:270,text:"Values"},stackLabels:{enabled:!1,formatter:function(){return B.numberFormat(this.total,
--1)},style:D(aa.line.dataLabels.style,{color:"#000000"})}},defaultLeftAxisOptions:{labels:{x:-15,y:null},title:{rotation:270}},defaultRightAxisOptions:{labels:{x:15,y:null},title:{rotation:90}},defaultBottomAxisOptions:{labels:{autoRotation:[-45],x:0,y:null},title:{rotation:0}},defaultTopAxisOptions:{labels:{autoRotation:[-45],x:0,y:-15},title:{rotation:0}},init:function(a,b){var c=b.isX;this.chart=a;this.horiz=a.inverted?!c:c;this.coll=(this.isXAxis=c)?"xAxis":"yAxis";this.opposite=b.opposite;this.side=
-b.side||(this.horiz?this.opposite?0:2:this.opposite?1:3);this.setOptions(b);var d=this.options,e=d.type;this.labelFormatter=d.labels.formatter||this.defaultLabelFormatter;this.userOptions=b;this.minPixelPadding=0;this.reversed=d.reversed;this.visible=d.visible!==!1;this.zoomEnabled=d.zoomEnabled!==!1;this.categories=d.categories||e==="category";this.names=this.names||[];this.isLog=e==="logarithmic";this.isDatetimeAxis=e==="datetime";this.isLinked=q(d.linkedTo);this.ticks={};this.labelEdge=[];this.minorTicks=
-{};this.plotLinesAndBands=[];this.alternateBands={};this.len=0;this.minRange=this.userMinRange=d.minRange||d.maxZoom;this.range=d.range;this.offset=d.offset||0;this.stacks={};this.oldStacks={};this.stacksTouched=0;this.min=this.max=null;this.crosshair=p(d.crosshair,ta(a.options.tooltip.crosshairs)[c?0:1],!1);var f,d=this.options.events;sa(this,a.axes)===-1&&(c&&!this.isColorAxis?a.axes.splice(a.xAxis.length,0,this):a.axes.push(this),a[this.coll].push(this));this.series=this.series||[];if(a.inverted&&
-c&&this.reversed===z)this.reversed=!0;this.removePlotLine=this.removePlotBand=this.removePlotBandOrLine;for(f in d)M(this,f,d[f]);if(this.isLog)this.val2lin=Da,this.lin2val=na},setOptions:function(a){this.options=D(this.defaultOptions,this.isXAxis?{}:this.defaultYAxisOptions,[this.defaultTopAxisOptions,this.defaultRightAxisOptions,this.defaultBottomAxisOptions,this.defaultLeftAxisOptions][this.side],D(N[this.coll],a))},defaultLabelFormatter:function(){var a=this.axis,b=this.value,c=a.categories,d=
-this.dateTimeLabelFormat,e=N.lang.numericSymbols,f=e&&e.length,g,h=a.options.labels.format,a=a.isLog?b:a.tickInterval;if(h)g=Ka(h,this);else if(c)g=b;else if(d)g=Qa(d,b);else if(f&&a>=1E3)for(;f--&&g===z;)c=Math.pow(1E3,f+1),a>=c&&b*10%c===0&&e[f]!==null&&(g=B.numberFormat(b/c,-1)+e[f]);g===z&&(g=P(b)>=1E4?B.numberFormat(b,-1):B.numberFormat(b,-1,z,""));return g},getSeriesExtremes:function(){var a=this,b=a.chart;a.hasVisibleSeries=!1;a.dataMin=a.dataMax=a.threshold=null;a.softThreshold=!a.isXAxis;
-a.buildStacks&&a.buildStacks();o(a.series,function(c){if(c.visible||!b.options.chart.ignoreHiddenSeries){var d=c.options,e=d.threshold,f;a.hasVisibleSeries=!0;a.isLog&&e<=0&&(e=null);if(a.isXAxis){if(d=c.xData,d.length)a.dataMin=F(p(a.dataMin,d[0]),Ra(d)),a.dataMax=t(p(a.dataMax,d[0]),Ea(d))}else{c.getExtremes();f=c.dataMax;c=c.dataMin;if(q(c)&&q(f))a.dataMin=F(p(a.dataMin,c),c),a.dataMax=t(p(a.dataMax,f),f);if(q(e))a.threshold=e;if(!d.softThreshold||a.isLog)a.softThreshold=!1}}})},translate:function(a,
-b,c,d,e,f){var g=this.linkedParent||this,h=1,i=0,k=d?g.oldTransA:g.transA,d=d?g.oldMin:g.min,j=g.minPixelPadding,e=(g.isOrdinal||g.isBroken||g.isLog&&e)&&g.lin2val;if(!k)k=g.transA;if(c)h*=-1,i=g.len;g.reversed&&(h*=-1,i-=h*(g.sector||g.len));b?(a=a*h+i,a-=j,a=a/k+d,e&&(a=g.lin2val(a))):(e&&(a=g.val2lin(a)),f==="between"&&(f=0.5),a=h*(a-d)*k+i+h*j+(ma(f)?k*f*g.pointRange:0));return a},toPixels:function(a,b){return this.translate(a,!1,!this.horiz,null,!0)+(b?0:this.pos)},toValue:function(a,b){return this.translate(a-
-(b?0:this.pos),!0,!this.horiz,null,!0)},getPlotLinePath:function(a,b,c,d,e){var f=this.chart,g=this.left,h=this.top,i,k,j=c&&f.oldChartHeight||f.chartHeight,l=c&&f.oldChartWidth||f.chartWidth,m;i=this.transB;var n=function(a,b,c){if(ac)d?a=F(t(b,a),c):m=!0;return a},e=p(e,this.translate(a,null,null,c)),a=c=A(e+i);i=k=A(j-e-i);isNaN(e)?m=!0:this.horiz?(i=h,k=j-this.bottom,a=c=n(a,g,g+this.width)):(a=g,c=l-this.right,i=k=n(i,h,h+this.height));return m&&!d?null:f.renderer.crispLine(["M",a,i,"L",
-c,k],b||1)},getLinearTickPositions:function(a,b,c){var d,e=fa(T(b/a)*a),f=fa(ua(c/a)*a),g=[];if(b===c&&ma(b))return[b];for(b=e;b<=f;){g.push(b);b=fa(b+a);if(b===d)break;d=b}return g},getMinorTickPositions:function(){var a=this.options,b=this.tickPositions,c=this.minorTickInterval,d=[],e,f=this.pointRangePadding||0;e=this.min-f;var f=this.max+f,g=f-e;if(g&&g/c=this.minRange,f,g,h,i,k,j;if(this.isXAxis&&this.minRange===z&&!this.isLog)q(a.min)||q(a.max)?this.minRange=null:(o(this.series,function(a){i=a.xData;for(g=k=a.xIncrement?1:i.length-1;g>0;g--)if(h=i[g]-
-i[g-1],f===z||h=n?(s=n,k=0):b.dataMax<=n&&(R=n,i=0)),b.min=p(v,s,b.dataMin),b.max=p(x,R,b.dataMax));if(e)!a&&F(b.min,p(b.dataMin,b.min))<=0&&X(10,1),b.min=fa(Da(b.min),15),b.max=fa(Da(b.max),15);if(b.range&&q(b.max))b.userMin=b.min=v=t(b.min,b.minFromRange()),b.userMax=x=b.max,b.range=null;b.beforePadding&&b.beforePadding();b.adjustForMinRange();if(!m&&!b.axisPointRange&&!b.usePercentage&&!h&&q(b.min)&&q(b.max)&&(c=b.max-b.min))!q(v)&&k&&(b.min-=c*k),!q(x)&&
-i&&(b.max+=c*i);if(ma(d.floor))b.min=t(b.min,d.floor);if(ma(d.ceiling))b.max=F(b.max,d.ceiling);if(r&&q(b.dataMin))if(n=n||0,!q(v)&&b.min=n)b.min=n;else if(!q(x)&&b.max>n&&b.dataMax<=n)b.max=n;b.tickInterval=b.min===b.max||b.min===void 0||b.max===void 0?1:h&&!j&&l===b.linkedParent.options.tickPixelInterval?j=b.linkedParent.tickInterval:p(j,this.tickAmount?(b.max-b.min)/t(this.tickAmount-1,1):void 0,m?1:(b.max-b.min)*l/t(b.len,l));g&&!a&&o(b.series,function(a){a.processData(b.min!==b.oldMin||
-b.max!==b.oldMax)});b.setAxisTranslation(!0);b.beforeSetTickPositions&&b.beforeSetTickPositions();if(b.postProcessTickInterval)b.tickInterval=b.postProcessTickInterval(b.tickInterval);if(b.pointRange&&!j)b.tickInterval=t(b.pointRange,b.tickInterval);a=p(d.minTickInterval,b.isDatetimeAxis&&b.closestPointRange);if(!j&&b.tickInterval0.5&&b.tickInterval<5&&b.max>1E3&&b.max<9999)),
-!!this.tickAmount);if(!this.tickAmount&&this.len)b.tickInterval=b.unsquish();this.setTickPositions()},setTickPositions:function(){var a=this.options,b,c=a.tickPositions,d=a.tickPositioner,e=a.startOnTick,f=a.endOnTick,g;this.tickmarkOffset=this.categories&&a.tickmarkPlacement==="between"&&this.tickInterval===1?0.5:0;this.minorTickInterval=a.minorTickInterval==="auto"&&this.tickInterval?this.tickInterval/5:a.minorTickInterval;this.tickPositions=b=c&&c.slice();if(!b&&(b=this.isDatetimeAxis?this.getTimeTicks(this.normalizeTimeTickInterval(this.tickInterval,
-a.units),this.min,this.max,a.startOfWeek,this.ordinalPositions,this.closestPointRange,!0):this.isLog?this.getLogTickPositions(this.tickInterval,this.min,this.max):this.getLinearTickPositions(this.tickInterval,this.min,this.max),b.length>this.len&&(b=[b[0],b.pop()]),this.tickPositions=b,d&&(d=d.apply(this,[this.min,this.max]))))this.tickPositions=b=d;if(!this.isLinked)this.trimTicks(b,e,f),this.min===this.max&&q(this.min)&&!this.tickAmount&&(g=!0,this.min-=0.5,this.max+=0.5),this.single=g,!c&&!d&&
-this.adjustTickAmount()},trimTicks:function(a,b,c){var d=a[0],e=a[a.length-1],f=this.minPointOffset||0;if(b)this.min=d;else for(;this.min-f>a[0];)a.shift();if(c)this.max=e;else for(;this.max+f c&&(this.tickInterval*=2,this.setTickPositions());if(q(d)){for(a=c=b.length;a--;)(d===3&&a%2===1||d<=2&&a>0&&a=e&&(b=e));this.displayBtn=a!==z||b!==z;this.setExtremes(a,b,!1,z,{trigger:"zoom"});return!0},setAxisSize:function(){var a=this.chart,b=this.options,c=b.offsetLeft||0,d=this.horiz,e=p(b.width,a.plotWidth-c+(b.offsetRight||0)),f=p(b.height,a.plotHeight),g=p(b.top,a.plotTop),b=p(b.left,a.plotLeft+c),c=/%$/;c.test(f)&&(f=Math.round(parseFloat(f)/
-100*a.plotHeight));c.test(g)&&(g=Math.round(parseFloat(g)/100*a.plotHeight+a.plotTop));this.left=b;this.top=g;this.width=e;this.height=f;this.bottom=a.chartHeight-f-g;this.right=a.chartWidth-e-b;this.len=t(d?e:f,0);this.pos=d?b:g},getExtremes:function(){var a=this.isLog;return{min:a?fa(na(this.min)):this.min,max:a?fa(na(this.max)):this.max,dataMin:this.dataMin,dataMax:this.dataMax,userMin:this.userMin,userMax:this.userMax}},getThreshold:function(a){var b=this.isLog,c=b?na(this.min):this.min,b=b?na(this.max):
-this.max;a===null?a=b<0?b:c:c>a?a=c:b15&&a<165?"right":a>195&&a<345?"left":"center"},unsquish:function(){var a=this.ticks,b=this.options.labels,c=this.horiz,d=this.tickInterval,e=d,f=this.len/(((this.categories?1:0)+this.max-this.min)/d),g,h=b.rotation,i=this.chart.renderer.fontMetrics(b.style.fontSize,a[0]&&a[0].label),k,j=Number.MAX_VALUE,l,m=function(a){a/=f||1;a=a>1?ua(a):1;return a*
-d};c?(l=!b.staggerLines&&!b.step&&(q(h)?[h]:f=-90&&a<=90)k=m(P(i.h/$(ga*a))),b=k+P(a/360),bm)m=a.labelLength}),m>i&&m>h.h?k.rotation=this.labelRotation:this.labelRotation=0;else if(g&&(l={width:i+"px"},!j)){l.textOverflow="clip";for(n=c.length;!f&&n--;)if(r=c[n],i=d[r].label)if(i.styles.textOverflow===
-"ellipsis"&&i.css({textOverflow:"clip"}),i.getBBox().height>this.len/c.length-(h.h-h.f)||d[r].labelLength>g)i.specCss={textOverflow:"ellipsis"}}if(k.rotation&&(l={width:(m>a.chartHeight*0.5?a.chartHeight*0.33:a.chartHeight)+"px"},!j))l.textOverflow="ellipsis";if(this.labelAlign=e.align||this.autoLabelAlign(this.labelRotation))k.align=this.labelAlign;o(c,function(a){var b=(a=d[a])&&a.label;if(b)b.attr(k),l&&b.css(D(l,b.specCss)),delete b.specCss,a.rotation=k.rotation});this.tickRotCorr=b.rotCorr(h.b,
-this.labelRotation||0,this.side!==0)},hasData:function(){return this.hasVisibleSeries||q(this.min)&&q(this.max)&&!!this.tickPositions},getOffset:function(){var a=this,b=a.chart,c=b.renderer,d=a.options,e=a.tickPositions,f=a.ticks,g=a.horiz,h=a.side,i=b.inverted?[1,0,3,2][h]:h,k,j,l=0,m,n=0,r=d.title,s=d.labels,R=0,v=a.opposite,x=b.axisOffset,b=b.clipOffset,w=[-1,1,1,-1][h],u,ba=a.axisParent;k=a.hasData();a.showAxis=j=k||p(d.showEmpty,!0);a.staggerLines=a.horiz&&s.staggerLines;if(!a.axisGroup)a.gridGroup=
-c.g("grid").attr({zIndex:d.gridZIndex||1}).add(ba),a.axisGroup=c.g("axis").attr({zIndex:d.zIndex||2}).add(ba),a.labelGroup=c.g("axis-labels").attr({zIndex:s.zIndex||7}).addClass("highcharts-"+a.coll.toLowerCase()+"-labels").add(ba);if(k||a.isLinked){if(o(e,function(b){f[b]?f[b].addLabel():f[b]=new Va(a,b)}),a.renderUnsquish(),s.reserveSpace!==!1&&(h===0||h===2||{1:"left",3:"right"}[h]===a.labelAlign||a.labelAlign==="center")&&o(e,function(a){R=t(f[a].getLabelSize(),R)}),a.staggerLines)R*=a.staggerLines,
-a.labelOffset=R*(a.opposite?-1:1)}else for(u in f)f[u].destroy(),delete f[u];if(r&&r.text&&r.enabled!==!1){if(!a.axisTitle)a.axisTitle=c.text(r.text,0,0,r.useHTML).attr({zIndex:7,rotation:r.rotation||0,align:r.textAlign||{low:v?"right":"left",middle:"center",high:v?"left":"right"}[r.align]}).addClass("highcharts-"+this.coll.toLowerCase()+"-title").css(r.style).add(a.axisGroup),a.axisTitle.isNew=!0;if(j)l=a.axisTitle.getBBox()[g?"height":"width"],m=r.offset,n=q(m)?0:p(r.margin,g?5:10);a.axisTitle[j?
-"show":"hide"](!0)}a.offset=w*p(d.offset,x[h]);a.tickRotCorr=a.tickRotCorr||{x:0,y:0};c=h===2?a.tickRotCorr.y:0;g=Math.abs(R)+n+(R&&w*(g?p(s.y,a.tickRotCorr.y+8):s.x)-c);a.axisTitleMargin=p(m,g);x[h]=t(x[h],a.axisTitleMargin+l+w*a.offset,g);d=d.offset?0:T(d.lineWidth/2)*2;b[i]=t(b[i],d)},getLinePath:function(a){var b=this.chart,c=this.opposite,d=this.offset,e=this.horiz,f=this.left+(c?this.width:0)+d,d=b.chartHeight-this.bottom-(c?this.height:0)+d;c&&(a*=-1);return b.renderer.crispLine(["M",e?this.left:
-f,e?d:this.top,"L",e?b.chartWidth-this.right:f,e?d:b.chartHeight-this.bottom],a)},getTitlePosition:function(){var a=this.horiz,b=this.left,c=this.top,d=this.len,e=this.options.title,f=a?b:c,g=this.opposite,h=this.offset,i=e.x||0,k=e.y||0,j=C(e.style.fontSize||12),d={low:f+(a?0:d),middle:f+d/2,high:f+(a?d:0)}[e.align],b=(a?c+this.height:b)+(a?1:-1)*(g?-1:1)*this.axisTitleMargin+(this.side===2?j:0);return{x:a?d+i:b+(g?this.width:0)+h+i,y:a?b+k-(g?this.height:0)+h:d+k}},render:function(){var a=this,
-b=a.chart,c=b.renderer,d=a.options,e=a.isLog,f=a.isLinked,g=a.tickPositions,h=a.axisTitle,i=a.ticks,k=a.minorTicks,j=a.alternateBands,l=d.stackLabels,m=d.alternateGridColor,n=a.tickmarkOffset,r=d.lineWidth,s,p=b.hasRendered&&q(a.oldMin)&&!isNaN(a.oldMin),v=a.showAxis,x=c.globalAnimation,w,t;a.labelEdge.length=0;a.overlap=!1;o([i,k,j],function(a){for(var b in a)a[b].isActive=!1});if(a.hasData()||f){a.minorTickInterval&&!a.categories&&o(a.getMinorTickPositions(),function(b){k[b]||(k[b]=new Va(a,b,"minor"));
-p&&k[b].isNew&&k[b].render(null,!0);k[b].render(null,!1,1)});if(g.length&&(o(g,function(b,c){if(!f||b>=a.min&&b<=a.max)i[b]||(i[b]=new Va(a,b)),p&&i[b].isNew&&i[b].render(c,!0,0.1),i[b].render(c)}),n&&(a.min===0||a.single)))i[-1]||(i[-1]=new Va(a,-1,null,!0)),i[-1].render(-1);m&&o(g,function(c,d){t=g[d+1]!==z?g[d+1]+n:a.max-n;if(d%2===0&&c=G.second?0:j*T(i.getMilliseconds()/j));if(k>=G.second)i[Hb](k>=G.minute?0:j*T(i.getSeconds()/j));if(k>=G.minute)i[Ib](k>=G.hour?0:j*T(i[tb]()/j));if(k>=G.hour)i[Jb](k>=G.day?0:j*T(i[ub]()/j));if(k>=G.day)i[wb](k>=G.month?
-1:j*T(i[$a]()/j));k>=G.month&&(i[xb](k>=G.year?0:j*T(i[ab]()/j)),h=i[bb]());k>=G.year&&(h-=h%j,i[yb](h));if(k===G.week)i[wb](i[$a]()-i[vb]()+p(d,1));b=1;if(qb||Za)i=i.getTime(),i=new qa(i+Ya(i));h=i[bb]();for(var d=i.getTime(),l=i[ab](),m=i[$a](),n=!g||!!Za,r=(G.day+(g?Ya(i):i.getTimezoneOffset()*6E4))%G.day;d=0.5)a=A(a),g=this.getLinearTickPositions(a,b,c);else if(a>=0.08)for(var f=T(b),h,i,k,j,l,e=a>0.3?[1,2,4]:a>0.15?[1,2,4,6,8]:[1,2,3,4,5,6,7,8,9];fb&&(!d||j<=c)&&j!==z&&g.push(j),j>c&&(l=!0),j=k}else if(b=na(b),c=na(c),a=e[d?
-"minorTickInterval":"tickInterval"],a=p(a==="auto"?null:a,this._minorAutoInterval,(c-b)*(e.tickPixelInterval/(d?5:1))/((d?f/this.tickPositions.length:f)||1)),a=sb(a,null,rb(a)),g=Ba(this.getLinearTickPositions(a,b,c),Da),!d)this._minorAutoInterval=a/5;if(!d)this.tickInterval=a;return g};var Pb=B.Tooltip=function(){this.init.apply(this,arguments)};Pb.prototype={init:function(a,b){var c=b.borderWidth,d=b.style,e=C(d.padding);this.chart=a;this.options=b;this.crosshairs=[];this.now={x:0,y:0};this.isHidden=
-!0;this.label=a.renderer.label("",0,0,b.shape||"callout",null,null,b.useHTML,null,"tooltip").attr({padding:e,fill:b.backgroundColor,"stroke-width":c,r:b.borderRadius,zIndex:8}).css(d).css({padding:0}).add().attr({y:-9999});ha||this.label.shadow(b.shadow);this.shared=b.shared},destroy:function(){if(this.label)this.label=this.label.destroy();clearTimeout(this.hideTimer);clearTimeout(this.tooltipTimeout)},move:function(a,b,c,d){var e=this,f=e.now,g=e.options.animation!==!1&&!e.isHidden&&(P(a-f.x)>1||
-P(b-f.y)>1),h=e.followPointer||e.len>1;u(f,{x:g?(2*f.x+a)/3:a,y:g?(f.y+b)/2:b,anchorX:h?z:g?(2*f.anchorX+c)/3:c,anchorY:h?z:g?(f.anchorY+d)/2:d});e.label.attr(f);if(g)clearTimeout(this.tooltipTimeout),this.tooltipTimeout=setTimeout(function(){e&&e.move(a,b,c,d)},32)},hide:function(a){var b=this;clearTimeout(this.hideTimer);a=p(a,this.options.hideDelay,500);if(!this.isHidden)this.hideTimer=Pa(function(){b.label[a?"fadeOut":"hide"]();b.isHidden=!0},a)},getAnchor:function(a,b){var c,d=this.chart,e=d.inverted,
-f=d.plotTop,g=d.plotLeft,h=0,i=0,k,j,a=ta(a);c=a[0].tooltipPos;this.followPointer&&b&&(b.chartX===z&&(b=d.pointer.normalize(b)),c=[b.chartX-d.plotLeft,b.chartY-f]);c||(o(a,function(a){k=a.series.yAxis;j=a.series.xAxis;h+=a.plotX+(!e&&j?j.left-g:0);i+=(a.plotLow?(a.plotLow+a.plotHigh)/2:a.plotY)+(!e&&k?k.top-f:0)}),h/=a.length,i/=a.length,c=[e?d.plotWidth-i:h,this.shared&&!e&&a.length>1&&b?b.chartY-f:e?d.plotHeight-h:i]);return Ba(c,A)},getPosition:function(a,b,c){var d=this.chart,e=this.distance,
-f={},g=c.h||0,h,i=["y",d.chartHeight,b,c.plotY+d.plotTop,d.plotTop,d.plotTop+d.plotHeight],k=["x",d.chartWidth,a,c.plotX+d.plotLeft,d.plotLeft,d.plotLeft+d.plotWidth],j=p(c.ttBelow,d.inverted&&!c.negative||!d.inverted&&c.negative),l=function(a,b,c,d,h,i){var k=cb?d:d+g);else return!1},m=function(a,b,c,d){var g;db-e?g=!1:f[a]=db-c/2?b-c-2:d-c/2;return g},n=function(a){var b=
-i;i=k;k=b;h=a},r=function(){l.apply(0,i)!==!1?m.apply(0,k)===!1&&!h&&(n(!0),r()):h?f.x=f.y=0:(n(!0),r())};(d.inverted||this.len>1)&&n();r();return f},defaultFormatter:function(a){var b=this.points||ta(this),c;c=[a.tooltipFooterHeaderFormatter(b[0])];c=c.concat(a.bodyFormatter(b));c.push(a.tooltipFooterHeaderFormatter(b[0],!0));return c.join("")},refresh:function(a,b){var c=this.chart,d=this.label,e=this.options,f,g,h,i={},k,j=[];k=e.formatter||this.defaultFormatter;var i=c.hoverPoints,l,m=this.shared;
-clearTimeout(this.hideTimer);this.followPointer=ta(a)[0].series.tooltipOptions.followPointer;h=this.getAnchor(a,b);f=h[0];g=h[1];m&&(!a.series||!a.series.noSharedTooltip)?(c.hoverPoints=a,i&&o(i,function(a){a.setState()}),o(a,function(a){a.setState("hover");j.push(a.getLabelConfig())}),i={x:a[0].category,y:a[0].y},i.points=j,this.len=j.length,a=a[0]):i=a.getLabelConfig();k=k.call(i,this);i=a.series;this.distance=p(i.tooltipOptions.distance,16);k===!1?this.hide():(this.isHidden&&(Oa(d),d.attr("opacity",
-1).show()),d.attr({text:k}),l=e.borderColor||a.color||i.color||"#606060",d.attr({stroke:l}),this.updatePosition({plotX:f,plotY:g,negative:a.negative,ttBelow:a.ttBelow,h:h[2]||0}),this.isHidden=!1);H(c,"tooltipRefresh",{text:k,x:f+c.plotLeft,y:g+c.plotTop,borderColor:l})},updatePosition:function(a){var b=this.chart,c=this.label,c=(this.options.positioner||this.getPosition).call(this,c.width,c.height,a);this.move(A(c.x),A(c.y||0),a.plotX+b.plotLeft,a.plotY+b.plotTop)},getXDateFormat:function(a,b,c){var d,
-b=b.dateTimeLabelFormats,e=c&&c.closestPointRange,f,g={millisecond:15,second:12,minute:9,hour:6,day:3},h,i="millisecond";if(e){h=Qa("%m-%d %H:%M:%S.%L",a.x);for(f in G){if(e===G.week&&+Qa("%w",a.x)===c.options.startOfWeek&&h.substr(6)==="00:00:00.000"){f="week";break}if(G[f]>e){f=i;break}if(g[f]&&h.substr(g[f])!=="01-01 00:00:00.000".substr(g[f]))break;f!=="week"&&(i=f)}f&&(d=b[f])}else d=b.day;return d||b.year},tooltipFooterHeaderFormatter:function(a,b){var c=b?"footer":"header",d=a.series,e=d.tooltipOptions,
-f=e.xDateFormat,g=d.xAxis,h=g&&g.options.type==="datetime"&&ma(a.key),c=e[c+"Format"];h&&!f&&(f=this.getXDateFormat(a,e,g));h&&f&&(c=c.replace("{point.key}","{point.key:"+f+"}"));return Ka(c,{point:a,series:d})},bodyFormatter:function(a){return Ba(a,function(a){var c=a.series.tooltipOptions;return(c.pointFormatter||a.point.tooltipFormatter).call(a.point,c.pointFormat)})}};var ea;db=y&&y.documentElement.ontouchstart!==z;var Xa=B.Pointer=function(a,b){this.init(a,b)};Xa.prototype={init:function(a,b){var c=
-b.chart,d=c.events,e=ha?"":c.zoomType,c=a.inverted,f;this.options=b;this.chart=a;this.zoomX=f=/x/.test(e);this.zoomY=e=/y/.test(e);this.zoomHor=f&&!c||e&&c;this.zoomVert=e&&!c||f&&c;this.hasZoom=f||e;this.runChartClick=d&&!!d.click;this.pinchDown=[];this.lastValidTouch={};if(B.Tooltip&&b.tooltip.enabled)a.tooltip=new Pb(a,b.tooltip),this.followTouchMove=p(b.tooltip.followTouchMove,!0);this.setDOMEvents()},normalize:function(a,b){var c,d,a=a||E.event;if(!a.target)a.target=a.srcElement;d=a.touches?
-a.touches.length?a.touches.item(0):a.changedTouches[0]:a;if(!b)this.chartPosition=b=Ab(this.chart.container);d.pageX===z?(c=t(a.x,a.clientX-b.left),d=a.y):(c=d.pageX-b.left,d=d.pageY-b.top);return u(a,{chartX:A(c),chartY:A(d)})},getCoordinates:function(a){var b={xAxis:[],yAxis:[]};o(this.chart.axes,function(c){b[c.isXAxis?"xAxis":"yAxis"].push({axis:c,value:c.toValue(a[c.horiz?"chartX":"chartY"])})});return b},runPointActions:function(a){var b=this.chart,c=b.series,d=b.tooltip,e=d?d.shared:!1,f=b.hoverPoint,
-g=b.hoverSeries,h=[Number.MAX_VALUE,Number.MAX_VALUE],i,k,j=[],l=[],m;if(!e&&!g)for(b=0;bh+k&&(d=h+k),ei+j&&(e=i+j),this.hasDragged=Math.sqrt(Math.pow(n-d,2)+Math.pow(r-e,2)),this.hasDragged>10){l=b.isInsidePlot(n-h,r-i);if(b.hasCartesianSeries&&(this.zoomX||this.zoomY)&&l&&!s&&!m)this.selectionMarker=m=b.renderer.rect(h,i,f?1:k,g?1:j,0).attr({fill:c.selectionMarkerFill||"rgba(69,114,167,0.25)",zIndex:7}).add();m&&f&&(d-=n,m.attr({width:P(d),x:(d>0?0:d)+n}));
-m&&g&&(d=e-r,m.attr({height:P(d),y:(d>0?0:d)+r}));l&&!m&&c.panning&&b.pan(a,c.panning)}},drop:function(a){var b=this,c=this.chart,d=this.hasPinched;if(this.selectionMarker){var e={originalEvent:a,xAxis:[],yAxis:[]},f=this.selectionMarker,g=f.attr?f.attr("x"):f.x,h=f.attr?f.attr("y"):f.y,i=f.attr?f.attr("width"):f.width,k=f.attr?f.attr("height"):f.height,j;if(this.hasDragged||d)o(c.axes,function(c){if(c.zoomEnabled&&q(c.min)&&(d||b[{xAxis:"zoomX",yAxis:"zoomY"}[c.coll]])){var f=c.horiz,n=a.type===
-"touchend"?c.minPixelPadding:0,r=c.toValue((f?g:h)+n),f=c.toValue((f?g+i:h+k)-n);e[c.coll].push({axis:c,min:F(r,f),max:t(r,f)});j=!0}}),j&&H(c,"selection",e,function(a){c.zoom(u(a,d?{animation:!1}:null))});this.selectionMarker=this.selectionMarker.destroy();d&&this.scaleGroups()}if(c)L(c.container,{cursor:c._cursor}),c.cancelClick=this.hasDragged>10,c.mouseIsDown=this.hasDragged=this.hasPinched=!1,this.pinchDown=[]},onContainerMouseDown:function(a){a=this.normalize(a);a.preventDefault&&a.preventDefault();
-this.dragStart(a)},onDocumentMouseUp:function(a){S[ea]&&S[ea].pointer.drop(a)},onDocumentMouseMove:function(a){var b=this.chart,c=this.chartPosition,a=this.normalize(a,c);c&&!this.inClass(a.target,"highcharts-tracker")&&!b.isInsidePlot(a.chartX-b.plotLeft,a.chartY-b.plotTop)&&this.reset()},onContainerMouseLeave:function(a){var b=S[ea];if(b&&(a.relatedTarget||a.toElement))b.pointer.reset(),b.pointer.chartPosition=null},onContainerMouseMove:function(a){var b=this.chart;if(!q(ea)||!S[ea]||!S[ea].mouseIsDown)ea=
-b.index;a=this.normalize(a);a.returnValue=!1;b.mouseIsDown==="mousedown"&&this.drag(a);(this.inClass(a.target,"highcharts-tracker")||b.isInsidePlot(a.chartX-b.plotLeft,a.chartY-b.plotTop))&&!b.openMenu&&this.runPointActions(a)},inClass:function(a,b){for(var c;a;){if(c=K(a,"class")){if(c.indexOf(b)!==-1)return!0;if(c.indexOf("highcharts-container")!==-1)return!1}a=a.parentNode}},onTrackerMouseOut:function(a){var b=this.chart.hoverSeries,a=a.relatedTarget||a.toElement;if(b&&a&&!b.options.stickyTracking&&
-!this.inClass(a,"highcharts-tooltip")&&!this.inClass(a,"highcharts-series-"+b.index))b.onMouseOut()},onContainerClick:function(a){var b=this.chart,c=b.hoverPoint,d=b.plotLeft,e=b.plotTop,a=this.normalize(a);b.cancelClick||(c&&this.inClass(a.target,"highcharts-tracker")?(H(c.series,"click",u(a,{point:c})),b.hoverPoint&&c.firePointEvent("click",a)):(u(a,this.getCoordinates(a)),b.isInsidePlot(a.chartX-d,a.chartY-e)&&H(b,"click",a)))},setDOMEvents:function(){var a=this,b=a.chart.container;b.onmousedown=
-function(b){a.onContainerMouseDown(b)};b.onmousemove=function(b){a.onContainerMouseMove(b)};b.onclick=function(b){a.onContainerClick(b)};M(b,"mouseleave",a.onContainerMouseLeave);eb===1&&M(y,"mouseup",a.onDocumentMouseUp);if(db)b.ontouchstart=function(b){a.onContainerTouchStart(b)},b.ontouchmove=function(b){a.onContainerTouchMove(b)},eb===1&&M(y,"touchend",a.onDocumentTouchEnd)},destroy:function(){var a;V(this.chart.container,"mouseleave",this.onContainerMouseLeave);eb||(V(y,"mouseup",this.onDocumentMouseUp),
-V(y,"touchend",this.onDocumentTouchEnd));clearInterval(this.tooltipTimeout);for(a in this)this[a]=null}};u(B.Pointer.prototype,{pinchTranslate:function(a,b,c,d,e,f){(this.zoomHor||this.pinchHor)&&this.pinchTranslateDirection(!0,a,b,c,d,e,f);(this.zoomVert||this.pinchVert)&&this.pinchTranslateDirection(!1,a,b,c,d,e,f)},pinchTranslateDirection:function(a,b,c,d,e,f,g,h){var i=this.chart,k=a?"x":"y",j=a?"X":"Y",l="chart"+j,m=a?"width":"height",n=i["plot"+(a?"Left":"Top")],r,s,p=h||1,o=i.inverted,x=i.bounds[a?
-"h":"v"],w=b.length===1,q=b[0][l],t=c[0][l],u=!w&&b[1][l],A=!w&&c[1][l],B,c=function(){!w&&P(q-u)>20&&(p=h||P(t-A)/P(q-u));s=(n-t)/p+q;r=i["plot"+(a?"Width":"Height")]/p};c();b=s;bx.max&&(b=x.max-r,B=!0);B?(t-=0.8*(t-g[k][0]),w||(A-=0.8*(A-g[k][1])),c()):g[k]=[t,A];o||(f[k]=s-n,f[m]=r);f=o?1/p:p;e[m]=r;e[k]=b;d[o?a?"scaleY":"scaleX":"scale"+j]=p;d["translate"+j]=f*n+(t-f*q)},pinch:function(a){var b=this,c=b.chart,d=b.pinchDown,e=a.touches,f=e.length,g=b.lastValidTouch,h=
-b.hasZoom,i=b.selectionMarker,k={},j=f===1&&(b.inClass(a.target,"highcharts-tracker")&&c.runTrackerClick||b.runChartClick),l={};if(f>1)b.initiated=!0;h&&b.initiated&&!j&&a.preventDefault();Ba(e,function(a){return b.normalize(a)});if(a.type==="touchstart")o(e,function(a,b){d[b]={chartX:a.chartX,chartY:a.chartY}}),g.x=[d[0].chartX,d[1]&&d[1].chartX],g.y=[d[0].chartY,d[1]&&d[1].chartY],o(c.axes,function(a){if(a.zoomEnabled){var b=c.bounds[a.horiz?"h":"v"],d=a.minPixelPadding,e=a.toPixels(p(a.options.min,
-a.dataMin)),f=a.toPixels(p(a.options.max,a.dataMax)),g=F(e,f),e=t(e,f);b.min=F(a.pos,g-d);b.max=t(a.pos+a.len,e+d)}}),b.res=!0;else if(d.length){if(!i)b.selectionMarker=i=u({destroy:Aa,touch:!0},c.plotBox);b.pinchTranslate(d,e,k,i,l,g);b.hasPinched=h;b.scaleGroups(k,l);if(!h&&b.followTouchMove&&f===1)this.runPointActions(b.normalize(a));else if(b.res)b.res=!1,this.reset(!1,0)}},touch:function(a,b){var c=this.chart;ea=c.index;a.touches.length===1?(a=this.normalize(a),c.isInsidePlot(a.chartX-c.plotLeft,
-a.chartY-c.plotTop)&&!c.openMenu?(b&&this.runPointActions(a),this.pinch(a)):b&&this.reset()):a.touches.length===2&&this.pinch(a)},onContainerTouchStart:function(a){this.touch(a,!0)},onContainerTouchMove:function(a){this.touch(a)},onDocumentTouchEnd:function(a){S[ea]&&S[ea].pointer.drop(a)}});if(E.PointerEvent||E.MSPointerEvent){var va={},Db=!!E.PointerEvent,Sb=function(){var a,b=[];b.item=function(a){return this[a]};for(a in va)va.hasOwnProperty(a)&&b.push({pageX:va[a].pageX,pageY:va[a].pageY,target:va[a].target});
-return b},Eb=function(a,b,c,d){if((a.pointerType==="touch"||a.pointerType===a.MSPOINTER_TYPE_TOUCH)&&S[ea])d(a),d=S[ea].pointer,d[b]({type:c,target:a.currentTarget,preventDefault:Aa,touches:Sb()})};u(Xa.prototype,{onContainerPointerDown:function(a){Eb(a,"onContainerTouchStart","touchstart",function(a){va[a.pointerId]={pageX:a.pageX,pageY:a.pageY,target:a.currentTarget}})},onContainerPointerMove:function(a){Eb(a,"onContainerTouchMove","touchmove",function(a){va[a.pointerId]={pageX:a.pageX,pageY:a.pageY};
-if(!va[a.pointerId].target)va[a.pointerId].target=a.currentTarget})},onDocumentPointerUp:function(a){Eb(a,"onDocumentTouchEnd","touchend",function(a){delete va[a.pointerId]})},batchMSEvents:function(a){a(this.chart.container,Db?"pointerdown":"MSPointerDown",this.onContainerPointerDown);a(this.chart.container,Db?"pointermove":"MSPointerMove",this.onContainerPointerMove);a(y,Db?"pointerup":"MSPointerUp",this.onDocumentPointerUp)}});fb(Xa.prototype,"init",function(a,b,c){a.call(this,b,c);this.hasZoom&&
-L(b.container,{"-ms-touch-action":"none","touch-action":"none"})});fb(Xa.prototype,"setDOMEvents",function(a){a.apply(this);(this.hasZoom||this.followTouchMove)&&this.batchMSEvents(M)});fb(Xa.prototype,"destroy",function(a){this.batchMSEvents(V);a.call(this)})}var ob=B.Legend=function(a,b){this.init(a,b)};ob.prototype={init:function(a,b){var c=this,d=b.itemStyle,e=b.itemMarginTop||0;this.options=b;if(b.enabled)c.itemStyle=d,c.itemHiddenStyle=D(d,b.itemHiddenStyle),c.itemMarginTop=e,c.padding=d=p(b.padding,
-8),c.initialItemX=d,c.initialItemY=d-5,c.maxItemWidth=0,c.chart=a,c.itemHeight=0,c.symbolWidth=p(b.symbolWidth,16),c.pages=[],c.render(),M(c.chart,"endResize",function(){c.positionCheckboxes()})},colorizeItem:function(a,b){var c=this.options,d=a.legendItem,e=a.legendLine,f=a.legendSymbol,g=this.itemHiddenStyle.color,c=b?c.itemStyle.color:g,h=b?a.legendColor||a.color||"#CCC":g,g=a.options&&a.options.marker,i={fill:h},k;d&&d.css({fill:c,color:c});e&&e.attr({stroke:h});if(f){if(g&&f.isMarker)for(k in i.stroke=
-h,g=a.convertAttribs(g),g)d=g[k],d!==z&&(i[k]=d);f.attr(i)}},positionItem:function(a){var b=this.options,c=b.symbolPadding,b=!b.rtl,d=a._legendItemPos,e=d[0],d=d[1],f=a.checkbox;(a=a.legendGroup)&&a.element&&a.translate(b?e:this.legendWidth-e-2*c-4,d);if(f)f.x=e,f.y=d},destroyItem:function(a){var b=a.checkbox;o(["legendItem","legendLine","legendSymbol","legendGroup"],function(b){a[b]&&(a[b]=a[b].destroy())});b&&Ta(a.checkbox)},destroy:function(){var a=this.group,b=this.box;if(b)this.box=b.destroy();
-if(a)this.group=a.destroy()},positionCheckboxes:function(a){var b=this.group.alignAttr,c,d=this.clipHeight||this.legendHeight,e=this.titleHeight;if(b)c=b.translateY,o(this.allItems,function(f){var g=f.checkbox,h;g&&(h=c+e+g.y+(a||0)+3,L(g,{left:b.translateX+f.checkboxOffset+g.x-20+"px",top:h+"px",display:h>c-6&&h(m||b.chartWidth-2*k-s-d.x))this.itemX=s,this.itemY+=r+this.lastLineHeight+n,this.lastLineHeight=0;this.maxItemWidth=t(this.maxItemWidth,
-f);this.lastItemY=r+this.itemY+n;this.lastLineHeight=t(g,this.lastLineHeight);a._legendItemPos=[this.itemX,this.itemY];e?this.itemX+=f:(this.itemY+=r+g+n,this.lastLineHeight=g);this.offsetWidth=m||t((e?this.itemX-s-j:f)+k,this.offsetWidth)},getAllItems:function(){var a=[];o(this.chart.series,function(b){var c=b.options;if(p(c.showInLegend,!q(c.linkedTo)?z:!1,!0))a=a.concat(b.legendItems||(c.legendType==="point"?b.data:b))});return a},adjustMargins:function(a,b){var c=this.chart,d=this.options,e=d.align.charAt(0)+
-d.verticalAlign.charAt(0)+d.layout.charAt(0);this.display&&!d.floating&&o([/(lth|ct|rth)/,/(rtv|rm|rbv)/,/(rbh|cb|lbh)/,/(lbv|lm|ltv)/],function(f,g){f.test(e)&&!q(a[g])&&(c[nb[g]]=t(c[nb[g]],c.legend[(g+1)%2?"legendHeight":"legendWidth"]+[1,-1,-1,1][g]*d[g%2?"x":"y"]+p(d.margin,12)+b[g]))})},render:function(){var a=this,b=a.chart,c=b.renderer,d=a.group,e,f,g,h,i=a.box,k=a.options,j=a.padding,l=k.borderWidth,m=k.backgroundColor;a.itemX=a.initialItemX;a.itemY=a.initialItemY;a.offsetWidth=0;a.lastItemY=
-0;if(!d)a.group=d=c.g("legend").attr({zIndex:7}).add(),a.contentGroup=c.g().attr({zIndex:1}).add(d),a.scrollGroup=c.g().add(a.contentGroup);a.renderTitle();e=a.getAllItems();ib(e,function(a,b){return(a.options&&a.options.legendIndex||0)-(b.options&&b.options.legendIndex||0)});k.reversed&&e.reverse();a.allItems=e;a.display=f=!!e.length;a.lastLineHeight=0;o(e,function(b){a.renderItem(b)});g=(k.width||a.offsetWidth)+j;h=a.lastItemY+a.lastLineHeight+a.titleHeight;h=a.handleOverflow(h);h+=j;if(l||m){if(i){if(g>
-0&&h>0)i[i.isNew?"attr":"animate"](i.crisp({width:g,height:h})),i.isNew=!1}else a.box=i=c.rect(0,0,g,h,k.borderRadius,l||0).attr({stroke:k.borderColor,"stroke-width":l||0,fill:m||"none"}).add(d).shadow(k.shadow),i.isNew=!0;i[f?"show":"hide"]()}a.legendWidth=g;a.legendHeight=h;o(e,function(b){a.positionItem(b)});f&&d.align(u({width:g,height:h},k),!0,"spacingBox");b.isResizing||this.positionCheckboxes()},handleOverflow:function(a){var b=this,c=this.chart,d=c.renderer,e=this.options,f=e.y,f=c.spacingBox.height+
-(e.verticalAlign==="top"?-f:f)-this.padding,g=e.maxHeight,h,i=this.clipRect,k=e.navigation,j=p(k.animation,!0),l=k.arrowSize||12,m=this.nav,n=this.pages,r=this.padding,s,R=this.allItems,v=function(a){i.attr({height:a});if(b.contentGroup.div)b.contentGroup.div.style.clip="rect("+r+"px,9999px,"+(r+a)+"px,0)"};e.layout==="horizontal"&&(f/=2);g&&(f=F(f,g));n.length=0;if(a>f){this.clipHeight=h=t(f-20-this.titleHeight-r,0);this.currentPage=p(this.currentPage,1);this.fullHeight=a;o(R,function(a,b){var c=
-a._legendItemPos[1],d=A(a.legendItem.getBBox().height),e=n.length;if(!e||c-n[e-1]>h&&(s||c)!==n[e-1])n.push(s||c),e++;b===R.length-1&&c+d-n[e-1]>h&&n.push(c);c!==s&&(s=c)});if(!i)i=b.clipRect=d.clipRect(0,r,9999,0),b.contentGroup.clip(i);v(h);if(!m)this.nav=m=d.g().attr({zIndex:1}).add(this.group),this.up=d.symbol("triangle",0,0,l,l).on("click",function(){b.scroll(-1,j)}).add(m),this.pager=d.text("",15,10).css(k.style).add(m),this.down=d.symbol("triangle-down",0,0,l,l).on("click",function(){b.scroll(1,
-j)}).add(m);b.scroll(0);a=f}else if(m)v(c.chartHeight),m.hide(),this.scrollGroup.attr({translateY:1}),this.clipHeight=0;return a},scroll:function(a,b){var c=this.pages,d=c.length,e=this.currentPage+a,f=this.clipHeight,g=this.options.navigation,h=g.activeColor,g=g.inactiveColor,i=this.pager,k=this.padding;e>d&&(e=d);if(e>0)b!==z&&Ua(b,this.chart),this.nav.attr({translateX:k,translateY:f+this.padding+7+this.titleHeight,visibility:"visible"}),this.up.attr({fill:e===1?g:h}).css({cursor:e===1?"default":
-"pointer"}),i.attr({text:e+"/"+d}),this.down.attr({x:18+this.pager.getBBox().width,fill:e===d?g:h}).css({cursor:e===d?"default":"pointer"}),c=-c[e-1]+this.initialItemY,this.scrollGroup.animate({translateY:c}),this.currentPage=e,this.positionCheckboxes(c)}};J=B.LegendSymbolMixin={drawRectangle:function(a,b){var c=a.options.symbolHeight||a.fontMetrics.f;b.legendSymbol=this.chart.renderer.rect(0,a.baseline-c+1,a.symbolWidth,c,a.options.symbolRadius||0).attr({zIndex:3}).add(b.legendGroup)},drawLineMarker:function(a){var b=
-this.options,c=b.marker,d=a.symbolWidth,e=this.chart.renderer,f=this.legendGroup,a=a.baseline-A(a.fontMetrics.b*0.3),g;if(b.lineWidth){g={"stroke-width":b.lineWidth};if(b.dashStyle)g.dashstyle=b.dashStyle;this.legendLine=e.path(["M",0,a,"L",d,a]).attr(g).add(f)}if(c&&c.enabled!==!1)b=c.radius,this.legendSymbol=c=e.symbol(this.symbol,d/2-b,a-b,2*b,2*b,c).add(f),c.isMarker=!0}};(/Trident\/7\.0/.test(za)||Ma)&&fb(ob.prototype,"positionItem",function(a,b){var c=this,d=function(){b._legendItemPos&&a.call(c,
-b)};d();setTimeout(d)});var hb=B.Chart=function(){this.getArgs.apply(this,arguments)};B.chart=function(a,b,c){return new hb(a,b,c)};hb.prototype={callbacks:[],getArgs:function(){var a=[].slice.call(arguments);if(xa(a[0])||a[0].nodeName)this.renderTo=a.shift();this.init(a[0],a[1])},init:function(a,b){var c,d=a.series;a.series=null;c=D(N,a);c.series=a.series=d;this.userOptions=a;d=c.chart;this.margin=this.splashArray("margin",d);this.spacing=this.splashArray("spacing",d);var e=d.events;this.bounds=
-{h:{},v:{}};this.callback=b;this.isResizing=0;this.options=c;this.axes=[];this.series=[];this.hasCartesianSeries=d.showAxes;var f=this,g;f.index=S.length;S.push(f);eb++;d.reflow!==!1&&M(f,"load",function(){f.initReflow()});if(e)for(g in e)M(f,g,e[g]);f.xAxis=[];f.yAxis=[];f.animation=ha?!1:p(d.animation,!0);f.pointCount=f.colorCounter=f.symbolCounter=0;f.firstRender()},initSeries:function(a){var b=this.options.chart;(b=I[a.type||b.type||b.defaultSeriesType])||X(17,!0);b=new b;b.init(this,a);return b},
-isInsidePlot:function(a,b,c){var d=c?b:a,a=c?a:b;return d>=0&&d<=this.plotWidth&&a>=0&&a<=this.plotHeight},redraw:function(a){var b=this.axes,c=this.series,d=this.pointer,e=this.legend,f=this.isDirtyLegend,g,h,i=this.hasCartesianSeries,k=this.isDirtyBox,j=c.length,l=j,m=this.renderer,n=m.isHidden(),r=[];Ua(a,this);n&&this.cloneRenderTo();for(this.layOutTitles();l--;)if(a=c[l],a.options.stacking&&(g=!0,a.isDirty)){h=!0;break}if(h)for(l=j;l--;)if(a=c[l],a.options.stacking)a.isDirty=!0;o(c,function(a){a.isDirty&&
-a.options.legendType==="point"&&(a.updateTotals&&a.updateTotals(),f=!0)});if(f&&e.options.enabled)e.render(),this.isDirtyLegend=!1;g&&this.getStacks();if(i&&!this.isResizing)this.maxTicks=null,o(b,function(a){a.setScale()});this.getMargins();i&&(o(b,function(a){a.isDirty&&(k=!0)}),o(b,function(a){var b=a.min+","+a.max;if(a.extKey!==b)a.extKey=b,r.push(function(){H(a,"afterSetExtremes",u(a.eventArgs,a.getExtremes()));delete a.eventArgs});(k||g)&&a.redraw()}));k&&this.drawChartBox();o(c,function(a){a.isDirty&&
-a.visible&&(!a.isCartesian||a.xAxis)&&a.redraw()});d&&d.reset(!0);m.draw();H(this,"redraw");n&&this.cloneRenderTo(!0);o(r,function(a){a.call()})},get:function(a){var b=this.axes,c=this.series,d,e;for(d=0;d19?this.containerHeight:600))},cloneRenderTo:function(a){var b=this.renderToClone,c=this.container;a?b&&(this.renderTo.appendChild(c),Ta(b),delete this.renderToClone):(c&&c.parentNode===this.renderTo&&this.renderTo.removeChild(c),this.renderToClone=b=this.renderTo.cloneNode(0),L(b,{position:"absolute",top:"-9999px",display:"block"}),b.style.setProperty&&b.style.setProperty("display","block",
-"important"),y.body.appendChild(b),c&&b.appendChild(c))},getContainer:function(){var a,b=this.options,c=b.chart,d,e;a=this.renderTo;var f="highcharts-"+zb++;if(!a)this.renderTo=a=c.renderTo;if(xa(a))this.renderTo=a=y.getElementById(a);a||X(13,!0);d=C(K(a,"data-highcharts-chart"));!isNaN(d)&&S[d]&&S[d].hasRendered&&S[d].destroy();K(a,"data-highcharts-chart",this.index);a.innerHTML="";!c.skipClone&&!a.offsetWidth&&this.cloneRenderTo();this.getChartSize();d=this.chartWidth;e=this.chartHeight;this.container=
-a=Z(La,{className:"highcharts-container"+(c.className?" "+c.className:""),id:f},u({position:"relative",overflow:"hidden",width:d+"px",height:e+"px",textAlign:"left",lineHeight:"normal",zIndex:0,"-webkit-tap-highlight-color":"rgba(0,0,0,0)"},c.style),this.renderToClone||a);this._cursor=a.style.cursor;this.renderer=new (B[c.renderer]||cb)(a,d,e,c.style,c.forExport,b.exporting&&b.exporting.allowHTML);ha&&this.renderer.create(this,a,d,e);this.renderer.chartIndex=this.index},getMargins:function(a){var b=
-this.spacing,c=this.margin,d=this.titleOffset;this.resetMargins();if(d&&!q(c[0]))this.plotTop=t(this.plotTop,d+this.options.title.margin+b[0]);this.legend.adjustMargins(c,b);this.extraBottomMargin&&(this.marginBottom+=this.extraBottomMargin);this.extraTopMargin&&(this.plotTop+=this.extraTopMargin);a||this.getAxisMargins()},getAxisMargins:function(){var a=this,b=a.axisOffset=[0,0,0,0],c=a.margin;a.hasCartesianSeries&&o(a.axes,function(a){a.visible&&a.getOffset()});o(nb,function(d,e){q(c[e])||(a[d]+=
-b[e])});a.setChartSize()},reflow:function(a){var b=this,c=b.options.chart,d=b.renderTo,e=c.width||ja(d,"width"),f=c.height||ja(d,"height"),c=a?a.target:E;if(!b.hasUserSize&&!b.isPrinting&&e&&f&&(c===E||c===y)){if(e!==b.containerWidth||f!==b.containerHeight)clearTimeout(b.reflowTimeout),b.reflowTimeout=Pa(function(){if(b.container)b.setSize(e,f,!1),b.hasUserSize=null},a?100:0);b.containerWidth=e;b.containerHeight=f}},initReflow:function(){var a=this,b=function(b){a.reflow(b)};M(E,"resize",b);M(a,"destroy",
-function(){V(E,"resize",b)})},setSize:function(a,b,c){var d=this,e,f,g=d.renderer;d.isResizing+=1;Ua(c,d);d.oldChartHeight=d.chartHeight;d.oldChartWidth=d.chartWidth;if(q(a))d.chartWidth=e=t(0,A(a)),d.hasUserSize=!!e;if(q(b))d.chartHeight=f=t(0,A(b));a=g.globalAnimation;(a?Wa:L)(d.container,{width:e+"px",height:f+"px"},a);d.setChartSize(!0);g.setSize(e,f,c);d.maxTicks=null;o(d.axes,function(a){a.isDirty=!0;a.setScale()});o(d.series,function(a){a.isDirty=!0});d.isDirtyLegend=!0;d.isDirtyBox=!0;d.layOutTitles();
-d.getMargins();d.redraw(c);d.oldChartHeight=null;H(d,"resize");a=g.globalAnimation;Pa(function(){d&&H(d,"endResize",null,function(){d.isResizing-=1})},a===!1?0:a&&a.duration||500)},setChartSize:function(a){var b=this.inverted,c=this.renderer,d=this.chartWidth,e=this.chartHeight,f=this.options.chart,g=this.spacing,h=this.clipOffset,i,k,j,l;this.plotLeft=i=A(this.plotLeft);this.plotTop=k=A(this.plotTop);this.plotWidth=j=t(0,A(d-i-this.marginRight));this.plotHeight=l=t(0,A(e-k-this.marginBottom));this.plotSizeX=
-b?l:j;this.plotSizeY=b?j:l;this.plotBorderWidth=f.plotBorderWidth||0;this.spacingBox=c.spacingBox={x:g[3],y:g[0],width:d-g[3]-g[1],height:e-g[0]-g[2]};this.plotBox=c.plotBox={x:i,y:k,width:j,height:l};d=2*T(this.plotBorderWidth/2);b=ua(t(d,h[3])/2);c=ua(t(d,h[0])/2);this.clipBox={x:b,y:c,width:T(this.plotSizeX-t(d,h[1])/2-b),height:t(0,T(this.plotSizeY-t(d,h[2])/2-c))};a||o(this.axes,function(a){a.setAxisSize();a.setAxisTranslation()})},resetMargins:function(){var a=this;o(nb,function(b,c){a[b]=p(a.margin[c],
-a.spacing[c])});a.axisOffset=[0,0,0,0];a.clipOffset=[0,0,0,0]},drawChartBox:function(){var a=this.options.chart,b=this.renderer,c=this.chartWidth,d=this.chartHeight,e=this.chartBackground,f=this.plotBackground,g=this.plotBorder,h=this.plotBGImage,i=a.borderWidth||0,k=a.backgroundColor,j=a.plotBackgroundColor,l=a.plotBackgroundImage,m=a.plotBorderWidth||0,n,r=this.plotLeft,p=this.plotTop,o=this.plotWidth,v=this.plotHeight,x=this.plotBox,w=this.clipRect,t=this.clipBox;n=i+(a.shadow?8:0);if(i||k)if(e)e.animate(e.crisp({width:c-
-n,height:d-n}));else{e={fill:k||"none"};if(i)e.stroke=a.borderColor,e["stroke-width"]=i;this.chartBackground=b.rect(n/2,n/2,c-n,d-n,a.borderRadius,i).attr(e).addClass("highcharts-background").add().shadow(a.shadow)}if(j)f?f.animate(x):this.plotBackground=b.rect(r,p,o,v,0).attr({fill:j}).add().shadow(a.plotShadow);if(l)h?h.animate(x):this.plotBGImage=b.image(l,r,p,o,v).add();w?w.animate({width:t.width,height:t.height}):this.clipRect=b.clipRect(t);if(m)g?(g.strokeWidth=-m,g.animate(g.crisp({x:r,y:p,
-width:o,height:v}))):this.plotBorder=b.rect(r,p,o,v,0,-m).attr({stroke:a.plotBorderColor,"stroke-width":m,fill:"none",zIndex:1}).add();this.isDirtyBox=!1},propFromSeries:function(){var a=this,b=a.options.chart,c,d=a.options.series,e,f;o(["inverted","angular","polar"],function(g){c=I[b.type||b.defaultSeriesType];f=a[g]||b[g]||c&&c.prototype[g];for(e=d&&d.length;!f&&e--;)(c=I[d[e].type])&&c.prototype[g]&&(f=!0);a[g]=f})},linkSeries:function(){var a=this,b=a.series;o(b,function(a){a.linkedSeries.length=
-0});o(b,function(b){var d=b.options.linkedTo;if(xa(d)&&(d=d===":previous"?a.series[b.index-1]:a.get(d)))d.linkedSeries.push(b),b.linkedParent=d,b.visible=p(b.options.visible,d.options.visible,b.visible)})},renderSeries:function(){o(this.series,function(a){a.translate();a.render()})},renderLabels:function(){var a=this,b=a.options.labels;b.items&&o(b.items,function(c){var d=u(b.style,c.style),e=C(d.left)+a.plotLeft,f=C(d.top)+a.plotTop+12;delete d.left;delete d.top;a.renderer.text(c.html,e,f).attr({zIndex:2}).css(d).add()})},
-render:function(){var a=this.axes,b=this.renderer,c=this.options,d,e,f,g;this.setTitle();this.legend=new ob(this,c.legend);this.getStacks&&this.getStacks();this.getMargins(!0);this.setChartSize();d=this.plotWidth;e=this.plotHeight-=21;o(a,function(a){a.setScale()});this.getAxisMargins();f=d/this.plotWidth>1.1;g=e/this.plotHeight>1.05;if(f||g)this.maxTicks=null,o(a,function(a){(a.horiz&&f||!a.horiz&&g)&&a.setTickInterval(!0)}),this.getMargins();this.drawChartBox();this.hasCartesianSeries&&o(a,function(a){a.visible&&
-a.render()});if(!this.seriesGroup)this.seriesGroup=b.g("series-group").attr({zIndex:3}).add();this.renderSeries();this.renderLabels();this.showCredits(c.credits);this.hasRendered=!0},showCredits:function(a){if(a.enabled&&!this.credits)this.credits=this.renderer.text(a.text,0,0).on("click",function(){if(a.href)E.location.href=a.href}).attr({align:a.position.align,zIndex:8}).css(a.style).add().align(a.position)},destroy:function(){var a=this,b=a.axes,c=a.series,d=a.container,e,f=d&&d.parentNode;H(a,
-"destroy");S[a.index]=z;eb--;a.renderTo.removeAttribute("data-highcharts-chart");V(a);for(e=b.length;e--;)b[e]=b[e].destroy();for(e=c.length;e--;)c[e]=c[e].destroy();o("title,subtitle,chartBackground,plotBackground,plotBGImage,plotBorder,seriesGroup,clipRect,credits,pointer,scroller,rangeSelector,legend,resetZoomButton,tooltip,renderer".split(","),function(b){var c=a[b];c&&c.destroy&&(a[b]=c.destroy())});if(d)d.innerHTML="",V(d),f&&Ta(d);for(e in a)delete a[e]},isReadyToRender:function(){var a=this;
-return!ca&&E==E.top&&y.readyState!=="complete"||ha&&!E.canvg?(ha?Ob.push(function(){a.firstRender()},a.options.global.canvasToolsURL):y.attachEvent("onreadystatechange",function(){y.detachEvent("onreadystatechange",a.firstRender);y.readyState==="complete"&&a.firstRender()}),!1):!0},firstRender:function(){var a=this,b=a.options;if(a.isReadyToRender()){a.getContainer();H(a,"init");a.resetMargins();a.setChartSize();a.propFromSeries();a.getAxes();o(b.series||[],function(b){a.initSeries(b)});a.linkSeries();
-H(a,"beforeRender");if(B.Pointer)a.pointer=new Xa(a,b);a.render();a.renderer.draw();if(!a.renderer.imgCount)a.onload();a.cloneRenderTo(!0)}},onload:function(){var a=this;o([this.callback].concat(this.callbacks),function(b){b&&a.index!==void 0&&b.apply(a,[a])});a.renderer.imgCount||H(a,"load")},splashArray:function(a,b){var c=b[a],c=Y(c)?c:[c,c,c,c];return[p(b[a+"Top"],c[0]),p(b[a+"Right"],c[1]),p(b[a+"Bottom"],c[2]),p(b[a+"Left"],c[3])]}};var Cb=B.CenteredSeriesMixin={getCenter:function(){var a=this.options,
-b=this.chart,c=2*(a.slicedOffset||0),d=b.plotWidth-2*c,b=b.plotHeight-2*c,e=a.center,e=[p(e[0],"50%"),p(e[1],"50%"),a.size||"100%",a.innerSize||0],f=F(d,b),g,h;for(g=0;g<4;++g)h=e[g],a=g<2||g===2&&/%$/.test(h),e[g]=(/%$/.test(h)?[d,b,f,e[2]][g]*parseFloat(h)/100:parseFloat(h))+(a?c:0);e[3]>e[2]&&(e[3]=e[2]);return e}},Ha=function(){};Ha.prototype={init:function(a,b,c){this.series=a;this.color=a.color;this.applyOptions(b,c);this.pointAttr={};if(a.options.colorByPoint&&(b=a.options.colors||a.chart.options.colors,
-this.color=this.color||b[a.colorCounter++],a.colorCounter===b.length))a.colorCounter=0;a.chart.pointCount++;return this},applyOptions:function(a,b){var c=this.series,d=c.options.pointValKey||c.pointValKey,a=Ha.prototype.optionsToObject.call(this,a);u(this,a);this.options=this.options?u(this.options,a):a;if(d)this.y=this[d];this.isNull=this.y===null;if(typeof this.x!=="number"&&c)this.x=b===void 0?c.autoIncrement():b;return this},optionsToObject:function(a){var b={},c=this.series,d=c.options.keys,
-e=d||c.pointArrayMap||["y"],f=e.length,g=0,h=0;if(typeof a==="number"||a===null)b[e[0]]=a;else if(Ia(a)){if(!d&&a.length>f){c=typeof a[0];if(c==="string")b.name=a[0];else if(c==="number")b.x=a[0];g++}for(;hn){for(c=0;j===null&&ci||this.forceCrop))if(b[d-1]p)b=[],c=[];else if(b[0]p)e=this.cropData(this.xData,this.yData,n,p),b=e.xData,c=e.yData,e=e.start,f=!0;for(i=b.length||1;--i;)d=m?k(b[i])-k(b[i-1]):b[i]-b[i-1],d>0&&(g===z||d=c){f=t(0,i-h);break}for(c=i;cd){g=c+h;break}return{xData:a.slice(f,g),yData:b.slice(f,g),start:f,end:g}},generatePoints:function(){var a=this.options.data,b=this.data,c,d=this.processedXData,e=this.processedYData,f=this.pointClass,g=d.length,h=this.cropStart||0,i,k=this.hasGroupedData,j,l=[],m;if(!b&&!k)b=[],b.length=a.length,b=this.data=b;for(m=0;m0),k=this.getExtremesFromAll||this.options.getExtremesFromAll||this.cropped||
-(c[l+1]||k)>=g&&(c[l-1]||k)<=h,i&&k)if(i=j.length)for(;i--;)j[i]!==null&&(e[f++]=j[i]);else e[f++]=j;this.dataMin=Ra(e);this.dataMax=Ea(e)},translate:function(){this.processedXData||this.processData();this.generatePoints();for(var a=this.options,b=a.stacking,c=this.xAxis,d=c.categories,e=this.yAxis,f=this.points,g=f.length,h=!!this.modifyValue,i=a.pointPlacement,k=i==="between"||ma(i),j=a.threshold,l=a.startFromThreshold?j:0,m,n,r,o,R=Number.MAX_VALUE,a=0;a=0&&n<=e.len&&m>=0&&m<=c.len;v.clientX=k?c.translate(x,0,0,0,1):m;v.negative=v.y<(j||0);v.category=d&&d[v.x]!==z?d[v.x]:v.x;a&&(R=F(R,P(m-r)));r=m}this.closestPointRangePx=R},getValidPoints:function(a){return Na(a||this.points,function(a){return!a.isNull})},setClip:function(a){var b=this.chart,c=this.options,d=b.renderer,e=b.inverted,f=this.clipBox,g=f||b.clipBox,
-h=this.sharedClipKey||["_sharedClip",a&&a.duration,a&&a.easing,g.height,c.xAxis,c.yAxis].join(","),i=b[h],k=b[h+"m"];if(!i){if(a)g.width=0,b[h+"m"]=k=d.clipRect(-99,e?-b.plotLeft:-b.plotTop,99,e?b.chartWidth:b.chartHeight);b[h]=i=d.clipRect(g)}a&&(i.count+=1);if(c.clip!==!1)this.group.clip(a||f?i:b.clipRect),this.markerGroup.clip(k),this.sharedClipKey=h;a||(i.count-=1,i.count<=0&&h&&b[h]&&(f||(b[h]=b[h].destroy()),b[h+"m"]&&(b[h+"m"]=b[h+"m"].destroy())))},animate:function(a){var b=this.chart,c=this.options.animation,
-d;if(c&&!Y(c))c=aa[this.type].animation;a?this.setClip(c):(d=this.sharedClipKey,(a=b[d])&&a.animate({width:b.plotSizeX},c),b[d+"m"]&&b[d+"m"].animate({width:b.plotSizeX+99},c),this.animate=null)},afterAnimate:function(){this.setClip();H(this,"afterAnimate")},drawPoints:function(){var a,b=this.points,c=this.chart,d,e,f,g,h,i,k,j,l=this.options.marker,m=this.pointAttr[""],n,r,o,t=this.markerGroup,v=p(l.enabled,this.xAxis.isRadial,this.closestPointRangePx>2*l.radius);if(l.enabled!==!1||this._hasPointMarkers)for(f=
-b.length;f--;)if(g=b[f],d=T(g.plotX),e=g.plotY,j=g.graphic,n=g.marker||{},r=!!g.marker,a=v&&n.enabled===z||n.enabled,o=g.isInside,a&&e!==z&&!isNaN(e)&&g.y!==null)if(a=g.pointAttr[g.selected?"select":""]||m,h=a.r,i=p(n.symbol,this.symbol),k=i.indexOf("url")===0,j)j[o?"show":"hide"](!0).attr(a).animate(u({x:d-h,y:e-h},j.symbolName?{width:2*h,height:2*h}:{}));else{if(o&&(h>0||k))g.graphic=c.renderer.symbol(i,d-h,e-h,2*h,2*h,r?n:l).attr(a).add(t)}else if(j)g.graphic=j.destroy()},convertAttribs:function(a,
-b,c,d){var e=this.pointAttrToOptions,f,g,h={},a=a||{},b=b||{},c=c||{},d=d||{};for(f in e)g=e[f],h[f]=p(a[g],b[f],c[f],d[f]);return h},getAttribs:function(){var a=this,b=a.options,c=aa[a.type].marker?b.marker:b,d=c.states,e=d.hover,f,g=a.color,h=a.options.negativeColor;f={stroke:g,fill:g};var i=a.points||[],k,j,l=[],m=a.pointAttrToOptions;k=a.hasPointSpecificOptions;var n=c.lineColor,r=c.fillColor;j=b.turboThreshold;var s=a.zones,t=a.zoneAxis||"y",v;b.marker?(e.radius=e.radius||c.radius+e.radiusPlus,
-e.lineWidth=e.lineWidth||c.lineWidth+e.lineWidthPlus):(e.color=e.color||ia(e.color||g).brighten(e.brightness).get(),e.negativeColor=e.negativeColor||ia(e.negativeColor||h).brighten(e.brightness).get());l[""]=a.convertAttribs(c,f);o(["hover","select"],function(b){l[b]=a.convertAttribs(d[b],l[""])});a.pointAttr=l;g=i.length;if(!j||g=f.value;)f=s[++k];j.color=j.fillColor=
-p(f.color,a.color)}k=b.colorByPoint||j.color;if(j.options)for(v in m)q(c[m[v]])&&(k=!0);if(k){c=c||{};k=[];d=c.states||{};f=d.hover=d.hover||{};if(!b.marker||j.negative&&!f.fillColor&&!e.fillColor)f[a.pointAttrToOptions.fill]=f.color||!j.options.color&&e[j.negative&&h?"negativeColor":"color"]||ia(j.color).brighten(f.brightness||e.brightness).get();f={color:j.color};if(!r)f.fillColor=j.color;if(!n)f.lineColor=j.color;c.hasOwnProperty("color")&&!c.color&&delete c.color;k[""]=a.convertAttribs(u(f,c),
-l[""]);k.hover=a.convertAttribs(d.hover,l.hover,k[""]);k.select=a.convertAttribs(d.select,l.select,k[""])}else k=l;j.pointAttr=k}},destroy:function(){var a=this,b=a.chart,c=/AppleWebKit\/533/.test(za),d,e=a.data||[],f,g,h;H(a,"destroy");V(a);o(a.axisTypes||[],function(b){if(h=a[b])oa(h.series,a),h.isDirty=h.forceRedraw=!0});a.legendItem&&a.chart.legend.destroyItem(a);for(d=e.length;d--;)(f=e[d])&&f.destroy&&f.destroy();a.points=null;clearTimeout(a.animationTimeout);for(g in a)a[g]instanceof O&&!a[g].survive&&
-(d=c&&g==="group"?"hide":"destroy",a[g][d]());if(b.hoverSeries===a)b.hoverSeries=null;oa(b.series,a);for(g in a)delete a[g]},getGraphPath:function(a,b,c){var d=this,e=d.options,f=e.step,g,h=[],i,a=a||d.points;(g=a.reversed)&&a.reverse();(f={right:1,center:2}[f]||f&&3)&&g&&(f=4-f);e.connectNulls&&!b&&!c&&(a=this.getValidPoints(a));o(a,function(g,j){var l=g.plotX,m=g.plotY,n=a[j-1];if((g.leftCliff||n&&n.rightCliff)&&!c)i=!0;g.isNull&&!q(b)&&j>0?i=!e.connectNulls:g.isNull&&!b?i=!0:(j===0||i?n=["M",g.plotX,
-g.plotY]:d.getPointSpline?n=d.getPointSpline(a,g,j):f?(n=f===1?["L",n.plotX,m]:f===2?["L",(n.plotX+l)/2,n.plotY,"L",(n.plotX+l)/2,m]:["L",l,n.plotY],n.push("L",l,m)):n=["L",l,m],h.push.apply(h,n),i=!1)});return d.graphPath=h},drawGraph:function(){var a=this,b=this.options,c=[["graph",b.lineColor||this.color,b.dashStyle]],d=b.lineWidth,e=b.linecap!=="square",f=(this.gappedPath||this.getGraphPath).call(this),g=this.fillGraph&&this.color||"none";o(this.zones,function(d,e){c.push(["zoneGraph"+e,d.color||
-a.color,d.dashStyle||b.dashStyle])});o(c,function(c,i){var k=c[0],j=a[k];if(j)j.animate({d:f});else if((d||g)&&f.length)j={stroke:c[1],"stroke-width":d,fill:g,zIndex:1},c[2]?j.dashstyle=c[2]:e&&(j["stroke-linecap"]=j["stroke-linejoin"]="round"),a[k]=a.chart.renderer.path(f).attr(j).add(a.group).shadow(i<2&&b.shadow)})},applyZones:function(){var a=this,b=this.chart,c=b.renderer,d=this.zones,e,f,g=this.clips||[],h,i=this.graph,k=this.area,j=t(b.chartWidth,b.chartHeight),l=this[(this.zoneAxis||"y")+
-"Axis"],m,n=l.reversed,r=b.inverted,s=l.horiz,q,v,x,w=!1;if(d.length&&(i||k)&&l.min!==z)i&&i.hide(),k&&k.hide(),m=l.getExtremes(),o(d,function(d,o){e=n?s?b.plotWidth:0:s?0:l.toPixels(m.min);e=F(t(p(f,e),0),j);f=F(t(A(l.toPixels(p(d.value,m.max),!0)),0),j);w&&(e=f=l.toPixels(m.max));q=Math.abs(e-f);v=F(e,f);x=t(e,f);if(l.isXAxis){if(h={x:r?x:v,y:0,width:q,height:j},!s)h.x=b.plotHeight-h.x}else if(h={x:0,y:r?x:v,width:j,height:q},s)h.y=b.plotWidth-h.y;b.inverted&&c.isVML&&(h=l.isXAxis?{x:0,y:n?v:x,
-height:h.width,width:b.chartWidth}:{x:h.y-b.plotLeft-b.spacingBox.x,y:0,width:h.height,height:b.chartHeight});g[o]?g[o].animate(h):(g[o]=c.clipRect(h),i&&a["zoneGraph"+o].clip(g[o]),k&&a["zoneArea"+o].clip(g[o]));w=d.value>m.max}),this.clips=g},invertGroups:function(){function a(){var a={width:b.yAxis.len,height:b.xAxis.len};o(["group","markerGroup"],function(c){b[c]&&b[c].attr(a).invert()})}var b=this,c=b.chart;if(b.xAxis)M(c,"resize",a),M(b,"destroy",function(){V(c,"resize",a)}),a(),b.invertGroups=
-a},plotGroup:function(a,b,c,d,e){var f=this[a],g=!f;g&&(this[a]=f=this.chart.renderer.g(b).attr({zIndex:d||0.1}).add(e),f.addClass("highcharts-series-"+this.index));f.attr({visibility:c})[g?"attr":"animate"](this.getPlotBox());return f},getPlotBox:function(){var a=this.chart,b=this.xAxis,c=this.yAxis;if(a.inverted)b=c,c=this.xAxis;return{translateX:b?b.left:a.plotLeft,translateY:c?c.top:a.plotTop,scaleX:1,scaleY:1}},render:function(){var a=this,b=a.chart,c,d=a.options,e=(c=d.animation)&&!!a.animate&&
-b.renderer.isSVG&&p(c.duration,500)||0,f=a.visible?"inherit":"hidden",g=d.zIndex,h=a.hasRendered,i=b.seriesGroup;c=a.plotGroup("group","series",f,g,i);a.markerGroup=a.plotGroup("markerGroup","markers",f,g,i);e&&a.animate(!0);a.getAttribs();c.inverted=a.isCartesian?b.inverted:!1;a.drawGraph&&(a.drawGraph(),a.applyZones());o(a.points,function(a){a.redraw&&a.redraw()});a.drawDataLabels&&a.drawDataLabels();a.visible&&a.drawPoints();a.drawTracker&&a.options.enableMouseTracking!==!1&&a.drawTracker();b.inverted&&
-a.invertGroups();d.clip!==!1&&!a.sharedClipKey&&!h&&c.clip(b.clipRect);e&&a.animate();if(!h)a.animationTimeout=Pa(function(){a.afterAnimate()},e);a.isDirty=a.isDirtyData=!1;a.hasRendered=!0},redraw:function(){var a=this.chart,b=this.isDirtyData,c=this.isDirty,d=this.group,e=this.xAxis,f=this.yAxis;d&&(a.inverted&&d.attr({width:a.plotWidth,height:a.plotHeight}),d.animate({translateX:p(e&&e.left,a.plotLeft),translateY:p(f&&f.top,a.plotTop)}));this.translate();this.render();b&&H(this,"updatedData");
-(c||b)&&delete this.kdTree},kdDimensions:1,kdAxisArray:["clientX","plotY"],searchPoint:function(a,b){var c=this.xAxis,d=this.yAxis,e=this.chart.inverted;return this.searchKDTree({clientX:e?c.len-a.chartY+c.pos:a.chartX-c.pos,plotY:e?d.len-a.chartX+d.pos:a.chartY-d.pos},b)},buildKDTree:function(){function a(c,e,f){var g,h;if(h=c&&c.length)return g=b.kdAxisArray[e%f],c.sort(function(a,b){return a[g]-b[g]}),h=Math.floor(h/2),{point:c[h],left:a(c.slice(0,h),e+1,f),right:a(c.slice(h+1),e+1,f)}}var b=this,
-c=b.kdDimensions;delete b.kdTree;Pa(function(){b.kdTree=a(b.getValidPoints(),c,c)},b.options.kdNow?0:1)},searchKDTree:function(a,b){function c(a,b,k,j){var l=b.point,m=d.kdAxisArray[k%j],n,p,o=l;p=q(a[e])&&q(l[e])?Math.pow(a[e]-l[e],2):null;n=q(a[f])&&q(l[f])?Math.pow(a[f]-l[f],2):null;n=(p||0)+(n||0);l.dist=q(n)?Math.sqrt(n):Number.MAX_VALUE;l.distX=q(p)?Math.sqrt(p):Number.MAX_VALUE;m=a[m]-l[m];n=m<0?"left":"right";p=m<0?"right":"left";b[n]&&(n=c(a,b[n],k+1,j),o=n[g]0&&this.singleStacks===!1&&(q.points[v][0]=q.points[this.index+","+w+",0"][0]);
-e==="percent"?(s=s?i:k,j&&m[s]&&m[s][w]?(s=m[s][w],q.total=s.total=t(s.total,q.total)+P(u)||0):q.total=fa(q.total+(P(u)||0))):q.total=fa(q.total+(u||0));q.cum=p(q.cum,g)+(u||0);u!==null&&q.points[v].push(q.cum);c[x]=q.cum}if(e==="percent")l.usePercentage=!0;this.stackedYData=c;l.oldStacks={}}};Q.prototype.setPercentStacks=function(){var a=this,b=a.stackKey,c=a.yAxis.stacks,d=a.processedXData,e;o([b,"-"+b],function(b){var f;for(var g=d.length,h,i;g--;)if(h=d[g],e=a.getStackIndicator(e,h,a.index),f=
-(i=c[b]&&c[b][h])&&i.points[e.key],h=f)i=i.total?100/i.total:0,h[0]=fa(h[0]*i),h[1]=fa(h[1]*i),a.stackedYData[g]=h[1]})};Q.prototype.getStackIndicator=function(a,b,c){!q(a)||a.x!==b?a={x:b,index:0}:a.index++;a.key=[c,b,a.index].join(",");return a};u(hb.prototype,{addSeries:function(a,b,c){var d,e=this;a&&(b=p(b,!0),H(e,"addSeries",{options:a},function(){d=e.initSeries(a);e.isDirtyLegend=!0;e.linkSeries();b&&e.redraw(c)}));return d},addAxis:function(a,b,c,d){var e=b?"xAxis":"yAxis",f=this.options;
-new ka(this,D(a,{index:this[e].length,isX:b}));f[e]=ta(f[e]||{});f[e].push(a);p(c,!0)&&this.redraw(d)},showLoading:function(a){var b=this,c=b.options,d=b.loadingDiv,e=c.loading,f=function(){d&&L(d,{left:b.plotLeft+"px",top:b.plotTop+"px",width:b.plotWidth+"px",height:b.plotHeight+"px"})};if(!d)b.loadingDiv=d=Z(La,{className:"highcharts-loading"},u(e.style,{zIndex:10,display:"none"}),b.container),b.loadingSpan=Z("span",null,e.labelStyle,d),M(b,"redraw",f);b.loadingSpan.innerHTML=a||c.lang.loading;
-if(!b.loadingShown)L(d,{opacity:0,display:""}),Wa(d,{opacity:e.style.opacity},{duration:e.showDuration||0}),b.loadingShown=!0;f()},hideLoading:function(){var a=this.options,b=this.loadingDiv;b&&Wa(b,{opacity:0},{duration:a.loading.hideDuration||100,complete:function(){L(b,{display:"none"})}});this.loadingShown=!1}});u(Ha.prototype,{update:function(a,b,c,d){function e(){f.applyOptions(a);if(f.y===null&&h)f.graphic=h.destroy();if(Y(a)&&!Ia(a))f.redraw=function(){if(h&&h.element&&a&&a.marker&&a.marker.symbol)f.graphic=
-h.destroy();if(a&&a.dataLabels&&f.dataLabel)f.dataLabel=f.dataLabel.destroy();f.redraw=null};i=f.index;g.updateParallelArrays(f,i);if(l&&f.name)l[f.x]=f.name;j.data[i]=Y(j.data[i])?f.options:a;g.isDirty=g.isDirtyData=!0;if(!g.fixedBox&&g.hasCartesianSeries)k.isDirtyBox=!0;if(j.legendType==="point")k.isDirtyLegend=!0;b&&k.redraw(c)}var f=this,g=f.series,h=f.graphic,i,k=g.chart,j=g.options,l=g.xAxis&&g.xAxis.names,b=p(b,!0);d===!1?e():f.firePointEvent("update",{options:a},e)},remove:function(a,b){this.series.removePoint(sa(this,
-this.series.data),a,b)}});u(Q.prototype,{addPoint:function(a,b,c,d){var e=this,f=e.options,g=e.data,h=e.graph,i=e.area,k=e.chart,j=e.xAxis&&e.xAxis.names,l=h&&h.shift||0,m=["graph","area"],h=f.data,n,r=e.xData;Ua(d,k);if(c){for(d=e.zones.length;d--;)m.push("zoneGraph"+d,"zoneArea"+d);o(m,function(a){if(e[a])e[a].shift=l+(f.step?2:1)})}if(i)i.isArea=!0;b=p(b,!0);i={series:e};e.pointClass.prototype.applyOptions.apply(i,[a]);m=i.x;d=r.length;if(e.requireSorting&&mm;)d--;e.updateParallelArrays(i,
-"splice",d,0,0);e.updateParallelArrays(i,d);if(j&&i.name)j[m]=i.name;h.splice(d,0,a);n&&(e.data.splice(d,0,null),e.processData());f.legendType==="point"&&e.generatePoints();c&&(g[0]&&g[0].remove?g[0].remove(!1):(g.shift(),e.updateParallelArrays(i,"shift"),h.shift()));e.isDirty=!0;e.isDirtyData=!0;b&&(e.getAttribs(),k.redraw())},removePoint:function(a,b,c){var d=this,e=d.data,f=e[a],g=d.points,h=d.chart,i=function(){g&&g.length===e.length&&g.splice(a,1);e.splice(a,1);d.options.data.splice(a,1);d.updateParallelArrays(f||
-{series:d},"splice",a,1);f&&f.destroy();d.isDirty=!0;d.isDirtyData=!0;b&&h.redraw()};Ua(c,h);b=p(b,!0);f?f.firePointEvent("remove",null,i):i()},remove:function(a,b){var c=this,d=c.chart;H(c,"remove",null,function(){c.destroy();d.isDirtyLegend=d.isDirtyBox=!0;d.linkSeries();p(a,!0)&&d.redraw(b)})},update:function(a,b){var c=this,d=this.chart,e=this.userOptions,f=this.type,g=I[f].prototype,h=["group","markerGroup","dataLabelsGroup"],i;if(a.type&&a.type!==f||a.zIndex!==void 0)h.length=0;o(h,function(a){h[a]=
-c[a];delete c[a]});a=D(e,{animation:!1,index:this.index,pointStart:this.xData[0]},{data:this.options.data},a);this.remove(!1);for(i in g)this[i]=z;u(this,I[a.type||f].prototype);o(h,function(a){c[a]=h[a]});this.init(d,a);d.linkSeries();p(b,!0)&&d.redraw(!1)}});u(ka.prototype,{update:function(a,b){var c=this.chart,a=c.options[this.coll][this.options.index]=D(this.userOptions,a);this.destroy(!0);this._addedPlotLB=this.chart._labelPanes=z;this.init(c,u(a,{events:z}));c.isDirtyBox=!0;p(b,!0)&&c.redraw()},
-remove:function(a){for(var b=this.chart,c=this.coll,d=this.series,e=d.length;e--;)d[e]&&d[e].remove(!1);oa(b.axes,this);oa(b[c],this);b.options[c].splice(this.options.index,1);o(b[c],function(a,b){a.options.index=b});this.destroy();b.isDirtyBox=!0;p(a,!0)&&b.redraw()},setTitle:function(a,b){this.update({title:a},b)},setCategories:function(a,b){this.update({categories:a},b)}});var wa=pa(Q);I.line=wa;aa.area=D(da,{softThreshold:!1,threshold:0});var la=pa(Q,{type:"area",singleStacks:!1,getStackPoints:function(){var a=
-[],b=[],c=this.xAxis,d=this.yAxis,e=d.stacks[this.stackKey],f={},g=this.points,h=this.index,i=d.series,k=i.length,j,l=p(d.options.reversedStacks,!0)?1:-1,m,n;if(this.options.stacking){for(m=0;m=0&&m=0&&ma&&h>e?(h=t(a,e),k=2*e-h):hc&&k>e?(k=t(c,e),
-h=2*e-k):k0.5;b=Math.round(b)+f;d-=
-b;g&&(b-=1,d+=1);return{x:a,y:b,width:c,height:d}},translate:function(){var a=this,b=a.chart,c=a.options,d=a.borderWidth=p(c.borderWidth,a.closestPointRange*a.xAxis.transA<2?0:1),e=a.yAxis,f=a.translatedThreshold=e.getThreshold(c.threshold),g=p(c.minPointLength,5),h=a.getColumnMetrics(),i=h.width,k=a.barW=t(i,1+2*d),j=a.pointXOffset=h.offset;b.inverted&&(f-=0.5);c.pointPadding&&(k=ua(k));Q.prototype.translate.apply(a);o(a.points,function(c){var d=F(p(c.yBottom,f),9E4),h=999+P(d),h=F(t(-h,c.plotY),
-e.len+h),o=c.plotX+j,s=k,q=F(h,d),v,u=t(h,d)-q;P(u)g?d-g:f-(v?g:0));c.barX=o;c.pointWidth=i;c.tooltipPos=b.inverted?[e.len+e.pos-b.plotLeft-h,a.xAxis.len-o-s/2,u]:[o+s/2,h+e.pos-b.plotTop,u];c.shapeType="rect";c.shapeArgs=a.crispCol(o,q,s,u)})},getSymbol:Aa,drawLegendSymbol:J.drawRectangle,drawGraph:Aa,drawPoints:function(){var a=this,b=this.chart,c=a.options,d=b.renderer,e=c.animationLimit||250,f,g;o(a.points,function(h){var i=
-h.plotY,k=h.graphic;if(i!==z&&!isNaN(i)&&h.y!==null)f=h.shapeArgs,i=q(a.borderWidth)?{"stroke-width":a.borderWidth}:{},g=h.pointAttr[h.selected?"select":""]||a.pointAttr[""],k?(Oa(k),k.attr(i).attr(g)[b.pointCount\u25cf
{series.name} ',
-pointFormat:"x: {point.x} y: {point.y} "}});la=pa(Q,{type:"scatter",sorted:!1,requireSorting:!1,noSharedTooltip:!0,trackerGroups:["group","markerGroup","dataLabelsGroup"],takeOrdinalPosition:!1,kdDimensions:2,drawGraph:function(){this.options.lineWidth&&Q.prototype.drawGraph.call(this)}});I.scatter=la;aa.pie=D(da,{borderColor:"#FFFFFF",borderWidth:1,center:[null,null],clip:!1,colorByPoint:!0,dataLabels:{distance:30,enabled:!0,formatter:function(){return this.y===null?void 0:
-this.point.name},x:0},ignoreHiddenPoint:!0,legendType:"point",marker:null,size:null,showInLegend:!1,slicedOffset:10,states:{hover:{brightness:0.1,shadow:!1}},stickyTracking:!1,tooltip:{followPointer:!0}});da={type:"pie",isCartesian:!1,pointClass:pa(Ha,{init:function(){Ha.prototype.init.apply(this,arguments);var a=this,b;a.name=p(a.name,"Slice");b=function(b){a.slice(b.type==="select")};M(a,"select",b);M(a,"unselect",b);return a},setVisible:function(a,b){var c=this,d=c.series,e=d.chart,f=d.options.ignoreHiddenPoint,
-b=p(b,f);if(a!==c.visible){c.visible=c.options.visible=a=a===z?!c.visible:a;d.options.data[sa(c,d.data)]=c.options;o(["graphic","dataLabel","connector","shadowGroup"],function(b){if(c[b])c[b][a?"show":"hide"](!0)});c.legendItem&&e.legend.colorizeItem(c,a);!a&&c.state==="hover"&&c.setState("");if(f)d.isDirty=!0;b&&e.redraw()}},slice:function(a,b,c){var d=this.series;Ua(c,d.chart);p(b,!0);this.sliced=this.options.sliced=a=q(a)?a:!this.sliced;d.options.data[sa(this,d.data)]=this.options;a=a?this.slicedTranslation:
-{translateX:0,translateY:0};this.graphic.animate(a);this.shadowGroup&&this.shadowGroup.animate(a)},haloPath:function(a){var b=this.shapeArgs,c=this.series.chart;return this.sliced||!this.visible?[]:this.series.chart.renderer.symbols.arc(c.plotLeft+b.x,c.plotTop+b.y,b.r+a,b.r+a,{innerR:this.shapeArgs.r,start:b.start,end:b.end})}}),requireSorting:!1,directTouch:!0,noSharedTooltip:!0,trackerGroups:["group","dataLabelsGroup"],axisTypes:[],pointAttrToOptions:{stroke:"borderColor","stroke-width":"borderWidth",
-fill:"color"},animate:function(a){var b=this,c=b.points,d=b.startAngleRad;if(!a)o(c,function(a){var c=a.graphic,g=a.shapeArgs;c&&(c.attr({r:a.startR||b.center[3]/2,start:d,end:d}),c.animate({r:g.r,start:g.start,end:g.end},b.options.animation))}),b.animate=null},updateTotals:function(){var a,b=0,c=this.points,d=c.length,e,f=this.options.ignoreHiddenPoint;for(a=0;a0&&(e.visible||!f)?e.y/b*100:0,e.total=b},generatePoints:function(){Q.prototype.generatePoints.call(this);
-this.updateTotals()},translate:function(a){this.generatePoints();var b=0,c=this.options,d=c.slicedOffset,e=d+c.borderWidth,f,g,h,i=c.startAngle||0,k=this.startAngleRad=ra/180*(i-90),i=(this.endAngleRad=ra/180*(p(c.endAngle,i+360)-90))-k,j=this.points,l=c.dataLabels.distance,c=c.ignoreHiddenPoint,m,n=j.length,o;if(!a)this.center=a=this.getCenter();this.getX=function(b,c){h=W.asin(F((b-a[1])/(a[2]/2+l),1));return a[0]+(c?-1:1)*U(h)*(a[2]/2+l)};for(m=0;m1.5*ra?h-=2*ra:h<-ra/2&&(h+=2*ra);o.slicedTranslation={translateX:A(U(h)*d),translateY:A($(h)*d)};f=U(h)*a[2]/2;g=$(h)*a[2]/2;o.tooltipPos=[a[0]+f*0.7,a[1]+g*0.7];o.half=h<-ra/2||h>ra/2?1:0;o.angle=h;e=F(e,l/2);o.labelPos=[a[0]+f+U(h)*l,a[1]+g+$(h)*l,a[0]+f+U(h)*e,a[1]+g+$(h)*e,a[0]+f,a[1]+g,l<0?"center":o.half?"right":"left",h]}},drawGraph:null,drawPoints:function(){var a=
-this,b=a.chart.renderer,c,d,e=a.options.shadow,f,g,h,i;if(e&&!a.shadowGroup)a.shadowGroup=b.g("shadow").add(a.group);o(a.points,function(k){if(k.y!==null){d=k.graphic;h=k.shapeArgs;f=k.shadowGroup;g=k.pointAttr[k.selected?"select":""];if(!g.stroke)g.stroke=g.fill;if(e&&!f)f=k.shadowGroup=b.g("shadow").add(a.shadowGroup);c=k.sliced?k.slicedTranslation:{translateX:0,translateY:0};f&&f.attr(c);if(d)d.setRadialReference(a.center).attr(g).animate(u(h,c));else{i={"stroke-linejoin":"round"};if(!k.visible)i.visibility=
-"hidden";k.graphic=d=b[k.shapeType](h).setRadialReference(a.center).attr(g).attr(i).attr(c).add(a.group).shadow(e,f)}}})},searchPoint:Aa,sortByAngle:function(a,b){a.sort(function(a,d){return a.angle!==void 0&&(d.angle-a.angle)*b})},drawLegendSymbol:J.drawRectangle,getCenter:Cb.getCenter,getSymbol:Aa};da=pa(Q,da);I.pie=da;Q.prototype.drawDataLabels=function(){var a=this,b=a.options,c=b.cursor,d=b.dataLabels,e=a.points,f,g,h=a.hasRendered||0,i,k,j=a.chart.renderer;if(d.enabled||a._hasPointLabels)a.dlProcessOptions&&
-a.dlProcessOptions(d),k=a.plotGroup("dataLabelsGroup","data-labels",d.defer?"hidden":"visible",d.zIndex||6),p(d.defer,!0)&&(k.attr({opacity:+h}),h||M(a,"afterAnimate",function(){a.visible&&k.show();k[b.animation?"animate":"attr"]({opacity:1},{duration:200})})),g=d,o(e,function(e){var h,n=e.dataLabel,o,s,t=e.connector,v=!0,x,w={};f=e.dlOptions||e.options&&e.options.dataLabels;h=p(f&&f.enabled,g.enabled)&&e.y!==null;if(n&&!h)e.dataLabel=n.destroy();else if(h){d=D(g,f);x=d.style;h=d.rotation;o=e.getLabelConfig();
-i=d.format?Ka(d.format,o):d.formatter.call(o,d);x.color=p(d.color,x.color,a.color,"black");if(n)if(q(i))n.attr({text:i}),v=!1;else{if(e.dataLabel=n=n.destroy(),t)e.connector=t.destroy()}else if(q(i)){n={fill:d.backgroundColor,stroke:d.borderColor,"stroke-width":d.borderWidth,r:d.borderRadius||0,rotation:h,padding:d.padding,zIndex:1};if(x.color==="contrast")w.color=d.inside||d.distance<0||b.stacking?j.getContrast(e.color||a.color):"#000000";if(c)w.cursor=c;for(s in n)n[s]===z&&delete n[s];n=e.dataLabel=
-j[h?"text":"label"](i,0,-9999,d.shape,null,null,d.useHTML).attr(n).css(u(x,w)).add(k).shadow(d.shadow)}n&&a.alignDataLabel(e,n,d,null,v)}})};Q.prototype.alignDataLabel=function(a,b,c,d,e){var f=this.chart,g=f.inverted,h=p(a.plotX,-9999),i=p(a.plotY,-9999),k=b.getBBox(),j=f.renderer.fontMetrics(c.style.fontSize).b,l=c.rotation,m=c.align,n=this.visible&&(a.series.forceDL||f.isInsidePlot(h,A(i),g)||d&&f.isInsidePlot(h,g?d.x+1:d.y+d.height-1,g)),o=p(c.overflow,"justify")==="justify";if(n)d=u({x:g?f.plotWidth-
-i:h,y:A(g?f.plotHeight-h:i),width:0,height:0},d),u(c,{width:k.width,height:k.height}),l?(o=!1,g=f.renderer.rotCorr(j,l),g={x:d.x+c.x+d.width/2+g.x,y:d.y+c.y+d.height/2},b[e?"attr":"animate"](g).attr({align:c.align}),h=(l+720)%360,h=h>180&&h<360,m==="left"?g.y-=h?k.height:0:m==="center"?(g.x-=k.width/2,g.y-=k.height/2):m==="right"&&(g.x-=k.width,g.y-=h?0:k.height)):(b.align(c,null,d),g=b.alignAttr),o?this.justifyDataLabel(b,c,g,k,d,e):p(c.crop,!0)&&(n=f.isInsidePlot(g.x,g.y)&&f.isInsidePlot(g.x+k.width,
-g.y+k.height)),c.shape&&!l&&b.attr({anchorX:a.plotX,anchorY:a.plotY});if(!n)Oa(b),b.attr({y:-9999}),b.placed=!1};Q.prototype.justifyDataLabel=function(a,b,c,d,e,f){var g=this.chart,h=b.align,i=b.verticalAlign,k,j,l=a.box?0:a.padding||0;k=c.x+l;if(k<0)h==="right"?b.align="left":b.x=-k,j=!0;k=c.x+d.width-l;if(k>g.plotWidth)h==="left"?b.align="right":b.x=g.plotWidth-k,j=!0;k=c.y+l;if(k<0)i==="bottom"?b.verticalAlign="top":b.y=-k,j=!0;k=c.y+d.height-l;if(k>g.plotHeight)i==="top"?b.verticalAlign="bottom":
-b.y=g.plotHeight-k,j=!0;if(j)a.placed=!f,a.align(b,null,e)};if(I.pie)I.pie.prototype.drawDataLabels=function(){var a=this,b=a.data,c,d=a.chart,e=a.options.dataLabels,f=p(e.connectorPadding,10),g=p(e.connectorWidth,1),h=d.plotWidth,i=d.plotHeight,k,j,l=p(e.softConnector,!0),m=e.distance,n=a.center,r=n[2]/2,q=n[1],u=m>0,v,x,w,B=[[],[]],z,y,E,D,C,G=[0,0,0,0],L=function(a,b){return b.y-a.y};if(a.visible&&(e.enabled||a._hasPointLabels)){Q.prototype.drawDataLabels.apply(a);o(b,function(a){if(a.dataLabel&&
-a.visible)B[a.half].push(a),a.dataLabel._pos=null});for(D=2;D--;){var H=[],M=[],I=B[D],K=I.length,J;if(K){a.sortByAngle(I,D-0.5);for(C=b=0;!b&&I[C];)b=I[C]&&I[C].dataLabel&&(I[C].dataLabel.getBBox().height||21),C++;if(m>0){x=F(q+r+m,d.plotHeight);for(C=t(0,q-r-m);C<=x;C+=b)H.push(C);x=H.length;if(K>x){c=[].concat(I);c.sort(L);for(C=K;C--;)c[C].rank=C;for(C=K;C--;)I[C].rank>=x&&I.splice(C,1);K=I.length}for(C=0;C0){if(x=M.pop(),J=x.i,y=x.y,c>y&&H[J+1]!==null||ch-f&&(G[1]=t(A(z+x-h+f),G[1])),y-b/2<0?G[0]=t(A(-y+b/2),G[0]):y+b/2>i&&(G[2]=t(A(y+b/2-i),G[2]))}}}if(Ea(G)===0||this.verifyDataLabelOverflow(G))this.placeDataLabels(),u&&g&&o(this.points,function(b){k=b.connector;w=b.labelPos;if((v=b.dataLabel)&&v._pos&&b.visible)E=v._attr.visibility,z=v.connX,y=v.connY,j=l?["M",z+(w[6]==="left"?5:-5),y,"C",z,y,2*w[2]-w[4],2*w[3]-w[5],w[2],w[3],"L",w[4],w[5]]:["M",z+(w[6]==="left"?5:-5),y,"L",
-w[2],w[3],"L",w[4],w[5]],k?(k.animate({d:j}),k.attr("visibility",E)):b.connector=k=a.chart.renderer.path(j).attr({"stroke-width":g,stroke:e.connectorColor||b.color||"#606060",visibility:E}).add(a.dataLabelsGroup);else if(k)b.connector=k.destroy()})}},I.pie.prototype.placeDataLabels=function(){o(this.points,function(a){var b=a.dataLabel;if(b&&a.visible)(a=b._pos)?(b.attr(b._attr),b[b.moved?"animate":"attr"](a),b.moved=!0):b&&b.attr({y:-9999})})},I.pie.prototype.alignDataLabel=Aa,I.pie.prototype.verifyDataLabelOverflow=
-function(a){var b=this.center,c=this.options,d=c.center,e=c.minSize||80,f=e,g;d[0]!==null?f=t(b[2]-t(a[1],a[3]),e):(f=t(b[2]-a[1]-a[3],e),b[0]+=(a[3]-a[1])/2);d[1]!==null?f=t(F(f,b[2]-t(a[0],a[2])),e):(f=t(F(f,b[2]-a[0]-a[2]),e),b[1]+=(a[0]-a[2])/2);fp(this.translatedThreshold,g.yAxis.len)),k=p(c.inside,!!this.options.stacking);if(h){d=D(h);if(d.y<0)d.height+=d.y,d.y=0;h=d.y+d.height-g.yAxis.len;h>0&&(d.height-=h);f&&(d={x:g.yAxis.len-d.y-d.height,y:g.xAxis.len-d.x-d.width,width:d.height,height:d.width});if(!k)f?(d.x+=i?0:d.width,d.width=0):(d.y+=i?d.height:0,d.height=0)}c.align=p(c.align,!f||k?"center":i?"right":"left");c.verticalAlign=p(c.verticalAlign,
-f||k?"middle":i?"top":"bottom");Q.prototype.alignDataLabel.call(this,a,b,c,d,e)};(function(a){var b=a.Chart,c=a.each,d=a.pick,e=a.addEvent;b.prototype.callbacks.push(function(a){function b(){var e=[];c(a.series,function(a){var b=a.options.dataLabels,f=a.dataLabelCollections||["dataLabel"];(b.enabled||a._hasPointLabels)&&!b.allowOverlap&&a.visible&&c(f,function(b){c(a.points,function(a){if(a[b])a[b].labelrank=d(a.labelrank,a.shapeArgs&&a.shapeArgs.height),e.push(a[b])})})});a.hideOverlappingLabels(e)}
-b();e(a,"redraw",b)});b.prototype.hideOverlappingLabels=function(a){var b=a.length,d,e,k,j,l,m,n,o,p;for(e=0;el.x+n.translateX+(k.width-p)||m.x+o.translateX+(j.width-
-p)l.y+n.translateY+(k.height-p)||m.y+o.translateY+(j.height-p)h;if(b.series.length&&(i||l>F(j.dataMin,j.min))&&(!i||k
@@ -20,6 +21,7 @@