Reputation: 1848
I have a simple amCharts v4 chart with a function that adds some series and axes.
If I call the function from the script, the chart is displayed correctly, but if it is called externally from a button click or timeout, the legend displays but the series and axes do not. Is there something extra that needs to be done if the series is added later?
var chart = am4core.create("chartdiv", am4charts.XYChart);
chart.data = generateChartData();
chart.legend = new am4charts.Legend();
chart.cursor = new am4charts.XYCursor();
// Create axes
var dateAxis = chart.xAxes.push(new am4charts.DateAxis());
dateAxis.renderer.minGridDistance = 50;
// Create series
function createAxisAndSeries(field, name, opposite, bullet) {
var valueAxis = chart.yAxes.push(new am4charts.ValueAxis());
var series = chart.series.push(new am4charts.LineSeries());
series.dataFields.valueY = field;
series.dataFields.dateX = "date";
series.strokeWidth = 2;
series.yAxis = valueAxis;
series.name = name;
series.tooltipText = "{name}: [bold]{valueY}[/]";
var interfaceColors = new am4core.InterfaceColorSet();
}
var axisAndSeriesList = [];
function addAxisAndSeries(name) {
if (name==="Visits") {
createAxisAndSeries("visits", "Visits", false, "circle");
} else if (name==="Views") {
createAxisAndSeries("views", "Views", true, "triangle");
} else if (name==="Hits") {
createAxisAndSeries("hits", "Hits", true, "rectangle");
} else {
console.warn('what is ' + name +'?');
}
}
// generate some random data, quite different range
function generateChartData() {
var chartData = [];
var firstDate = new Date();
firstDate.setDate(firstDate.getDate() - 100);
firstDate.setHours(0, 0, 0, 0);
var visits = 1600;
var hits = 2900;
var views = 8700;
for (var i = 0; i < 15; i++) {
var newDate = new Date(firstDate);
newDate.setDate(newDate.getDate() + i);
visits += Math.round((Math.random()<0.5?1:-1)*Math.random()*10);
hits += Math.round((Math.random()<0.5?1:-1)*Math.random()*10);
views += Math.round((Math.random()<0.5?1:-1)*Math.random()*10);
chartData.push({date: newDate, visits: visits, hits: hits, views: views });
}
return chartData;
}
function addSeries() {
console.log('Add all 3 in the series');
addAxisAndSeries("Visits");
addAxisAndSeries("Views");
addAxisAndSeries("Hits");
}
// These work
// addAxisAndSeries("Visits");
// addAxisAndSeries("Views");
// addAxisAndSeries("Hits");
// This works
// addSeries();
// This does not work
// setTimeout(function(){
// addSeries();
// }, 3000);
// Clicking on "Add series" button does not work (from HTML)
// <input type="button" onclick="addSeries()" value="Add series" />
See sample pen: https://codepen.io/anon/pen/YdYJKy?editors=0011
Upvotes: 1
Views: 601
Reputation: 3655
You were on the right track in your answer:
The series inherit data from the chart, but apparently that ends with the script.
As you've witnessed, when adding a series dynamically, basically the chart doesn't make presumptions whether the asynchronously-added series will have its own data or will use the chart's. To have the chart continue to provide its data to newly-added series, run chart.invalidateData();
.
Here's a fork of your demo that adds that to the addSeries()
function:
https://codepen.io/team/amcharts/pen/bb863c597a46895f87d2b67534c353f6
Now the function works whether synchronously or asynchronously, whether via setTimeout
or via the button.
Upvotes: 2
Reputation: 1848
The series inherit data from the chart, but apparently that ends with the script.
So chart.data might have {date: '2001-01-01', visits: 100, hits: 200, views: 300}
and each series can just specify which data element to use. Once the script ends, this apparently no longer applies and each additional series must have its own data.
To get the example to work as expected, I commented out this line:
// chart.data = generateChartData(); /* works with this line, but not needed */
And added the data with each series like this:
var series = chart.series.push(new am4charts.LineSeries());
series.data = generateChartData(); // <---- new line here
series.dataFields.valueY = field;
Updated pen: https://codepen.io/anon/pen/VqyVjr?editors=0011
I'm still not clear why this data flow does not continue, but have something that works. Anyone who can shed light on why, please do.
Upvotes: 1