Flot是純Javascript實現的基於jQuery的圖表插件,主要支持線狀圖和柱狀圖的繪制(通過插件也可以支持餅狀圖)。
它的特點是使用簡單、圖形美觀,支持鼠標跟蹤及縮放功能。
Flot是基於canvas進行圖表的繪制,可以在IE6+/Firefox2+/Safari3+/Opera9.5+/Chrome等主流瀏覽器上運行;其中IE9以下瀏覽器不支持canvas標記,需要額外引用excanvas庫(VML)來實現。
基本使用
首先,在頁面頭部引用腳本:
<!--[if lte IE 8]><script src="js/excanvas.min.js"></script><![endif]--> <script src="js/jquery.min.js"></script> <script src="js/jquery.flot.min.js"></script>
在頁面中創建一個html標記,如div,然后通過樣式來指定圖表的大小:
<div id="placeholder" style="width:600px;height:300px;"></div>
最后,在DOM Ready事件中調用Flot的繪制方法$.plot:
$(function () { $.plot($("#placeholder"), [[[0, 0], [1, 2]]]); });
這樣就簡單的繪制了一條線。
數據格式
flot的數據格式是數組,數組中包含多個系列的數據,每個系列的數據對應一條線:
[ series1, series2, ... ]
每一個系列的數據可以是一個數組或者對象。
數組格式的數據,每一個點都是一個數組(分x/y軸):
[ [x1, y1], [x2, y2], ... ]
如下定義了三個點:
[ [1, 3], [2, 14.01], [3.5, 3.14] ]
繪制圖表的時候,會把這三個點連接起來;假如中間有個點使用了空值即null,這個點的兩邊則不會連接起來:
[ [1, 3], [2, 14.01], null, [3.5, 3.14], [5, 8] ]
需要注意的是,每個點的數據必須是數字,如果是字符串,可能會得到奇怪的錯誤。
對象格式的數據,如下:
{ color: color or number //顏色,如果不設置會自動生成 data: rawdata //數據 label: string //用於圖例說明 lines: specific lines options bars: specific bars options points: specific points options xaxis: number yaxis: number clickable: boolean hoverable: boolean shadowSize: number highlightColor: color or number }
通常不需要關心其他選項,只需要指定label和data:
{ label: "y = 3", data: [[0, 3], [10, 3]] }
對象格式的數據提供更大的靈活性,也更有利於代碼的可讀性,如下定義了兩個系列即兩條線:
[ { label: "Foo", data: [ [10, 1], [17, -14], [30, 5] ] }, { label: "Bar", data: [ [11, 13], [19, 11], [30, -7] ] } ]
選項設置
所有的選項都是可選的,改變某個屬性,只需要指定特定的屬性名稱:
{ // 自定義數據系列 series: { //共有屬性:點、線、柱狀圖的顯示方式 lines, points, bars: { // 是否顯示 show: boolean // 線寬度 lineWidth: number // 是否填充 fill: boolean or number // 填充色,如rgba(255, 255, 255, 0.8) fillColor: null or color/gradient } // 只針對點的屬性 points: { //點的半徑 radius: number // 繪制點的方法,默認為內置的圓形,可以通過自定義函數來定義其他形狀 symbol: "circle" or function } // 只針對柱狀圖的屬性 bars: { barWidth: number align: "left", "right" or "center" horizontal: boolean } // 只針對線的屬性 lines: { // 指定兩個點之間是用水平線還是垂直線連接 steps: boolean } // 設置陰影的大小,0消除陰影 shadowSize: number // 鼠標懸停時的顏色 highlightColor: color or number } // 設置各個對應的數據序列,即線的顏色 colors: [ color1, color2, ... ] // 網格設置 grid: { // 是否顯示格子 show: boolean // 數據的線是否繪制在網格線下 aboveData: boolean // 網格線顏色 color: color // 網格背景顏色 backgroundColor: color/gradient or null margin: number or margin object({top,left,bottom,right}) // 刻度與網格間距 labelMargin: number axisMargin: number markings: array of markings or (fn: axes -> array of markings) // 邊框寬度 borderWidth: number // 邊框顏色 borderColor: color or null minBorderMargin: number or null // 監聽鼠標點擊,會生成plotclick事件 clickable: boolean // 監聽鼠標移動,會生成plothover事件 hoverable: boolean // 鼠標附近元素高亮顯示 autoHighlight: boolean mouseActiveRadius: number } interaction: { // 最大重繪延遲 redrawOverlayInterval: number or -1 } // x,y軸的設置 xaxis, yaxis: { show: null or true/false // 刻度文字顯示的位置 position: "bottom" or "top" or "left" or "right" // 設置成time類型時可以用時間作為數據 mode: null or "time" ("time" requires jquery.flot.time.js plugin) // 時區,僅用於time模式 timezone: null, "browser" or timezone (only makes sense for mode: "time") // 軸文字和刻度文字顏色 color: null or color spec // 單獨定義刻度文字顏色 tickColor: null or color spec font: null or font spec object // 最大最小只范圍,不設置則自動計算 min: null or number max: null or number autoscaleMargin: null or number // 對數據進行計算后再繪制 transform: null or fn: number -> number inverseTransform: null or fn: number -> number // 用於自定義刻度顯示 ticks: null or number or ticks array or (fn: axis -> ticks array) tickSize: number or array minTickSize: number or array // 格式化刻度顯示 tickFormatter: (fn: number, object -> string) or string // 刻度顯示精確度,即小數位數 tickDecimals: null or number // 刻度區域大小 labelWidth: null or number labelHeight: null or number reserveSpace: null or true tickLength: null or number alignTicksWithAxis: null or number } // 定義多個坐標軸 xaxes: [] yaxes: [] // 圖例 legend: { show: boolean // 格式化圖例的顯示 labelFormatter: null or (fn: string, series object -> string) labelBoxBorderColor: color noColumns: number position: "ne" or "nw" or "se" or "sw" margin: number of pixels or [x margin, y margin] backgroundColor: null or color backgroundOpacity: number between 0 and 1
//圖例的容器,用於從圖表中分離 container: null or jQuery object/DOM element/jQuery expression sorted: null/false, true, "ascending", "descending" or a comparator } }
格式化圖例的顯示
通過legend參數的labelFormatter參數來格式化圖例的顯示,其中series為一個對象(屬性參考對象格式的數據):
labelFormatter: function (label, series) { // series is the series object for the label return '<a href="#' + label + '" title="' + series.label + '">' + label + '</a>'; }
軸的設置
自定義刻度的顯示,可以通過ticks參數來設置,如下定義X軸:
xaxis: { ticks: [0, 2, 4, 8, 10, 15] }
這樣軸上只會顯示以上定義的刻度。當有時候數據超出這個范圍時,部分刻度會被隱藏,這時候就需要手動指定min/max參數,如下:
$.plot($("#placeholder"), [{ label: "Foo", data: [[10, 1], [17, -14], [30, 5]] }, { label: "Bar", data: [[11, 13], [19, 11], [30, -7]] } ], { xaxis: { ticks: [0, 2, 4, 8, 10, 15], min: 0, max: 30 } } );
ticks參數還可以定制刻度顯示的文字:
ticks: [[0, "零"], [2, "二"], [4, "四"], [8, "八"], [10, "十"], [15, "十五"]]
最強大的還是通過自定義函數,通過tickFormatter參數:
tickFormatter: function(axis) { return "數字" + axis.toString(); }
繪制多個刻度軸
如下,繪制兩個y軸,同時需要在數據中指定屬於哪個軸:
$.plot($("#placeholder"), [ { label: "Foo", data: [[10, 1], [17, -14], [30, 5]] }, { label: "Bar", data: [[11, 13], [19, 11], [30, -7]] }, { label: "Three", data: [[2, 6], [5, 8], [18, 15]], yaxis: 2 }, ], { xaxes: [{ position: "bottom" }], yaxes: [{ position: "left" }, { position: "right", min: 2 }] } );
時間格式的數據
使用時間格式的數據需要引用jquery.flot.time.js,它支持以下格式的時間格式化:
%a: weekday name (customizable) %b: month name (customizable) %d: day of month, zero-padded (01-31) %e: day of month, space-padded ( 1-31) %H: hours, 24-hour time, zero-padded (00-23) %I: hours, 12-hour time, zero-padded (01-12) %m: month, zero-padded (01-12) %M: minutes, zero-padded (00-59) %S: seconds, zero-padded (00-59) %y: year (two digits) %Y: year (four digits) %p: am/pm %P: AM/PM (uppercase version of %p) %w: weekday as number (0-6, 0 being Sunday)
還支持自定義月份、一周中每一天的名稱:
monthNames: ["jan", "feb", "mar", "apr", "maj", "jun", "jul", "aug", "sep", "okt", "nov", "dec"] dayNames: ["dim", "lun", "mar", "mer", "jeu", "ven", "sam"]
使用如下:
$.plot($("#placeholder"), [{ label: "Foo", data: [[new Date(2010, 1, 1), 1], [new Date(2010, 5, 1), -14], [new Date(2010, 10, 1), 5]] }, { label: "Bar", data: [[new Date(2010, 2, 1), 13], [new Date(2010, 6, 1), 11], [new Date(2010, 12, 1), -7]] } ], { xaxis: { mode: "time", timeformat: "%y/%m/%d" } } );
當然,如果不使用timeformat的話,也可以用tickFormatter來格式化顯示:
tickFormatter: function (val, axis) { var d = new Date(val); console.log(val) return (d.getUTCMonth() + 1) + "/" + d.getUTCDate() + "/" + d.getFullYear(); }
特殊的顯示需求
可能需要在同一個點上進行時間的對比,比如x軸:
$.plot($("#placeholder"), [ { label: "Foo", data: [[1, new Date(2010, 1, 1)], [2, new Date(2010, 5, 1)], [3, new Date(2010, 10, 1)]] }, { label: "Bar", data: [[1, new Date(2010, 2, 1)], [2, new Date(2010, 6, 1)], [3, new Date(2010, 12, 1)]] } ], { yaxis: { mode: "time", timeformat: "%y/%m/%d" }, xaxis: { ticks: [[1, "一"], [2, "二"], [3, "三"]] } } );
在以上方法中,把x軸和x軸刻度的值一一對應,當然也可以換成y軸。
控制線和點的顯示
通過series參數,可以控制線的填充、點的顯示(點默認是不顯示的):
series: { lines: { show: true, fill:true }, points: { show: true, fill: false } }
顏色的控制
flot有多個參數都用到了顏色,均可以通過定義單個、或多個顏色來控制每個數據呈現的顏色:
colors: ["#d18b2c", "#dba255", "#919733"]
再比如網格的背景色:
grid: { backgroundColor: { colors: ["#000", "#999"] } }
顏色還有更加詳細的選項來定義:
{ colors: [{ opacity: 0.8 }, { brightness: 0.6, opacity: 0.8 } ] }
跟蹤鼠標事件
主要有鼠標移動和點擊事件,需要先開啟相應開關:
grid: { clickable: true, hoverable: true }
然后再綁定相應的事件,如點擊事件:
$("#placeholder").bind("plotclick", function (event, pos, item) { console.log("You clicked at " + pos.x + ", " + pos.y); // axis coordinates for other axes, if present, are in pos.x2, pos.x3, ... // if you need global screen coordinates, they are pos.pageX, pos.pageY if (item) { console.log(item.series, item.datapoint); console.log("You clicked a point!"); } });
plothover事件的的綁定也一樣。item對象主要有以下屬性:
item: { datapoint: the point, e.g. [0, 2] dataIndex: the index of the point in the data array series: the series object seriesIndex: the index of the series pageX, pageY: the global screen coordinates of the point }
內置方法
- highlight(series, datapoint):高亮顯示point
- unhighlight(series, datapoint) or unhighlight():取消高亮point,沒有參數則取消高亮當前的point
- setData(data):重新設置數據,需要調用draw()方法來重繪
- setupGrid():重新計算坐標、軸,需要調用draw()方法來重繪
- draw():重繪圖表
- triggerRedrawOverlay():更新可交互的區域,如point
- width()/height():獲取寬高
- offset():獲取偏移
- pointOffset({ x: xpos, y: ypos }):獲取某個點相對於placeholder的div的偏移
- resize():調整圖表的大小
- shutdown():清理即取消綁定所有事件處理函數
還有一些其他函數,但需要你比較了解flot內部運作,否則可能產生不好的結果:
- getData():獲取數據,即在$.plot方法中定義的數據
- getAxes():獲取坐標軸
- getPlaceholder():獲取placeholder元素
- getCanvas():獲取canvas對象
- getPlotOffset():獲取偏移
- getOptions():獲取設置的選項
如highlight方法,就可以在click事件中使用:
var pl = $.plot($("#placeholder"), data, options); $("#placeholder").bind("plotclick", function (event, pos, item) { if (item) { pl.highlight(item.series, item.datapoint); } });
flot還提供了一些函數,用於在繪圖各個流程步驟中進行一些額外的處理,這里不再列出。
相關資源
插件主頁:http://code.google.com/p/flot/ (API文檔:http://people.iola.dk/olau/flot/API.txt)
最新版本:https://github.com/flot/flot (API文檔:https://github.com/flot/flot/blob/master/API.md)
在線DEMO:http://people.iola.dk/olau/flot/examples/
Flot的插件:http://code.google.com/p/flot/wiki/Plugins (實現更多類型的圖表)