Take a looka t my JS below, for my drawChart function for a google chart. This works as I expected. HOWEVER, because var chart ... is inside the drawChart function, the animations do not work - instead google thinks it's creating a brand new chart each time, and just refreshes the chart.
I would like to do something like in their examples, where the data moves according to my settings (1000ms, default easing: linear). Examples are here: https://developers.google.com/chart/interactive/docs/animation
If I pull out the var chart ... from the drawChart function, I get a "Chart not defined" error. Appreciate the help from anyone who has worked with google charts a lot. Thanks for the help.
var chart = "notSet";
google.load('visualization', '1.0', {'packages':['corechart']});
google.setOnLoadCallback(setGoogleData);
google.setOnLoadCallback(drawChart);
newValue = 0;
var data = [];
function setGoogleData(){
data[0] = new google.visualization.DataTable(JSON_DATA_LOCATED_HERE);
data[1] = new google.visualization.DataTable(JSON_DATA_LOCATED_HERE);
var chart = new google.visualization.LineChart(document.getElementById('stopByTripChart'));
}
function drawChart() {
if(chart == "notSet"){
var chart = new google.visualization.LineChart(document.getElementById('stopByTripChart'));
}
var options = {"title":"Average Load Summary","titlePosition":"in","width":1100,"height":700,"hAxis.slantedTextAngle":90,"hAxis.position":"out","pointSize":5,"animation.duration":1000,"animation.easing":"linear","hAxis.showTextEvery":1,"hAxis.title":"Stops"};
chart.draw(data[newValue], options);
}
function changeChart(){
newValue = document.getElementById("chartNumber").value;
drawChart();
}
I've never tried Google charts myself, but I think such a code would work:
var chart = null;
function drawChart() {
if(chart === null){
chart = new google.visualization.LineChart(document.getElementById('stopByTripChart'));
}
var options = {"title":"Average Load Summary",
"titlePosition":"in",
"width":1100,
"height":700,
"hAxis" :{"slantedTextAngle":90,
"position":"out",
"showTextEvery":1,
"title":"Stops"},
"pointSize":5,
"animation":{"duration":1000,
"easing": 'out'};
chart.draw(data[newValue], options);
}
function changeChart(){
newValue = document.getElementById("chartNumber").value;
drawChart();
}
Otherwise, the error about chart not being defined might come from the fact that you might have placed your code before the load of the google library. Hence, chart was called before the google objects existed (tho it's hard to tell with just that snippet).
Related
The bulk of the examples I've found showing Google Charts have simple little arrays...
I need to pull an array from my server.
I can get a pie chart to draw, but it doesn't update.
Here is my attempt to get a flexible, redrawing pie chart:
At the top of my javascript, but before document.ready:
google.load("visualization", "1", {packages:["corechart"]});
google.setOnLoadCallback(drawChart);
My drawChart function:
function drawChart(arrFeedbackResult3) {
console.log('Draw a fucking chart ... ') + console.log(arrFeedbackResult3);
var chart_data = new google.visualization.DataTable(arrFeedbackResult3);
var options = {
title: 'Comments by Group',
sliceVisibilityThreshold: 1/20, // Only > 5% will be shown.
width: 400,
height: 400
};
chart = new
google.visualization.PieChart(document.getElementById('groupPieChartDiv'));
chart.draw(chart_data, options);
// chart = new google.visualization.PieChart(document.getElementById('groupPieChartDiv'));
// chart.draw(data, options);
}
And the function that, after a button is clicked, passes fresh data to drawChart:
function setupFeedback3(arrFeedbackResult3){ // Create Group summary Graphs
console.log('Groups summary from DB: ') + console.log(arrFeedbackResult3);
drawChart(arrFeedbackResult3);
} // END setupFeedback3
I get a "table has no columns" message on my page with the above code.
The array, arrFeedbackResult3, is formatted correctly and does render a chart when I change the code but end up without the ability to refresh.
Any help appreciated. I think I'm just missing the basic flow of using Google Charts...and how/where the callback should be used.
Updating with my next attempt after a very generous and detailed reply.
My js is in a separate file from the html. I cannot get the passing of an array via callback to work. I get "not a constructor" errors or "not a function." I think because adding a parenthetical value breaks the code.
I also don't understand the comment about document.ready in the answer...I have kept document.ready in order to load all my other functions.
Right after document.ready I have:
google.charts.load('current', {
packages:['corechart'],
callback: drawChart
});
Then, after my db POST to get data, I call:
function setupFeedback3(result){ // Create Group summary Graphs
arrFeedbackResult3 = result; //Store in global variable for access by chart
drawChart();
} // END setupFeedback3
arrFeedbackResult3 is a GLOBAL variable - only way I could get the data to the draw chart function.
Then:
function drawChart() {
console.log('Draw a chart ... ') + console.log(arrFeedbackResult3);
// var chart_data = new google.visualization.DataTable(arrFeedbackResult3);
var chart_data = google.visualization.arrayToDataTable(arrFeedbackResult3);
var options = {
title: 'Comments by Group',
sliceVisibilityThreshold: 1/20,
width: 400,
height: 400
};
var chart = new google.visualization.PieChart(document.getElementById('groupPieChartDiv'));
chart.draw(chart_data, options);
}
This is working, and the chart does update as you feed different data, but it seems a shoddy state of affairs. One specific example of passing data, vs. a stupid simple example or using AJAX inside the function, would have been really helpful.
first, recommend not using jsapi to load the library.
according to the release notes...
The version of Google Charts that remains available via the jsapi loader is no longer being updated consistently. Please use the new gstatic loader.js from now on.
<script src="https://www.gstatic.com/charts/loader.js"></script>
this will only change the load statement...
google.charts.load('current', {packages:['corechart']});
next, the callback can be added to the load statement...
google.charts.load('current', {
packages:['corechart'],
callback: drawChart
});
or you can use the promise it returns...
google.charts.load('current', {
packages:['corechart']
}).then(drawChart);
also, the load statement will wait until the document is ready by default,
so it can be used in place of --> $(document).ready
finally, when creating a data table,
the argument for the constructor should be JSON, not a simple array
see Format of the Constructor's JavaScript Literal data Parameter,
for the specific JSON format
if you want to create a data table from a simple array,
use static method --> arrayToDataTable
recommend setup similar to following...
google.charts.load('current', {
packages:['corechart']
}).then(function () {
// get data
drawChart(arrayData);
});
function drawChart(arrayData) {
var chart_data = google.visualization.arrayToDataTable(arrayData);
var options = {
title: 'Comments by Group',
sliceVisibilityThreshold: 1/20,
width: 400,
height: 400
};
var chart = new google.visualization.PieChart(document.getElementById('groupPieChartDiv'));
chart.draw(chart_data, options);
}
function setupFeedback(arrayData) {
// get data
drawChart(arrayData);
}
UPDATE
you can use the promise the load statement returns as the callback and the document ready
just move the code as shown below...
then you can load your ajax call to get the data
google.charts.load('current', {
packages:['corechart']
}).then(function () {
// move code from document ready here
// get data
getData();
});
function getData() {
$.ajax({
type: 'POST',
contentType: 'application/json',
url: sourceURL,
success: setupFeedback
});
}
function setupFeedback(result) {
// you could draw the chart here
// just move the code from drawChart
// or pass the data along to another function
drawChart(result);
}
function drawChart(result) {
var chart_data = google.visualization.arrayToDataTable(result);
var options = {
title: 'Comments by Group',
sliceVisibilityThreshold: 1/20,
width: 400,
height: 400
};
var chart = new google.visualization.PieChart(document.getElementById('groupPieChartDiv'));
chart.draw(chart_data, options);
}
I am using same chart in 2 different places and the data is being loaded dynamically.
In one of the place i am using HighChart and for other i use HighStock to get the Navigator,Scrollbar facility.
What i'm trying to achieve is i am loading data asynchronously and the chart shows loading text/a loader until it gets data from the server.This works perfectly fine for HighChart. But when it comes to HighStock things are not working. It shows data differently than what i am expecting it to be.
Let me explain, The chart is initialized first and when it fetches data from server i tried to log the value of xAxis here, it shows 1 for HighChart which is correct but for HighStock the statement show 2 xAxis.
//HighChart
var MyChart = {
initHighcharts: function() {
this.chart = new Highcharts.Chart({
// Chart related configuration
},
series: []
});
this.chart.showLoading();
},
updateChart: function(data) {
console.log('x axis', this.chart.xAxis);// Here i get 1 xAxis
// Load data here
this.chart.redraw();
this.chart.hideLoading();
},
};
MyChart.initHighcharts();
setTimeout(function() {
var data = someData;
MyChart.updateChart(data);
}, 2000);
I don't understand what goes wrong here when i change the HighChart to HighStock.The only piece of information i changed here is
this.chart = new Highcharts.StockChart({
//HighStock chart
var MyChart = {
initHighcharts: function() {
this.chart = new Highcharts.StockChart({
// Chart related configuration
},
series: []
});
this.chart.showLoading();
},
updateChart: function(data) {
console.log('x axis', this.chart.xAxis);// Here i get 2 xAxis
// Load data here
this.chart.redraw();
this.chart.hideLoading();
},
};
MyChart.initHighcharts();
setTimeout(function() {
var data = someData;
MyChart.updateChart(data);
}, 2000)
Here are the two fiddle that show the error i am facing,
HighChart Fiddle
HighStock Fiddle
I have logged the length of xAxis, Please open console window to see the xAxis value. Am i doing something wrong here?
Any help is much appreciated!!
Thanks
I'm trying to create a Bar Chart using Google's jsapi, and I've downloaded the following code (with my own changes), that needs to create Bar Chart.
google.load("visualization", "1", {packages:["corechart"]});
drawChart(AvgTimeInConference, keysSorted3);
function drawChart(AvgTimeInConference, keysSorted3) {
var DataTable=[];
DataTable.push(['Conference', 'Average Duration']);
for (var i=0; i<keysSorted3.length; i++)
{
if(keysSorted3[i]!=="")
{
var x=[keysSorted3[i], AvgTimeInConference[keysSorted3[i]]];
DataTable.push(x);
}
}
var data = new google.visualization.arrayToDataTable(DataTable);
var options = {
title: 'average durations length of the conferences, grouped by Conference Type',
vAxis: {title: 'Average Duration', titleTextStyle: {color: 'red'}}
};
var chart = new google.visualization.BarChart(document.getElementById('chart_div'));
chart.draw(data, options);
}
The code works greate, until it gets to the line "var data = new google.visualization.arrayToDataTable(DataTable);". Data Table at this point is an array that contains the data in cells (first cell - headers, second and on are the data according to headers). When trying to use that function, the run get stuck and doesn't move on. doe's anyone has an idea why it happens? is DataTable not in the right format? Thanks!
Edit: The DataTable object from debug
I have the following code:
<script type="text/javascript">
// Load the Visualization API and the piechart package.
google.load('visualization', '1', {'packages':['corechart']});
// Set a callback to run when the Google Visualization API is loaded.
google.setOnLoadCallback(drawChart);
function drawChart() {
// Create our data table out of JSON data loaded from server.
// var data = new google.visualization.DataTable('<>');
var data = google.visualization.arrayToDataTable([['Generation', 'Descendants'],[0,300], [85,300],[125,0] ]);
var options = {
title: 'Derating chart',
// Draw a trendline for data series 0.
lineWidth: 2,
hAxis: {title: 'Temperature [°C]', titleTextStyle: {color: 'black'}, logScale: false},
vAxis: {
title: "Irms [A]",
maxValue:8
},
pointSize:5
};
// Instantiate and draw our chart, passing in some options.
// Do not forget to check your div ID
var chart = new google.visualization.ScatterChart(document.getElementById('chart_div'));
chart.draw(data, options);
}
</script>
It's quite simple, but I have the following problem:
- In my chart I have 3 points, is it possible to interpolate the values between that points? I need to display the values between them when you put the mouse over the line
There should be an option for this... but checking forums and documentation have found none. Closest to this is using a trendline, but values don´t match your line. So your only way is doing something manually. Here is a workaround I made using jquery :
//you need to have in options tooltip:{isHtml:true} for this to work
google.visualization.events.addListener(chart, 'ready', function(){
$('#chart_div svg path').mousemove(function(e){
$('.google-visualization-tooltip').remove(); // remove previous tooltips
var x=e.offsetX; // get x coordinate
var y=e.offsetY; //get y coordinate
var xValue= Math.round(chart.getChartLayoutInterface().getHAxisValue(x)); // get chart x value at coordinate
var yValue=Math.round( chart.getChartLayoutInterface().getVAxisValue(y)); // get chart y value at coordinate
// create tooltip
var tootlip = $('<div class= "google-visualization-tooltip"><ul class="google-visualization-tooltip-item-list"><li class="google-visualization-tooltip-item"><span >X : '+xValue+'</span></li><li class="google-visualization-tooltip-item"><span>Y : '+yValue+'</span></li></ul></div>');
tootlip.css({position:'absolute', left:(x+20)+'px', top:(y-100)+'px', width:'100px', height:'70px'}) // set tooltip position
$('#chart_div').append(tootlip); // add tooltip to chart
})
$('#chart_div svg path').mouseout(function(e){
$('.google-visualization-tooltip').remove();
})
})
Full fiddle: http://jsfiddle.net/juvian/48ouLbmm/
Note: without the mouseout it works better, but tooltip stays until next mouseover
I am making a google chart whith show and hide functionality.Means chart will be hidden on the page load and when user clicks a button chart will be made visible.
My code
<script type="text/javascript">
google.load("visualization", "1", { packages: ["corechart"] });
google.setOnLoadCallback(drawChart);
function drawChart() {
var items = $(".label1").text();
var data = google.visualization.arrayToDataTable([
<%= chartItems %>
]);
var options = {
title: 'Poll Results'
};
var chart = new google.visualization.PieChart(document.getElementById('chart_div'));
chart.draw(data, options);
}
</script>
<div id="chart_div" style="display:none; width:800px;height:500px;"></div>
My problem is that when user clicks on the button and chart is visible its not taking the full width and height(800x500).rather its taking an unknown dimension(400x200).
Note: when the chart is made visible in the page load itself, It works correctly.
Code is same change in HTML like this
<div id="chart_div" style=" width:800px;height:500px;"></div>
You can do as marios suggested and set dimensions inside that chart's options, but that won't fix all of the problems that come along with drawing a chart inside a hidden div. The Visualization APIs dimensional measurements don't work well inside hidden divs, so elements get positioned in the wrong place and have the wrong size in some browsers. You need to unhide the div immediately prior to drawing the chart, and you can hide it again when the chart is done drawing. Here's example code that does this:
var container = document.getElementById('chart_div');
container.style.display = 'block';
var chart = new google.visualization.PieChart(container);
google.visualization.events.addListener(chart, 'ready', function () {
container.style.display = 'none';
});
chart.draw(data, options);
Use chartArea:{} to set width & height
function drawChart() {
var items = $(".label1").text();
var data = google.visualization.arrayToDataTable([
<%= chartItems %>
]);
var options = {
title: 'Poll Results',
chartArea: {
width: 800,
height: 500
}
};
var chart = new google.visualization.PieChart(document.getElementById('chart_div'));
chart.draw(data, options);
}
I confirm that this is a bug. It work if the div is hidden "visibility:hidden;"
It does not work if the CSS shows "display:none"
There is an option to ask for specific width and height the google chart api https://developers.google.com/chart/interactive/docs/customizing_charts?hl=es.
Directly give width in chart option.
For eg:
options='{
"width": "800"
}'