以下提供幾個程式碼範例,協助您瞭解如何使用 Google Visualization API。
資料表範例
function drawTable() {
var data = new google.visualization.DataTable();
data.addColumn('string', 'Name');
data.addColumn('number', 'Salary');
data.addColumn('boolean', 'Full Time');
data.addRows(5);
data.setCell(0, 0, 'John');
data.setCell(0, 1, 10000, '$10,000');
data.setCell(0, 2, true);
data.setCell(1, 0, 'Mary');
data.setCell(1, 1, 25000, '$25,000');
data.setCell(1, 2, true);
data.setCell(2, 0, 'Steve');
data.setCell(2, 1, 8000, '$8,000');
data.setCell(2, 2, false);
data.setCell(3, 0, 'Ellen');
data.setCell(3, 1, 20000, '$20,000');
data.setCell(3, 2, true);
data.setCell(4, 0, 'Mike');
data.setCell(4, 1, 12000, '$12,000');
data.setCell(4, 2, false);
var table = new google.visualization.Table(document.getElementById('table_div'));
table.draw(data, {showRowNumber: true, width: '100%', height: '100%'});
google.visualization.events.addListener(table, 'select', function() {
var row = table.getSelection()[0].row;
alert('You selected ' + data.getValue(row, 0));
});
}
自訂表格範例
<style>
.bold-green-font {
font-weight: bold;
color: green;
}
.bold-font {
font-weight: bold;
}
.right-text {
text-align: right;
}
.large-font {
font-size: 15px;
}
.italic-darkblue-font {
font-style: italic;
color: darkblue;
}
.italic-purple-font {
font-style: italic;
color: purple;
}
.underline-blue-font {
text-decoration: underline;
color: blue;
}
.gold-border {
border: 3px solid gold;
}
.deeppink-border {
border: 3px solid deeppink;
}
.orange-background {
background-color: orange;
}
.orchid-background {
background-color: orchid;
}
.beige-background {
background-color: beige;
}
</style>
...
function drawTable() {
var cssClassNames = {
'headerRow': 'italic-darkblue-font large-font bold-font',
'tableRow': '',
'oddTableRow': 'beige-background',
'selectedTableRow': 'orange-background large-font',
'hoverTableRow': '',
'headerCell': 'gold-border',
'tableCell': '',
'rowNumberCell': 'underline-blue-font'};
var options = {'showRowNumber': true, 'allowHtml': true, 'cssClassNames': cssClassNames};
var data = new google.visualization.DataTable();
data.addColumn('string', 'Name');
data.addColumn('number', 'Salary');
data.addColumn('boolean', 'Full Time');
data.addRows(5);
data.setCell(0, 0, 'John');
data.setCell(0, 1, 10000, '$10,000', {'className': 'bold-green-font large-font right-text'});
data.setCell(0, 2, true, {'style': 'background-color: red;'});
data.setCell(1, 0, 'Mary', null, {'className': 'bold-font'});
data.setCell(1, 1, 25000, '$25,000', {'className': 'bold-font right-text'});
data.setCell(1, 2, true, {'className': 'bold-font'});
data.setCell(2, 0, 'Steve', null, {'className': 'deeppink-border'});
data.setCell(2, 1, 8000, '$8,000', {'className': 'deeppink-border right-text'});
data.setCell(2, 2, false, null);
data.setCell(3, 0, 'Ellen', null, {'className': 'italic-purple-font large-font'});
data.setCell(3, 1, 20000, '$20,000');
data.setCell(3, 2, true);
data.setCell(4, 0, 'Mike');
data.setCell(4, 1, 12000, '$12,000');
data.setCell(4, 2, false);
var container = document.getElementById('table');
var table = new google.visualization.Table(container);
table.draw(data, options);
table.setSelection([{'row': 4}]);
}
度量範例
Temperature:
<html>
<head>
<script type="text/javascript" src="https://www.gstatic.com/charts/loader.js"></script>
<script type="text/javascript">
google.charts.load('current', {'packages':['gauge']});
google.charts.setOnLoadCallback(drawGauge);
var gaugeOptions = {min: 0, max: 280, yellowFrom: 200, yellowTo: 250,
redFrom: 250, redTo: 280, minorTicks: 5};
var gauge;
function drawGauge() {
gaugeData = new google.visualization.DataTable();
gaugeData.addColumn('number', 'Engine');
gaugeData.addColumn('number', 'Torpedo');
gaugeData.addRows(2);
gaugeData.setCell(0, 0, 120);
gaugeData.setCell(0, 1, 80);
gauge = new google.visualization.Gauge(document.getElementById('gauge_div'));
gauge.draw(gaugeData, gaugeOptions);
}
function changeTemp(dir) {
gaugeData.setValue(0, 0, gaugeData.getValue(0, 0) + dir * 25);
gaugeData.setValue(0, 1, gaugeData.getValue(0, 1) + dir * 20);
gauge.draw(gaugeData, gaugeOptions);
}
</script>
</head>
<body>
<div id="gauge_div" style="width:280px; height: 140px;"></div>
<input type="button" value="Go Faster" onclick="changeTemp(1)" />
<input type="button" value="Slow down" onclick="changeTemp(-1)" />
</body>
</html>
互動範例
這個範例說明如何結合圖表來創造更複雜的互動性。
這項工具會示範下列功能:
- 如何使用 DataView 物件來限制及設定資料表中的資料格式。
- 如何將兩個圖表連結至相同資料。
- 如何使用表格圖表的「sort'」事件、
- 如何使用 formatters 重新格式化顯示的資料。
按一下表格標題,即可查看一併排序的柱狀圖。
請注意,您可以使用控制項和資訊主頁合併多個圖表及控制選項,控管圖表顯示的資料。
function drawSort() {
var data = new google.visualization.DataTable();
data.addColumn('string', 'Name');
data.addColumn('number', 'Salary');
data.addColumn('boolean', 'Full Time');
data.addRows(5);
data.setCell(0, 0, 'John');
data.setCell(0, 1, 10000);
data.setCell(0, 2, true);
data.setCell(1, 0, 'Mary');
data.setCell(1, 1, 25000);
data.setCell(1, 2, true);
data.setCell(2, 0, 'Steve');
data.setCell(2, 1, 8000);
data.setCell(2, 2, false);
data.setCell(3, 0, 'Ellen');
data.setCell(3, 1, 20000);
data.setCell(3, 2, true);
data.setCell(4, 0, 'Mike');
data.setCell(4, 1, 12000);
data.setCell(4, 2, false);
var view = new google.visualization.DataView(data);
view.setColumns([0, 1]);
var formatter = new google.visualization.NumberFormat({prefix: '$'});
formatter.format(data, 1); // Apply formatter to second column
var table = new google.visualization.Table(document.getElementById('table_sort_div'));
table.draw(data, {width: '100%', height: '100%'});
var chart = new google.visualization.BarChart(document.getElementById('chart_sort_div'));
chart.draw(view);
google.visualization.events.addListener(table, 'sort',
function(event) {
data.sort([{column: event.column, desc: !event.ascending}]);
chart.draw(view);
});
}
完整 HTML 網頁範例
建立網頁的端對端範例,用於在網頁中嵌入視覺化圖表。還會示範連結至 Google 試算表的圖表,以及使用視覺化「事件」互動的兩個圖表。
這個範例顯示一個簡單的統計資料頁面,提供立牌電影連鎖店的熱門電影和電影院地點。
這個頁麵包含「地圖」和「資料表」視覺呈現,可彼此互動以顯示劇院地點。頁面含有柱狀圖,顯示每部電影的售票數量。並從 Google 試算表衍生資料。 您可以查看這份試算表的發布版本,瞭解完整內容。
<html>
<head>
<script type="text/javascript" src="https://www.gstatic.com/charts/loader.js"></script>
<script type="text/javascript">
google.charts.load('current', {
'packages': ['table', 'map', 'corechart'],
// Note: you will need to get a mapsApiKey for your project.
// See: https://developers.google.com/chart/interactive/docs/basic_load_libs#load-settings
'mapsApiKey': 'AIzaSyD-9tSrke72PouQMnMX-a7eZSW0jkFMBWY'
});
google.charts.setOnLoadCallback(initialize);
function initialize() {
// The URL of the spreadsheet to source data from.
var query = new google.visualization.Query(
'https://spreadsheets.google.com/pub?key=pCQbetd-CptF0r8qmCOlZGg');
query.send(draw);
}
function draw(response) {
if (response.isError()) {
alert('Error in query');
}
var ticketsData = response.getDataTable();
var chart = new google.visualization.ColumnChart(
document.getElementById('chart_div'));
chart.draw(ticketsData, {'isStacked': true, 'legend': 'bottom',
'vAxis': {'title': 'Number of tickets'}});
var geoData = google.visualization.arrayToDataTable([
['Lat', 'Lon', 'Name', 'Food?'],
[51.5072, -0.1275, 'Cinematics London', true],
[48.8567, 2.3508, 'Cinematics Paris', true],
[55.7500, 37.6167, 'Cinematics Moscow', false]]);
var geoView = new google.visualization.DataView(geoData);
geoView.setColumns([0, 1]);
var table =
new google.visualization.Table(document.getElementById('table_div'));
table.draw(geoData, {showRowNumber: false, width: '100%', height: '100%'});
var map =
new google.visualization.Map(document.getElementById('map_div'));
map.draw(geoView, {showTip: true});
// Set a 'select' event listener for the table.
// When the table is selected, we set the selection on the map.
google.visualization.events.addListener(table, 'select',
function() {
map.setSelection(table.getSelection());
});
// Set a 'select' event listener for the map.
// When the map is selected, we set the selection on the table.
google.visualization.events.addListener(map, 'select',
function() {
table.setSelection(map.getSelection());
});
}
</script>
</head>
<body>
<table align="center">
<tr valign="top">
<td style="width: 50%;">
<div id="map_div" style="width: 400px; height: 300;"></div>
</td>
<td style="width: 50%;">
<div id="table_div"></div>
</td>
</tr>
<tr>
<td colSpan=2>
<div id="chart_div" style="align: center; width: 700px; height: 300px;"></div>
</td>
</tr>
</table>
</body>
</html>
查詢包裝函式範例
這個範例說明如何建立 JavaScript 物件,納入為您傳送查詢的許多層面。這個物件稱為 QueryWrapper,以查詢字串、視覺化的處理常式和一組視覺呈現選項進行例項化。這會向外部呼叫端 sendAndDraw()
公開一種方法,此方法會傳送查詢字串、處理回應,並呼叫視覺化的 draw()
,或在查詢傳回錯誤時顯示錯誤訊息。此代管頁面會以組織圖視覺化呈現結果。
以下是代管網頁的程式碼:
<!DOCTYPE html>
<html>
<head>
<title>Query Wrapper Example</title>
<script type="text/javascript" src="https://www.gstatic.com/charts/loader.js"></script>
<script type="text/javascript" src="querywrapper.js"></script>
<script type="text/javascript">
google.charts.load('current', {'packages' : ['orgchart']});
google.charts.setOnLoadCallback(function() { sendAndDraw('') });
var dataSourceUrl = 'https://spreadsheets.google.com/tq?key=rCaVQNfFDMhOM6ENNYeYZ9Q&pub=1';
var query;
function sendAndDraw(queryString) {
var container = document.getElementById('orgchart');
var orgChart = new google.visualization.OrgChart(container);
query && query.abort();
query = new google.visualization.Query(dataSourceUrl + queryString);
var queryWrapper = new QueryWrapper(query, orgChart, {'size': 'large'}, container);
queryWrapper.sendAndDraw();
}
</script>
</head>
<body>
<h1>Query Wrapper Example</h1>
<form action="">
<span> This example uses the following spreadsheet: <br />
<a href="https://spreadsheets.google.com/pub?key=rCaVQNfFDMhOM6ENNYeYZ9Q">
https://spreadsheets.google.com/pub?key=rCaVQNfFDMhOM6ENNYeYZ9Q
</a></span>
<br /><br />
<select onChange="sendAndDraw(this.value)">
<option value="">No query string</option>
<option value="&tq=limit 3">query=limit 3</option>
<option value="&tq=select G,H">(Error) query=select G,H</option>
</select>
</form>
<br />
<div id="orgchart"></div>
</body>
</html>
以下是 QueryWrapper 物件的 JavaScript。
/**
* A google.visualization.Query Wrapper. Sends a
* query and draws the visualization with the returned data or outputs an
* error message.
*
* DISCLAIMER: This is an example code which you can copy and change as
* required. It is used with the google visualization API which is assumed to
* be loaded to the page. For more info see:
* https://developers.google.com/chart/interactive/docs/reference#Query
*/
/**
* Constructs a new query wrapper with the given query, visualization,
* visualization options, and error message container. The visualization
* should support the draw(dataTable, options) method.
* @constructor
*/
var QueryWrapper = function(query, visualization, visOptions, errorContainer) {
this.query = query;
this.visualization = visualization;
this.options = visOptions || {};
this.errorContainer = errorContainer;
this.currentDataTable = null;
if (!visualization || !('draw' in visualization) ||
(typeof(visualization['draw']) != 'function')) {
throw Error('Visualization must have a draw method.');
}
};
/** Draws the last returned data table, if no data table exists, does nothing.*/
QueryWrapper.prototype.draw = function() {
if (!this.currentDataTable) {
return;
}
this.visualization.draw(this.currentDataTable, this.options);
};
/**
* Sends the query and upon its return draws the visualization.
* If the query is set to refresh then the visualization will be drawn upon
* each refresh.
*/
QueryWrapper.prototype.sendAndDraw = function() {
var query = this.query;
var self = this;
query.send(function(response) {self.handleResponse(response)});
};
/** Handles the query response returned by the data source. */
QueryWrapper.prototype.handleResponse = function(response) {
this.currentDataTable = null;
if (response.isError()) {
this.handleErrorResponse(response);
} else {
this.currentDataTable = response.getDataTable();
this.draw();
}
};
/** Handles a query response error returned by the data source. */
QueryWrapper.prototype.handleErrorResponse = function(response) {
var message = response.getMessage();
var detailedMessage = response.getDetailedMessage();
if (this.errorContainer) {
google.visualization.errors.addError(this.errorContainer,
message, detailedMessage, {'showInTooltip': false});
} else {
throw Error(message + ' ' + detailedMessage);
}
};
/** Aborts the sending and drawing. */
QueryWrapper.prototype.abort = function() {
this.query.abort();
};
資料表查詢包裝函式範例
以下範例說明如何在分頁式表格視覺化中顯示大型資料集,而不必透過單一要求擷取所有資料。如果網頁上有大量資料,您就會想要避免在網頁上一次要求或儲存所有資料的負擔。
JavaScript 會定義一個物件 TableQueryWrapper,管理發出要求的 google.visualization.Query
物件和資料表視覺化作業,處理排序和分頁作業。此物件已透過 google.visualization.Query
例項例項化、用於保存視覺呈現的頁面元素控制代碼以及它擲回的任何錯誤,以及傳送至 draw()
方法的任何選項 (包括要擷取的資料列數量,做為 pageSize
選項)。這個物件可擷取及處理分頁和排序事件,藉此管理表格視覺化。
使用者頁面向前或向後傳送時,TableQueryWrapper 會建立並傳送具有適當 LIMIT 和 OFFSET 值的新查詢,以便重新填入資料表頁面,藉此處理事件。同樣地,當使用者按一下資料欄來變更排序順序時,TableQueryWrapper 會透過建立並傳送具有適當 ORDER BY 子句的新查詢來處理事件,並重設回偏移 0。
在以下範例中,下拉式選單方塊可讓您選取要顯示的資料表列數。如果發生異動,代管頁面會建立新的 TableQueryWrapper 執行個體,然後傳送含有 LIMIT 子句的新查詢,該子句反映所選的資料列數量,但沒有 OFFSET 子句 (也就是跳回第一個資料列)。
以下是代管網頁的程式碼:
<!DOCTYPE html>
<html>
<head>
<title>Table Query Wrapper Example</title>
<script type="text/javascript" src="https://www.gstatic.com/charts/loader.js"></script>
<script type="text/javascript" src="tablequerywrapper.js"></script>
<script type="text/javascript">
google.charts.load('current', {'packages' : ['table']});
google.charts.setOnLoadCallback(init);
var dataSourceUrl = 'https://spreadsheets.google.com/tq?key=rh_6pF1K_XsruwVr_doofvw&pub=1';
var query, options, container;
function init() {
query = new google.visualization.Query(dataSourceUrl);
container = document.getElementById("table");
options = {'pageSize': 5};
sendAndDraw();
}
function sendAndDraw() {
query.abort();
var tableQueryWrapper = new TableQueryWrapper(query, container, options);
tableQueryWrapper.sendAndDraw();
}
function setOption(prop, value) {
options[prop] = value;
sendAndDraw();
}
</script>
</head>
<body>
<p>This example uses the following spreadsheet: <br />
<a href="https://spreadsheets.google.com/pub?key=rh_6pF1K_XsruwVr_doofvw">
https://spreadsheets.google.com/pub?key=rh_6pF1K_XsruwVr_doofvw
</a>
</p>
<form action="">
Number of rows to show:
<select onChange="setOption('pageSize', parseInt(this.value, 10))">
<option value="0">0</option>
<option value="3">3</option>
<option selected=selected value="5">5</option>
<option value="8">8</option>
<option value="-1">-1</option>
</select>
</form>
<br />
<div id="table"></div>
</body>
</html>
以下是 TableQueryWrapper 物件的 JavaScript 程式碼:
/**
* A wrapper for a query and a table visualization.
* The object only requests 1 page + 1 row at a time, by default, in order
* to minimize the amount of data held locally.
* Table sorting and pagination is executed by issuing
* additional requests with appropriate query parameters.
* E.g., for getting the data sorted by column 'A' the following query is
* attached to the request: 'tq=order by A'.
*
* Note: Discards query strings set by the user on the query object using
* google.visualization.Query#setQuery.
*
* DISCLAIMER: This is an example code which you can copy and change as
* required. It is used with the google visualization API table visualization
* which is assumed to be loaded to the page. For more info see:
* https://developers.google.com/chart/interactive/docs/gallery/table
* https://developers.google.com/chart/interactive/docs/reference#Query
*/
/**
* Constructs a new table query wrapper for the specified query, container
* and tableOptions.
*
* Note: The wrapper clones the options object to adjust some of its properties.
* In particular:
* sort {string} set to 'event'.
* page {string} set to 'event'.
* pageSize {Number} If number <= 0 set to 10.
* showRowNumber {boolean} set to true.
* firstRowNumber {number} set according to the current page.
* sortAscending {boolean} set according to the current sort.
* sortColumn {number} set according to the given sort.
* @constructor
*/
var TableQueryWrapper = function(query, container, options) {
this.table = new google.visualization.Table(container);
this.query = query;
this.sortQueryClause = '';
this.pageQueryClause = '';
this.container = container;
this.currentDataTable = null;
var self = this;
var addListener = google.visualization.events.addListener;
addListener(this.table, 'page', function(e) {self.handlePage(e)});
addListener(this.table, 'sort', function(e) {self.handleSort(e)});
options = options || {};
options = TableQueryWrapper.clone(options);
options['sort'] = 'event';
options['page'] = 'event';
options['showRowNumber'] = true;
var buttonConfig = 'pagingButtonsConfiguration';
options[buttonConfig] = options[buttonConfig] || 'both';
options['pageSize'] = (options['pageSize'] > 0) ? options['pageSize'] : 10;
this.pageSize = options['pageSize'];
this.tableOptions = options;
this.currentPageIndex = 0;
this.setPageQueryClause(0);
};
/**
* Sends the query and upon its return draws the Table visualization in the
* container. If the query refresh interval is set then the visualization will
* be redrawn upon each refresh.
*/
TableQueryWrapper.prototype.sendAndDraw = function() {
this.query.abort();
var queryClause = this.sortQueryClause + ' ' + this.pageQueryClause;
this.query.setQuery(queryClause);
this.table.setSelection([]);
var self = this;
this.query.send(function(response) {self.handleResponse(response)});
};
/** Handles the query response after a send returned by the data source. */
TableQueryWrapper.prototype.handleResponse = function(response) {
this.currentDataTable = null;
if (response.isError()) {
google.visualization.errors.addError(this.container, response.getMessage(),
response.getDetailedMessage(), {'showInTooltip': false});
} else {
this.currentDataTable = response.getDataTable();
this.table.draw(this.currentDataTable, this.tableOptions);
}
};
/** Handles a sort event with the given properties. Will page to page=0. */
TableQueryWrapper.prototype.handleSort = function(properties) {
var columnIndex = properties['column'];
var isAscending = properties['ascending'];
this.tableOptions['sortColumn'] = columnIndex;
this.tableOptions['sortAscending'] = isAscending;
// dataTable exists since the user clicked the table.
var colID = this.currentDataTable.getColumnId(columnIndex);
this.sortQueryClause = 'order by `' + colID + (!isAscending ? '` desc' : '`');
// Calls sendAndDraw internally.
this.handlePage({'page': 0});
};
/** Handles a page event with the given properties. */
TableQueryWrapper.prototype.handlePage = function(properties) {
var localTableNewPage = properties['page']; // 1, -1 or 0
var newPage = 0;
if (localTableNewPage != 0) {
newPage = this.currentPageIndex + localTableNewPage;
}
if (this.setPageQueryClause(newPage)) {
this.sendAndDraw();
}
};
/**
* Sets the pageQueryClause and table options for a new page request.
* In case the next page is requested - checks that another page exists
* based on the previous request.
* Returns true if a new page query clause was set, false otherwise.
*/
TableQueryWrapper.prototype.setPageQueryClause = function(pageIndex) {
var pageSize = this.pageSize;
if (pageIndex < 0) {
return false;
}
var dataTable = this.currentDataTable;
if ((pageIndex == this.currentPageIndex + 1) && dataTable) {
if (dataTable.getNumberOfRows() <= pageSize) {
return false;
}
}
this.currentPageIndex = pageIndex;
var newStartRow = this.currentPageIndex * pageSize;
// Get the pageSize + 1 so that we can know when the last page is reached.
this.pageQueryClause = 'limit ' + (pageSize + 1) + ' offset ' + newStartRow;
// Note: row numbers are 1-based yet dataTable rows are 0-based.
this.tableOptions['firstRowNumber'] = newStartRow + 1;
return true;
};
/** Performs a shallow clone of the given object. */
TableQueryWrapper.clone = function(obj) {
var newObj = {};
for (var key in obj) {
newObj[key] = obj[key];
}
return newObj;
};
滑鼠遊標懸停工具提示範例
本範例說明如何監聽滑鼠遊標懸停事件,以便在圖表中顯示工具提示。
<script>
// barsVisualization must be global in our script tag to be able
// to get and set selection.
var barsVisualization;
function drawMouseoverVisualization() {
var data = new google.visualization.DataTable();
data.addColumn('string', 'Year');
data.addColumn('number', 'Score');
data.addRows([
['2005',3.6],
['2006',4.1],
['2007',3.8],
['2008',3.9],
['2009',4.6]
]);
barsVisualization = new google.visualization.ColumnChart(document.getElementById('mouseoverdiv'));
barsVisualization.draw(data, null);
// Add our over/out handlers.
google.visualization.events.addListener(barsVisualization, 'onmouseover', barMouseOver);
google.visualization.events.addListener(barsVisualization, 'onmouseout', barMouseOut);
}
function barMouseOver(e) {
barsVisualization.setSelection([e]);
}
function barMouseOut(e) {
barsVisualization.setSelection([{'row': null, 'column': null}]);
}
</script>