I'd like to know the proper way to make a dashboard with multiple highcharts in a single page, I'm loading data to the charts with AJAX from a PHP method.
With 1 chart I'm doing it like this:
Controller
public function random_values(){
//CakePHP code
$this->autoRender = FALSE;
header("Content-type: text/json");
$x = time() * 1000;
$y = rand(1,100);
$ret = array($x, $y);
echo json_encode($ret);
}
View
<script type="text/javascript">
var chart; //global
function requestData() {
$.ajax({
url: 'singlecharts/random_values',
success: function(point) {
var series = chart.series[0],
shift = series.data.length > 20; // shift if the series is longer than 20
// add the point
chart.series[0].addPoint(eval(point), true, shift);
// call it again after one second
setTimeout(requestData, 1000);
},
cache: false
});
}
$(document).ready(function() {
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
defaultSeriesType: 'spline',
events: {
load: requestData
}
},
title: {
text: 'Live random data'
},
xAxis: {
type: 'datetime',
tickPixelInterval: 150,
maxZoom: 20 * 1000
},
yAxis: {
minPadding: 0.2,
maxPadding: 0.2,
title: {
text: 'Value',
margin: 80
}
},
series: [{
name: 'Random data',
data: []
}]
});
});
</script>
But how do I do to make many charts, everyone with its own ajax request.
Any help will be appreciated it, thank you.
EDIT
This is what I've tried so far and isn't working.
Controller:
public function random_one(){
$this->autoRender = FALSE;
//Set the JSON header
header("Content-type: text/json");
//The x value is the current JavaScript time, ...
$x = time() * 1000;
//The y value is a random number
$y = rand(1,100);
//Create a PHP array and echo it as JSON
$ret = array($x, $y);
echo json_encode($ret);
}
public function random_two(){
$this->autoRender = FALSE;
//Set the JSON header
header("Content-type: text/json");
//The x value is the current JavaScript time, ...
$x = time() * 1000;
//The y value is a random number
$y = rand(1,100);
//Create a PHP array and echo it as JSON
$ret = array($x, $y);
echo json_encode($ret);
}
View
<script type="text/javascript">
var chart; //global
function requestData() {
$.ajax({
url: 'charts/random_one',
success: function(point) {
var series = chart.series[0],
shift = series.data.length > 20; // shift if the series is longer than 20
// add the point
chart.series[0].addPoint(eval(point), true, shift);
// call it again after one second
setTimeout(requestData, 1000);
},
cache: false
});
}
$(document).ready(function() {
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
defaultSeriesType: 'spline',
events: {
load: requestData
}
},
title: {
text: 'Live random data one'
},
xAxis: {
type: 'datetime',
tickPixelInterval: 150,
maxZoom: 20 * 1000
},
yAxis: {
minPadding: 0.2,
maxPadding: 0.2,
title: {
text: 'Value',
margin: 80
}
},
series: [{
name: 'Random data #1',
data: []
}]
});
});
var chart2; //global
function requestDataTwo() {
$.ajax({
url: 'charts/random_two',
success: function(point) {
var series = chart2.series[0],
shift = series.data.length > 20; // shift if the series is longer than 20
// add the point
chart2.series[0].addPoint(eval(point), true, shift);
// call it again after one second
setTimeout(requestData, 1000);
},
cache: false
});
}
$(document).ready(function() {
chart2 = new Highcharts.Chart({
chart: {
renderTo: 'container-two',
defaultSeriesType: 'spline',
events: {
load: requestDataTwo
}
},
title: {
text: 'Live random data two'
},
xAxis: {
type: 'datetime',
tickPixelInterval: 150,
maxZoom: 20 * 1000
},
yAxis: {
minPadding: 0.2,
maxPadding: 0.2,
title: {
text: 'Value',
margin: 80
}
},
series: [{
name: 'Random data #2',
data: []
}]
});
});
</script>
The problem was that Highcharts demo tells you to render the chart in "container" div and CakePHP default layout also uses a "container" div. There was a conflict between those two.
Thank you guys.
Your setTimeout(requestData, 1000); is the same in both requestData and requestDataTwo. You need them both to be independent of each other, otherwise, the one will always return with not 1, but twice the number of requests...
function requestDataTwo() {
$.ajax({
url: 'test.php?random_two',
success: function(point) {
var series = chart2.series[0],
shift = series.data.length > 20; // shift if the series is longer than 20
// add the point
chart2.series[0].addPoint(eval(point), true, shift);
// call it again after one second
setTimeout(requestData, 1000); **<-- Change this here to requestDataTwo**
},
cache: false
});
}
Just as well... You need to add this to your php "controller"
<?php
switch (key($_GET)) {
case 'random_two':
random_two();
die();
break;
case 'random_one':
random_one();
die();
break;
}
?>
Have you checked similar posts here on stack overflow?
Cannot display multiple Highcharts on a single page
Manage multiple highchart charts in a single webpage
Using multiple Highcharts in a single page
Create six chart with the same rendering,different data (highchart )
It could also help to view the source of the Highcharts demo page that has many charts on one page, and see how they are called.
Highcharts demo
Sorry I can´t help more. Might have more time later this evening :)
If you want to use multiple charts on a single page first of create different variables for all the charts like var chart1, chart2;
Now on $(document).ready define all the chart variables for different charts and give appropriate properties especially renderTo property. You can define different ajax calls for different charts by using separate load events for charts.
Related
I've created a chart and I want to update in real time, that's why I use ajax. My question is, how to display the ajax response? Below is my sample script of my chart. Please help me. Thank you very well.
Chart.php -
$(document).ready(function () {
Highcharts.chart('container', {
chart: {
type: 'bar'
},
title: {
text: "TITLE"
},
series: [{
name: 'Present',
data: [*//must display the ajax response here//*]
}]
});
});
ajax.php
<script>
function fanc_no(){
$.ajax({
url: "test.php",
success: function(result){
$("#container").html(result);
}
});
}
window.setInterval(function(){
func_no();
}, 1000);
</script>
Take a look at the load function:
chart: {
events: {
load: function () {
// set up the updating of the chart each second
var series = this.series[0];
setInterval(function () {
var x = (new Date()).getTime(), // current time
y = Math.round(Math.random() * 100);
series.addPoint([x, y], true, true);
}, 1000);
}
}
}
Now, inside the setInterval function, you have to call your ajax and pass the result as shown.
Take a look at the official docs for it.
i'm trying to make a modal dialog in html, and when something is pressed to draw a google chart in the modal.
function inter(id)
{
var arr = [['Album','Vizualizari']];
$.ajax({
url: 'popular.php',
type: 'GET',
dataType: 'json',
success: function (json) {
$.each(json,function (i ,value )
{
var c =[value.title, value.popular];
arr.push(c);
});
google.charts.load('current', {'packages':['bar']});
google.charts.setOnLoadCallback(drawStuff);
function drawStuff() {
google.visualization
var data = new google.visualization.arrayToDataTable(arr);
var options = {
title: 'Chess opening moves',
width: 800,
legend: { position: 'none' },
bars: 'vertical', // Required for Material Bar Charts.
axes: {
y: {
0: { side: 'top', label: 'Percentage'} // Top x-axis.
}
},
bar: { groupWidth: "100%" }
};
var chart = new google.charts.Bar(document.getElementById('top_x_div'));
chart.draw(data, options);
};
}});
}
It worked but only on first modal. When i try to open another modal i've got the follow error : google.charts.load() cannot be called more than once . How can i draw the chart using another callback, not 'setOnLoadCallback' ?
Your problem is that your function contain these two lines :
google.charts.load('current', {'packages':['bar']});
google.charts.setOnLoadCallback(drawStuff);
This is wrong. google.charts.load() loads the google visualization API and setOnLoadCallback() is executed once when the API has finished loading. But you do not want to show the chart when google visualization is loaded, but when the user click a button (or whatever) to show a modal. So remove setOnLoadCallback completely and move load() out to the global scope - simply call drawStuff() manually from the success handler :
google.charts.load('current', {'packages':['bar']});
function inter(id) {
var arr = [
['Album', 'Vizualizari']
];
$.ajax({
url: 'popular.php',
type: 'GET',
dataType: 'json',
success: function(json) {
$.each(json, function(i, value) {
var c = [value.title, value.popular];
arr.push(c);
});
drawStuff(arr);
})
})
function drawStuff(arr) {
var data = new google.visualization.arrayToDataTable(arr);
var options = {
title: 'Chess opening moves',
width: 800,
legend: {
position: 'none'
},
bars: 'vertical', // Required for Material Bar Charts.
axes: {
y: {
0: {
side: 'top',
label: 'Percentage'
} // Top x-axis.
}
},
bar: {
groupWidth: "100%"
}
};
var chart = new google.charts.Bar(document.getElementById('top_x_div'));
chart.draw(data, options);
}
}
I m trying to figure it out that is it possible to make the json data fetched dynamically from a database with the help of php and mysql and can be plotted with highcharts that too dynamic auto updating? Any help would be appreciated.
following the code i have tried and is not working properly and want to implement to the the website for 10 lines.
<HTML>
<HEAD>
<TITLE>highchart example</TITLE>
<script type="text/javascript"src="http://code.jquery.com/jquery-1.10.1.min.js"></script>
<script src="http://code.highcharts.com/highcharts.js"></script>
<script src="http://code.highcharts.com/modules/exporting.js"></script>
<script type="text/javascript">
var chart;
function requestData() {
$.ajax({
url: 'live-server-data.php',
success: function(point) {
var series = chart.series[0],
shift = series.data.length > 20; // shift if the series is
// longer than 2
// add the point
chart.series[0].addPoint(point, true, shift);
// call it again after one second
setTimeout(requestData1, 1000);
},
cache: false,
});
}
function requestData1() {
$.ajax({
url: 'live-server-data.php',
success: function(point) {
var series2 = chart.series[1],
shift = series2.data.length > 20; // shift if the series is
// longer than 20
// add the point
chart.series[1].addPoint(point, true, shift);
// call it again after one second
setTimeout(requestData, 1000);
},
cache: false,
});
}
$(function () {
$(document).ready(function() {
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
defaultSeriesType: 'spline',
events: {
load: requestData
}
},
title: {
text: 'Live random data'
},
xAxis: {
type: 'datetime',
tickPixelInterval: 150,
maxZoom: 20 * 1000
},
yAxis:
{
minPadding: 0.2,
maxPadding: 0.2,
title: {
text: '',
margin: 80
}
},
series: [
{
name: 'Random data',
data: []
},
{
name: ' hahaha',
data: []
}
],
});
});
});
</script>
</HEAD>
<BODY>
<div id="container"
style="min-width: 728px; height: 400px; margin: 0 auto"></div>
</BODY>
</HTML>
*** the live-server-data.php is as followed:
<?php
// Set the JSON header
header("Content-type: text/json");
// The x value is the current JavaScript time, which is the Unix time multiplied
// by 1000.
$x = time() * 1000;
// The y value is a random number
$y = rand(48,52);
// Create a PHP array and echo it as JSON
$ret = array($x, $y);
echo json_encode($ret);
?>
You can try with
var options = {
chart: {
renderTo: 'chart',
},
credits: {
enabled: false
},
title: {
text: 'Impression/Click Overview',
x: -20
},
xAxis: {
categories: [{}]
},
tooltip: {
formatter: function() {
var s = '<b>'+ this.x +'</b>';
$.each(this.points, function(i, point) {
s += '<br/>'+point.series.name+': '+point.y;
});
return s;
},
shared: true
},
series: [{},{}]
};
$.ajax({
url: "json.php",
data: 'show=impression',
type:'post',
dataType: "json",
success: function(data){
options.xAxis.categories = data.categories;
options.series[0].name = 'Impression';
options.series[0].data = data.impression;
options.series[1].name = 'Click';
options.series[1].data = data.clicks;
var chart = new Highcharts.Chart(options);
}
});
The highcharts website has some useful articles about working with dynamic data. That is probably the best place to start.
http://www.highcharts.com/docs/working-with-data/preprocessing-live-data
http://www.highcharts.com/docs/working-with-data/preprocessing-data-from-a-database
Try something out, and if you have trouble, come back here with a more specific question showing what you have tried. As it stands, your question is too broad, and will probably get closed.
An ajax request for updating data looks something like:
function requestData() {
$.ajax({
url: 'live-server-data.php',
success: function(point) {
var series = chart.series[0],
shift = series.data.length > 20; // shift if the series is // longer than 20
// add the point
chart.series[0].addPoint(point, true, shift);
// call it again after one second
setTimeout(requestData, 1000);
},
cache: false
});
}
I am trying to build column based highcharts, and here is my code in jquery:
var options = {
chart: {
renderTo: 'container',
type: 'column'
},
credits: {
enabled: false
},
title: {
text: 'PCP Histogram',
x: -20
},
xAxis: {
categories: [{}]
},
legend: {
layout: 'vertical',
align: 'right',
verticalAlign: 'top',
x: -10,
y: 100,
borderWidth: 0
},
tooltip: {
formatter: function() {
var s = '<b>'+ this.x +'</b>';
$.each(this.points, function(i, point) {
s += '<br/>'+point.series.name+': '+point.y;
});
return s;
},
shared: true
},
series: [{},{}]
};
$.ajax({
url: "file.php",
type: "post",
dataType: "json",
success: function(data){
options.xAxis.categories = data.categories;
options.series[0].name = 'Avg1';
options.series[0].data = data.avg1;
options.series[1].name = 'Avg2';
options.series[1].data = data.avg2;
var chart = new Highcharts.Chart(options);
And I getting the data from file php like this:
file.php
$graph_data = array('categories'=>$categories, 'avg1'=>$avg, 'avg2'=>$avg);
print json_encode($graph_data, JSON_NUMERIC_CHECK);
It is working fine with two columns per category,
What I want now is: the graph_data can have n number of avg datas,
so basically it will be n number of columns.
$graph_data = array('categories'=>$categories, 'avg1'=>$avg1, ... 'avgn'=>$avgn);
When I do it manually it works, but I will not know how many of them will be there, so I want the code to do i.
Any idea how I can do it?
Any help appreciated.
make an array of avg instead of having avg1, avg2 etc....
$graph_data = array('categories'=>$categories, 'avgs'=>$array_of_avgs)
then in javascript side
success: function(data){
options.xAxis.categories = data.categories;
for(var i in data.avgs){
options.series[i].name = 'Avg'+i;
options.series[i].data = data.avgs[i];
}
var chart = new Highcharts.Chart(options);
And everything will be fine
I'm trying to create a chart using data from my database calling json, but its not showing the results in the chart.
Here's my code so far:
$(document).ready(function() {
function requestData() {
$.ajax({
url: 'data.php',
datatype: 'json',
success: function(data) {
alert(data);
chart.series[0].setData(data[0]);
},
cache: false
});
}
var chart;
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
type: 'line',
events: {
load: requestData
}
},
xAxis: {
},
yAxis: {
title: {
text: 'Value'
}
},
series: [{
name: 'Random data',
data: []
}]
});
});
And here's my data.php code
$query = "SELECT tiempo,Fp1Ref
FROM GraficaEEG limit 10";
$data = mysqli_query($dbc, $query);
$i=0;
while($row = mysqli_fetch_array($data)) {
$row['tiempo'] = (float) $row['tiempo'];
$rows[$i]=array($row['tiempo'],(float)$row['Fp1Ref']);
$i++;
}
echo json_encode($rows);
The data i receive is this:
[[0,3001],[0.005,4937.22],[0.01,4130.55],[0.015,4213.15],[0.02,4010.61],[0.025,3914.34],[0.03,3785.33],[0.035,3666.13],[0.04,3555.25],[0.045,3447.77]]
So i think is the proper way to pass data for the chart, so i don't quite get whats wrong, thank you in advance.
I think the problem is that when your requestData() function is fired the chart variable still isn't fully built and doesn't know it has the series property.
To fix this, instead of chart in your requestData() function, reference this (which means the chart object in that context).
I tried this out in jsfiddle here http://jsfiddle.net/elcabo/p2r6g/.
Also post the js code below.
$(function () {
$(document).ready(function() {
//Function bits
function requestData(event) {
var tiemposAlAzar = [[10,20],[20,50]];
//The 'this' will refer to the chart when fired
this.series[0].setData(tiemposAlAzar);
};
var chart;
//Chart bits
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
type: 'line',
events:{
load: requestData
}
},
xAxis: {},
yAxis: {
title: {
text: 'Value'
}
},
series: [{
name: 'Random data',
data: []
}]
});
});
});
This url may help you to create dynamic highchart that need to pull data from database.
In json.php code you can put your sql query and replace static array to dynamic array
http://www.kliptu.com/free-script/dynamic-highchart-example-with-jquery-php-json
The example also shows how to manage multiple series with json.
And tooltips with all series data at mouse point.
You can modify example as per your script requirement.