[animate] bars, with changes in number of them
This commit is contained in:
parent
8452e909bb
commit
dc1fa4d373
197
dist/frappe-charts.esm.js
vendored
197
dist/frappe-charts.esm.js
vendored
@ -234,7 +234,7 @@ function getStringWidth(string, charWidth) {
|
|||||||
|
|
||||||
function getBarHeightAndYAttr(yTop, zeroLine) {
|
function getBarHeightAndYAttr(yTop, zeroLine) {
|
||||||
let height, y;
|
let height, y;
|
||||||
if (yTop < zeroLine) {
|
if (yTop <= zeroLine) {
|
||||||
height = zeroLine - yTop;
|
height = zeroLine - yTop;
|
||||||
y = yTop;
|
y = yTop;
|
||||||
} else {
|
} else {
|
||||||
@ -286,13 +286,14 @@ const REPLACE_ALL_NEW_DUR = 250;
|
|||||||
const STD_EASING = 'easein';
|
const STD_EASING = 'easein';
|
||||||
|
|
||||||
function translate(unit, oldCoord, newCoord, duration) {
|
function translate(unit, oldCoord, newCoord, duration) {
|
||||||
|
let old = typeof oldCoord === 'string' ? oldCoord : oldCoord.join(', ');
|
||||||
return [
|
return [
|
||||||
unit,
|
unit,
|
||||||
{transform: newCoord.join(', ')},
|
{transform: newCoord.join(', ')},
|
||||||
duration,
|
duration,
|
||||||
STD_EASING,
|
STD_EASING,
|
||||||
"translate",
|
"translate",
|
||||||
{transform: oldCoord.join(', ')}
|
{transform: old}
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -319,6 +320,42 @@ function animateRegion(rectGroup, newY1, newY2, oldY2) {
|
|||||||
return [rectAnim, groupAnim];
|
return [rectAnim, groupAnim];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function animateBar(bar, x, yTop, width, index=0, meta={}) {
|
||||||
|
let [height, y] = getBarHeightAndYAttr(yTop, meta.zeroLine);
|
||||||
|
if(bar.nodeName !== 'rect') {
|
||||||
|
let rect = bar.childNodes[0];
|
||||||
|
let rectAnim = [
|
||||||
|
rect,
|
||||||
|
{width: width, height: height},
|
||||||
|
UNIT_ANIM_DUR,
|
||||||
|
STD_EASING
|
||||||
|
];
|
||||||
|
|
||||||
|
let old = bar.getAttribute("transform").split("(")[1].slice(0, -1);
|
||||||
|
let groupAnim = translate(bar, old, [x, y], MARKER_LINE_ANIM_DUR);
|
||||||
|
return [rectAnim, groupAnim];
|
||||||
|
} else {
|
||||||
|
return [[bar, {width: width, height: height, x: x, y: y}, UNIT_ANIM_DUR, STD_EASING]];
|
||||||
|
}
|
||||||
|
// bar.animate({height: args.newHeight, y: yTop}, UNIT_ANIM_DUR, mina.easein);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
|
||||||
|
<filter id="glow" x="-10%" y="-10%" width="120%" height="120%">
|
||||||
|
<feGaussianBlur stdDeviation="0.5 0.5" result="glow"></feGaussianBlur>
|
||||||
|
<feMerge>
|
||||||
|
<feMergeNode in="glow"></feMergeNode>
|
||||||
|
<feMergeNode in="glow"></feMergeNode>
|
||||||
|
<feMergeNode in="glow"></feMergeNode>
|
||||||
|
</feMerge>
|
||||||
|
</filter>
|
||||||
|
|
||||||
|
filter: url(#glow);
|
||||||
|
fill: #fff;
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
const AXIS_TICK_LENGTH = 6;
|
const AXIS_TICK_LENGTH = 6;
|
||||||
const LABEL_MARGIN = 4;
|
const LABEL_MARGIN = 4;
|
||||||
const FONT_SIZE = 10;
|
const FONT_SIZE = 10;
|
||||||
@ -383,13 +420,7 @@ function makeSVGGroup(parent, className, transform='') {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function wrapInSVGGroup(elements, className='') {
|
|
||||||
let g = createSVG('g', {
|
|
||||||
className: className
|
|
||||||
});
|
|
||||||
elements.forEach(e => g.appendChild(e));
|
|
||||||
return g;
|
|
||||||
}
|
|
||||||
|
|
||||||
function makePath(pathStr, className='', stroke='none', fill='none') {
|
function makePath(pathStr, className='', stroke='none', fill='none') {
|
||||||
return createSVG('path', {
|
return createSVG('path', {
|
||||||
@ -627,31 +658,40 @@ function yRegion(y1, y2, width, label) {
|
|||||||
function datasetBar(x, yTop, width, color, label='', index=0, offset=0, meta={}) {
|
function datasetBar(x, yTop, width, color, label='', index=0, offset=0, meta={}) {
|
||||||
let [height, y] = getBarHeightAndYAttr(yTop, meta.zeroLine);
|
let [height, y] = getBarHeightAndYAttr(yTop, meta.zeroLine);
|
||||||
// console.log(yTop, meta.zeroLine, y, offset);
|
// console.log(yTop, meta.zeroLine, y, offset);
|
||||||
|
y -= offset;
|
||||||
|
|
||||||
let rect = createSVG('rect', {
|
let rect = createSVG('rect', {
|
||||||
className: `bar mini`,
|
className: `bar mini`,
|
||||||
style: `fill: ${color}`,
|
style: `fill: ${color}`,
|
||||||
'data-point-index': index,
|
'data-point-index': index,
|
||||||
x: x - meta.barsWidth/2,
|
x: x,
|
||||||
y: y - offset,
|
y: y,
|
||||||
width: width,
|
width: width,
|
||||||
height: height || meta.minHeight
|
height: height || meta.minHeight // TODO: correct y for positive min height
|
||||||
});
|
});
|
||||||
|
|
||||||
if(!label && !label.length) {
|
if(!label && !label.length) {
|
||||||
return rect;
|
return rect;
|
||||||
} else {
|
} else {
|
||||||
|
rect.setAttribute('y', 0);
|
||||||
|
rect.setAttribute('x', 0);
|
||||||
let text = createSVG('text', {
|
let text = createSVG('text', {
|
||||||
className: 'data-point-value',
|
className: 'data-point-value',
|
||||||
x: x,
|
x: width/2,
|
||||||
y: y - offset,
|
y: 0,
|
||||||
dy: (FONT_SIZE / 2 * -1) + 'px',
|
dy: (FONT_SIZE / 2 * -1) + 'px',
|
||||||
'font-size': FONT_SIZE + 'px',
|
'font-size': FONT_SIZE + 'px',
|
||||||
'text-anchor': 'middle',
|
'text-anchor': 'middle',
|
||||||
innerHTML: label
|
innerHTML: label
|
||||||
});
|
});
|
||||||
|
|
||||||
return wrapInSVGGroup([rect, text]);
|
let group = createSVG('g', {
|
||||||
|
transform: `translate(${x}, ${y})`
|
||||||
|
});
|
||||||
|
group.appendChild(rect);
|
||||||
|
group.appendChild(text);
|
||||||
|
|
||||||
|
return group;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1227,11 +1267,11 @@ function zeroDataPrep(realData) {
|
|||||||
let zeroArray = new Array(datasetLength).fill(0);
|
let zeroArray = new Array(datasetLength).fill(0);
|
||||||
|
|
||||||
let zeroData = {
|
let zeroData = {
|
||||||
labels: realData.labels,
|
labels: realData.labels.slice(0, -1),
|
||||||
datasets: realData.datasets.map(d => {
|
datasets: realData.datasets.map(d => {
|
||||||
return {
|
return {
|
||||||
name: '',
|
name: '',
|
||||||
values: zeroArray,
|
values: zeroArray.slice(0, -1),
|
||||||
chartType: d.chartType
|
chartType: d.chartType
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
@ -1261,14 +1301,12 @@ class ChartComponent$1 {
|
|||||||
|
|
||||||
getData,
|
getData,
|
||||||
makeElements,
|
makeElements,
|
||||||
postMake,
|
|
||||||
animateElements
|
animateElements
|
||||||
}) {
|
}) {
|
||||||
this.layerTransform = layerTransform;
|
this.layerTransform = layerTransform;
|
||||||
this.constants = constants;
|
this.constants = constants;
|
||||||
|
|
||||||
this.makeElements = makeElements;
|
this.makeElements = makeElements;
|
||||||
this.postMake = postMake;
|
|
||||||
this.getData = getData;
|
this.getData = getData;
|
||||||
|
|
||||||
this.animateElements = animateElements;
|
this.animateElements = animateElements;
|
||||||
@ -1291,9 +1329,7 @@ class ChartComponent$1 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
make() {
|
make() {
|
||||||
this.preMake && this.preMake();
|
|
||||||
this.render(this.data);
|
this.render(this.data);
|
||||||
this.postMake && this.postMake();
|
|
||||||
this.oldData = this.data;
|
this.oldData = this.data;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1331,8 +1367,8 @@ let componentConfigs = {
|
|||||||
},
|
},
|
||||||
|
|
||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
let newPos = newData.positions;
|
let newPos = newData.positions;
|
||||||
let newLabels = newData.labels;
|
let newLabels = newData.labels;
|
||||||
let oldPos = this.oldData.positions;
|
let oldPos = this.oldData.positions;
|
||||||
let oldLabels = this.oldData.labels;
|
let oldLabels = this.oldData.labels;
|
||||||
|
|
||||||
@ -1362,8 +1398,8 @@ let componentConfigs = {
|
|||||||
},
|
},
|
||||||
|
|
||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
let newPos = newData.positions;
|
let newPos = newData.positions;
|
||||||
let newLabels = newData.labels;
|
let newLabels = newData.labels;
|
||||||
let oldPos = this.oldData.positions;
|
let oldPos = this.oldData.positions;
|
||||||
let oldLabels = this.oldData.labels;
|
let oldLabels = this.oldData.labels;
|
||||||
|
|
||||||
@ -1394,8 +1430,8 @@ let componentConfigs = {
|
|||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
||||||
|
|
||||||
let newPos = newData.map(d => d.position);
|
let newPos = newData.map(d => d.position);
|
||||||
let newLabels = newData.map(d => d.label);
|
let newLabels = newData.map(d => d.label);
|
||||||
|
|
||||||
let oldPos = this.oldData.map(d => d.position);
|
let oldPos = this.oldData.map(d => d.position);
|
||||||
let oldLabels = this.oldData.map(d => d.label);
|
let oldLabels = this.oldData.map(d => d.label);
|
||||||
@ -1426,9 +1462,9 @@ let componentConfigs = {
|
|||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
||||||
|
|
||||||
let newPos = newData.map(d => d.end);
|
let newPos = newData.map(d => d.end);
|
||||||
let newLabels = newData.map(d => d.label);
|
let newLabels = newData.map(d => d.label);
|
||||||
let newStarts = newData.map(d => d.start);
|
let newStarts = newData.map(d => d.start);
|
||||||
|
|
||||||
let oldPos = this.oldData.map(d => d.end);
|
let oldPos = this.oldData.map(d => d.end);
|
||||||
let oldLabels = this.oldData.map(d => d.label);
|
let oldLabels = this.oldData.map(d => d.label);
|
||||||
@ -1459,57 +1495,67 @@ let componentConfigs = {
|
|||||||
makeElements(data) {
|
makeElements(data) {
|
||||||
let c = this.constants;
|
let c = this.constants;
|
||||||
return data.yPositions.map((y, j) => {
|
return data.yPositions.map((y, j) => {
|
||||||
// console.log(data.cumulativeYPos, data.cumulativeYPos[j]);
|
|
||||||
return datasetBar(
|
return datasetBar(
|
||||||
data.xPositions[j],
|
data.xPositions[j],
|
||||||
y,
|
y,
|
||||||
c.barWidth,
|
data.barWidth,
|
||||||
c.color,
|
c.color,
|
||||||
(c.valuesOverPoints ? (c.stacked ? data.cumulativeYs[j] : data.values[j]) : ''),
|
(c.valuesOverPoints ? (c.stacked ? data.cumulativeYs[j] : data.values[j]) : ''),
|
||||||
j,
|
j,
|
||||||
y - (c.stacked ? data.cumulativeYPos[j] : y),
|
y - (c.stacked ? data.cumulativeYPos[j] : y),
|
||||||
{
|
{
|
||||||
zeroLine: c.zeroLine,
|
zeroLine: data.zeroLine,
|
||||||
barsWidth: c.barsWidth,
|
barsWidth: data.barsWidth,
|
||||||
minHeight: c.minHeight
|
minHeight: c.minHeight
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
postMake() {
|
|
||||||
if((!this.constants.stacked)) {
|
|
||||||
this.layer.setAttribute('transform',
|
|
||||||
`translate(${this.constants.width * this.constants.index}, 0)`);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
// [this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
let c = this.constants;
|
||||||
|
|
||||||
// let newPos = newData.map(d => d.end);
|
let newXPos = newData.xPositions;
|
||||||
// let newLabels = newData.map(d => d.label);
|
let newYPos = newData.yPositions;
|
||||||
// let newStarts = newData.map(d => d.start);
|
let newCYPos = newData.cumulativeYPos;
|
||||||
|
let newValues = newData.values;
|
||||||
|
let newCYs = newData.cumulativeYs;
|
||||||
|
|
||||||
// let oldPos = this.oldData.map(d => d.end);
|
|
||||||
// let oldLabels = this.oldData.map(d => d.label);
|
|
||||||
// let oldStarts = this.oldData.map(d => d.start);
|
|
||||||
|
|
||||||
// this.render(oldPos.map((pos, i) => {
|
let oldXPos = this.oldData.xPositions;
|
||||||
// return {
|
let oldYPos = this.oldData.yPositions;
|
||||||
// start: oldStarts[i],
|
let oldCYPos = this.oldData.cumulativeYPos;
|
||||||
// end: oldPos[i],
|
let oldValues = this.oldData.values;
|
||||||
// label: newLabels[i]
|
let oldCYs = this.oldData.cumulativeYs;
|
||||||
// }
|
|
||||||
// }));
|
|
||||||
|
|
||||||
// let animateElements = [];
|
[oldXPos, newXPos] = equilizeNoOfElements(oldXPos, newXPos);
|
||||||
|
[oldYPos, newYPos] = equilizeNoOfElements(oldYPos, newYPos);
|
||||||
|
[oldCYPos, newCYPos] = equilizeNoOfElements(oldCYPos, newCYPos);
|
||||||
|
[oldValues, newValues] = equilizeNoOfElements(oldValues, newValues);
|
||||||
|
[oldCYs, newCYs] = equilizeNoOfElements(oldCYs, newCYs);
|
||||||
|
|
||||||
// this.store.map((rectGroup, i) => {
|
this.render({
|
||||||
// animateElements = animateElements.concat(animateRegion(
|
xPositions: oldXPos,
|
||||||
// rectGroup, newStarts[i], newPos[i], oldPos[i]
|
yPositions: oldYPos,
|
||||||
// ));
|
cumulativeYPos: oldCYPos,
|
||||||
// });
|
|
||||||
|
|
||||||
// return animateElements;
|
values: newValues,
|
||||||
|
cumulativeYs: newCYs,
|
||||||
|
|
||||||
|
zeroLine: this.oldData.zeroLine,
|
||||||
|
barsWidth: this.oldData.barsWidth,
|
||||||
|
barWidth: this.oldData.barWidth,
|
||||||
|
});
|
||||||
|
|
||||||
|
let animateElements = [];
|
||||||
|
|
||||||
|
this.store.map((bar, i) => {
|
||||||
|
animateElements = animateElements.concat(animateBar(
|
||||||
|
bar, newXPos[i], newYPos[i], newData.barWidth, c.index,
|
||||||
|
{zeroLine: newData.zeroLine}
|
||||||
|
));
|
||||||
|
});
|
||||||
|
|
||||||
|
return animateElements;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -1519,7 +1565,8 @@ let componentConfigs = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
function getComponent(name, constants, getData) {
|
function getComponent(name, constants, getData) {
|
||||||
let config = componentConfigs[name];
|
let keys = Object.keys(componentConfigs).filter(k => name.includes(k));
|
||||||
|
let config = componentConfigs[keys[0]];
|
||||||
Object.assign(config, {
|
Object.assign(config, {
|
||||||
constants: constants,
|
constants: constants,
|
||||||
getData: getData
|
getData: getData
|
||||||
@ -1891,9 +1938,6 @@ class AxisChart extends BaseChart {
|
|||||||
}
|
}
|
||||||
|
|
||||||
initComponents() {
|
initComponents() {
|
||||||
let s = this.state;
|
|
||||||
// console.log('this.state', Object.assign({}, this.state));
|
|
||||||
// console.log('this.state', this.state);
|
|
||||||
this.componentConfigs = [
|
this.componentConfigs = [
|
||||||
[
|
[
|
||||||
'yAxis',
|
'yAxis',
|
||||||
@ -1936,14 +1980,11 @@ class AxisChart extends BaseChart {
|
|||||||
// console.log('barDatasets', barDatasets, this.state.datasets);
|
// console.log('barDatasets', barDatasets, this.state.datasets);
|
||||||
|
|
||||||
// Bars
|
// Bars
|
||||||
let spaceRatio = this.barOptions.spaceRatio || BAR_CHART_SPACE_RATIO;
|
|
||||||
let barsWidth = s.unitWidth * (1 - spaceRatio);
|
|
||||||
let barWidth = barsWidth/(this.barOptions.stacked ? 1 : barDatasets.length);
|
|
||||||
|
|
||||||
let barsConfigs = barDatasets.map(d => {
|
let barsConfigs = barDatasets.map(d => {
|
||||||
let index = d.index;
|
let index = d.index;
|
||||||
return [
|
return [
|
||||||
'barGraph',
|
'barGraph' + '-' + d.index,
|
||||||
{
|
{
|
||||||
index: index,
|
index: index,
|
||||||
color: this.colors[index],
|
color: this.colors[index],
|
||||||
@ -1951,20 +1992,28 @@ class AxisChart extends BaseChart {
|
|||||||
// same for all datasets
|
// same for all datasets
|
||||||
valuesOverPoints: this.valuesOverPoints,
|
valuesOverPoints: this.valuesOverPoints,
|
||||||
minHeight: this.height * MIN_BAR_PERCENT_HEIGHT,
|
minHeight: this.height * MIN_BAR_PERCENT_HEIGHT,
|
||||||
barsWidth: barsWidth,
|
|
||||||
barWidth: barWidth,
|
|
||||||
zeroLine: s.yAxis.zeroLine
|
|
||||||
},
|
},
|
||||||
function() {
|
function() {
|
||||||
let s = this.state;
|
let s = this.state;
|
||||||
let d = s.datasets[index];
|
let d = s.datasets[index];
|
||||||
|
|
||||||
|
let spaceRatio = this.barOptions.spaceRatio || BAR_CHART_SPACE_RATIO;
|
||||||
|
let barsWidth = s.unitWidth * (1 - spaceRatio);
|
||||||
|
let barWidth = barsWidth/(this.barOptions.stacked ? 1 : barDatasets.length);
|
||||||
|
|
||||||
|
let xPositions = s.xAxis.positions.map(x => x - barsWidth/2 + barWidth * index);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
xPositions: s.xAxis.positions,
|
xPositions: xPositions,
|
||||||
yPositions: d.yPositions,
|
yPositions: d.yPositions,
|
||||||
cumulativeYPos: d.cumulativeYPos,
|
cumulativeYPos: d.cumulativeYPos,
|
||||||
|
|
||||||
values: d.values,
|
values: d.values,
|
||||||
cumulativeYs: d.cumulativeYs
|
cumulativeYs: d.cumulativeYs,
|
||||||
|
|
||||||
|
zeroLine: s.yAxis.zeroLine,
|
||||||
|
barsWidth: barsWidth,
|
||||||
|
barWidth: barWidth,
|
||||||
};
|
};
|
||||||
}.bind(this)
|
}.bind(this)
|
||||||
];
|
];
|
||||||
|
|||||||
2
dist/frappe-charts.min.cjs.js
vendored
2
dist/frappe-charts.min.cjs.js
vendored
File diff suppressed because one or more lines are too long
2
dist/frappe-charts.min.esm.js
vendored
2
dist/frappe-charts.min.esm.js
vendored
File diff suppressed because one or more lines are too long
2
dist/frappe-charts.min.iife.js
vendored
2
dist/frappe-charts.min.iife.js
vendored
File diff suppressed because one or more lines are too long
2
dist/frappe-charts.min.iife.js.map
vendored
2
dist/frappe-charts.min.iife.js.map
vendored
File diff suppressed because one or more lines are too long
2
docs/assets/js/frappe-charts.min.js
vendored
2
docs/assets/js/frappe-charts.min.js
vendored
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@ -1,7 +1,7 @@
|
|||||||
// Composite Chart
|
// Composite Chart
|
||||||
// ================================================================================
|
// ================================================================================
|
||||||
let report_count_list = [17, 40, 33, 44, 126, 156,
|
let report_count_list = [17, 40, 33, 44, 126, 156,
|
||||||
324, 333, 478, 495, 373];
|
324, 333, 478, 495, 176];
|
||||||
|
|
||||||
let bar_composite_data = {
|
let bar_composite_data = {
|
||||||
labels: ["2007", "2008", "2009", "2010", "2011", "2012",
|
labels: ["2007", "2008", "2009", "2010", "2011", "2012",
|
||||||
|
|||||||
@ -209,14 +209,11 @@ export default class AxisChart extends BaseChart {
|
|||||||
// console.log('barDatasets', barDatasets, this.state.datasets);
|
// console.log('barDatasets', barDatasets, this.state.datasets);
|
||||||
|
|
||||||
// Bars
|
// Bars
|
||||||
let spaceRatio = this.barOptions.spaceRatio || BAR_CHART_SPACE_RATIO;
|
|
||||||
let barsWidth = s.unitWidth * (1 - spaceRatio);
|
|
||||||
let barWidth = barsWidth/(this.barOptions.stacked ? 1 : barDatasets.length);
|
|
||||||
|
|
||||||
let barsConfigs = barDatasets.map(d => {
|
let barsConfigs = barDatasets.map(d => {
|
||||||
let index = d.index;
|
let index = d.index;
|
||||||
return [
|
return [
|
||||||
'barGraph',
|
'barGraph' + '-' + d.index,
|
||||||
{
|
{
|
||||||
index: index,
|
index: index,
|
||||||
color: this.colors[index],
|
color: this.colors[index],
|
||||||
@ -224,20 +221,28 @@ export default class AxisChart extends BaseChart {
|
|||||||
// same for all datasets
|
// same for all datasets
|
||||||
valuesOverPoints: this.valuesOverPoints,
|
valuesOverPoints: this.valuesOverPoints,
|
||||||
minHeight: this.height * MIN_BAR_PERCENT_HEIGHT,
|
minHeight: this.height * MIN_BAR_PERCENT_HEIGHT,
|
||||||
barsWidth: barsWidth,
|
|
||||||
barWidth: barWidth,
|
|
||||||
zeroLine: s.yAxis.zeroLine
|
|
||||||
},
|
},
|
||||||
function() {
|
function() {
|
||||||
let s = this.state;
|
let s = this.state;
|
||||||
let d = s.datasets[index];
|
let d = s.datasets[index];
|
||||||
|
|
||||||
|
let spaceRatio = this.barOptions.spaceRatio || BAR_CHART_SPACE_RATIO;
|
||||||
|
let barsWidth = s.unitWidth * (1 - spaceRatio);
|
||||||
|
let barWidth = barsWidth/(this.barOptions.stacked ? 1 : barDatasets.length);
|
||||||
|
|
||||||
|
let xPositions = s.xAxis.positions.map(x => x - barsWidth/2 + barWidth * index);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
xPositions: s.xAxis.positions,
|
xPositions: xPositions,
|
||||||
yPositions: d.yPositions,
|
yPositions: d.yPositions,
|
||||||
cumulativeYPos: d.cumulativeYPos,
|
cumulativeYPos: d.cumulativeYPos,
|
||||||
|
|
||||||
values: d.values,
|
values: d.values,
|
||||||
cumulativeYs: d.cumulativeYs
|
cumulativeYs: d.cumulativeYs,
|
||||||
|
|
||||||
|
zeroLine: s.yAxis.zeroLine,
|
||||||
|
barsWidth: barsWidth,
|
||||||
|
barWidth: barWidth,
|
||||||
};
|
};
|
||||||
}.bind(this)
|
}.bind(this)
|
||||||
];
|
];
|
||||||
|
|||||||
@ -64,11 +64,11 @@ export function zeroDataPrep(realData) {
|
|||||||
let zeroArray = new Array(datasetLength).fill(0);
|
let zeroArray = new Array(datasetLength).fill(0);
|
||||||
|
|
||||||
let zeroData = {
|
let zeroData = {
|
||||||
labels: realData.labels,
|
labels: realData.labels.slice(0, -1),
|
||||||
datasets: realData.datasets.map(d => {
|
datasets: realData.datasets.map(d => {
|
||||||
return {
|
return {
|
||||||
name: '',
|
name: '',
|
||||||
values: zeroArray,
|
values: zeroArray.slice(0, -1),
|
||||||
chartType: d.chartType
|
chartType: d.chartType
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
|
|||||||
@ -44,41 +44,6 @@ export class AxisController extends AxisChartController {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class BarChartController extends AxisChartController {
|
|
||||||
constructor(meta) {
|
|
||||||
super(meta);
|
|
||||||
}
|
|
||||||
|
|
||||||
setupArgs() {
|
|
||||||
this.consts = {
|
|
||||||
spaceRatio: 0.5,
|
|
||||||
minHeight: this.meta.totalHeight * MIN_BAR_PERCENT_HEIGHT
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
refreshMeta(meta) {
|
|
||||||
if(meta) {
|
|
||||||
super.refreshMeta(meta);
|
|
||||||
}
|
|
||||||
let m = this.meta;
|
|
||||||
this.consts.barsWidth = m.unitWidth - m.unitWidth * this.consts.spaceRatio;
|
|
||||||
|
|
||||||
this.consts.width = this.consts.barsWidth / (m.options && m.options.stacked
|
|
||||||
? m.options.stacked : m.noOfDatasets);
|
|
||||||
}
|
|
||||||
|
|
||||||
animate(bar, x, yTop, index, noOfDatasets) {
|
|
||||||
let start = x - this.meta.unitWidth/4;
|
|
||||||
let width = (this.meta.unitWidth/2)/noOfDatasets;
|
|
||||||
let [height, y] = getBarHeightAndYAttr(yTop, this.meta.zeroLine, this.meta.totalHeight);
|
|
||||||
|
|
||||||
x = start + (width * index);
|
|
||||||
|
|
||||||
return [bar, {width: width, height: height, x: x, y: y}, UNIT_ANIM_DUR, STD_EASING];
|
|
||||||
// bar.animate({height: args.newHeight, y: yTop}, UNIT_ANIM_DUR, mina.easein);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export class LineChartController extends AxisChartController {
|
export class LineChartController extends AxisChartController {
|
||||||
constructor(meta) {
|
constructor(meta) {
|
||||||
super(meta);
|
super(meta);
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
import { makeSVGGroup } from '../utils/draw';
|
import { makeSVGGroup } from '../utils/draw';
|
||||||
import { xLine, yLine, yMarker, yRegion, datasetBar } from '../utils/draw';
|
import { xLine, yLine, yMarker, yRegion, datasetBar } from '../utils/draw';
|
||||||
import { equilizeNoOfElements } from '../utils/draw-utils';
|
import { equilizeNoOfElements } from '../utils/draw-utils';
|
||||||
import { Animator, translateHoriLine, translateVertLine, animateRegion } from '../utils/animate';
|
import { Animator, translateHoriLine, translateVertLine, animateRegion, animateBar } from '../utils/animate';
|
||||||
|
|
||||||
class ChartComponent {
|
class ChartComponent {
|
||||||
constructor({
|
constructor({
|
||||||
@ -11,14 +11,12 @@ class ChartComponent {
|
|||||||
|
|
||||||
getData,
|
getData,
|
||||||
makeElements,
|
makeElements,
|
||||||
postMake,
|
|
||||||
animateElements
|
animateElements
|
||||||
}) {
|
}) {
|
||||||
this.layerTransform = layerTransform;
|
this.layerTransform = layerTransform;
|
||||||
this.constants = constants;
|
this.constants = constants;
|
||||||
|
|
||||||
this.makeElements = makeElements;
|
this.makeElements = makeElements;
|
||||||
this.postMake = postMake;
|
|
||||||
this.getData = getData;
|
this.getData = getData;
|
||||||
|
|
||||||
this.animateElements = animateElements;
|
this.animateElements = animateElements;
|
||||||
@ -41,9 +39,7 @@ class ChartComponent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
make() {
|
make() {
|
||||||
this.preMake && this.preMake();
|
|
||||||
this.render(this.data);
|
this.render(this.data);
|
||||||
this.postMake && this.postMake();
|
|
||||||
this.oldData = this.data;
|
this.oldData = this.data;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -81,8 +77,8 @@ let componentConfigs = {
|
|||||||
},
|
},
|
||||||
|
|
||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
let newPos = newData.positions;
|
let newPos = newData.positions;
|
||||||
let newLabels = newData.labels;
|
let newLabels = newData.labels;
|
||||||
let oldPos = this.oldData.positions;
|
let oldPos = this.oldData.positions;
|
||||||
let oldLabels = this.oldData.labels;
|
let oldLabels = this.oldData.labels;
|
||||||
|
|
||||||
@ -112,8 +108,8 @@ let componentConfigs = {
|
|||||||
},
|
},
|
||||||
|
|
||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
let newPos = newData.positions;
|
let newPos = newData.positions;
|
||||||
let newLabels = newData.labels;
|
let newLabels = newData.labels;
|
||||||
let oldPos = this.oldData.positions;
|
let oldPos = this.oldData.positions;
|
||||||
let oldLabels = this.oldData.labels;
|
let oldLabels = this.oldData.labels;
|
||||||
|
|
||||||
@ -144,8 +140,8 @@ let componentConfigs = {
|
|||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
||||||
|
|
||||||
let newPos = newData.map(d => d.position);
|
let newPos = newData.map(d => d.position);
|
||||||
let newLabels = newData.map(d => d.label);
|
let newLabels = newData.map(d => d.label);
|
||||||
|
|
||||||
let oldPos = this.oldData.map(d => d.position);
|
let oldPos = this.oldData.map(d => d.position);
|
||||||
let oldLabels = this.oldData.map(d => d.label);
|
let oldLabels = this.oldData.map(d => d.label);
|
||||||
@ -176,9 +172,9 @@ let componentConfigs = {
|
|||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
[this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
||||||
|
|
||||||
let newPos = newData.map(d => d.end);
|
let newPos = newData.map(d => d.end);
|
||||||
let newLabels = newData.map(d => d.label);
|
let newLabels = newData.map(d => d.label);
|
||||||
let newStarts = newData.map(d => d.start);
|
let newStarts = newData.map(d => d.start);
|
||||||
|
|
||||||
let oldPos = this.oldData.map(d => d.end);
|
let oldPos = this.oldData.map(d => d.end);
|
||||||
let oldLabels = this.oldData.map(d => d.label);
|
let oldLabels = this.oldData.map(d => d.label);
|
||||||
@ -209,57 +205,67 @@ let componentConfigs = {
|
|||||||
makeElements(data) {
|
makeElements(data) {
|
||||||
let c = this.constants;
|
let c = this.constants;
|
||||||
return data.yPositions.map((y, j) => {
|
return data.yPositions.map((y, j) => {
|
||||||
// console.log(data.cumulativeYPos, data.cumulativeYPos[j]);
|
|
||||||
return datasetBar(
|
return datasetBar(
|
||||||
data.xPositions[j],
|
data.xPositions[j],
|
||||||
y,
|
y,
|
||||||
c.barWidth,
|
data.barWidth,
|
||||||
c.color,
|
c.color,
|
||||||
(c.valuesOverPoints ? (c.stacked ? data.cumulativeYs[j] : data.values[j]) : ''),
|
(c.valuesOverPoints ? (c.stacked ? data.cumulativeYs[j] : data.values[j]) : ''),
|
||||||
j,
|
j,
|
||||||
y - (c.stacked ? data.cumulativeYPos[j] : y),
|
y - (c.stacked ? data.cumulativeYPos[j] : y),
|
||||||
{
|
{
|
||||||
zeroLine: c.zeroLine,
|
zeroLine: data.zeroLine,
|
||||||
barsWidth: c.barsWidth,
|
barsWidth: data.barsWidth,
|
||||||
minHeight: c.minHeight
|
minHeight: c.minHeight
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
postMake() {
|
|
||||||
if((!this.constants.stacked)) {
|
|
||||||
this.layer.setAttribute('transform',
|
|
||||||
`translate(${this.constants.width * this.constants.index}, 0)`);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
animateElements(newData) {
|
animateElements(newData) {
|
||||||
// [this.oldData, newData] = equilizeNoOfElements(this.oldData, newData);
|
let c = this.constants;
|
||||||
|
|
||||||
// let newPos = newData.map(d => d.end);
|
let newXPos = newData.xPositions;
|
||||||
// let newLabels = newData.map(d => d.label);
|
let newYPos = newData.yPositions;
|
||||||
// let newStarts = newData.map(d => d.start);
|
let newCYPos = newData.cumulativeYPos;
|
||||||
|
let newValues = newData.values;
|
||||||
|
let newCYs = newData.cumulativeYs;
|
||||||
|
|
||||||
// let oldPos = this.oldData.map(d => d.end);
|
|
||||||
// let oldLabels = this.oldData.map(d => d.label);
|
|
||||||
// let oldStarts = this.oldData.map(d => d.start);
|
|
||||||
|
|
||||||
// this.render(oldPos.map((pos, i) => {
|
let oldXPos = this.oldData.xPositions;
|
||||||
// return {
|
let oldYPos = this.oldData.yPositions;
|
||||||
// start: oldStarts[i],
|
let oldCYPos = this.oldData.cumulativeYPos;
|
||||||
// end: oldPos[i],
|
let oldValues = this.oldData.values;
|
||||||
// label: newLabels[i]
|
let oldCYs = this.oldData.cumulativeYs;
|
||||||
// }
|
|
||||||
// }));
|
|
||||||
|
|
||||||
// let animateElements = [];
|
[oldXPos, newXPos] = equilizeNoOfElements(oldXPos, newXPos);
|
||||||
|
[oldYPos, newYPos] = equilizeNoOfElements(oldYPos, newYPos);
|
||||||
|
[oldCYPos, newCYPos] = equilizeNoOfElements(oldCYPos, newCYPos);
|
||||||
|
[oldValues, newValues] = equilizeNoOfElements(oldValues, newValues);
|
||||||
|
[oldCYs, newCYs] = equilizeNoOfElements(oldCYs, newCYs);
|
||||||
|
|
||||||
// this.store.map((rectGroup, i) => {
|
this.render({
|
||||||
// animateElements = animateElements.concat(animateRegion(
|
xPositions: oldXPos,
|
||||||
// rectGroup, newStarts[i], newPos[i], oldPos[i]
|
yPositions: oldYPos,
|
||||||
// ));
|
cumulativeYPos: oldCYPos,
|
||||||
// });
|
|
||||||
|
|
||||||
// return animateElements;
|
values: newValues,
|
||||||
|
cumulativeYs: newCYs,
|
||||||
|
|
||||||
|
zeroLine: this.oldData.zeroLine,
|
||||||
|
barsWidth: this.oldData.barsWidth,
|
||||||
|
barWidth: this.oldData.barWidth,
|
||||||
|
});
|
||||||
|
|
||||||
|
let animateElements = [];
|
||||||
|
|
||||||
|
this.store.map((bar, i) => {
|
||||||
|
animateElements = animateElements.concat(animateBar(
|
||||||
|
bar, newXPos[i], newYPos[i], newData.barWidth, c.index,
|
||||||
|
{zeroLine: newData.zeroLine}
|
||||||
|
));
|
||||||
|
});
|
||||||
|
|
||||||
|
return animateElements;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -269,7 +275,8 @@ let componentConfigs = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function getComponent(name, constants, getData) {
|
export function getComponent(name, constants, getData) {
|
||||||
let config = componentConfigs[name];
|
let keys = Object.keys(componentConfigs).filter(k => name.includes(k));
|
||||||
|
let config = componentConfigs[keys[0]];
|
||||||
Object.assign(config, {
|
Object.assign(config, {
|
||||||
constants: constants,
|
constants: constants,
|
||||||
getData: getData
|
getData: getData
|
||||||
|
|||||||
@ -8,13 +8,14 @@ export const REPLACE_ALL_NEW_DUR = 250;
|
|||||||
export const STD_EASING = 'easein';
|
export const STD_EASING = 'easein';
|
||||||
|
|
||||||
export function translate(unit, oldCoord, newCoord, duration) {
|
export function translate(unit, oldCoord, newCoord, duration) {
|
||||||
|
let old = typeof oldCoord === 'string' ? oldCoord : oldCoord.join(', ');
|
||||||
return [
|
return [
|
||||||
unit,
|
unit,
|
||||||
{transform: newCoord.join(', ')},
|
{transform: newCoord.join(', ')},
|
||||||
duration,
|
duration,
|
||||||
STD_EASING,
|
STD_EASING,
|
||||||
"translate",
|
"translate",
|
||||||
{transform: oldCoord.join(', ')}
|
{transform: old}
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -41,6 +42,26 @@ export function animateRegion(rectGroup, newY1, newY2, oldY2) {
|
|||||||
return [rectAnim, groupAnim];
|
return [rectAnim, groupAnim];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function animateBar(bar, x, yTop, width, index=0, meta={}) {
|
||||||
|
let [height, y] = getBarHeightAndYAttr(yTop, meta.zeroLine);
|
||||||
|
if(bar.nodeName !== 'rect') {
|
||||||
|
let rect = bar.childNodes[0];
|
||||||
|
let rectAnim = [
|
||||||
|
rect,
|
||||||
|
{width: width, height: height},
|
||||||
|
UNIT_ANIM_DUR,
|
||||||
|
STD_EASING
|
||||||
|
]
|
||||||
|
|
||||||
|
let old = bar.getAttribute("transform").split("(")[1].slice(0, -1);
|
||||||
|
let groupAnim = translate(bar, old, [x, y], MARKER_LINE_ANIM_DUR);
|
||||||
|
return [rectAnim, groupAnim];
|
||||||
|
} else {
|
||||||
|
return [[bar, {width: width, height: height, x: x, y: y}, UNIT_ANIM_DUR, STD_EASING]];
|
||||||
|
}
|
||||||
|
// bar.animate({height: args.newHeight, y: yTop}, UNIT_ANIM_DUR, mina.easein);
|
||||||
|
}
|
||||||
|
|
||||||
export var Animator = (function() {
|
export var Animator = (function() {
|
||||||
var Animator = function(totalHeight, totalWidth, zeroLine, avgUnitWidth) {
|
var Animator = function(totalHeight, totalWidth, zeroLine, avgUnitWidth) {
|
||||||
// constants
|
// constants
|
||||||
|
|||||||
@ -2,7 +2,7 @@ import { fillArray } from './helpers';
|
|||||||
|
|
||||||
export function getBarHeightAndYAttr(yTop, zeroLine) {
|
export function getBarHeightAndYAttr(yTop, zeroLine) {
|
||||||
let height, y;
|
let height, y;
|
||||||
if (yTop < zeroLine) {
|
if (yTop <= zeroLine) {
|
||||||
height = zeroLine - yTop;
|
height = zeroLine - yTop;
|
||||||
y = yTop;
|
y = yTop;
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@ -363,31 +363,40 @@ export function yRegion(y1, y2, width, label) {
|
|||||||
export function datasetBar(x, yTop, width, color, label='', index=0, offset=0, meta={}) {
|
export function datasetBar(x, yTop, width, color, label='', index=0, offset=0, meta={}) {
|
||||||
let [height, y] = getBarHeightAndYAttr(yTop, meta.zeroLine);
|
let [height, y] = getBarHeightAndYAttr(yTop, meta.zeroLine);
|
||||||
// console.log(yTop, meta.zeroLine, y, offset);
|
// console.log(yTop, meta.zeroLine, y, offset);
|
||||||
|
y -= offset;
|
||||||
|
|
||||||
let rect = createSVG('rect', {
|
let rect = createSVG('rect', {
|
||||||
className: `bar mini`,
|
className: `bar mini`,
|
||||||
style: `fill: ${color}`,
|
style: `fill: ${color}`,
|
||||||
'data-point-index': index,
|
'data-point-index': index,
|
||||||
x: x - meta.barsWidth/2,
|
x: x,
|
||||||
y: y - offset,
|
y: y,
|
||||||
width: width,
|
width: width,
|
||||||
height: height || meta.minHeight
|
height: height || meta.minHeight // TODO: correct y for positive min height
|
||||||
});
|
});
|
||||||
|
|
||||||
if(!label && !label.length) {
|
if(!label && !label.length) {
|
||||||
return rect;
|
return rect;
|
||||||
} else {
|
} else {
|
||||||
|
rect.setAttribute('y', 0);
|
||||||
|
rect.setAttribute('x', 0);
|
||||||
let text = createSVG('text', {
|
let text = createSVG('text', {
|
||||||
className: 'data-point-value',
|
className: 'data-point-value',
|
||||||
x: x,
|
x: width/2,
|
||||||
y: y - offset,
|
y: 0,
|
||||||
dy: (FONT_SIZE / 2 * -1) + 'px',
|
dy: (FONT_SIZE / 2 * -1) + 'px',
|
||||||
'font-size': FONT_SIZE + 'px',
|
'font-size': FONT_SIZE + 'px',
|
||||||
'text-anchor': 'middle',
|
'text-anchor': 'middle',
|
||||||
innerHTML: label
|
innerHTML: label
|
||||||
});
|
});
|
||||||
|
|
||||||
return wrapInSVGGroup([rect, text]);
|
let group = createSVG('g', {
|
||||||
|
transform: `translate(${x}, ${y})`
|
||||||
|
});
|
||||||
|
group.appendChild(rect);
|
||||||
|
group.appendChild(text);
|
||||||
|
|
||||||
|
return group;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user