Chartjs 是一套免費且開放原始碼(採用 MIT 授權) 的網頁圖表繪製套件,可繪製 6 種基本圖表:line(折線圖/線條圖)、bar(條狀圖,直/橫條)、radar(雷達圖)、doughnut & pie(圓餅圖/甜甜圈圖)、polar area(極座標圖餅圖/南丁格爾玫瑰圖/雞冠花圖/風花圖)、bubble(氣泡圖),
2 種衍伸圖表(不知道這兩種圖表的中文名稱):
scatter(散佈圖)、area
還可以上述 8 種圖表混合使用。
將 chartjs 上傳到您的網站內的指定目錄下,在本例為 /plugin/
PHP 網頁內容
...
...
<head>
<script src="/jquery/jquery-1.11.3.min.js"></script> <!-- jQuery 不是必需, 但我不熟純 javascript -->
<script src="/plugin/chartjs/Chart.bundle.min.js"></script>
<script src="/plugin/chartjs/Chart.min.js"></script>
<script src="/plugin/chartjs/chartjs-plugin-zoom.min.js"></script>
<script src="/plugin/chartjs/utils.js"></script>
<script src="/plugin/chartjs/moment-with-locales.min.js"></script>
</head>
<!-- 設定圖表尺寸 -->
<style>
.chart
{
height:100; width:45%; margin: 20px;
}
</style>
...
...
<body>
<?php
// 宣告存放數據的陣列
$aExname = array(); // 考試名稱
$aDlday = array(); // 單日下載
$aDlcnt = array(); // 總下載數
$aExamday = array(); // 單日練習
$aExamcnt = array(); // 總練習數
// 建立資料庫連線, 並取得資料
$pdoStat = $pdo->prepare($sql);
$pdoStat->execute();
$rs = $pdoStat->fetchAll();
if(count($rs)>0)
{
foreach($rs as $row)
{
// 將各欄位值存入陣列
array_push($aExname, $row['exname']); // 考試名稱
array_push($aDlday, $row['dlday']); // 單日下載
array_push($aDlcnt, $row['dlcnt']); // 總下載數
array_push($aExamday, $row['examday']); // 單日練習
array_push($aExamcnt, $row['examcnt']); // 總練習數
}
// 將陣列自 PHP 轉出變為 javascript 陣列
// str_pad() 沒什麼作用, 只是讓轉出的 HTML 原始碼易於閱讀而已
echo str_pad(" ", 28)."<script language='javascript'>\n";
echo str_pad(" ", 28).'var aExname = '.json_encode($aExname).";\n"; // 考試名稱
echo str_pad(" ", 28).'var aDlday = '.json_encode($aDlday).";\n"; // 單日下載
echo str_pad(" ", 28).'var aDlcnt = '.json_encode($aDlcnt).";\n"; // 總下載數
echo str_pad(" ", 28).'var aExamday = '.json_encode($aExamday).";\n"; // 單日練習
echo str_pad(" ", 28).'var aExamcnt = '.json_encode($aExamcnt).";\n"; // 總練習數
echo str_pad(" ", 28)."</script>\n";
}
?>
// 左, 右 放置 2 個直條圖
<div class="chart" style="float:left;">
<!-- 各考試單日統計 -->
<canvas id="chartDay" />
</div>
<div class="chart" style="float:right;">
<!-- 各考試總計 -->
<canvas id="chartTotal" />
</div>
<script language='javascript'>
var ctx1 = $("#chartDay");
var myChart1 = new Chart(ctx1,
{
type: 'bar', // 指定圖表為直條圖
data: {
datasets: [{
data: aExamday,
label: "單日練習",
borderColor: window.chartColors.green, // 有這幾個基本顏色可選:red, orange, yellow, green, blue, purple, grey
backgroundColor: window.chartColors.green
},
{
data: aDlday,
label: "單日下載",
borderColor: window.chartColors.red, // 折線顏色
backgroundColor: window.chartColors.red // legend 色塊顏色
}
],
labels: aExname
},
options: {
animation: {
duration: 0, // 不以動畫方式畫線
},
title: { // 圖表標題
display: true,
text: "各考試單日統計",
fontSize: 18
},
legend:{ // 各色直條圖所代表的群體
position: 'top' // 置於圖表上方, 另可置於 bottom, left, right
},
scales: {
yAxes: [{ // Y 軸的樣式
type: 'linear',
position: 'left',
ticks: { // 加上千位符
userCallback: function(value, index, values)
{
return value.toLocaleString();
}
}
}]
},
tooltips: { // 直條內的提示數字加上 千位符
callbacks: {
// this callback is used to create the tooltip label
label: function(tooltipItem, data)
{
var dataLabel = data.labels[tooltipItem.index];
var value = ': $' + data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index].toLocaleString();
if (Chart.helpers.isArray(dataLabel))
{
dataLabel = dataLabel.slice();
dataLabel[0] += value;
}
else
{
dataLabel += value;
}
return dataLabel;
}
}
},
onClick: function (event, arr)
{
// 可以指定點擊某個直條時,跳轉至指定的網頁
switch(arr[0]._view['label'])
{
case '條件1': window.location.href = "下個網頁";
break;
case '條件2': window.location.href = "下個網頁";
break;
...
...
}
}
}
});
/////////////////
var ctx2 = $("#chartTotal");
var myChart2 = new Chart(ctx2,
{
type: 'bar',
data: {
datasets: [{
data: aExamcnt,
label: "總練習數",
borderColor: window.chartColors.green,
backgroundColor: window.chartColors.yellow
},
{
data: aDlcnt,
label: "總下載數",
borderColor: window.chartColors.blue,
backgroundColor: window.chartColors.blue
}
],
labels: aExname
},
options: {
animation: {
duration: 0, // 不以動畫方式畫線
},
title: {
display: true,
text: "各考試總計",
fontSize: 18
},
legend:{
position: 'top'
},
scales: {
yAxes: [{
type: 'linear',
position: 'left',
ticks: { // 加上千位符
userCallback: function(value, index, values)
{
return value.toLocaleString();
}
}
}]
},
tooltips: { // 直條內的提示數字加上 千位符
callbacks: {
// this callback is used to create the tooltip label
label: function(tooltipItem, data)
{
var dataLabel = data.labels[tooltipItem.index];
var value = ': $' + data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index].toLocaleString();
if (Chart.helpers.isArray(dataLabel))
{
dataLabel = dataLabel.slice();
dataLabel[0] += value;
}
else
{
dataLabel += value;
}
return dataLabel;
}
}
},
onClick: function (event, arr)
{
// 可以指定點擊某個直條時,跳轉至指定的網頁
switch(arr[0]._view['label'])
{
case '條件1': window.location.href = "下個網頁";
break;
case '條件2': window.location.href = "下個網頁";
break;
...
...
}
}
}
});
</script>
...
...
</body>
</html>
圖表成果如下:
* 因圖表寬度較小,因此 chartjs 自動隱藏某些考試名稱,以下圖為例,只顯示單數欄的考試名稱
* 滑鼠至直條內時會顯示相應的數值
* 不知道是不是沒摸索到顏色的配置方法,Chartjs 不會自動幫您配顏色,所以您必須要自己先建立一個顏色陣列,要用時,再到陣列取顏色值;或是自己以亂數產生顏色值,只是以亂數產生,有時會碰到相臨 2 個顏色太相近的窘境。
還有另一套圖表套件 ---- ZingChart,老人家自己覺得蠻好用又功能強大,但下載免費版使用時,圖表會強制顯示該公司的 LOGO 打廣告。
若不在意該公司的 LOGO 老人家倒是蠻推 ZingChart 的,因為好上手,學習曲線低;但如果不想顯示 LOGO......就付費吧(老人家的長官就不希望看到 LOGO,所以後來採用 Chartjs)。
最新發現! Apache 基金會的 Apache ECharts,開放源碼,而且免費,也不難學習,更推!!
相關筆記 ----

沒有留言:
張貼留言