在这一篇中将介绍一个完整的对象级别插件示例,叫做子弹图插件。关于子弹头图表是什么可以百度查一下,它和我们常见的柱状图很相似。最终效果如下图所示
图一
先回顾一下上一篇文章中说过开发一个对象级别插件分为以下三步:
第一、创建静态的HTML模板和CSS文件
第二、编写插件逻辑,在选定的页面元素上动态添加HTML结构
第三、如果需要和用户交互,还应动态绑定相应的处理事件
在本文展示的这个插件示例中包含了上述三个步骤,将会一一进行说明。这个插件并不是我自己从头开发的。我是在别人的基础上做了适当的修改完成的。原插件的地址可以访问这里获得:
https://github.com/NETTUTS/An-In-Depth-Review-of-the-jQuery-Widget-Factory
插件所用到的HTML模板和CSS样式基本都是原来的,只做了很少的修改。而插件的JS逻辑内容则全部是我重写过的。
下面开始介绍插件的内容。
第一步:创建HTML和CSS静态结构
1.1 HTML标签(文件:model.html)
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>子弹图静态HTML模型</title>
<link rel="stylesheet" href="jquery.bulletchart.css">
</head>
<body>
<div class="chart bullet-chart" style="width: 85%;">
<div class="legend">
<div class="legend-item" data-index="0">
<span class="legend-symbol bar"></span><span class="legend-label">Projected
Target</span>
</div>
<div class="legend-item" data-index="1">
<span class="legend-symbol bar blue"></span><span
class="legend-label">Actual Target</span>
</div>
<div class="legend-item" data-index="2">
<span class="legend-symbol marker green"></span><span
class="legend-label">Green Line</span>
</div>
<div class="legend-item" data-index="3">
<span class="legend-symbol marker red"></span><span
class="legend-label">Minimum Threshold</span>
</div>
</div>
<div class="chart-container">
<div class="bar" style="width: 80%;"></div>
<div class="bar blue" style="width: 70%;"></div>
<div class="marker green" style="left: 60%;"></div>
<div class="marker red" style="left: 50%;"></div>
</div>
<div class="tick-bar">
<span class="tick" style="left: 0%;"></span><span class="tick-label"
style="left: 0%;">0</span><span class="tick" style="left: 25%;"></span><span
class="tick-label" style="left: 25%;">25</span><span class="tick"
style="left: 50%;"></span><span class="tick-label"
style="left: 50%;">50</span><span class="tick" style="left: 75%;"></span><span
class="tick-label" style="left: 75%;">75</span><span class="tick"
style="left: 100%;"></span><span class="tick-label"
style="left: 100%;">100</span>
</div>
</div>
</body>
</html>
1.2 CSS文件(jquery.bulletchart.css)
.bullet-chart { font-size: 16px; -webkit-user-select: none; }
/* 留出足够空间显示图表的刻度 */
.bullet-chart {
padding-bottom : 50px;
}
.bullet-chart .chart-container {
height: 30px;
background: #EEE;
position: relative;
/* margin-left: 2.1em; */
}
/* Bar 默认为灰色 */
.bullet-chart .bar {
background: #777;
position: absolute;
/* 垂直居中 */
height: 10px;
top: 50%;
margin-top: -5px;
}
/* Marker */
.bullet-chart .marker {
background: #555;
width: 2px;
height: 20px;
position: absolute;
left: 250px;
top: 50%;
margin-top: -10px;
}
.bullet-chart .red { background: #cd6668; }
.bullet-chart .green { background: #72cd84; }
.bullet-chart .blue { background: #64a0cb; }
.bullet-chart .purple { background: #a77cdb; }
.bullet-chart .orange { background: #ffb95e; }
.bullet-chart .cyan { background: #a0e2ff; }
/* Ticks */
.bullet-chart .tick-bar {
position: relative;
top: 30px;
border-top: 1px solid #AAA;
}
.bullet-chart .tick-bar .tick {
position: absolute;
width: 1px;
height: 6px;
top: -1px;
background: #AAA;
}
.bullet-chart .tick-bar .tick-label {
text-align: center;
position: absolute;
font-size: 0.6em;
width: 2.1em;
margin-left: -1.05em;
top: 5px;
color: #AAA;
}
/* Legend */
.bullet-chart .legend {
margin: 0 0 1em 0;
border: 1px solid #EEE;
padding: 0.5em 0 0 0.5em;
max-width: 300px;
}
.bullet-chart .legend .legend-item {
display: inline-block;
margin: 0 0.5em 0.5em 0;
background: #FFE;
padding: 0 5px;
border-radius: 2px;
cursor: pointer;
}
.legend-item .legend-symbol {
position: static;
margin: 0px;
display: inline-block;
vertical-align: middle;
}
.legend-item .legend-symbol.marker {
height: 12px;
width: 2px;
}
.legend-item .legend-symbol.bar {
height: 12px;
width: 7px;
}
.legend-item .legend-label {
font-size: 0.6em;
vertical-align: middle;
margin-left: 5px;
}
.fade { opacity: 0.5; }
有了HTML和CSS我们就能看到插件运行后的最终效果图。如图一所示。这只是开发的第一步,但也是很重要的一步。这个时候不能仅仅效果一出来就急着去写插件逻辑(JS代码)。应该先对其兼容性做到足够的测试。确保在写JS之前插件所用到的HTML和CSS已经确定不再改变,尤其是HTML结构上不能随意改变。至于原因很明显,HTML结构的改变会导致原来的JS不可用的。
第二步、第三步:编写插件逻辑,添加用户交互事件
2.1 JS文件(jquery.bulletchart.js)
由于代码比较多,不会一一解释,当然还是在关键的地方加上了注释。而且,这里也包含了第三步的内容,即添加相应的用户事件。代码也不是太复杂,相信有jQuery经验的你能够看懂。
/**
* 子弹图插件,基于网上的一个控件改编而成
* 网上原插件地址:https://github.com/NETTUTS/An-In-Depth-Review-of-the-jQuery-Widget-Factory
* http://net.tutsplus.com/tutorials/javascript-ajax/an-in-depth-review-of-jquerys-widget-factory/
* 日期:2013-6-5
* @author 张书振
*/
(function($) {
$.fn.bulletchart = function(options) {
var settings = {
// 宽度为相对于容器的百分比: 0 - 100
size: 100,
// 显示的图形有两种,一种是bar,只是以竖线显示,另一种是marker,以矩形条显示
// title 是显示的名称,value是百分比值 0-100,css可以指定颜色值 green,blue,purple,red,orange,cyan
// [{ title: 'Sample Bar', value: 75, css: '' }],
bars: [],
// [{ title: 'Sample Marker', value: 50, css: 'green' }],
markers: [],
// 刻度必须是百分比数值 : 0 - 100
ticks: [0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]
};
settings = $.extend(settings, options || {});
return this.each(function() {
init($(this));
});
/**
* 初始化插件函数
* @param $target 将要应用插件的目标DOM节点,是个jQuery对象
*/
function init($target) {
$target.addClass("bullet-chart");
// 设置图标的显示宽度,百分比
$target.css("width", settings.size + "%");
//添加legend
var $legend = $("<div class='legend'></div>").appendTo($target);
var legendIndex = 0;
$.each(settings.bars, function() { // 此循环遍历添加bar类型 legend内容
var $legendItem = $("<div class='legend-item'></div>")
.attr("data-index", legendIndex++) // 给每个legendItem添加索引,便于单击事件处理
.appendTo($legend);
var $legendSymbol = $("<span class='legend-symbol bar'></span>").appendTo($legendItem);
$legendSymbol.addClass(this.css);
var $legendLabel = $("<span class='legend-label'></span>").appendTo($legendItem);
$legendLabel.text(this.title);
});
$.each(settings.markers, function() { // 此循环遍历添加marker类型 legend内容
var $legendItem = $("<div class='legend-item'></div>")
.attr("data-index", legendIndex++)
.appendTo($legend);
var $legendSymbol = $("<span class='legend-symbol marker'></span>").appendTo($legendItem);
$legendSymbol.addClass(this.css);
var $legendLabel = $("<span class='legend-label'></span>").appendTo($legendItem);
$legendLabel.text(this.title);
});
//添加图表
var $container = $("<div class='chart-container'></div>").appendTo($target);
var $tickbar = $("<div class='tick-bar'></div>").appendTo($target);
//刻度
$.each(settings.ticks, function() {
$("<span class='tick'></span>")
.css("left", this + "%")
.appendTo($tickbar);
$("<span class='tick-label'><span>")
.css("left", this + "%")
.text(this)
.appendTo($tickbar);
});
//绘制bar 和 marker 图形
$.each(settings.bars, function() {
$("<div class='bar'></div>")
.addClass(this.css)
.animate({ width : this.value + "%" })
.appendTo($container);
});
$.each(settings.markers, function() {
$("<div class='marker'></div>")
.addClass(this.css)
.css("left", this.value + "%")
.appendTo($container);
});
// 这里就是第三步的内容,为legend添加事件,鼠标单击事件,显示或隐藏相应的bar和marker图形
$(".legend-item", $target).toggle(
function(event) {
var $legendItem = $(this);
$legendItem.addClass("fade");
$(".chart-container>.bar, .chart-container>.marker", $target).eq($legendItem.attr("data-index"))
.fadeOut();
},
function(event) {
var $legendItem = $(this);
$legendItem.removeClass("fade");
$(".chart-container>.bar, .chart-container>.marker", $target).eq($legendItem.attr("data-index"))
.fadeIn();
}
);
}
};
})(jQuery);
2.2 Demo测试页面(demo.html)
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>BulletChart: A jQuery Widget</title>
<meta name="description" content="BulletChart: A jQuery Widget">
<meta name="author" content="SitePoint">
<link rel="stylesheet" href="jquery.bulletchart.css">
<script src="jquery-1.8.3.js"></script>
<script src="jquery.bulletchart.js"></script>
<script type="text/javascript">
$(function(){
$("#bulletChartBtn").click(function(){
$('.chart').bulletchart({
size: 85,
bars: [
{ title: 'Projected Target', value: 80, css: '' },
{ title: 'Actual Target', value: 70, css: 'blue' }
],
markers: [
{ title: 'Green Line', value: 60, css: 'green' },
{ title: 'Minimum Threshold', value: 50, css: 'red' }
],
ticks: [0, 25, 50, 75, 100]
});
});
});
</script>
</head>
<body>
<input id="bulletChartBtn" type="button" value="BulletChart"/><br/>
<div class="chart"></div>
<div class="chart"></div>
</body>
</html>
示例下载地址
http://download.csdn.net/detail/zhang_shuzhen/5523297