How to read and change axes on already drawn Google chart?

I have a page with several google charts, mostly combo charts and line charts. For example:

chart = new google.visualization.LineChart(chartDiv); 

After the page has already been drawn, I would like to be able to read the maximum values ​​from the axes, and then redraw the diagrams so that they all have the same maximum values ​​on their axes (that is, to make them easier to compare at a glance). I do not know these maximum values ​​in advance.

I could change the parameters and redraw the charts with

 chart.draw(data, options) 

but I'm not sure how to infer data from the axes. The chart object has a method called .getChartLayoutInterface() This seems promising, but I'm not sure how to use it. For example, this works:

 var b = c.getChartLayoutInterface().getChartAreaBoundingBox(); 

but

 var b = c.getChartLayoutInterface().getVAxisValue(); 

returns null .

+1
javascript google-visualization google-api
source share
2 answers

You will need to ask @Sjoerd how getChartLayoutInterface () works, since there seems to be no documentation on the Internet.

In the meantime, you can get the minimum and maximum values ​​of each chart you create, and then take the maximum and minimum values ​​of max / min for all charts combined.

Using these max / min values, you can manually set min / max for each chart (with some good rounding). To make rounding nice, I suggest the following:

 // Take the Max/Min of all data values in all graphs var totalMax = 345; var totalMin = -123; // Figure out the largest number (positive or negative) var biggestNumber = Math.max(Math.abs(totalMax),Math.abs(totalMin)); // Round to an exponent of 10 appropriate for the biggest number var roundingExp = Math.floor(Math.log(biggestNumber) / Math.LN10); var roundingDec = Math.pow(10,roundingExp); // Round your max and min to the nearest exponent of 10 var newMax = Math.ceil(totalMax/roundingDec)*roundingDec; var newMin = Math.floor(totalMin/roundingDec)*roundingDec; // Determine the range of your values var range = newMax - newMin; // Define the number of gridlines (default 5) var gridlines = 5; // Determine an appropriate gap between gridlines var interval = range / (gridlines - 1); // Round that interval up to the exponent of 10 var newInterval = Math.ceil(interval/roundingDec)*roundingDec; // Re-round your max and min to the new interval var finalMax = Math.ceil(totalMax/newInterval)*newInterval; var finalMin = Math.floor(totalMin/newInterval)*newInterval; 

This is similar to how Google defines max / min values ​​(sometimes, if you have, say, -6.2 and 3.1 as values, it will use 3.1 for grid lines, even if it's an odd number). But by creating your own rounding, you can get around to figuring out how Google rounds (which is a tricky proposition).

Let me know if you do not understand correctly.

+1
source share

According to the getVAxisValue documentation getVAxisValue function has the following signature:

getVAxisValue(position, optional_axis_index)

Returns a logical vertical value at a position that is an offset from the top edge of the chart container. May be negative.

Example: chart.getChartLayoutInterface().getVAxisValue(300) .

Call this after drawing the chart.

Return Type: number


Since your goal is to read the maximum values ​​from the axes and then redraw the charts so that they all have the same maximum values ​​on their axes, I would suggest the following solution

calculate min / max google.visualization.DataTable values:

 function calcMinMax(data, colIndex) { var totalMin = data.getValue(0,colIndex); var totalMax = data.getValue(0,colIndex); for(var i = 0; i < data.getNumberOfRows();i++){ if ( data.getValue(i, colIndex) < totalMin ) { totalMin = data.getValue(i, colIndex); } if ( data.getValue(i, colIndex) > totalMax ) { totalMax = data.getValue(i, colIndex); } } return {'min': totalMin, 'max': totalMax }; } 

and set the viewWindow option:

 var vAxisMinMax = calcMinMax(data,1); options.vAxis = {'viewWindow': {'min': vAxisMinMax.min, 'max': vAxisMinMax.max}}; 

Example

 google.load('visualization', '1', { packages: ['corechart', 'line'] }); google.setOnLoadCallback(drawBasic); function drawBasic() { var data = new google.visualization.DataTable(); data.addColumn('number', 'X'); data.addColumn('number', 'Dogs'); data.addRows([ [0, 5], [1, 10], [2, 23], [3, 17], [4, 18], [5, 9], [6, 11], [7, 27], [8, 33], [9, 40], [10, 32], [11, 35], [12, 30], [13, 40], [14, 42], [15, 47], [16, 44], [17, 48], [18, 52], [19, 54], [20, 42], [21, 55], [22, 56], [23, 57], [24, 60], [25, 50], [26, 52], [27, 51], [28, 49], [29, 53], [30, 55], [31, 60], [32, 61], [33, 59], [34, 62], [35, 65], [36, 62], [37, 58], [38, 55], [39, 61], [40, 64], [41, 65], [42, 63], [43, 66], [44, 67], [45, 69], [46, 69], [47, 70], [48, 72], [49, 68], [50, 66], [51, 65], [52, 67], [53, 70], [54, 71], [55, 72], [56, 73], [57, 75], [58, 70], [59, 68], [60, 64], [61, 60], [62, 65], [63, 67], [64, 68], [65, 69], [66, 70], [67, 72], [68, 75], [69, 80] ]); var options = { hAxis: { title: 'Time' }, vAxis: { title: 'Popularity' } }; var chart = new google.visualization.LineChart(document.getElementById('chart_div')); var vAxisMinMax = calcMinMax(data,1); options.vAxis = {'viewWindow': {'min': vAxisMinMax.min, 'max': vAxisMinMax.max}}; chart.draw(data, options); } function calcMinMax(data, colIndex) { var totalMin = data.getValue(0,colIndex); var totalMax = data.getValue(0,colIndex); for(var i = 0; i < data.getNumberOfRows();i++){ if ( data.getValue(i, colIndex) < totalMin ) { totalMin = data.getValue(i, colIndex); } if ( data.getValue(i, colIndex) > totalMax ) { totalMax = data.getValue(i, colIndex); } } return {'min': totalMin, 'max': totalMax }; } 
 <script type="text/javascript" src="https://www.google.com/jsapi"></script> <div id="chart_div"></div> 
0
source share

All Articles