调用plot函数的方法如下:
1
|
var
plot = $.plot(placeholder, data, options)
|
1
2
3
4
5
6
7
8
9
10
11
12
13
|
{
color: color or number
data: rawdata
label: string
lines: specific lines options
bars: specific bars options
points: specific points options
xaxis: 1 or 2
yaxis: 1 or 2
clickable: boolean
hoverable: boolean
shadowSize: number
}
|
1
2
3
4
|
{
label:
"y = 3"
,
data: [[0, 3], [10, 3]]
}
|
label是说明这一个数据序列的含义的,如果只有一个序列的话就没有必要设置这个属性。如果有多个序列,就要设置label,从而可以在图中区分出序列的含义。
如果不设置color,那么会自动生成color来进行显示。
如果你想让用户添加和删除数据序列的话,剩下的属性就非常有用了。
xaxis和yaxis选项设置使用哪个维度,默认是设置成1的,如果设置成2的话,就使用第二个维度(x轴在上面,y轴在右边)。
clickable和hoverable可以设置成false,当整个图表设置成可交互时,这个选项可以让这条特定的数据序列让用户无法交互。
没有说明的属性会在后面详细介绍,大多数情况话都是使用默认值。当你要使用自己定义的值时,就会把默认的值给覆盖。
这是一个比较复杂的数据序列定义:
[ { label: "Foo", data: [ [10, 1], [17, -14], [30, 5] ] },
{ label: "Bar", data: [ [11, 13], [19, 11], [30, -7] ] } ]
Options的含义:
所有的选项都是完全可选的。如果想要修改的话,把它当作一个对象来处理就可以了:
1
2
3
4
5
6
|
var
options = {
series: {
lines: { show:
true
},
points: { show:
true
}
}
};
|
1
2
3
4
5
6
7
8
9
10
11
|
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
}
|
1
2
3
4
|
labelFormatter:
function
(label, series) {
// series is the series object for the label
return
'<a href="#'
+ label +
'" mce_href="#'
+ label +
'">'
+ label +
'</a>'
;
}
|
关于轴的用户设置:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
xaxis, yaxis: {
show:
null
or
true
/
false
position:
"bottom"
or
"top"
or
"left"
or
"right"
mode:
null
or
"time"
color:
null
or color spec
tickColor:
null
or color spec
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: range -> 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
}
|
show:如果不设置这个属性的话,flot会自动的来选择,比如:数据与轴有关系的话,那么就会把轴显示出来,当然更灵活的方式还是用
true或者false来设定这个属性。
position:用来定义轴文字显示的位置,是在X轴的上方还是下方,是在Y轴的左边还是右边。
mode:轴的数据类型,默认的是数值类型,当设置成time类型的话,就可以用时间做为一个轴。
color:定义轴标识文字和坐标的颜色。如果不设置的话,就与图表中网格的颜色是相同的。当然也可以自己来设置颜色,使用"tickColor"还
可以单独定义坐标的颜色。
min/max:描述轴最大值和最小值范围。如果不设置的话,flot会自动的计算并生成一个范围来进行显示。
autoscaleMargin:这个有一点难理解。flot自动计算min/max的范围的时候会加上一个值,从而防止有的点会放到图的边缘。这个属性只能
在不设置max/min的时候才可以使用。如果设置了一个margin,flot会延长轴的结束点从而构成一个完整的坐标。默认的设置是x轴没有margin,y轴有0.02的margin。默认的设置已经可以满足大多数的使用了。
"transform","inverseTransform":可以对原始的数据进行一些特殊的计算以后再进行绘制。比如:可以通过这种方法来绘制一些非线性
的曲线。例如:
1
2
3
4
|
xaxis: {
transform:
function
(v) {
return
Math.log(v); },
inverseTransform:
function
(v) {
return
Math.exp(v); }
}
|
1
2
3
4
|
yaxis: {
transform:
function
(v) {
return
-v; },
inverseTransform:
function
(v) {
return
-v; }
}
|
剩下的选项都是处理刻度的。如果不对刻度进行任何的设置的话,坐标生成函数会自动的计算刻度。算法会先估算刻度的个数,再计算出两个刻度之间的间隔大小,从而可以生成完整的刻度了。你可以给算法设置刻度的个数("ticks"),算法会根据原始数据的范围返回一个最接近你设置的刻度数的一个值,也就是说如果你设置了3,那么它返回5个坐标也是很正常的,因为算法认为5个刻度会更合适。如果不设置刻度的话,把"ticks"设置成0或者空数组就可以了。还可以通过设置"tickSize"来定义两个刻度之间的差值,如果设置成2,那么刻度就会是2,4,6. 通过"minTickSize"可以设置两个刻度差值的最小值。对于时间刻度,我们可以设置数组来完成:[2, "month"]。
最狠的方法还是直接忽略flot自带的算法,完全使用数组自己定义的刻度:Flot还支持更牛X的可扩展性,就是可以调用一个函数来形成各个刻度的值。在函数中需要通过最小值,最大值和自己设定的一个间隔来计算出一个数组,作为各个刻度:
1
2
3
4
5
6
7
8
9
10
|
function
piTickGenerator(axis) {
var
res = [], i = Math.floor(axis.min / Math.PI);
do
{
var
v = i * Math.PI;
res.push([v, i +
"\u03c0"
]);
++i;
}
while
(v < axis.max);
return
res;
}
|
给"tickFormatter"定义也一个函数可以灵活的格式化刻度的显示,函数有两个参数,一个是刻度的值,一个是轴上的最大值和最小值,返回值一定要是string类型:
function formatter(val, axis) {
return val.toFixed(axis.tickDecimals);
}
对于一个轴对象,有min和max这两个属性,还有"tickDecimals"是坐标显示的精度,"tickSize"是两个刻度之间的差值,有了这么多的属性,就可以自己定制刻度的显示内容:
1
2
3
4
5
6
7
8
|
function
suffixFormatter(val, axis) {
if
(val > 1000000)
return
(val / 1000000).toFixed(axis.tickDecimals) +
" MB"
;
else
if
(val > 1000)
return
(val / 1000).toFixed(axis.tickDecimals) +
" kB"
;
else
return
val.toFixed(axis.tickDecimals) +
" B"
;
}
|
"labelWidth"和"labelHeight"是定义刻度显示区域的。"reserveSpace"的意思是即使你不定义轴,flot也会使用这个属性把轴占用的空间给预留出来。当绘制单行多轴图表时与"labelWidth"和"labelHeight"一起使用会得到很多的效果。
"tickLength"定义坐标刻度的长度,null是默认设置,也就是一个很小的刻度,如果设置成0,在轴上就不会显示刻度。
"alignTicksWithAxis":如果设置成其它轴的数字,Flot会在自动生成刻度的时候会与其它轴上的刻度对齐的。这样会更加的美观,尤其是图中有网格,并且有多具轴的时候,非常的实用。
绘制多个轴:
如果你需要绘制多个轴的话,数据序列就要按照下面的格式给出,{ data: [...], yaxis: 2 }表明这个序列要使用第二个Y轴。这时要设置轴的显示形式的话,就不能直接使用xaxis/yaxis的选项了,而是要有两个数组:
{
xaxes: [ { position: "top" } ],
yaxes: [ { }, { position: "right", min: 20 } ]
}
如果所有的Y轴都想设置成相同的值的话,使用yaxis: { min: 0 }就可以了。
时间类型的数据序列:
============================
时间序列比数据序列就有一点难了。因为时间序列并不是按照10进制来排列的,所以Flot需要把时间转换成数值,再进行处理。Flot是通过javascript中的timestamps来支持时间序列的。timestamp是一个时间距1970年1月1日00:00:00的毫秒数,类似与Unix系统中使用的timestamps,只不过javascript的单位是毫秒,unix的意单位是秒。可以通过下面的来获取浏览器的timestamp:
alert((new Date()).getTime())
一般来说,大家都希望在网页上显示本地的时间,但是Flot只能把timestamp转换成UTC的时间来显示,所以唯一的方法就是获取本浏览当前的timestamp,和时区,再对timestamp的值进行计算,从而得到UTC时间与当前时间相等时的UTC timestamp。再把转换后的值提供给Flot来绘图。
这时就可以用转换后的timestamp来构造原始的数据的,并把轴的类型定义成"time",Flot就可以自动的计算刻度并格式化它们。当然了,也可以自己定义刻度,但是一定要使用数值型的参数,不能是对象类型。刻度的生成和格式化也可以通过轴的选项来自定义:
minTickSize: array
timeformat: null or format string
monthNames: null or array of size 12 of strings
twelveHourClock: boolean
"timeformat":时间的显示形式:
xaxis: {
mode: "time"
timeformat: "%y/%m/%d"
}
时间刻度就会显示成"2000/12/24",具体的格式定义参考下面:
%h: 小时
%H: 小时 (左边补0)
%M: 分钟 (左边补0)
%S: 秒 (左边补0)
%d: 日, 用 %0d 来左边补0
%m: 月, 用 %0m 来左边补0
%y: 年 (4位数)
%b: 月的名字 (英文名字)
%p: 12小时投制显示(am/pm), %h/%H
%P: 12小时投制显示 (其中的AM/PM)
月份的名字是可以自定义的:
monthNames: ["jan", "feb", "mar", "apr", "maj", "jun", "jul", "aug", "sep", "okt", "nov", "dec"]
当"twelveHourClock"被设置成true时,时间就会用12时制来显示。
你还可以通过函数来控制刻度的显示内容。下面的例子是把December 24格式化成24/12:
1
2
3
4
|
tickFormatter:
function
(val, axis) {
var
d =
new
Date(val);
return
d.getUTCDate() +
"/"
+ (d.getUTCMonth() + 1);
}
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
|
series: {
lines, points, bars: {
show: boolean
lineWidth: number
fill: boolean or number
fillColor:
null
or color/gradient
}
points: {
radius: number
symbol:
"circle"
or
function
}
bars: {
barWidth: number
align:
"left"
or
"center"
horizontal: boolean
}
lines: {
steps: boolean
}
shadowSize: number
}
|
1
2
3
4
5
6
|
var
options = {
series: {
lines: { show:
true
, fill:
true
, fillColor:
"rgba(255, 255, 255, 0.8)"
},
points: { show:
true
, fill:
false
}
}
};
|
1
2
3
4
5
6
7
|
function
cross(ctx, x, y, radius, shadow) {
var
size = radius * Math.sqrt(Math.PI) / 2;
ctx.moveTo(x - size, y - size);
ctx.lineTo(x + size, y + size);
ctx.moveTo(x - size, y + size);
ctx.lineTo(x + size, y - size);
}
|
"shadowSize"用来设置阴影的大小,单位是pixels,设置成0的话就可以删除阴影。
"colors"数组是用来设置在绘图过程中各条线使用的颜色的默认值:
colors: ["#d18b2c", "#dba255", "#919733"]
如果数据序列的数量比定义的颜色数量多的话,flot还会生成一些新的颜色用于绘制图表。
自定义网格
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
grid: {
show: boolean
aboveData: boolean
color: color
backgroundColor: color/gradient or
null
labelMargin: number
axisMargin: number
markings: array of markings or (fn: axes -> array of markings)
borderWidth: number
borderColor: color or
null
minBorderMargin: number or
null
clickable: boolean
hoverable: boolean
autoHighlight: boolean
mouseActiveRadius: number
}
|
1
2
3
4
5
6
|
markings:
function
(axes) {
var
markings = [];
for
(
var
x = Math.floor(axes.xaxis.min); x < axes.xaxis.max; x += 2)
markings.push({ xaxis: { from: x, to: x + 1 } });
return
markings;
}
|
1
2
3
4
5
6
7
8
9
10
11
12
|
$.plot($(
"#placeholder"
), [ d ], { grid: { clickable:
true
} });
$(
"#placeholder"
).bind(
"plotclick"
,
function
(event, pos, item) {
alert(
"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) {
highlight(item.series, item.datapoint);
alert(
"You clicked a point!"
);
}
});
|
1
2
3
4
5
6
7
|
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
}
|
如果使用上面的方法来显示一些信息的话,那么就需要监听"mouseout"事件。"mouseActiveRadius"用来定义鼠标做用的范围。如果有多个数据点在这个范围中的话,Flot只会选择最接近的那一个。对柱状图而言,最高的那个柱子会被选中。
如果不想有交互的话,就可以"hoverable" 和 "clickable" 设置成false:{ data: [...], label: "Foo", clickable: false }。
梯度颜色的定义
===================
定义的方法: { colors: [ color1, color2, ... ] }
如果想让网格的背景从黑色到灰色的话:
grid: {
backgroundColor: { colors: ["#000", "#999"] }
}
对数据序列,可以设置颜色的透明度和亮度:
{ colors: [{ opacity: 0.8 }, { brightness: 0.6, opacity: 0.8 } ] }
第一个只有透明度,第二个还包含了亮度。对于柱形图来说,下面的例子可以让柱子逐渐的消失:
bars: {
show: true,
lineWidth: 0,
fill: true,
fillColor: { colors: [ { opacity: 0.8 }, { opacity: 0.1 } ] }
}
Flot目前只能支持垂直方向上从上到下的渐变,因为IE只支持这个模式。
Plot方法
---------------
由plot函数生成的对象提供了可调用的方法
- highlight(series, datapoint)
用来高亮显示一个数据点。你可以通过"plotclick"事件获取对象,或者使用highlight(1, 3)来高亮显示第2个数据序列中的第4个数据点。
- unhighlight(series, datapoint) or unhighlight()
删除高亮显示,如果有参数的话,就是删除指定高亮的点,如果没有参数的话,plot就会删除图表中所有的高亮显示。
- setData(data)
用来重新设置数据。但是轴的取值范围,刻度坐标,标签是不会重新绘制的,可以调用draw()让plot绘制新的曲线,但是其它部分不会改变。用这个函数可以变速的更新一个图表中的曲线,前提条件是所有值的取值范围是没有改变的。
- setupGrid()
重新计算轴的取值范围,并设置刻度和标签。如果调用过setData的话,就可以使用这个函数重新绘制有影响的部分。
- draw()
重新绘制图表中的显示曲线部分。
- triggerRedrawOverlay()
在可绘制区域上更新可交互的部分,如选择区域和点的高亮。当要自己编写插件时是非常有用的。图表并不会马上重新绘制,而是可以设置一个定时器来获取多次的重给事件。
- width()/height()
获取可绘制区域的宽度和高度。也就是网格中的区域。
- offset()
返回网格中可绘图的区域相对于整个文档的偏移,当计算鼠标所在的位置时很重要。把event.pageX/Y减去这个偏移就是在绘图区域中的坐标。
- pointOffset({ x: xpos, y: ypos })
(x,y)这个数据点在包含绘图div窗口中的偏移。
- resize()
如果绘图窗口的大小发生改变,就可以调用这个函数来重新绘图。
- shutdown()
关闭已经注册的所有事件的处理函数。
还会一些其它的函数,但是需要你了解Flot内部的代码流程。如果你修改了获取到对象中的属性的话,那么你就修改了Flot内部使用的对象,Flot无法及时的更新你修改的内容,还有可能会影响绘图功能,所以使用的时候一定要小心。具体的使用方法可以参考原版的文档。
- getData()
- getAxes()
- getPlaceholder()
- getCanvas()
- getPlotOffset()
- getOptions()
Hooks(钩子函数)
======================
Plot对象在绘制过程中可以添加许多的钩子函数,从而添加一些方法,在方法还可以访问Flot中的内部数据。
下面就是Flot处理流程的概要:
1. 插件的初始化,处理各个选项
2. 构造绘图区域
3. 设置各类数据:处理用户录入的数据,计算显示用的颜色,把原始数据转化成内部格式,规格化数据,查看最大最小值用来设置轴的取值范围。
4. 网格的设置:计算轴的空间,刻度,刻度的标签。
5. 绘图: 绘制网格,按照顺序绘图
6. 设置事件处理的自定义函数
7. 答复事件。
8. 关闭:一般都是发生在整个图表被重写的时候发生。
钩子函数一个简单的函数,并放在了一个特定的数组当中。你可以使用"hooks"来添加钩子函数,当绘图完成以后,钩子函数仍然是起作用的,因为它的定义已经存在于plot的对象中了。
1
2
3
4
5
6
7
8
|
// define a simple draw hook
function
hellohook(plot, canvascontext) { alert(
"hello!"
); };
// pass it in, in an array since we might want to specify several
var
plot = $.plot(placeholder, data, { hooks: { draw: [hellohook] } });
// we can now find it again in plot.hooks.draw[0] unless a plugin
// has added other hooks
|
1
2
3
4
5
|
function
multiply(plot, series, datapoints) {
var
points = datapoints.points, ps = datapoints.pointsize;
for
(
var
i = 0; i < points.length; i += ps)
points[i + 1] *= 2;
}
|
1
2
3
4
5
|
function
(plot, eventHolder) {
eventHolder.mousedown(
function
(e) {
alert(
"You pressed the mouse at "
+ e.pageX +
" "
+ e.pageY);
});
}
|