mirror of
https://github.com/chartjs/Chart.js.git
synced 2026-02-01 17:47:09 +00:00
Merge pull request #3256 from simonbrunel/code-cleanup
ESLint and cleanup
This commit is contained in:
commit
7dcbde48f9
@ -46,7 +46,7 @@ rules:
|
||||
block-scoped-var: 0
|
||||
complexity: [2, 6]
|
||||
consistent-return: 0
|
||||
curly: 0
|
||||
curly: [2, all]
|
||||
default-case: 0
|
||||
dot-location: 0
|
||||
dot-notation: 0
|
||||
@ -57,7 +57,6 @@ rules:
|
||||
no-case-declarations: 2
|
||||
no-div-regex: 2
|
||||
no-else-return: 0
|
||||
no-empty-label: 2
|
||||
no-empty-pattern: 2
|
||||
no-eq-null: 2
|
||||
no-eval: 2
|
||||
@ -140,7 +139,7 @@ rules:
|
||||
func-style: 0
|
||||
id-length: 0
|
||||
id-match: 0
|
||||
indent: 0
|
||||
indent: [2, tab]
|
||||
jsx-quotes: 0
|
||||
key-spacing: 0
|
||||
linebreak-style: 0
|
||||
|
||||
@ -34,7 +34,7 @@ To build, run `gulp build`.
|
||||
|
||||
To test, run `gulp test`.
|
||||
|
||||
To test against code standards, run `gulp jshint`.
|
||||
To test against code standards, run `gulp lint`.
|
||||
|
||||
More information on building and testing can be found in [gulpfile.js](gulpfile.js).
|
||||
|
||||
|
||||
@ -34,7 +34,7 @@ New contributions to the library are welcome, but we ask that you please follow
|
||||
|
||||
- Use tabs for indentation, not spaces.
|
||||
- Only change the individual files in `/src`.
|
||||
- Check that your code will pass `jshint` code standards, `gulp jshint` will run this for you.
|
||||
- Check that your code will pass `eslint` code standards, `gulp lint` will run this for you.
|
||||
- Check that your code will pass tests, `gulp test` will run tests for you.
|
||||
- Keep pull requests concise, and document new functionality in the relevant `.md` file.
|
||||
- Consider whether your changes are useful for all users, or if creating a Chart.js plugin would be more appropriate.
|
||||
|
||||
70
gulpfile.js
70
gulpfile.js
@ -1,23 +1,23 @@
|
||||
var gulp = require('gulp'),
|
||||
concat = require('gulp-concat'),
|
||||
file = require('gulp-file'),
|
||||
uglify = require('gulp-uglify'),
|
||||
util = require('gulp-util'),
|
||||
jshint = require('gulp-jshint'),
|
||||
size = require('gulp-size'),
|
||||
connect = require('gulp-connect'),
|
||||
replace = require('gulp-replace'),
|
||||
htmlv = require('gulp-html-validator'),
|
||||
insert = require('gulp-insert'),
|
||||
zip = require('gulp-zip'),
|
||||
exec = require('child_process').exec,
|
||||
package = require('./package.json'),
|
||||
karma = require('gulp-karma'),
|
||||
browserify = require('browserify'),
|
||||
streamify = require('gulp-streamify'),
|
||||
source = require('vinyl-source-stream'),
|
||||
merge = require('merge-stream'),
|
||||
collapse = require('bundle-collapser/plugin');
|
||||
var gulp = require('gulp');
|
||||
var concat = require('gulp-concat');
|
||||
var connect = require('gulp-connect');
|
||||
var eslint = require('gulp-eslint');
|
||||
var file = require('gulp-file');
|
||||
var htmlv = require('gulp-html-validator');
|
||||
var insert = require('gulp-insert');
|
||||
var replace = require('gulp-replace');
|
||||
var size = require('gulp-size');
|
||||
var streamify = require('gulp-streamify');
|
||||
var uglify = require('gulp-uglify');
|
||||
var util = require('gulp-util');
|
||||
var zip = require('gulp-zip');
|
||||
var exec = require('child_process').exec;
|
||||
var karma = require('gulp-karma');
|
||||
var browserify = require('browserify');
|
||||
var source = require('vinyl-source-stream');
|
||||
var merge = require('merge-stream');
|
||||
var collapse = require('bundle-collapser/plugin');
|
||||
var package = require('./package.json');
|
||||
|
||||
var srcDir = './src/';
|
||||
var outDir = './dist/';
|
||||
@ -43,7 +43,7 @@ var testFiles = [
|
||||
// Disable tests which need to be rewritten based on changes introduced by
|
||||
// the following changes: https://github.com/chartjs/Chart.js/pull/2346
|
||||
'!./test/core.layoutService.tests.js',
|
||||
'!./test/defaultConfig.tests.js',
|
||||
'!./test/defaultConfig.tests.js'
|
||||
];
|
||||
|
||||
gulp.task('bower', bowerTask);
|
||||
@ -51,8 +51,8 @@ gulp.task('build', buildTask);
|
||||
gulp.task('package', packageTask);
|
||||
gulp.task('coverage', coverageTask);
|
||||
gulp.task('watch', watchTask);
|
||||
gulp.task('jshint', jshintTask);
|
||||
gulp.task('test', ['jshint', 'validHTML', 'unittest']);
|
||||
gulp.task('lint', lintTask);
|
||||
gulp.task('test', ['lint', 'validHTML', 'unittest']);
|
||||
gulp.task('size', ['library-size', 'module-sizes']);
|
||||
gulp.task('server', serverTask);
|
||||
gulp.task('validHTML', validHTMLTask);
|
||||
@ -130,11 +130,25 @@ function packageTask() {
|
||||
.pipe(gulp.dest(outDir));
|
||||
}
|
||||
|
||||
function jshintTask() {
|
||||
return gulp.src(srcDir + '**/*.js')
|
||||
.pipe(jshint('config.jshintrc'))
|
||||
.pipe(jshint.reporter('jshint-stylish'))
|
||||
.pipe(jshint.reporter('fail'));
|
||||
function lintTask() {
|
||||
var files = [
|
||||
srcDir + '**/*.js',
|
||||
];
|
||||
|
||||
// NOTE(SB) codeclimate has 'complexity' and 'max-statements' eslint rules way too strict
|
||||
// compare to what the current codebase can support, and since it's not straightforward
|
||||
// to fix, let's turn them as warnings and rewrite code later progressively.
|
||||
var options = {
|
||||
rules: {
|
||||
'complexity': [1, 6],
|
||||
'max-statements': [1, 30]
|
||||
}
|
||||
};
|
||||
|
||||
return gulp.src(files)
|
||||
.pipe(eslint(options))
|
||||
.pipe(eslint.format())
|
||||
.pipe(eslint.failAfterError());
|
||||
}
|
||||
|
||||
function validHTMLTask() {
|
||||
|
||||
@ -17,22 +17,19 @@
|
||||
"gulp": "3.9.x",
|
||||
"gulp-concat": "~2.1.x",
|
||||
"gulp-connect": "~2.0.5",
|
||||
"gulp-eslint": "^2.0.0",
|
||||
"gulp-file": "^0.3.0",
|
||||
"gulp-html-validator": "^0.0.2",
|
||||
"gulp-insert": "~0.5.0",
|
||||
"gulp-jshint": "~1.5.1",
|
||||
"gulp-karma": "0.0.4",
|
||||
"gulp-replace": "^0.5.4",
|
||||
"gulp-size": "~0.4.0",
|
||||
"gulp-streamify": "^1.0.2",
|
||||
"gulp-uglify": "~0.2.x",
|
||||
"gulp-umd": "~0.2.0",
|
||||
"gulp-util": "~2.2.x",
|
||||
"gulp-zip": "~3.2.0",
|
||||
"jasmine": "^2.3.2",
|
||||
"jasmine-core": "^2.3.4",
|
||||
"jquery": "^2.1.4",
|
||||
"jshint-stylish": "~2.1.0",
|
||||
"karma": "^0.12.37",
|
||||
"karma-browserify": "^5.0.1",
|
||||
"karma-chrome-launcher": "^0.2.0",
|
||||
@ -41,8 +38,7 @@
|
||||
"karma-jasmine": "^0.3.6",
|
||||
"karma-jasmine-html-reporter": "^0.1.8",
|
||||
"merge-stream": "^1.0.0",
|
||||
"vinyl-source-stream": "^1.1.0",
|
||||
"watchify": "^3.7.0"
|
||||
"vinyl-source-stream": "^1.1.0"
|
||||
},
|
||||
"spm": {
|
||||
"main": "Chart.js"
|
||||
|
||||
@ -142,8 +142,8 @@ module.exports = function(Chart) {
|
||||
var fullBarWidth = categoryWidth / datasetCount;
|
||||
|
||||
if (xScale.ticks.length !== me.chart.data.labels.length) {
|
||||
var perc = xScale.ticks.length / me.chart.data.labels.length;
|
||||
fullBarWidth = fullBarWidth * perc;
|
||||
var perc = xScale.ticks.length / me.chart.data.labels.length;
|
||||
fullBarWidth = fullBarWidth * perc;
|
||||
}
|
||||
|
||||
var barWidth = fullBarWidth * xScale.options.barPercentage;
|
||||
@ -326,7 +326,7 @@ module.exports = function(Chart) {
|
||||
},
|
||||
label: function(tooltipItem, data) {
|
||||
var datasetLabel = data.datasets[tooltipItem.datasetIndex].label || '';
|
||||
return datasetLabel + ': ' + tooltipItem.xLabel;
|
||||
return datasetLabel + ': ' + tooltipItem.xLabel;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -405,8 +405,9 @@ module.exports = function(Chart) {
|
||||
// Find first (starting) corner with fallback to 'bottom'
|
||||
var borders = ['bottom', 'left', 'top', 'right'];
|
||||
var startCorner = borders.indexOf(vm.borderSkipped, 0);
|
||||
if (startCorner === -1)
|
||||
if (startCorner === -1) {
|
||||
startCorner = 0;
|
||||
}
|
||||
|
||||
function cornerAt(index) {
|
||||
return corners[(startCorner + index) % 4];
|
||||
@ -414,8 +415,9 @@ module.exports = function(Chart) {
|
||||
|
||||
// Draw rectangle from 'startCorner'
|
||||
ctx.moveTo.apply(ctx, cornerAt(0));
|
||||
for (var i = 1; i < 4; i++)
|
||||
for (var i = 1; i < 4; i++) {
|
||||
ctx.lineTo.apply(ctx, cornerAt(i));
|
||||
}
|
||||
|
||||
ctx.fill();
|
||||
if (vm.borderWidth) {
|
||||
|
||||
@ -166,8 +166,8 @@ module.exports = function(Chart) {
|
||||
minSize = Math.min(availableWidth / size.width, availableHeight / size.height);
|
||||
offset = {x: (max.x + min.x) * -0.5, y: (max.y + min.y) * -0.5};
|
||||
}
|
||||
chart.borderWidth = me.getMaxBorderWidth(meta.data);
|
||||
|
||||
chart.borderWidth = me.getMaxBorderWidth(meta.data);
|
||||
chart.outerRadius = Math.max((minSize - chart.borderWidth) / 2, 0);
|
||||
chart.innerRadius = Math.max(cutoutPercentage ? (chart.outerRadius / 100) * (cutoutPercentage) : 1, 0);
|
||||
chart.radiusLength = (chart.outerRadius - chart.innerRadius) / chart.getVisibleDatasetCount();
|
||||
@ -268,23 +268,23 @@ module.exports = function(Chart) {
|
||||
return 0;
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
//gets the max border or hover width to properly scale pie charts
|
||||
getMaxBorderWidth: function (elements) {
|
||||
var max = 0,
|
||||
getMaxBorderWidth: function (elements) {
|
||||
var max = 0,
|
||||
index = this.index,
|
||||
length = elements.length,
|
||||
borderWidth,
|
||||
hoverWidth;
|
||||
|
||||
for (var i = 0; i < length; i++) {
|
||||
borderWidth = elements[i]._model ? elements[i]._model.borderWidth : 0;
|
||||
hoverWidth = elements[i]._chart ? elements[i]._chart.config.data.datasets[index].hoverBorderWidth : 0;
|
||||
|
||||
max = borderWidth > max ? borderWidth : max;
|
||||
max = hoverWidth > max ? hoverWidth : max;
|
||||
}
|
||||
return max;
|
||||
}
|
||||
for (var i = 0; i < length; i++) {
|
||||
borderWidth = elements[i]._model ? elements[i]._model.borderWidth : 0;
|
||||
hoverWidth = elements[i]._chart ? elements[i]._chart.config.data.datasets[index].hoverBorderWidth : 0;
|
||||
|
||||
max = borderWidth > max ? borderWidth : max;
|
||||
max = hoverWidth > max ? hoverWidth : max;
|
||||
}
|
||||
return max;
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
@ -250,20 +250,23 @@ module.exports = function(Chart) {
|
||||
var me = this;
|
||||
var meta = me.getMeta();
|
||||
var area = me.chart.chartArea;
|
||||
var points = (meta.data || []);
|
||||
var i, ilen, point, model, controlPoints;
|
||||
|
||||
// Only consider points that are drawn in case the spanGaps option is used
|
||||
var points = (meta.data || []);
|
||||
if (meta.dataset._model.spanGaps) points = points.filter(function(pt) { return !pt._model.skip; });
|
||||
var i, ilen, point, model, controlPoints;
|
||||
if (meta.dataset._model.spanGaps) {
|
||||
points = points.filter(function(pt) {
|
||||
return !pt._model.skip;
|
||||
});
|
||||
}
|
||||
|
||||
function capControlPoint(pt, min, max) {
|
||||
return Math.max(Math.min(pt, max), min);
|
||||
}
|
||||
|
||||
if (meta.dataset._model.cubicInterpolationMode == 'monotone') {
|
||||
if (meta.dataset._model.cubicInterpolationMode === 'monotone') {
|
||||
helpers.splineCurveMonotone(points);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
for (i = 0, ilen = points.length; i < ilen; ++i) {
|
||||
point = points[i];
|
||||
model = point._model;
|
||||
@ -289,7 +292,6 @@ module.exports = function(Chart) {
|
||||
model.controlPointNextY = capControlPoint(model.controlPointNextY, area.top, area.bottom);
|
||||
}
|
||||
}
|
||||
|
||||
},
|
||||
|
||||
draw: function(ease) {
|
||||
|
||||
@ -461,7 +461,7 @@ module.exports = function(Chart) {
|
||||
}, me);
|
||||
|
||||
return elementsArray;
|
||||
},
|
||||
},
|
||||
|
||||
getElementsAtEventForMode: function(e, mode) {
|
||||
var me = this;
|
||||
@ -472,8 +472,8 @@ module.exports = function(Chart) {
|
||||
return me.getElementsAtEvent(e);
|
||||
case 'dataset':
|
||||
return me.getDatasetAtEvent(e);
|
||||
case 'x-axis':
|
||||
return me.getElementsAtXAxis(e);
|
||||
case 'x-axis':
|
||||
return me.getElementsAtXAxis(e);
|
||||
default:
|
||||
return e;
|
||||
}
|
||||
@ -499,14 +499,14 @@ module.exports = function(Chart) {
|
||||
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
|
||||
};
|
||||
type: null,
|
||||
data: [],
|
||||
dataset: null,
|
||||
controller: null,
|
||||
hidden: null, // See isDatasetVisible() comment
|
||||
xAxisID: null,
|
||||
yAxisID: null
|
||||
};
|
||||
}
|
||||
|
||||
return meta;
|
||||
@ -591,7 +591,7 @@ module.exports = function(Chart) {
|
||||
break;
|
||||
case 'label':
|
||||
case 'dataset':
|
||||
case 'x-axis':
|
||||
case 'x-axis':
|
||||
// elements = elements;
|
||||
break;
|
||||
default:
|
||||
|
||||
@ -7,7 +7,7 @@ module.exports = function(Chart) {
|
||||
|
||||
// Base class for all dataset controllers (line, bar, etc)
|
||||
Chart.DatasetController = function(chart, datasetIndex) {
|
||||
this.initialize.call(this, chart, datasetIndex);
|
||||
this.initialize(chart, datasetIndex);
|
||||
};
|
||||
|
||||
helpers.extend(Chart.DatasetController.prototype, {
|
||||
@ -157,9 +157,8 @@ module.exports = function(Chart) {
|
||||
model.borderColor = custom.hoverBorderColor ? custom.hoverBorderColor : valueOrDefault(dataset.hoverBorderColor, index, getHoverColor(model.borderColor));
|
||||
model.borderWidth = custom.hoverBorderWidth ? custom.hoverBorderWidth : valueOrDefault(dataset.hoverBorderWidth, index, model.borderWidth);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
|
||||
});
|
||||
|
||||
Chart.DatasetController.extend = helpers.inherits;
|
||||
};
|
||||
@ -2,103 +2,103 @@
|
||||
|
||||
module.exports = function(Chart) {
|
||||
|
||||
var helpers = Chart.helpers;
|
||||
var helpers = Chart.helpers;
|
||||
|
||||
Chart.elements = {};
|
||||
Chart.elements = {};
|
||||
|
||||
Chart.Element = function(configuration) {
|
||||
helpers.extend(this, configuration);
|
||||
this.initialize.apply(this, arguments);
|
||||
};
|
||||
Chart.Element = function(configuration) {
|
||||
helpers.extend(this, configuration);
|
||||
this.initialize.apply(this, arguments);
|
||||
};
|
||||
|
||||
helpers.extend(Chart.Element.prototype, {
|
||||
helpers.extend(Chart.Element.prototype, {
|
||||
|
||||
initialize: function() {
|
||||
this.hidden = false;
|
||||
},
|
||||
initialize: function() {
|
||||
this.hidden = false;
|
||||
},
|
||||
|
||||
pivot: function() {
|
||||
var me = this;
|
||||
if (!me._view) {
|
||||
me._view = helpers.clone(me._model);
|
||||
}
|
||||
me._start = helpers.clone(me._view);
|
||||
return me;
|
||||
},
|
||||
pivot: function() {
|
||||
var me = this;
|
||||
if (!me._view) {
|
||||
me._view = helpers.clone(me._model);
|
||||
}
|
||||
me._start = helpers.clone(me._view);
|
||||
return me;
|
||||
},
|
||||
|
||||
transition: function(ease) {
|
||||
var me = this;
|
||||
|
||||
if (!me._view) {
|
||||
me._view = helpers.clone(me._model);
|
||||
}
|
||||
transition: function(ease) {
|
||||
var me = this;
|
||||
|
||||
// No animation -> No Transition
|
||||
if (ease === 1) {
|
||||
me._view = me._model;
|
||||
me._start = null;
|
||||
return me;
|
||||
}
|
||||
if (!me._view) {
|
||||
me._view = helpers.clone(me._model);
|
||||
}
|
||||
|
||||
if (!me._start) {
|
||||
me.pivot();
|
||||
}
|
||||
// No animation -> No Transition
|
||||
if (ease === 1) {
|
||||
me._view = me._model;
|
||||
me._start = null;
|
||||
return me;
|
||||
}
|
||||
|
||||
helpers.each(me._model, function(value, key) {
|
||||
if (!me._start) {
|
||||
me.pivot();
|
||||
}
|
||||
|
||||
if (key[0] === '_') {
|
||||
// Only non-underscored properties
|
||||
}
|
||||
helpers.each(me._model, function(value, key) {
|
||||
|
||||
// Init if doesn't exist
|
||||
else if (!me._view.hasOwnProperty(key)) {
|
||||
if (typeof value === 'number' && !isNaN(me._view[key])) {
|
||||
me._view[key] = value * ease;
|
||||
} else {
|
||||
me._view[key] = value;
|
||||
}
|
||||
}
|
||||
if (key[0] === '_') {
|
||||
// Only non-underscored properties
|
||||
}
|
||||
|
||||
// No unnecessary computations
|
||||
else if (value === me._view[key]) {
|
||||
// It's the same! Woohoo!
|
||||
}
|
||||
// Init if doesn't exist
|
||||
else if (!me._view.hasOwnProperty(key)) {
|
||||
if (typeof value === 'number' && !isNaN(me._view[key])) {
|
||||
me._view[key] = value * ease;
|
||||
} else {
|
||||
me._view[key] = value;
|
||||
}
|
||||
}
|
||||
|
||||
// Color transitions if possible
|
||||
else if (typeof value === 'string') {
|
||||
try {
|
||||
var color = helpers.color(me._model[key]).mix(helpers.color(me._start[key]), ease);
|
||||
me._view[key] = color.rgbString();
|
||||
} catch (err) {
|
||||
me._view[key] = value;
|
||||
}
|
||||
}
|
||||
// Number transitions
|
||||
else if (typeof value === 'number') {
|
||||
var startVal = me._start[key] !== undefined && isNaN(me._start[key]) === false ? me._start[key] : 0;
|
||||
me._view[key] = ((me._model[key] - startVal) * ease) + startVal;
|
||||
}
|
||||
// Everything else
|
||||
else {
|
||||
me._view[key] = value;
|
||||
}
|
||||
}, me);
|
||||
// No unnecessary computations
|
||||
else if (value === me._view[key]) {
|
||||
// It's the same! Woohoo!
|
||||
}
|
||||
|
||||
return me;
|
||||
},
|
||||
// Color transitions if possible
|
||||
else if (typeof value === 'string') {
|
||||
try {
|
||||
var color = helpers.color(me._model[key]).mix(helpers.color(me._start[key]), ease);
|
||||
me._view[key] = color.rgbString();
|
||||
} catch (err) {
|
||||
me._view[key] = value;
|
||||
}
|
||||
}
|
||||
// Number transitions
|
||||
else if (typeof value === 'number') {
|
||||
var startVal = me._start[key] !== undefined && isNaN(me._start[key]) === false ? me._start[key] : 0;
|
||||
me._view[key] = ((me._model[key] - startVal) * ease) + startVal;
|
||||
}
|
||||
// Everything else
|
||||
else {
|
||||
me._view[key] = value;
|
||||
}
|
||||
}, me);
|
||||
|
||||
tooltipPosition: function() {
|
||||
return {
|
||||
x: this._model.x,
|
||||
y: this._model.y
|
||||
};
|
||||
},
|
||||
return me;
|
||||
},
|
||||
|
||||
hasValue: function() {
|
||||
return helpers.isNumber(this._model.x) && helpers.isNumber(this._model.y);
|
||||
}
|
||||
});
|
||||
tooltipPosition: function() {
|
||||
return {
|
||||
x: this._model.x,
|
||||
y: this._model.y
|
||||
};
|
||||
},
|
||||
|
||||
Chart.Element.extend = helpers.inherits;
|
||||
hasValue: function() {
|
||||
return helpers.isNumber(this._model.x) && helpers.isNumber(this._model.y);
|
||||
}
|
||||
});
|
||||
|
||||
Chart.Element.extend = helpers.inherits;
|
||||
|
||||
};
|
||||
|
||||
@ -238,7 +238,7 @@ module.exports = function(Chart) {
|
||||
return function() {
|
||||
return id++;
|
||||
};
|
||||
})();
|
||||
}());
|
||||
//-- Math methods
|
||||
helpers.isNumber = function(n) {
|
||||
return !isNaN(parseFloat(n)) && isFinite(n);
|
||||
@ -358,16 +358,25 @@ module.exports = function(Chart) {
|
||||
var i, pointBefore, pointCurrent, pointAfter;
|
||||
for (i = 0; i < pointsLen; ++i) {
|
||||
pointCurrent = pointsWithTangents[i];
|
||||
if (pointCurrent.model.skip) continue;
|
||||
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) {
|
||||
pointCurrent.deltaK = (pointAfter.model.y - pointCurrent.model.y) / (pointAfter.model.x - pointCurrent.model.x);
|
||||
}
|
||||
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;
|
||||
|
||||
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
|
||||
@ -375,16 +384,22 @@ module.exports = function(Chart) {
|
||||
for (i = 0; i < pointsLen - 1; ++i) {
|
||||
pointCurrent = pointsWithTangents[i];
|
||||
pointAfter = pointsWithTangents[i + 1];
|
||||
if (pointCurrent.model.skip || pointAfter.model.skip) continue;
|
||||
if (helpers.almostEquals(pointCurrent.deltaK, 0, this.EPSILON))
|
||||
{
|
||||
if (pointCurrent.model.skip || pointAfter.model.skip) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (helpers.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;
|
||||
if (squaredMagnitude <= 9) {
|
||||
continue;
|
||||
}
|
||||
|
||||
tauK = 3 / Math.sqrt(squaredMagnitude);
|
||||
pointCurrent.mK = alphaK * tauK * pointCurrent.deltaK;
|
||||
pointAfter.mK = betaK * tauK * pointCurrent.deltaK;
|
||||
@ -394,7 +409,10 @@ module.exports = function(Chart) {
|
||||
var deltaX;
|
||||
for (i = 0; i < pointsLen; ++i) {
|
||||
pointCurrent = pointsWithTangents[i];
|
||||
if (pointCurrent.model.skip) continue;
|
||||
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) {
|
||||
@ -413,7 +431,6 @@ module.exports = function(Chart) {
|
||||
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.previousItem = function(collection, index, loop) {
|
||||
@ -660,7 +677,7 @@ module.exports = function(Chart) {
|
||||
function(callback) {
|
||||
return window.setTimeout(callback, 1000 / 60);
|
||||
};
|
||||
})();
|
||||
}());
|
||||
helpers.cancelAnimFrame = (function() {
|
||||
return window.cancelAnimationFrame ||
|
||||
window.webkitCancelAnimationFrame ||
|
||||
@ -670,7 +687,7 @@ module.exports = function(Chart) {
|
||||
function(callback) {
|
||||
return window.clearTimeout(callback, 1000 / 60);
|
||||
};
|
||||
})();
|
||||
}());
|
||||
//-- DOM methods
|
||||
helpers.getRelativePosition = function(evt, chart) {
|
||||
var mouseX, mouseY;
|
||||
@ -751,7 +768,7 @@ module.exports = function(Chart) {
|
||||
if (typeof(styleValue) === 'string') {
|
||||
valueInPixels = parseInt(styleValue, 10);
|
||||
|
||||
if (styleValue.indexOf('%') != -1) {
|
||||
if (styleValue.indexOf('%') !== -1) {
|
||||
// percentage * size in dimension
|
||||
valueInPixels = valueInPixels / 100 * node.parentNode[parentProperty];
|
||||
}
|
||||
@ -802,15 +819,17 @@ module.exports = function(Chart) {
|
||||
};
|
||||
helpers.getMaximumWidth = function(domNode) {
|
||||
var container = domNode.parentNode;
|
||||
var padding = parseInt(helpers.getStyle(container, 'padding-left')) + parseInt(helpers.getStyle(container, 'padding-right'));
|
||||
var w = container.clientWidth - padding;
|
||||
var paddingLeft = parseInt(helpers.getStyle(container, 'padding-left'), 10);
|
||||
var paddingRight = parseInt(helpers.getStyle(container, 'padding-right'), 10);
|
||||
var w = container.clientWidth - paddingLeft - paddingRight;
|
||||
var cw = helpers.getConstraintWidth(domNode);
|
||||
return isNaN(cw)? w : Math.min(w, cw);
|
||||
};
|
||||
helpers.getMaximumHeight = function(domNode) {
|
||||
var container = domNode.parentNode;
|
||||
var padding = parseInt(helpers.getStyle(container, 'padding-top')) + parseInt(helpers.getStyle(container, 'padding-bottom'));
|
||||
var h = container.clientHeight - padding;
|
||||
var paddingTop = parseInt(helpers.getStyle(container, 'padding-top'), 10);
|
||||
var paddingBottom = parseInt(helpers.getStyle(container, 'padding-bottom'), 10);
|
||||
var h = container.clientHeight - paddingTop - paddingBottom;
|
||||
var ch = helpers.getConstraintHeight(domNode);
|
||||
return isNaN(ch)? h : Math.min(h, ch);
|
||||
};
|
||||
@ -964,7 +983,7 @@ module.exports = function(Chart) {
|
||||
|
||||
(hiddenIframe.contentWindow || hiddenIframe).onresize = function() {
|
||||
if (callback) {
|
||||
callback();
|
||||
return callback();
|
||||
}
|
||||
};
|
||||
};
|
||||
@ -985,7 +1004,7 @@ module.exports = function(Chart) {
|
||||
helpers.arrayEquals = function(a0, a1) {
|
||||
var i, ilen, v0, v1;
|
||||
|
||||
if (!a0 || !a1 || a0.length != a1.length) {
|
||||
if (!a0 || !a1 || a0.length !== a1.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -997,7 +1016,7 @@ module.exports = function(Chart) {
|
||||
if (!helpers.arrayEquals(v0, v1)) {
|
||||
return false;
|
||||
}
|
||||
} else if (v0 != v1) {
|
||||
} else if (v0 !== v1) {
|
||||
// NOTE: two different object instances will never be equal: {x:20} != {x:20}
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -341,12 +341,10 @@ module.exports = function(Chart) {
|
||||
|
||||
// Draw pointStyle as legend symbol
|
||||
Chart.canvasHelpers.drawPoint(ctx, legendItem.pointStyle, radius, centerX, centerY);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
// Draw box as legend symbol
|
||||
if (!isLineWidthZero)
|
||||
{
|
||||
ctx.strokeRect(x, y, boxWidth, fontSize);
|
||||
if (!isLineWidthZero) {
|
||||
ctx.strokeRect(x, y, boxWidth, fontSize);
|
||||
}
|
||||
ctx.fillRect(x, y, boxWidth, fontSize);
|
||||
}
|
||||
|
||||
@ -170,12 +170,12 @@ module.exports = function(Chart) {
|
||||
var me = this;
|
||||
// Convert ticks to strings
|
||||
me.ticks = me.ticks.map(function(numericalTick, index, ticks) {
|
||||
if (me.options.ticks.userCallback) {
|
||||
return me.options.ticks.userCallback(numericalTick, index, ticks);
|
||||
}
|
||||
return me.options.ticks.callback(numericalTick, index, ticks);
|
||||
},
|
||||
me);
|
||||
if (me.options.ticks.userCallback) {
|
||||
return me.options.ticks.userCallback(numericalTick, index, ticks);
|
||||
}
|
||||
return me.options.ticks.callback(numericalTick, index, ticks);
|
||||
},
|
||||
me);
|
||||
},
|
||||
afterTickToLabelConversion: function() {
|
||||
helpers.callCallback(this.options.afterTickToLabelConversion, [this]);
|
||||
|
||||
@ -2,92 +2,92 @@
|
||||
|
||||
module.exports = function(Chart) {
|
||||
|
||||
var helpers = Chart.helpers,
|
||||
globalOpts = Chart.defaults.global;
|
||||
var helpers = Chart.helpers,
|
||||
globalOpts = Chart.defaults.global;
|
||||
|
||||
globalOpts.elements.arc = {
|
||||
backgroundColor: globalOpts.defaultColor,
|
||||
borderColor: "#fff",
|
||||
borderWidth: 2
|
||||
};
|
||||
globalOpts.elements.arc = {
|
||||
backgroundColor: globalOpts.defaultColor,
|
||||
borderColor: "#fff",
|
||||
borderWidth: 2
|
||||
};
|
||||
|
||||
Chart.elements.Arc = Chart.Element.extend({
|
||||
inLabelRange: function(mouseX) {
|
||||
var vm = this._view;
|
||||
Chart.elements.Arc = Chart.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));
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
},
|
||||
inRange: function(chartX, chartY) {
|
||||
var vm = this._view;
|
||||
if (vm) {
|
||||
return (Math.pow(mouseX - vm.x, 2) < Math.pow(vm.radius + vm.hoverRadius, 2));
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
},
|
||||
inRange: function(chartX, chartY) {
|
||||
var vm = this._view;
|
||||
|
||||
if (vm) {
|
||||
var pointRelativePosition = helpers.getAngleFromPoint(vm, {
|
||||
x: chartX,
|
||||
y: chartY
|
||||
}),
|
||||
angle = pointRelativePosition.angle,
|
||||
distance = pointRelativePosition.distance;
|
||||
if (vm) {
|
||||
var pointRelativePosition = helpers.getAngleFromPoint(vm, {
|
||||
x: chartX,
|
||||
y: chartY
|
||||
}),
|
||||
angle = pointRelativePosition.angle,
|
||||
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;
|
||||
}
|
||||
//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),
|
||||
withinRadius = (distance >= vm.innerRadius && distance <= vm.outerRadius);
|
||||
//Check if within the range of the open/close angle
|
||||
var betweenAngles = (angle >= startAngle && angle <= endAngle),
|
||||
withinRadius = (distance >= vm.innerRadius && distance <= vm.outerRadius);
|
||||
|
||||
return (betweenAngles && withinRadius);
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
},
|
||||
tooltipPosition: function() {
|
||||
var vm = this._view;
|
||||
return (betweenAngles && withinRadius);
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
},
|
||||
tooltipPosition: function() {
|
||||
var vm = this._view;
|
||||
|
||||
var centreAngle = vm.startAngle + ((vm.endAngle - vm.startAngle) / 2),
|
||||
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 centreAngle = vm.startAngle + ((vm.endAngle - vm.startAngle) / 2),
|
||||
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,
|
||||
vm = this._view,
|
||||
sA = vm.startAngle,
|
||||
eA = vm.endAngle;
|
||||
var ctx = this._chart.ctx,
|
||||
vm = this._view,
|
||||
sA = vm.startAngle,
|
||||
eA = vm.endAngle;
|
||||
|
||||
ctx.beginPath();
|
||||
ctx.beginPath();
|
||||
|
||||
ctx.arc(vm.x, vm.y, vm.outerRadius, sA, eA);
|
||||
ctx.arc(vm.x, vm.y, vm.innerRadius, eA, sA, true);
|
||||
ctx.arc(vm.x, vm.y, vm.outerRadius, sA, eA);
|
||||
ctx.arc(vm.x, vm.y, vm.innerRadius, eA, sA, true);
|
||||
|
||||
ctx.closePath();
|
||||
ctx.strokeStyle = vm.borderColor;
|
||||
ctx.lineWidth = vm.borderWidth;
|
||||
ctx.closePath();
|
||||
ctx.strokeStyle = vm.borderColor;
|
||||
ctx.lineWidth = vm.borderWidth;
|
||||
|
||||
ctx.fillStyle = vm.backgroundColor;
|
||||
ctx.fillStyle = vm.backgroundColor;
|
||||
|
||||
ctx.fill();
|
||||
ctx.lineJoin = 'bevel';
|
||||
ctx.fill();
|
||||
ctx.lineJoin = 'bevel';
|
||||
|
||||
if (vm.borderWidth) {
|
||||
ctx.stroke();
|
||||
}
|
||||
}
|
||||
});
|
||||
if (vm.borderWidth) {
|
||||
ctx.stroke();
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
@ -48,8 +48,9 @@ module.exports = function(Chart) {
|
||||
// Find first (starting) corner with fallback to 'bottom'
|
||||
var borders = ['bottom', 'left', 'top', 'right'];
|
||||
var startCorner = borders.indexOf(vm.borderSkipped, 0);
|
||||
if (startCorner === -1)
|
||||
if (startCorner === -1) {
|
||||
startCorner = 0;
|
||||
}
|
||||
|
||||
function cornerAt(index) {
|
||||
return corners[(startCorner + index) % 4];
|
||||
@ -57,8 +58,9 @@ module.exports = function(Chart) {
|
||||
|
||||
// Draw rectangle from 'startCorner'
|
||||
ctx.moveTo.apply(ctx, cornerAt(0));
|
||||
for (var i = 1; i < 4; i++)
|
||||
for (var i = 1; i < 4; i++) {
|
||||
ctx.lineTo.apply(ctx, cornerAt(i));
|
||||
}
|
||||
|
||||
ctx.fill();
|
||||
if (vm.borderWidth) {
|
||||
|
||||
@ -70,9 +70,9 @@ module.exports = function(Chart) {
|
||||
var valueWidth = innerWidth / offsetAmt;
|
||||
var widthOffset = (valueWidth * (index - me.minIndex)) + me.paddingLeft;
|
||||
|
||||
if (me.options.gridLines.offsetGridLines && includeOffset || me.maxIndex === me.minIndex && includeOffset) {
|
||||
if (me.options.gridLines.offsetGridLines && includeOffset || me.maxIndex === me.minIndex && includeOffset) {
|
||||
widthOffset += (valueWidth / 2);
|
||||
}
|
||||
}
|
||||
|
||||
return me.left + Math.round(widthOffset);
|
||||
} else {
|
||||
|
||||
@ -243,7 +243,7 @@ module.exports = function(Chart) {
|
||||
range = helpers.log10(me.end) - helpers.log10(start);
|
||||
innerDimension = me.height - (paddingTop + paddingBottom);
|
||||
pixel = (me.bottom - paddingBottom) - (innerDimension / range * (helpers.log10(newVal) - helpers.log10(start)));
|
||||
}
|
||||
}
|
||||
}
|
||||
return pixel;
|
||||
},
|
||||
|
||||
@ -78,9 +78,9 @@ module.exports = function(Chart) {
|
||||
getLabelMoment: function(datasetIndex, index) {
|
||||
if (datasetIndex === null || index === null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (typeof this.labelMoments[datasetIndex] != 'undefined') {
|
||||
}
|
||||
|
||||
if (typeof this.labelMoments[datasetIndex] !== 'undefined') {
|
||||
return this.labelMoments[datasetIndex][index];
|
||||
}
|
||||
|
||||
|
||||
@ -230,10 +230,10 @@ describe('Test the layout service', function() {
|
||||
expect(chart.scales.xScale1.right).toBeCloseToPixel(512);
|
||||
expect(chart.scales.xScale1.top).toBeCloseToPixel(484);
|
||||
|
||||
expect(chart.scales.xScale2.bottom).toBeCloseToPixel(28);
|
||||
expect(chart.scales.xScale2.bottom).toBeCloseToPixel(60);
|
||||
expect(chart.scales.xScale2.left).toBeCloseToPixel(0);
|
||||
expect(chart.scales.xScale2.right).toBeCloseToPixel(512);
|
||||
expect(chart.scales.xScale2.top).toBeCloseToPixel(0);
|
||||
expect(chart.scales.xScale2.top).toBeCloseToPixel(32);
|
||||
|
||||
// Is yScale at the right spot
|
||||
expect(chart.scales.yScale.bottom).toBeCloseToPixel(484);
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user