mirror of
https://github.com/chartjs/Chart.js.git
synced 2024-10-07 12:49:07 +02:00
7dc71d009b
Add a new `offset` option to scales to add extra space at edges and remove the `includeOffset` argument from `getPixelForValue()` and `getPixelForTick()`. The bar controller now automatically calculates the bar width to avoid overlaps. When `offsetGridLines` is true, grid lines move to the left by one half of the tick interval, and labels don't move.
799 lines
20 KiB
JavaScript
799 lines
20 KiB
JavaScript
describe('Core helper tests', function() {
|
|
|
|
var helpers;
|
|
|
|
beforeAll(function() {
|
|
helpers = window.Chart.helpers;
|
|
});
|
|
|
|
it('should extend an object', function() {
|
|
var original = {
|
|
myProp1: 'abc',
|
|
myProp2: 56
|
|
};
|
|
|
|
var extension = {
|
|
myProp3: [2, 5, 6],
|
|
myProp2: 0
|
|
};
|
|
|
|
helpers.extend(original, extension);
|
|
|
|
expect(original).toEqual({
|
|
myProp1: 'abc',
|
|
myProp2: 0,
|
|
myProp3: [2, 5, 6],
|
|
});
|
|
});
|
|
|
|
it('should merge a normal config without scales', function() {
|
|
var baseConfig = {
|
|
valueProp: 5,
|
|
arrayProp: [1, 2, 3, 4, 5, 6],
|
|
objectProp: {
|
|
prop1: 'abc',
|
|
prop2: 56
|
|
}
|
|
};
|
|
|
|
var toMerge = {
|
|
valueProp2: null,
|
|
arrayProp: ['a', 'c'],
|
|
objectProp: {
|
|
prop1: 'c',
|
|
prop3: 'prop3'
|
|
}
|
|
};
|
|
|
|
var merged = helpers.configMerge(baseConfig, toMerge);
|
|
expect(merged).toEqual({
|
|
valueProp: 5,
|
|
valueProp2: null,
|
|
arrayProp: ['a', 'c'],
|
|
objectProp: {
|
|
prop1: 'c',
|
|
prop2: 56,
|
|
prop3: 'prop3'
|
|
}
|
|
});
|
|
});
|
|
|
|
it('should merge scale configs', function() {
|
|
var baseConfig = {
|
|
scales: {
|
|
prop1: {
|
|
abc: 123,
|
|
def: '456'
|
|
},
|
|
prop2: 777,
|
|
yAxes: [{
|
|
type: 'linear',
|
|
}, {
|
|
type: 'log'
|
|
}]
|
|
}
|
|
};
|
|
|
|
var toMerge = {
|
|
scales: {
|
|
prop1: {
|
|
def: 'bbb',
|
|
ghi: 78
|
|
},
|
|
prop2: null,
|
|
yAxes: [{
|
|
type: 'linear',
|
|
axisProp: 456
|
|
}, {
|
|
// pulls in linear default config since axis type changes
|
|
type: 'linear',
|
|
position: 'right'
|
|
}, {
|
|
// Pulls in linear default config since axis not in base
|
|
type: 'linear'
|
|
}]
|
|
}
|
|
};
|
|
|
|
var merged = helpers.configMerge(baseConfig, toMerge);
|
|
expect(merged).toEqual({
|
|
scales: {
|
|
prop1: {
|
|
abc: 123,
|
|
def: 'bbb',
|
|
ghi: 78
|
|
},
|
|
prop2: null,
|
|
yAxes: [{
|
|
type: 'linear',
|
|
axisProp: 456
|
|
}, {
|
|
display: true,
|
|
|
|
gridLines: {
|
|
color: 'rgba(0, 0, 0, 0.1)',
|
|
drawBorder: true,
|
|
drawOnChartArea: true,
|
|
drawTicks: true, // draw ticks extending towards the label
|
|
tickMarkLength: 10,
|
|
lineWidth: 1,
|
|
offsetGridLines: false,
|
|
display: true,
|
|
zeroLineColor: 'rgba(0,0,0,0.25)',
|
|
zeroLineWidth: 1,
|
|
zeroLineBorderDash: [],
|
|
zeroLineBorderDashOffset: 0.0,
|
|
borderDash: [],
|
|
borderDashOffset: 0.0
|
|
},
|
|
position: 'right',
|
|
offset: false,
|
|
scaleLabel: {
|
|
display: false,
|
|
labelString: '',
|
|
lineHeight: 1.2
|
|
},
|
|
ticks: {
|
|
beginAtZero: false,
|
|
minRotation: 0,
|
|
maxRotation: 50,
|
|
mirror: false,
|
|
padding: 0,
|
|
reverse: false,
|
|
display: true,
|
|
callback: merged.scales.yAxes[1].ticks.callback, // make it nicer, then check explicitly below
|
|
autoSkip: true,
|
|
autoSkipPadding: 0,
|
|
labelOffset: 0,
|
|
minor: {},
|
|
major: {},
|
|
},
|
|
type: 'linear'
|
|
}, {
|
|
display: true,
|
|
|
|
gridLines: {
|
|
color: 'rgba(0, 0, 0, 0.1)',
|
|
drawBorder: true,
|
|
drawOnChartArea: true,
|
|
drawTicks: true, // draw ticks extending towards the label,
|
|
tickMarkLength: 10,
|
|
lineWidth: 1,
|
|
offsetGridLines: false,
|
|
display: true,
|
|
zeroLineColor: 'rgba(0,0,0,0.25)',
|
|
zeroLineWidth: 1,
|
|
zeroLineBorderDash: [],
|
|
zeroLineBorderDashOffset: 0.0,
|
|
borderDash: [],
|
|
borderDashOffset: 0.0
|
|
},
|
|
position: 'left',
|
|
offset: false,
|
|
scaleLabel: {
|
|
display: false,
|
|
labelString: '',
|
|
lineHeight: 1.2
|
|
},
|
|
ticks: {
|
|
beginAtZero: false,
|
|
minRotation: 0,
|
|
maxRotation: 50,
|
|
mirror: false,
|
|
padding: 0,
|
|
reverse: false,
|
|
display: true,
|
|
callback: merged.scales.yAxes[2].ticks.callback, // make it nicer, then check explicitly below
|
|
autoSkip: true,
|
|
autoSkipPadding: 0,
|
|
labelOffset: 0,
|
|
minor: {},
|
|
major: {},
|
|
},
|
|
type: 'linear'
|
|
}]
|
|
}
|
|
});
|
|
|
|
// Are these actually functions
|
|
expect(merged.scales.yAxes[1].ticks.callback).toEqual(jasmine.any(Function));
|
|
expect(merged.scales.yAxes[2].ticks.callback).toEqual(jasmine.any(Function));
|
|
});
|
|
|
|
it('should filter an array', function() {
|
|
var data = [-10, 0, 6, 0, 7];
|
|
var callback = function(item) {
|
|
return item > 2;
|
|
};
|
|
expect(helpers.where(data, callback)).toEqual([6, 7]);
|
|
expect(helpers.findNextWhere(data, callback)).toEqual(6);
|
|
expect(helpers.findNextWhere(data, callback, 2)).toBe(7);
|
|
expect(helpers.findNextWhere(data, callback, 4)).toBe(undefined);
|
|
expect(helpers.findPreviousWhere(data, callback)).toBe(7);
|
|
expect(helpers.findPreviousWhere(data, callback, 3)).toBe(6);
|
|
expect(helpers.findPreviousWhere(data, callback, 0)).toBe(undefined);
|
|
});
|
|
|
|
it('should get the correct sign', function() {
|
|
expect(helpers.sign(0)).toBe(0);
|
|
expect(helpers.sign(10)).toBe(1);
|
|
expect(helpers.sign(-5)).toBe(-1);
|
|
});
|
|
|
|
it('should do a log10 operation', function() {
|
|
expect(helpers.log10(0)).toBe(-Infinity);
|
|
expect(helpers.log10(1)).toBe(0);
|
|
expect(helpers.log10(1000)).toBeCloseTo(3, 1e-9);
|
|
});
|
|
|
|
it('should correctly determine if two numbers are essentially equal', function() {
|
|
expect(helpers.almostEquals(0, Number.EPSILON, 2 * Number.EPSILON)).toBe(true);
|
|
expect(helpers.almostEquals(1, 1.1, 0.0001)).toBe(false);
|
|
expect(helpers.almostEquals(1e30, 1e30 + Number.EPSILON, 0)).toBe(false);
|
|
expect(helpers.almostEquals(1e30, 1e30 + Number.EPSILON, 2 * Number.EPSILON)).toBe(true);
|
|
});
|
|
|
|
it('should correctly determine if a numbers are essentially whole', function() {
|
|
expect(helpers.almostWhole(0.99999, 0.0001)).toBe(true);
|
|
expect(helpers.almostWhole(0.9, 0.0001)).toBe(false);
|
|
});
|
|
|
|
it('should generate integer ids', function() {
|
|
var uid = helpers.uid();
|
|
expect(uid).toEqual(jasmine.any(Number));
|
|
expect(helpers.uid()).toBe(uid + 1);
|
|
expect(helpers.uid()).toBe(uid + 2);
|
|
expect(helpers.uid()).toBe(uid + 3);
|
|
});
|
|
|
|
it('should detect a number', function() {
|
|
expect(helpers.isNumber(123)).toBe(true);
|
|
expect(helpers.isNumber('123')).toBe(true);
|
|
expect(helpers.isNumber(null)).toBe(false);
|
|
expect(helpers.isNumber(NaN)).toBe(false);
|
|
expect(helpers.isNumber(undefined)).toBe(false);
|
|
expect(helpers.isNumber('cbc')).toBe(false);
|
|
});
|
|
|
|
it('should convert between radians and degrees', function() {
|
|
expect(helpers.toRadians(180)).toBe(Math.PI);
|
|
expect(helpers.toRadians(90)).toBe(0.5 * Math.PI);
|
|
expect(helpers.toDegrees(Math.PI)).toBe(180);
|
|
expect(helpers.toDegrees(Math.PI * 3 / 2)).toBe(270);
|
|
});
|
|
|
|
it('should get an angle from a point', function() {
|
|
var center = {
|
|
x: 0,
|
|
y: 0
|
|
};
|
|
|
|
expect(helpers.getAngleFromPoint(center, {
|
|
x: 0,
|
|
y: 10
|
|
})).toEqual({
|
|
angle: Math.PI / 2,
|
|
distance: 10,
|
|
});
|
|
|
|
expect(helpers.getAngleFromPoint(center, {
|
|
x: Math.sqrt(2),
|
|
y: Math.sqrt(2)
|
|
})).toEqual({
|
|
angle: Math.PI / 4,
|
|
distance: 2
|
|
});
|
|
|
|
expect(helpers.getAngleFromPoint(center, {
|
|
x: -1.0 * Math.sqrt(2),
|
|
y: -1.0 * Math.sqrt(2)
|
|
})).toEqual({
|
|
angle: Math.PI * 1.25,
|
|
distance: 2
|
|
});
|
|
});
|
|
|
|
it('should spline curves', function() {
|
|
expect(helpers.splineCurve({
|
|
x: 0,
|
|
y: 0
|
|
}, {
|
|
x: 1,
|
|
y: 1
|
|
}, {
|
|
x: 2,
|
|
y: 0
|
|
}, 0)).toEqual({
|
|
previous: {
|
|
x: 1,
|
|
y: 1,
|
|
},
|
|
next: {
|
|
x: 1,
|
|
y: 1,
|
|
}
|
|
});
|
|
|
|
expect(helpers.splineCurve({
|
|
x: 0,
|
|
y: 0
|
|
}, {
|
|
x: 1,
|
|
y: 1
|
|
}, {
|
|
x: 2,
|
|
y: 0
|
|
}, 1)).toEqual({
|
|
previous: {
|
|
x: 0,
|
|
y: 1,
|
|
},
|
|
next: {
|
|
x: 2,
|
|
y: 1,
|
|
}
|
|
});
|
|
});
|
|
|
|
it('should spline curves with monotone cubic interpolation', function() {
|
|
var dataPoints = [
|
|
{_model: {x: 0, y: 0, skip: false}},
|
|
{_model: {x: 3, y: 6, skip: false}},
|
|
{_model: {x: 9, y: 6, skip: false}},
|
|
{_model: {x: 12, y: 60, skip: false}},
|
|
{_model: {x: 15, y: 60, skip: false}},
|
|
{_model: {x: 18, y: 120, skip: false}},
|
|
{_model: {x: null, y: null, skip: true}},
|
|
{_model: {x: 21, y: 180, skip: false}},
|
|
{_model: {x: 24, y: 120, skip: false}},
|
|
{_model: {x: 27, y: 125, skip: false}},
|
|
{_model: {x: 30, y: 105, skip: false}},
|
|
{_model: {x: 33, y: 110, skip: false}},
|
|
{_model: {x: 33, y: 110, skip: false}},
|
|
{_model: {x: 36, y: 170, skip: false}}
|
|
];
|
|
helpers.splineCurveMonotone(dataPoints);
|
|
expect(dataPoints).toEqual([{
|
|
_model: {
|
|
x: 0,
|
|
y: 0,
|
|
skip: false,
|
|
controlPointNextX: 1,
|
|
controlPointNextY: 2
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 3,
|
|
y: 6,
|
|
skip: false,
|
|
controlPointPreviousX: 2,
|
|
controlPointPreviousY: 6,
|
|
controlPointNextX: 5,
|
|
controlPointNextY: 6
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 9,
|
|
y: 6,
|
|
skip: false,
|
|
controlPointPreviousX: 7,
|
|
controlPointPreviousY: 6,
|
|
controlPointNextX: 10,
|
|
controlPointNextY: 6
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 12,
|
|
y: 60,
|
|
skip: false,
|
|
controlPointPreviousX: 11,
|
|
controlPointPreviousY: 60,
|
|
controlPointNextX: 13,
|
|
controlPointNextY: 60
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 15,
|
|
y: 60,
|
|
skip: false,
|
|
controlPointPreviousX: 14,
|
|
controlPointPreviousY: 60,
|
|
controlPointNextX: 16,
|
|
controlPointNextY: 60
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 18,
|
|
y: 120,
|
|
skip: false,
|
|
controlPointPreviousX: 17,
|
|
controlPointPreviousY: 100
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: null,
|
|
y: null,
|
|
skip: true
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 21,
|
|
y: 180,
|
|
skip: false,
|
|
controlPointNextX: 22,
|
|
controlPointNextY: 160
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 24,
|
|
y: 120,
|
|
skip: false,
|
|
controlPointPreviousX: 23,
|
|
controlPointPreviousY: 120,
|
|
controlPointNextX: 25,
|
|
controlPointNextY: 120
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 27,
|
|
y: 125,
|
|
skip: false,
|
|
controlPointPreviousX: 26,
|
|
controlPointPreviousY: 125,
|
|
controlPointNextX: 28,
|
|
controlPointNextY: 125
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 30,
|
|
y: 105,
|
|
skip: false,
|
|
controlPointPreviousX: 29,
|
|
controlPointPreviousY: 105,
|
|
controlPointNextX: 31,
|
|
controlPointNextY: 105
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 33,
|
|
y: 110,
|
|
skip: false,
|
|
controlPointPreviousX: 32,
|
|
controlPointPreviousY: 110,
|
|
controlPointNextX: 33,
|
|
controlPointNextY: 110
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 33,
|
|
y: 110,
|
|
skip: false,
|
|
controlPointPreviousX: 33,
|
|
controlPointPreviousY: 110,
|
|
controlPointNextX: 34,
|
|
controlPointNextY: 110
|
|
}
|
|
},
|
|
{
|
|
_model: {
|
|
x: 36,
|
|
y: 170,
|
|
skip: false,
|
|
controlPointPreviousX: 35,
|
|
controlPointPreviousY: 150
|
|
}
|
|
}]);
|
|
});
|
|
|
|
it('should get the next or previous item in an array', function() {
|
|
var testData = [0, 1, 2];
|
|
|
|
expect(helpers.nextItem(testData, 0, false)).toEqual(1);
|
|
expect(helpers.nextItem(testData, 2, false)).toEqual(2);
|
|
expect(helpers.nextItem(testData, 2, true)).toEqual(0);
|
|
expect(helpers.nextItem(testData, 1, true)).toEqual(2);
|
|
expect(helpers.nextItem(testData, -1, false)).toEqual(0);
|
|
|
|
expect(helpers.previousItem(testData, 0, false)).toEqual(0);
|
|
expect(helpers.previousItem(testData, 0, true)).toEqual(2);
|
|
expect(helpers.previousItem(testData, 2, false)).toEqual(1);
|
|
expect(helpers.previousItem(testData, 1, true)).toEqual(0);
|
|
});
|
|
|
|
it('should return the width of the longest text in an Array and 2D Array', function() {
|
|
var context = window.createMockContext();
|
|
var font = "normal 12px 'Helvetica Neue', 'Helvetica', 'Arial', sans-serif";
|
|
var arrayOfThings1D = ['FooBar', 'Bar'];
|
|
var arrayOfThings2D = [['FooBar_1', 'Bar_2'], 'Foo_1'];
|
|
|
|
|
|
// Regardless 'FooBar' is the longest label it should return (characters * 10)
|
|
expect(helpers.longestText(context, font, arrayOfThings1D, {})).toEqual(60);
|
|
expect(helpers.longestText(context, font, arrayOfThings2D, {})).toEqual(80);
|
|
// We check to make sure we made the right calls to the canvas.
|
|
expect(context.getCalls()).toEqual([{
|
|
name: 'measureText',
|
|
args: ['FooBar']
|
|
}, {
|
|
name: 'measureText',
|
|
args: ['Bar']
|
|
}, {
|
|
name: 'measureText',
|
|
args: ['FooBar_1']
|
|
}, {
|
|
name: 'measureText',
|
|
args: ['Bar_2']
|
|
}, {
|
|
name: 'measureText',
|
|
args: ['Foo_1']
|
|
}]);
|
|
});
|
|
|
|
it('compare text with current longest and update', function() {
|
|
var context = window.createMockContext();
|
|
var data = {};
|
|
var gc = [];
|
|
var longest = 70;
|
|
|
|
expect(helpers.measureText(context, data, gc, longest, 'foobar')).toEqual(70);
|
|
expect(helpers.measureText(context, data, gc, longest, 'foobar_')).toEqual(70);
|
|
expect(helpers.measureText(context, data, gc, longest, 'foobar_1')).toEqual(80);
|
|
// We check to make sure we made the right calls to the canvas.
|
|
expect(context.getCalls()).toEqual([{
|
|
name: 'measureText',
|
|
args: ['foobar']
|
|
}, {
|
|
name: 'measureText',
|
|
args: ['foobar_']
|
|
}, {
|
|
name: 'measureText',
|
|
args: ['foobar_1']
|
|
}]);
|
|
});
|
|
|
|
it('count look at all the labels and return maximum number of lines', function() {
|
|
window.createMockContext();
|
|
var arrayOfThings1 = ['Foo', 'Bar'];
|
|
var arrayOfThings2 = [['Foo', 'Bar'], 'Foo'];
|
|
var arrayOfThings3 = [['Foo', 'Bar', 'Boo'], ['Foo', 'Bar'], 'Foo'];
|
|
|
|
expect(helpers.numberOfLabelLines(arrayOfThings1)).toEqual(1);
|
|
expect(helpers.numberOfLabelLines(arrayOfThings2)).toEqual(2);
|
|
expect(helpers.numberOfLabelLines(arrayOfThings3)).toEqual(3);
|
|
});
|
|
|
|
it ('should get the maximum width and height for a node', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create the div we want to get the max size for
|
|
var innerDiv = document.createElement('div');
|
|
div.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumWidth(innerDiv)).toBe(200);
|
|
expect(helpers.getMaximumHeight(innerDiv)).toBe(300);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum width of a node that has a max-width style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create the div we want to get the max size for and set a max-width style
|
|
var innerDiv = document.createElement('div');
|
|
innerDiv.style.maxWidth = '150px';
|
|
div.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumWidth(innerDiv)).toBe(150);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum height of a node that has a max-height style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create the div we want to get the max size for and set a max-height style
|
|
var innerDiv = document.createElement('div');
|
|
innerDiv.style.maxHeight = '150px';
|
|
div.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumHeight(innerDiv)).toBe(150);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum width of a node when the parent has a max-width style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create an inner wrapper around our div we want to size and give that a max-width style
|
|
var parentDiv = document.createElement('div');
|
|
parentDiv.style.maxWidth = '150px';
|
|
div.appendChild(parentDiv);
|
|
|
|
// Create the div we want to get the max size for
|
|
var innerDiv = document.createElement('div');
|
|
parentDiv.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumWidth(innerDiv)).toBe(150);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum height of a node when the parent has a max-height style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create an inner wrapper around our div we want to size and give that a max-height style
|
|
var parentDiv = document.createElement('div');
|
|
parentDiv.style.maxHeight = '150px';
|
|
div.appendChild(parentDiv);
|
|
|
|
// Create the div we want to get the max size for
|
|
var innerDiv = document.createElement('div');
|
|
innerDiv.style.height = '300px'; // make it large
|
|
parentDiv.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumHeight(innerDiv)).toBe(150);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum width of a node that has a percentage max-width style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create the div we want to get the max size for and set a max-width style
|
|
var innerDiv = document.createElement('div');
|
|
innerDiv.style.maxWidth = '50%';
|
|
div.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumWidth(innerDiv)).toBe(100);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum height of a node that has a percentage max-height style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create the div we want to get the max size for and set a max-height style
|
|
var innerDiv = document.createElement('div');
|
|
innerDiv.style.maxHeight = '50%';
|
|
div.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumHeight(innerDiv)).toBe(150);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum width of a node when the parent has a percentage max-width style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create an inner wrapper around our div we want to size and give that a max-width style
|
|
var parentDiv = document.createElement('div');
|
|
parentDiv.style.maxWidth = '50%';
|
|
div.appendChild(parentDiv);
|
|
|
|
// Create the div we want to get the max size for
|
|
var innerDiv = document.createElement('div');
|
|
parentDiv.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumWidth(innerDiv)).toBe(100);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
it ('should get the maximum height of a node when the parent has a percentage max-height style', function() {
|
|
// Create div with fixed size as a test bed
|
|
var div = document.createElement('div');
|
|
div.style.width = '200px';
|
|
div.style.height = '300px';
|
|
|
|
document.body.appendChild(div);
|
|
|
|
// Create an inner wrapper around our div we want to size and give that a max-height style
|
|
var parentDiv = document.createElement('div');
|
|
parentDiv.style.maxHeight = '50%';
|
|
div.appendChild(parentDiv);
|
|
|
|
var innerDiv = document.createElement('div');
|
|
innerDiv.style.height = '300px'; // make it large
|
|
parentDiv.appendChild(innerDiv);
|
|
|
|
expect(helpers.getMaximumHeight(innerDiv)).toBe(150);
|
|
|
|
document.body.removeChild(div);
|
|
});
|
|
|
|
describe('Color helper', function() {
|
|
function isColorInstance(obj) {
|
|
return typeof obj === 'object' && obj.hasOwnProperty('values') && obj.values.hasOwnProperty('rgb');
|
|
}
|
|
|
|
it('should return a color when called with a color', function() {
|
|
expect(isColorInstance(helpers.color('rgb(1, 2, 3)'))).toBe(true);
|
|
});
|
|
|
|
it('should return a color when called with a CanvasGradient instance', function() {
|
|
var context = document.createElement('canvas').getContext('2d');
|
|
var gradient = context.createLinearGradient(0, 1, 2, 3);
|
|
|
|
expect(isColorInstance(helpers.color(gradient))).toBe(true);
|
|
});
|
|
});
|
|
|
|
describe('Background hover color helper', function() {
|
|
it('should return a CanvasPattern when called with a CanvasPattern', function(done) {
|
|
var dots = new Image();
|
|
dots.src = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAA4AAAAOCAMAAAAolt3jAAAAD1BMVEUAAAD///////////////+PQt5oAAAABXRSTlMAHlFhZsfk/BEAAAAqSURBVHgBY2BgZGJmYmSAAUYWEIDzmcBcJhiXGcxlRpPFrhdmMiqgvX0AcGIBEUAo6UAAAAAASUVORK5CYII=';
|
|
dots.onload = function() {
|
|
var chartContext = document.createElement('canvas').getContext('2d');
|
|
var patternCanvas = document.createElement('canvas');
|
|
var patternContext = patternCanvas.getContext('2d');
|
|
var pattern = patternContext.createPattern(dots, 'repeat');
|
|
patternContext.fillStyle = pattern;
|
|
|
|
var backgroundColor = helpers.getHoverColor(chartContext.createPattern(patternCanvas, 'repeat'));
|
|
|
|
expect(backgroundColor instanceof CanvasPattern).toBe(true);
|
|
|
|
done();
|
|
};
|
|
});
|
|
|
|
it('should return a modified version of color when called with a color', function() {
|
|
var originalColorRGB = 'rgb(70, 191, 189)';
|
|
|
|
expect(helpers.getHoverColor('#46BFBD')).not.toEqual(originalColorRGB);
|
|
});
|
|
});
|
|
});
|