UNPKG

@progress/kendo-ui

Version:

This package is part of the [Kendo UI for jQuery](http://www.telerik.com/kendo-ui) suite.

1,808 lines (1,469 loc) 230 kB
module.exports = /******/ (function(modules) { // webpackBootstrap /******/ // The module cache /******/ var installedModules = {}; /******/ // The require function /******/ function __webpack_require__(moduleId) { /******/ // Check if module is in cache /******/ if(installedModules[moduleId]) /******/ return installedModules[moduleId].exports; /******/ // Create a new module (and put it into the cache) /******/ var module = installedModules[moduleId] = { /******/ exports: {}, /******/ id: moduleId, /******/ loaded: false /******/ }; /******/ // Execute the module function /******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); /******/ // Flag the module as loaded /******/ module.loaded = true; /******/ // Return the exports of the module /******/ return module.exports; /******/ } /******/ // expose the modules object (__webpack_modules__) /******/ __webpack_require__.m = modules; /******/ // expose the module cache /******/ __webpack_require__.c = installedModules; /******/ // __webpack_public_path__ /******/ __webpack_require__.p = ""; /******/ // Load entry module and return exports /******/ return __webpack_require__(0); /******/ }) /************************************************************************/ /******/ ({ /***/ 0: /***/ (function(module, exports, __webpack_require__) { module.exports = __webpack_require__(866); /***/ }), /***/ 3: /***/ (function(module, exports) { module.exports = function() { throw new Error("define cannot be used indirect"); }; /***/ }), /***/ 859: /***/ (function(module, exports) { module.exports = require("../../kendo.drawing"); /***/ }), /***/ 862: /***/ (function(module, exports) { module.exports = require("../../kendo.core"); /***/ }), /***/ 866: /***/ (function(module, exports, __webpack_require__) { var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;(function(f, define){ !(__WEBPACK_AMD_DEFINE_ARRAY__ = [ __webpack_require__(862), __webpack_require__(859) ], __WEBPACK_AMD_DEFINE_FACTORY__ = (f), __WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ? (__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__), __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__)); })(function(){ (function ($) { /* jshint curly:false */ window.kendo.dataviz = window.kendo.dataviz || {}; var drawing = kendo.drawing; var util = drawing.util; var Path = drawing.Path; var Group = drawing.Group; var Class = kendo.Class; var geometry = kendo.geometry; var Rect = geometry.Rect; var Circle = geometry.Circle; var geometryTransform = geometry.transform; var Segment = geometry.Segment; var dataviz = kendo.dataviz; var deepExtend = kendo.deepExtend; var isFunction = kendo.isFunction; var __common_getter_js = kendo.getter; var ARC = "arc"; var AXIS_LABEL_CLICK = "axisLabelClick"; var BLACK = "#000"; var BOTTOM = "bottom"; var CENTER = "center"; var CIRCLE = "circle"; var COORD_PRECISION = 3; var CROSS = "cross"; var DATE = "date"; var DEFAULT_FONT = "12px sans-serif"; var DEFAULT_HEIGHT = 400; var DEFAULT_PRECISION = 10; var DEFAULT_WIDTH = 600; var END = "end"; var FORMAT_REGEX = /\{\d+:?/; var HEIGHT = "height"; var HIGHLIGHT_ZINDEX = 100; var INSIDE = "inside"; var LEFT = "left"; var MAX_VALUE = Number.MAX_VALUE; var MIN_VALUE = -Number.MAX_VALUE; var NONE = "none"; var NOTE_CLICK = "noteClick"; var NOTE_HOVER = "noteHover"; var NOTE_LEAVE = "noteLeave"; var OBJECT = "object"; var OUTSIDE = "outside"; var RIGHT = "right"; var START = "start"; var STRING = "string"; var TOP = "top"; var TRIANGLE = "triangle"; var VALUE = "value"; var WHITE = "#fff"; var WIDTH = "width"; var X = "x"; var Y = "y"; var constants = { ARC: ARC, AXIS_LABEL_CLICK: AXIS_LABEL_CLICK, BLACK: BLACK, BOTTOM: BOTTOM, CENTER: CENTER, CIRCLE: CIRCLE, COORD_PRECISION: COORD_PRECISION, CROSS: CROSS, DATE: DATE, DEFAULT_FONT: DEFAULT_FONT, DEFAULT_HEIGHT: DEFAULT_HEIGHT, DEFAULT_PRECISION: DEFAULT_PRECISION, DEFAULT_WIDTH: DEFAULT_WIDTH, END: END, FORMAT_REGEX: FORMAT_REGEX, HEIGHT: HEIGHT, HIGHLIGHT_ZINDEX: HIGHLIGHT_ZINDEX, INSIDE: INSIDE, LEFT: LEFT, MAX_VALUE: MAX_VALUE, MIN_VALUE: MIN_VALUE, NONE: NONE, NOTE_CLICK: NOTE_CLICK, NOTE_HOVER: NOTE_HOVER, NOTE_LEAVE: NOTE_LEAVE, OBJECT: OBJECT, OUTSIDE: OUTSIDE, RIGHT: RIGHT, START: START, STRING: STRING, TOP: TOP, TRIANGLE: TRIANGLE, VALUE: VALUE, WHITE: WHITE, WIDTH: WIDTH, X: X, Y: Y }; function isArray(value) { return Array.isArray(value); } function addClass(element, classes) { var classArray = isArray(classes) ? classes : [ classes ]; for (var idx = 0; idx < classArray.length; idx++) { var className = classArray[idx]; if (element.className.indexOf(className) === -1) { element.className += " " + className; } } } var SPACE_REGEX = /\s+/g; function removeClass(element, className) { if (element && element.className) { element.className = element.className.replace(className, "").replace(SPACE_REGEX, " "); } } function alignPathToPixel(path) { var offset = 0.5; if (path.options.stroke && kendo.drawing.util.defined(path.options.stroke.width)) { if (path.options.stroke.width % 2 === 0) { offset = 0; } } for (var i = 0; i < path.segments.length; i++) { path.segments[i].anchor().round(0).translate(offset, offset); } return path; } function clockwise(angle1, angle2) { // True if angle2 is clockwise of angle1 // assuming angles grow in clock-wise direction // (as in the pie and radar charts) return -angle1.x * angle2.y + angle1.y * angle2.x < 0; } function isNumber(value) { return typeof value === "number" && !isNaN(value); } function isString(value) { return typeof value === STRING; } function convertableToNumber(value) { return isNumber(value) || (isString(value) && isFinite(value)); } function isObject(value) { return typeof value === "object"; } function styleValue(value) { if (isNumber(value)) { return value + "px"; } return value; } var SIZE_STYLES_REGEX = /width|height|top|left|bottom|right/i; function isSizeField(field) { return SIZE_STYLES_REGEX.test(field); } function elementStyles(element, styles) { var stylesArray = isString(styles) ? [ styles ] : styles; if (isArray(stylesArray)) { var result = {}; var style = window.getComputedStyle(element); for (var idx = 0; idx < stylesArray.length; idx++) { var field = stylesArray[idx]; result[field] = isSizeField(field) ? parseFloat(style[field]) : style[field]; } return result; } else if (isObject(styles)) { for (var field$1 in styles) { element.style[field$1] = styleValue(styles[field$1]); } } } function getSpacing(value, defaultSpacing) { if (defaultSpacing === void 0) { defaultSpacing = 0; } var spacing = { top: 0, right: 0, bottom: 0, left: 0 }; if (typeof(value) === "number") { spacing[TOP] = spacing[RIGHT] = spacing[BOTTOM] = spacing[LEFT] = value; } else { spacing[TOP] = value[TOP] || defaultSpacing; spacing[RIGHT] = value[RIGHT] || defaultSpacing; spacing[BOTTOM] = value[BOTTOM] || defaultSpacing; spacing[LEFT] = value[LEFT] || defaultSpacing; } return spacing; } var defaultImplementation = { format: function (format, value) { return value; }, toString: function (value) { return value; }, parseDate: function (value) { return new Date(value); } }; var current = defaultImplementation; var IntlService = Class.extend({ }); IntlService.register = function(userImplementation) { current = userImplementation; }; if (Object.defineProperties) { Object.defineProperties(IntlService, { implementation: { get: function() { return current; } } }); } var FORMAT_REPLACE_REGEX = /\{(\d+)(:[^\}]+)?\}/g; var FormatService = Class.extend({ init: function(intlService) { this._intlService = intlService; }, auto: function(formatString) { var values = [], len = arguments.length - 1; while ( len-- > 0 ) values[ len ] = arguments[ len + 1 ]; var intl = this.intl; if (isString(formatString) && formatString.match(FORMAT_REGEX)) { return intl.format.apply(intl, [ formatString ].concat( values )); } return intl.toString(values[0], formatString); }, localeAuto: function(formatString, values, locale) { var intl = this.intl; var result; if (isString(formatString) && formatString.match(FORMAT_REGEX)) { result = formatString.replace(FORMAT_REPLACE_REGEX, function(match, index, placeholderFormat) { var value = values[parseInt(index, 10)]; return intl.toString(value, placeholderFormat ? placeholderFormat.substring(1) : "", locale); }); } else { result = intl.toString(values[0], formatString, locale); } return result; } }); if (Object.defineProperties) { Object.defineProperties(FormatService.fn, { intl: { get: function() { return this._intlService || IntlService.implementation; }, set: function(value) { this._intlService = value; } } }); } var ChartService = Class.extend({ init: function(chart, context) { if (context === void 0) { context = {}; } this._intlService = context.intlService; this.sender = context.sender || chart; this.format = new FormatService(context.intlService); this.chart = chart; this.rtl = Boolean(context.rtl); }, notify: function(name, args) { if (this.chart) { this.chart.trigger(name, args); } }, isPannable: function(axis) { var pannable = ((this.chart || {}).options || {}).pannable; return pannable && pannable.lock !== axis; } }); if (Object.defineProperties) { Object.defineProperties(ChartService.fn, { intl: { get: function() { return this._intlService || IntlService.implementation; }, set: function(value) { this._intlService = value; this.format.intl = value; } } }); } var current$1; var DomEventsBuilder = Class.extend({ }); DomEventsBuilder.register = function(userImplementation) { current$1 = userImplementation; }; DomEventsBuilder.create = function(element, events) { if (current$1) { return current$1.create(element, events); } }; var current$2 = { compile: function(template) { return template; } }; var TemplateService = Class.extend({ }); TemplateService.register = function(userImplementation) { current$2 = userImplementation; }; TemplateService.compile = function(template) { return current$2.compile(template); }; var services = { ChartService: ChartService, DomEventsBuilder: DomEventsBuilder, FormatService: FormatService, IntlService: IntlService, TemplateService: TemplateService }; function getTemplate(options) { if (options === void 0) { options = {}; } var template; if (options.template) { options.template = template = TemplateService.compile(options.template); } else if (isFunction(options.content)) { template = options.content; } return template; } function grep(array, callback) { var length = array.length; var result = []; for (var idx = 0; idx < length; idx++) { if (callback(array[idx])) { result .push(array[idx]); } } return result; } function hasClasses(element, classNames) { if (element.className) { var names = classNames.split(" "); for (var idx = 0; idx < names.length; idx++) { if (element.className.indexOf(names[idx]) !== -1) { return true; } } } } var HashMap = function HashMap() { this._map = {}; }; HashMap.prototype.get = function get (name) { return this._map[this._key(name)]; }; HashMap.prototype.set = function set (name, value) { this._map[this._key(name)] = value; }; HashMap.prototype._key = function _key (name) { return name instanceof Date ? name.getTime() : name; }; function inArray(value, array) { if (array) { return array.indexOf(value) !== -1; } } function interpolateValue(start, end, progress) { return kendo.drawing.util.round(start + (end - start) * progress, COORD_PRECISION); } var TRIGGER = 'trigger'; var InstanceObserver = Class.extend({ init: function(observer, handlers) { this.observer = observer; this.handlerMap = deepExtend({}, this.handlerMap, handlers); }, trigger: function(name, args) { var ref = this; var observer = ref.observer; var handlerMap = ref.handlerMap; var isDefaultPrevented; if (handlerMap[name]) { isDefaultPrevented = this.callObserver(handlerMap[name], args); } else if (observer[TRIGGER]) { isDefaultPrevented = this.callObserver(TRIGGER, name, args); } return isDefaultPrevented; }, callObserver: function(fnName) { var args = [], len = arguments.length - 1; while ( len-- > 0 ) args[ len ] = arguments[ len + 1 ]; return this.observer[fnName].apply(this.observer, args); }, requiresHandlers: function(names) { var this$1 = this; if (this.observer.requiresHandlers) { return this.observer.requiresHandlers(names); } for (var idx = 0; idx < names.length; idx++) { if (this$1.handlerMap[names[idx]]) { return true; } } } }); function map(array, callback) { var length = array.length; var result = []; for (var idx = 0; idx < length; idx++) { var value = callback(array[idx]); if (kendo.drawing.util.defined(value)) { result.push(value); } } return result; } function mousewheelDelta(e) { var delta = 0; if (e.wheelDelta) { delta = -e.wheelDelta / 120; delta = delta > 0 ? Math.ceil(delta) : Math.floor(delta); } if (e.detail) { delta = kendo.drawing.util.round(e.detail / 3); } return delta; } var ref = kendo.drawing.util; var append = ref.append; var bindEvents = ref.bindEvents; var defined = ref.defined; var deg = ref.deg; var elementOffset = ref.elementOffset; var elementSize = ref.elementSize; var eventElement = ref.eventElement; var eventCoordinates = ref.eventCoordinates; var last = ref.last; var limitValue = ref.limitValue; var objectKey = ref.objectKey; var rad = ref.rad; var round = ref.round; var unbindEvents = ref.unbindEvents; var valueOrDefault = ref.valueOrDefault; var FontLoader = Class.extend({ }); FontLoader.fetchFonts = function(options, fonts, state) { if (state === void 0) { state = { depth: 0 }; } var MAX_DEPTH = 5; if (!options || state.depth > MAX_DEPTH || !document.fonts) { return; } Object.keys(options).forEach(function(key) { var value = options[key]; if (key === "dataSource" || key[0] === "$" || !value) { return; } if (key === "font") { fonts.push(value); } else if (typeof value === "object") { state.depth++; FontLoader.fetchFonts(value, fonts, state); state.depth--; } }); }; FontLoader.loadFonts = function(fonts, callback) { var promises = []; if (fonts.length > 0 && document.fonts) { try { promises = fonts.map(function(font) { return document.fonts.load(font); }); } catch (e) { // Silence font-loading errors kendo.logToConsole(e); } Promise.all(promises).then(callback, callback); } else { callback(); } }; FontLoader.preloadFonts = function(options, callback) { var fonts = []; FontLoader.fetchFonts(options, fonts); FontLoader.loadFonts(fonts, callback); }; function setDefaultOptions(type, options) { var proto = type.prototype; if (proto.options) { proto.options = deepExtend({}, proto.options, options); } else { proto.options = options; } } function sparseArrayLimits(arr) { var min = MAX_VALUE; var max = MIN_VALUE; for (var idx = 0, length = arr.length; idx < length; idx++) { var value = arr[idx]; if (value !== null && isFinite(value)) { min = Math.min(min, value); max = Math.max(max, value); } } return { min: min === MAX_VALUE ? undefined : min, max: max === MIN_VALUE ? undefined : max }; } function autoMajorUnit(min, max) { var diff = round(max - min, DEFAULT_PRECISION - 1); if (diff === 0) { if (max === 0) { return 0.1; } diff = Math.abs(max); } var scale = Math.pow(10, Math.floor(Math.log(diff) / Math.log(10))); var relativeValue = round((diff / scale), DEFAULT_PRECISION); var scaleMultiplier = 1; if (relativeValue < 1.904762) { scaleMultiplier = 0.2; } else if (relativeValue < 4.761904) { scaleMultiplier = 0.5; } else if (relativeValue < 9.523809) { scaleMultiplier = 1; } else { scaleMultiplier = 2; } return round(scale * scaleMultiplier, DEFAULT_PRECISION); } var Point = Class.extend({ init: function(x, y) { this.x = x || 0; this.y = y || 0; }, clone: function() { return new Point(this.x, this.y); }, equals: function(point) { return point && this.x === point.x && this.y === point.y; }, rotate: function(center, degrees) { var theta = rad(degrees); var cosT = Math.cos(theta); var sinT = Math.sin(theta); var cx = center.x; var cy = center.y; var ref = this; var x = ref.x; var y = ref.y; this.x = round( cx + (x - cx) * cosT + (y - cy) * sinT, COORD_PRECISION ); this.y = round( cy + (y - cy) * cosT - (x - cx) * sinT, COORD_PRECISION ); return this; }, multiply: function(a) { this.x *= a; this.y *= a; return this; }, distanceTo: function(point) { var dx = this.x - point.x; var dy = this.y - point.y; return Math.sqrt(dx * dx + dy * dy); } }); Point.onCircle = function(center, angle, radius) { var radians = rad(angle); return new Point( center.x - radius * Math.cos(radians), center.y - radius * Math.sin(radians) ); }; var Box = Class.extend({ init: function(x1, y1, x2, y2) { this.x1 = x1 || 0; this.y1 = y1 || 0; this.x2 = x2 || 0; this.y2 = y2 || 0; }, equals: function(box) { return this.x1 === box.x1 && this.x2 === box.x2 && this.y1 === box.y1 && this.y2 === box.y2; }, width: function() { return this.x2 - this.x1; }, height: function() { return this.y2 - this.y1; }, translate: function(dx, dy) { this.x1 += dx; this.x2 += dx; this.y1 += dy; this.y2 += dy; return this; }, move: function(x, y) { var height = this.height(); var width = this.width(); if (defined(x)) { this.x1 = x; this.x2 = this.x1 + width; } if (defined(y)) { this.y1 = y; this.y2 = this.y1 + height; } return this; }, wrap: function(targetBox) { this.x1 = Math.min(this.x1, targetBox.x1); this.y1 = Math.min(this.y1, targetBox.y1); this.x2 = Math.max(this.x2, targetBox.x2); this.y2 = Math.max(this.y2, targetBox.y2); return this; }, wrapPoint: function(point) { var arrayPoint = isArray(point); var x = arrayPoint ? point[0] : point.x; var y = arrayPoint ? point[1] : point.y; this.wrap(new Box(x, y, x, y)); return this; }, snapTo: function(targetBox, axis) { if (axis === X || !axis) { this.x1 = targetBox.x1; this.x2 = targetBox.x2; } if (axis === Y || !axis) { this.y1 = targetBox.y1; this.y2 = targetBox.y2; } return this; }, alignTo: function(targetBox, anchor) { var height = this.height(); var width = this.width(); var axis = anchor === TOP || anchor === BOTTOM ? Y : X; var offset = axis === Y ? height : width; if (anchor === CENTER) { var targetCenter = targetBox.center(); var center = this.center(); this.x1 += targetCenter.x - center.x; this.y1 += targetCenter.y - center.y; } else if (anchor === TOP || anchor === LEFT) { this[axis + 1] = targetBox[axis + 1] - offset; } else { this[axis + 1] = targetBox[axis + 2]; } this.x2 = this.x1 + width; this.y2 = this.y1 + height; return this; }, shrink: function(dw, dh) { this.x2 -= dw; this.y2 -= dh; return this; }, expand: function(dw, dh) { this.shrink(-dw, -dh); return this; }, pad: function(padding) { var spacing = getSpacing(padding); this.x1 -= spacing.left; this.x2 += spacing.right; this.y1 -= spacing.top; this.y2 += spacing.bottom; return this; }, unpad: function(padding) { var spacing = getSpacing(padding); spacing.left = -spacing.left; spacing.top = -spacing.top; spacing.right = -spacing.right; spacing.bottom = -spacing.bottom; return this.pad(spacing); }, clone: function() { return new Box(this.x1, this.y1, this.x2, this.y2); }, center: function() { return new Point( this.x1 + this.width() / 2, this.y1 + this.height() / 2 ); }, containsPoint: function(point) { return point.x >= this.x1 && point.x <= this.x2 && point.y >= this.y1 && point.y <= this.y2; }, points: function() { return [ new Point(this.x1, this.y1), new Point(this.x2, this.y1), new Point(this.x2, this.y2), new Point(this.x1, this.y2) ]; }, getHash: function() { return [ this.x1, this.y1, this.x2, this.y2 ].join(","); }, overlaps: function(box) { return !(box.y2 < this.y1 || this.y2 < box.y1 || box.x2 < this.x1 || this.x2 < box.x1); }, rotate: function(rotation) { var width = this.width(); var height = this.height(); var ref = this.center(); var cx = ref.x; var cy = ref.y; var r1 = rotatePoint(0, 0, cx, cy, rotation); var r2 = rotatePoint(width, 0, cx, cy, rotation); var r3 = rotatePoint(width, height, cx, cy, rotation); var r4 = rotatePoint(0, height, cx, cy, rotation); width = Math.max(r1.x, r2.x, r3.x, r4.x) - Math.min(r1.x, r2.x, r3.x, r4.x); height = Math.max(r1.y, r2.y, r3.y, r4.y) - Math.min(r1.y, r2.y, r3.y, r4.y); this.x2 = this.x1 + width; this.y2 = this.y1 + height; return this; }, toRect: function() { return new Rect([ this.x1, this.y1 ], [ this.width(), this.height() ]); }, hasSize: function() { return this.width() !== 0 && this.height() !== 0; }, align: function(targetBox, axis, alignment) { var c1 = axis + 1; var c2 = axis + 2; var sizeFunc = axis === X ? WIDTH : HEIGHT; var size = this[sizeFunc](); if (inArray(alignment, [ LEFT, TOP ])) { this[c1] = targetBox[c1]; this[c2] = this[c1] + size; } else if (inArray(alignment, [ RIGHT, BOTTOM ])) { this[c2] = targetBox[c2]; this[c1] = this[c2] - size; } else if (alignment === CENTER) { this[c1] = targetBox[c1] + (targetBox[sizeFunc]() - size) / 2; this[c2] = this[c1] + size; } } }); function rotatePoint(x, y, cx, cy, angle) { var theta = rad(angle); return new Point( cx + (x - cx) * Math.cos(theta) + (y - cy) * Math.sin(theta), cy - (x - cx) * Math.sin(theta) + (y - cy) * Math.cos(theta) ); } var Ring = Class.extend({ init: function(center, innerRadius, radius, startAngle, angle) { this.center = center; this.innerRadius = innerRadius; this.radius = radius; this.startAngle = startAngle; this.angle = angle; }, clone: function() { return new Ring(this.center, this.innerRadius, this.radius, this.startAngle, this.angle); }, middle: function() { return this.startAngle + this.angle / 2; }, setRadius: function(newRadius, innerRadius) { if (innerRadius) { this.innerRadius = newRadius; } else { this.radius = newRadius; } return this; }, point: function(angle, innerRadius) { var radianAngle = rad(angle); var ax = Math.cos(radianAngle); var ay = Math.sin(radianAngle); var radius = innerRadius ? this.innerRadius : this.radius; var x = round(this.center.x - (ax * radius), COORD_PRECISION); var y = round(this.center.y - (ay * radius), COORD_PRECISION); return new Point(x, y); }, adjacentBox: function(distance, width, height) { var sector = this.clone().expand(distance); var midAndle = sector.middle(); var midPoint = sector.point(midAndle); var hw = width / 2; var hh = height / 2; var sa = Math.sin(rad(midAndle)); var ca = Math.cos(rad(midAndle)); var x = midPoint.x - hw; var y = midPoint.y - hh; if (Math.abs(sa) < 0.9) { x += hw * -ca / Math.abs(ca); } if (Math.abs(ca) < 0.9) { y += hh * -sa / Math.abs(sa); } return new Box(x, y, x + width, y + height); }, containsPoint: function(p) { var center = this.center; var innerRadius = this.innerRadius; var radius = this.radius; var startAngle = this.startAngle; var endAngle = this.startAngle + this.angle; var dx = p.x - center.x; var dy = p.y - center.y; var vector = new Point(dx, dy); var startPoint = this.point(startAngle); var startVector = new Point(startPoint.x - center.x, startPoint.y - center.y); var endPoint = this.point(endAngle); var endVector = new Point(endPoint.x - center.x, endPoint.y - center.y); var dist = round(dx * dx + dy * dy, COORD_PRECISION); return (startVector.equals(vector) || clockwise(startVector, vector)) && !clockwise(endVector, vector) && dist >= innerRadius * innerRadius && dist <= radius * radius; }, getBBox: function() { var this$1 = this; var box = new Box(MAX_VALUE, MAX_VALUE, MIN_VALUE, MIN_VALUE); var startAngle = round(this.startAngle % 360); var endAngle = round((startAngle + this.angle) % 360); var innerRadius = this.innerRadius; var allAngles = [ 0, 90, 180, 270, startAngle, endAngle ].sort(numericComparer); var startAngleIndex = allAngles.indexOf(startAngle); var endAngleIndex = allAngles.indexOf(endAngle); var angles; if (startAngle === endAngle) { angles = allAngles; } else { if (startAngleIndex < endAngleIndex) { angles = allAngles.slice(startAngleIndex, endAngleIndex + 1); } else { angles = [].concat( allAngles.slice(0, endAngleIndex + 1), allAngles.slice(startAngleIndex, allAngles.length) ); } } for (var i = 0; i < angles.length; i++) { var point = this$1.point(angles[i]); box.wrapPoint(point); box.wrapPoint(point, innerRadius); } if (!innerRadius) { box.wrapPoint(this.center); } return box; }, expand: function(value) { this.radius += value; return this; } }); function numericComparer(a, b) { return a - b; } var Sector = Ring.extend({ init: function(center, radius, startAngle, angle) { Ring.fn.init.call(this, center, 0, radius, startAngle, angle); }, expand: function(value) { return Ring.fn.expand.call(this, value); }, clone: function() { return new Sector(this.center, this.radius, this.startAngle, this.angle); }, setRadius: function(newRadius) { this.radius = newRadius; return this; } }); var DIRECTION_ANGLE = 0.001; //any value that will make the endAngle bigger than the start angle will work here. var ShapeBuilder = Class.extend({ createRing: function(sector, options) { var startAngle = sector.startAngle + 180; var endAngle = sector.angle + startAngle; //required in order to avoid reversing the arc direction in cases like 0.000000000000001 + 100 === 100 if (sector.angle > 0 && startAngle === endAngle) { endAngle += DIRECTION_ANGLE; } var center = new geometry.Point(sector.center.x, sector.center.y); var radius = Math.max(sector.radius, 0); var innerRadius = Math.max(sector.innerRadius, 0); var arc = new geometry.Arc(center, { startAngle: startAngle, endAngle: endAngle, radiusX: radius, radiusY: radius }); var path = Path.fromArc(arc, options).close(); if (innerRadius) { arc.radiusX = arc.radiusY = innerRadius; var innerEnd = arc.pointAt(endAngle); path.lineTo(innerEnd.x, innerEnd.y); path.arc(endAngle, startAngle, innerRadius, innerRadius, true); } else { path.lineTo(center.x, center.y); } return path; } }); ShapeBuilder.current = new ShapeBuilder(); var ChartElement = Class.extend({ init: function(options) { this.children = []; this.options = deepExtend({}, this.options, this.initUserOptions(options)); }, initUserOptions: function(options) { return options; }, reflow: function(targetBox) { var children = this.children; var box; for (var i = 0; i < children.length; i++) { var currentChild = children[i]; currentChild.reflow(targetBox); box = box ? box.wrap(currentChild.box) : currentChild.box.clone(); } this.box = box || targetBox; }, destroy: function() { var children = this.children; if (this.animation) { this.animation.destroy(); } for (var i = 0; i < children.length; i++) { children[i].destroy(); } }, getRoot: function() { var parent = this.parent; return parent ? parent.getRoot() : null; }, getSender: function() { var service = this.getService(); if (service) { return service.sender; } }, getService: function() { var element = this; while (element) { if (element.chartService) { return element.chartService; } element = element.parent; } }, translateChildren: function(dx, dy) { var children = this.children; var childrenCount = children.length; for (var i = 0; i < childrenCount; i++) { children[i].box.translate(dx, dy); } }, append: function() { var arguments$1 = arguments; var this$1 = this; for (var i = 0; i < arguments.length; i++) { var item = arguments$1[i]; this$1.children.push(item); item.parent = this$1; } }, renderVisual: function() { if (this.options.visible === false) { return; } this.createVisual(); this.addVisual(); this.renderChildren(); this.createAnimation(); this.renderComplete(); }, addVisual: function() { if (this.visual) { this.visual.chartElement = this; if (this.parent) { this.parent.appendVisual(this.visual); } } }, renderChildren: function() { var children = this.children; var length = children.length; for (var i = 0; i < length; i++) { children[i].renderVisual(); } }, createVisual: function() { this.visual = new Group({ zIndex: this.options.zIndex, visible: valueOrDefault(this.options.visible, true) }); }, createAnimation: function() { if (this.visual && this.options.animation) { this.animation = drawing.Animation.create( this.visual, this.options.animation ); } }, appendVisual: function(childVisual) { if (!childVisual.chartElement) { childVisual.chartElement = this; } if (childVisual.options.noclip) { this.clipRoot().visual.append(childVisual); } else if (defined(childVisual.options.zIndex)) { this.stackRoot().stackVisual(childVisual); } else if (this.isStackRoot) { this.stackVisual(childVisual); } else if (this.visual) { this.visual.append(childVisual); } else { // Allow chart elements without visuals to // pass through child visuals this.parent.appendVisual(childVisual); } }, clipRoot: function() { if (this.parent) { return this.parent.clipRoot(); } return this; }, stackRoot: function() { if (this.parent) { return this.parent.stackRoot(); } return this; }, stackVisual: function(childVisual) { var zIndex = childVisual.options.zIndex || 0; var visuals = this.visual.children; var length = visuals.length; var pos; for (pos = 0; pos < length; pos++) { var sibling = visuals[pos]; var here = valueOrDefault(sibling.options.zIndex, 0); if (here > zIndex) { break; } } this.visual.insert(pos, childVisual); }, traverse: function(callback) { var children = this.children; var length = children.length; for (var i = 0; i < length; i++) { var child = children[i]; callback(child); if (child.traverse) { child.traverse(callback); } } }, closest: function(match) { var element = this; var matched = false; while (element && !matched) { matched = match(element); if (!matched) { element = element.parent; } } if (matched) { return element; } }, renderComplete: function() {}, hasHighlight: function() { var options = (this.options || {}).highlight; return !(!this.createHighlight || (options && options.visible === false)); }, toggleHighlight: function(show) { var this$1 = this; var options = (this.options || {}).highlight || {}; var customVisual = options.visual; var highlight = this._highlight; if (!highlight) { var highlightOptions = { fill: { color: WHITE, opacity: 0.2 }, stroke: { color: WHITE, width: 1, opacity: 0.2 } }; if (customVisual) { highlight = this._highlight = customVisual( $.extend(this.highlightVisualArgs(), { createVisual: function () { return this$1.createHighlight(highlightOptions); }, sender: this.getSender(), series: this.series, dataItem: this.dataItem, category: this.category, value: this.value, percentage: this.percentage, runningTotal: this.runningTotal, total: this.total } )); if (!highlight) { return; } } else { highlight = this._highlight = this.createHighlight(highlightOptions); } if (!defined(highlight.options.zIndex)) { highlight.options.zIndex = valueOrDefault(options.zIndex, this.options.zIndex); } this.appendVisual(highlight); } highlight.visible(show); }, createGradientOverlay: function(element, options, gradientOptions) { var overlay = new Path($.extend({ stroke: { color: "none" }, fill: this.createGradient(gradientOptions), closed: element.options.closed }, options)); overlay.segments.elements(element.segments.elements()); return overlay; }, createGradient: function(options) { if (this.parent) { return this.parent.createGradient(options); } } }); ChartElement.prototype.options = { }; var BoxElement = ChartElement.extend({ init: function(options) { ChartElement.fn.init.call(this, options); this.options.margin = getSpacing(this.options.margin); this.options.padding = getSpacing(this.options.padding); }, reflow: function(targetBox) { var this$1 = this; var options = this.options; var width = options.width; var height = options.height; var shrinkToFit = options.shrinkToFit; var hasSetSize = width && height; var margin = options.margin; var padding = options.padding; var borderWidth = options.border.width; var box; var reflowPaddingBox = function () { this$1.align(targetBox, X, options.align); this$1.align(targetBox, Y, options.vAlign); this$1.paddingBox = box.clone().unpad(margin).unpad(borderWidth); }; var contentBox = targetBox.clone(); if (hasSetSize) { contentBox.x2 = contentBox.x1 + width; contentBox.y2 = contentBox.y1 + height; } if (shrinkToFit) { contentBox.unpad(margin).unpad(borderWidth).unpad(padding); } ChartElement.fn.reflow.call(this, contentBox); if (hasSetSize) { box = this.box = new Box(0, 0, width, height); } else { box = this.box; } if (shrinkToFit && hasSetSize) { reflowPaddingBox(); contentBox = this.contentBox = this.paddingBox.clone().unpad(padding); } else { contentBox = this.contentBox = box.clone(); box.pad(padding).pad(borderWidth).pad(margin); reflowPaddingBox(); } this.translateChildren( box.x1 - contentBox.x1 + margin.left + borderWidth + padding.left, box.y1 - contentBox.y1 + margin.top + borderWidth + padding.top ); var children = this.children; for (var i = 0; i < children.length; i++) { var item = children[i]; item.reflow(item.box); } }, align: function(targetBox, axis, alignment) { this.box.align(targetBox, axis, alignment); }, hasBox: function() { var options = this.options; return options.border.width || options.background; }, createVisual: function() { ChartElement.fn.createVisual.call(this); var options = this.options; if (options.visible && this.hasBox()) { this.visual.append(Path.fromRect( this.paddingBox.toRect(), this.visualStyle() )); } }, visualStyle: function() { var options = this.options; var border = options.border || {}; return { stroke: { width: border.width, color: border.color, opacity: valueOrDefault(border.opacity, options.opacity), dashType: border.dashType }, fill: { color: options.background, opacity: options.opacity }, cursor: options.cursor }; } }); setDefaultOptions(BoxElement, { align: LEFT, vAlign: TOP, margin: {}, padding: {}, border: { color: BLACK, width: 0 }, background: "", shrinkToFit: false, width: 0, height: 0, visible: true }); var ShapeElement = BoxElement.extend({ init: function(options, pointData) { BoxElement.fn.init.call(this, options); this.pointData = pointData; }, getElement: function() { var ref = this; var options = ref.options; var box = ref.paddingBox; var type = options.type; var rotation = options.rotation; var center = box.center(); var halfWidth = box.width() / 2; if (!options.visible || !this.hasBox()) { return null; } var style = this.visualStyle(); var element; if (type === CIRCLE) { element = new drawing.Circle( new Circle([ round(box.x1 + halfWidth, COORD_PRECISION), round(box.y1 + box.height() / 2, COORD_PRECISION) ], halfWidth), style ); } else if (type === TRIANGLE) { element = Path.fromPoints([ [ box.x1 + halfWidth, box.y1 ], [ box.x1, box.y2 ], [ box.x2, box.y2 ] ], style).close(); } else if (type === CROSS) { element = new drawing.MultiPath(style); element.moveTo(box.x1, box.y1).lineTo(box.x2, box.y2); element.moveTo(box.x1, box.y2).lineTo(box.x2, box.y1); } else { element = Path.fromRect(box.toRect(), style); } if (rotation) { element.transform(geometryTransform() .rotate(-rotation, [ center.x, center.y ]) ); } element.options.zIndex = options.zIndex; return element; }, createElement: function() { var this$1 = this; var customVisual = this.options.visual; var pointData = this.pointData || {}; var visual; if (customVisual) { visual = customVisual({ value: pointData.value, dataItem: pointData.dataItem, sender: this.getSender(), series: pointData.series, category: pointData.category, rect: this.paddingBox.toRect(), options: this.visualOptions(), createVisual: function () { return this$1.getElement(); } }); } else { visual = this.getElement(); } return visual; }, visualOptions: function() { var options = this.options; return { background: options.background, border: options.border, margin: options.margin, padding: options.padding, type: options.type, size: options.width, visible: options.visible }; }, createVisual: function() { this.visual = this.createElement(); } }); setDefaultOptions(ShapeElement, { type: CIRCLE, align: CENTER, vAlign: CENTER }); var LINEAR = "linear"; var RADIAL = "radial"; var GRADIENTS = { glass: { type: LINEAR, rotation: 0, stops: [ { offset: 0, color: WHITE, opacity: 0 }, { offset: 0.25, color: WHITE, opacity: 0.3 }, { offset: 1, color: WHITE, opacity: 0 } ] }, sharpBevel: { type: RADIAL, stops: [ { offset: 0, color: WHITE, opacity: 0.55 }, { offset: 0.65, color: WHITE, opacity: 0 }, { offset: 0.95, color: WHITE, opacity: 0.25 } ] }, roundedBevel: { type: RADIAL, stops: [ { offset: 0.33, color: WHITE, opacity: 0.06 }, { offset: 0.83, color: WHITE, opacity: 0.2 }, { offset: 0.95, color: WHITE, opacity: 0 } ] }, roundedGlass: { type: RADIAL, supportVML: false, stops: [ { offset: 0, color: WHITE, opacity: 0 }, { offset: 0.5, color: WHITE, opacity: 0.3 }, { offset: 0.99, color: WHITE, opacity: 0 } ] }, sharpGlass: { type: RADIAL, supportVML: false, stops: [ { offset: 0, color: WHITE, opacity: 0.2 }, { offset: 0.15, color: WHITE, opacity: 0.15 }, { offset: 0.17, color: WHITE, opacity: 0.35 }, { offset: 0.85, color: WHITE, opacity: 0.05 }, { offset: 0.87,