一步一步制作jquery插件Tabs实现过程


Posted in Javascript onJuly 06, 2010

tabs是现在网页应用最广的一种效果,jquery插件和非jquery插件也有不少,有一些朋友问我怎么用jquery.ui.tabs的ajax怎么只请求服务器一次原来我想其实很简单,看看官方的API就了解,不过我在回复这些朋友之前,用firebug查看了官方的ui.tabs发现,声明了ajax缓存,每点一个tabs时,仍然会有服务器请求这应该是服务器缓存,而不是实际上我们要求的只ajax一次,不再请求服务器了接下来我找了一下其它的tabs插件,基本上没有符合要求的,不是太庞大就是太简单,太过庞大的话不如用ui.tabs,文档和代码规范上都是可靠的因此,自制一个简洁的tabs插件还是有必要的在设计之前,先整理好思路,实现tabs,自动轮换,ajax等主要功能,然后是dom的排列形式,这里采用传统的
<div id="tabs">

<ul>

<li><a href="#tabs1">tabs1</a></li>

<li><a href="#tabs2" rel="ajax.htm">tabs2</a></li>

</ul>

<div id="tabs1">Hello World!</div>

<div id="tabs2"></div>
</div>
一个li对应一个div的方式,当ajax时,添加一个a的rel属性,并将内容写入对应的div中,再去掉rel属性,这样就只请求服务器一次,接下来都是div已经写入的内容了
我这里没有使用cookie,可以结合jquery.cookie插件,这样即使用户关闭网页下次再打开,也不用请求服务器了
一,首先写个jquery插件的闭包,园子里这两天有个朋友写了javascript的闭包概念,挺好的,有兴趣的朋友去看看

(function ($) { 
//code here 
})(jQuery);

二,插件命名,这里命名为aTabs,这样绑定的时候可以用$(...).aTabs(),本人英文名Allen,所以用a字头命名了~
$.fn.aTabs = function (options) { 
//api 
//main function 
}

三,把想好的功能写成API,供外部修改
$.fn.aTabs.defaults = { 
firstOn: 0, 
className: 'selected', 
eventName: 'all', //click,mouserover,all 
loadName: '加载中...', //ajax等待字符串 
fadeIn: 'normal', 
autoFade: false, 
autoFadeTime: 3 
}; 
var opts = $.extend({}, $.fn.aTabs.defaults, options); //这里可以将外部输入的代替掉默认的值,$.extend作用详见 <A href="http://api.jquery.com/jQuery.extend/">http://api.jquery.com/jQuery.extend/</A>,看不懂英文的直接看其中的例子就行

四,编写主体功能,说明在代码中看注释
return this.each(function () { //这里为每个绑定dom插件 
var target = $(this); 
var div = target.children().not("ul,span"); //所有的tabs显示体div 
var tabs = target.find('ul:eq(0) li'); //所有的tabs头部索引 
function Tabs() { 
if ($(this).hasClass(opts.className)) { 
return false; 
} 
tabsShow(div, $(this)); 
return false; 
} 
function tabsShow(div, li, index) { 
div.stop(true, true).hide(); 
//自动轮换用 
if (typeof (index) == "number") { 
if (li.find("a").attr("rel")) ajax(div, li); 
$(div[index]).stop(true,true).fadeIn(opts.fadeIn); 
tabs.stop(true, true).removeClass(opts.className); 
$(tabs[index]).stop(true, true).addClass(opts.className); 
} 
//非自动轮换 
else { 
var tabBody = div.filter(li.find("a").attr("href")); 
if (li.find("a").attr("rel")) ajax(div, li); 
tabBody.stop(true,true).fadeIn(opts.fadeIn); 
tabs.stop(true, true).removeClass(opts.className); 
li.stop(true, true).addClass(opts.className); 
} 
} 
function ajax(div, li) {//这里是关键ajax,通过操作rel的方式实现只请求服务器一次 
var href = li.find("a").attr("href"); 
var rel = li.find("a").attr("rel"); //ajax请求url 
var i = div.filter(href); //当前div 
if (rel) { //如果ajax请求url不为空,只ajax一次 
i.html(opts.loadName); 
$.ajax({ 
url: rel, 
cache: false, 
success: function (html) { 
i.html(html); 
}, 
error: function () { 
i.html('加载错误,请重试!'); 
} 
}); 
li.find("a").removeAttr("rel"); //只ajax一次 
} 
} 
if (opts.autoFade) { 
var index = opts.firstOn + 1; 
setInterval(function () { 
if (index >= div.length) { 
index = 0; 
} 
tabsShow(div, $(this), index++); 
}, opts.autoFadeTime * 1000); 
} 
tabs.bind(opts.eventName == 'all' ? 'click mouseover' : opts.eventName, Tabs) //绑定事件 
.filter(':first').trigger(opts.eventName == 'all' ? 'click' : opts.eventName); //自动触发事件 
});

最后,将以上整合,tabs插件就诞生了,下面是全部源码:
/* 
* 作者:黑曜石 
*/ 
(function ($) { 
$.fn.aTabs = function (options) { 
$.fn.aTabs.defaults = { 
firstOn: 0, 
className: 'selected', 
eventName: 'all', //click,mouserover,all 
loadName: '加载中...', //ajax等待字符串 
fadeIn: 'normal', 
autoFade: false, 
autoFadeTime: 3 
}; 
var opts = $.extend({}, $.fn.aTabs.defaults, options); 
return this.each(function () { 
var target = $(this); 
var div = target.children().not("ul,span"); //所有的tabs显示体div 
var tabs = target.find('ul:eq(0) li'); //所有的tabs头部索引 
function Tabs() { 
if ($(this).hasClass(opts.className)) { 
return false; 
} 
tabsShow(div, $(this)); 
return false; 
} 
function tabsShow(div, li, index) { 
div.stop(true, true).hide(); 
//自动轮换用 
if (typeof (index) == "number") { 
if (li.find("a").attr("rel")) ajax(div, li); 
$(div[index]).stop(true,true).fadeIn(opts.fadeIn); 
tabs.stop(true, true).removeClass(opts.className); 
$(tabs[index]).stop(true, true).addClass(opts.className); 
} 
//非自动轮换 
else { 
var tabBody = div.filter(li.find("a").attr("href")); 
if (li.find("a").attr("rel")) ajax(div, li); 
tabBody.stop(true,true).fadeIn(opts.fadeIn); 
tabs.stop(true, true).removeClass(opts.className); 
li.stop(true, true).addClass(opts.className); 
} 
} 
function ajax(div, li) { 
var href = li.find("a").attr("href"); 
var rel = li.find("a").attr("rel"); //ajax请求url 
var i = div.filter(href); //当前div 
if (rel) { //如果ajax请求url不为空,只ajax一次 
i.html(opts.loadName); 
$.ajax({ 
url: rel, 
cache: false, 
success: function (html) { 
i.html(html); 
}, 
error: function () { 
i.html('加载错误,请重试!'); 
} 
}); 
li.find("a").removeAttr("rel"); //只ajax一次 
} 
} 
if (opts.autoFade) { 
var index = opts.firstOn + 1; 
setInterval(function () { 
if (index >= div.length) { 
index = 0; 
} 
tabsShow(div, $(this), index++); 
}, opts.autoFadeTime * 1000); 
} 
tabs.bind(opts.eventName == 'all' ? 'click mouseover' : opts.eventName, Tabs) //绑定事件 
.filter(':first').trigger(opts.eventName == 'all' ? 'click' : opts.eventName); //自动触发事件 
}); 
}; 
})(jQuery);
Javascript 相关文章推荐
jquery 新手学习常见问题解决方法
Apr 18 Javascript
查找Oracle高消耗语句的方法
Mar 22 Javascript
jQuery下拉菜单的实现代码
Nov 03 Javascript
详解微信小程序 通过控制CSS实现view隐藏与显示
May 24 Javascript
妙用缓存调用链实现JS方法的重载
Apr 30 Javascript
JS实现的汉字与Unicode码相互转化功能分析
May 25 Javascript
浅谈PDF.js使用心得
Jun 07 Javascript
node版本管理工具n包使用教程详解
Nov 09 Javascript
Vue axios全局拦截 get请求、post请求、配置请求的实例代码
Nov 28 Javascript
Egg Vue SSR 服务端渲染数据请求与asyncData
Nov 24 Javascript
Vue+tracking.js 实现前端人脸检测功能
Apr 16 Javascript
微信小程序实现简单的select下拉框
Nov 23 Javascript
jQuery基础知识filter()和find()实例说明
Jul 06 #Javascript
jQuery中filter(),not(),split()使用方法
Jul 06 #Javascript
jQuery选择没有colspan属性的td的代码
Jul 06 #Javascript
jquery 查找新建元素代码
Jul 06 #Javascript
jquery 3D球状导航的文章分类
Jul 06 #Javascript
Javascript Function对象扩展之延时执行函数
Jul 06 #Javascript
JavaScript经典效果集锦
Jul 06 #Javascript
You might like
PHP图片上传类带图片显示
2006/11/25 PHP
PHP 命名空间实例说明
2011/01/27 PHP
ThinkPHP 表单自动验证运用示例
2014/10/13 PHP
php提示Warning:mysql_fetch_array() expects的解决方法
2014/12/16 PHP
PHP使用strtotime计算两个给定日期之间天数的方法
2015/03/18 PHP
PHP反射API示例分享
2016/10/08 PHP
PHP从二维数组得到N层分类树的实现代码
2016/10/11 PHP
PHP微信PC二维码登陆的实现思路
2017/07/13 PHP
可以支持多中格式的JS键盘
2007/05/02 Javascript
jquery实现网页查找功能示例分享
2014/02/12 Javascript
js点击选择文本的方法
2015/02/09 Javascript
BootStrap组件之进度条的基本用法
2017/01/19 Javascript
深入理解vue.js中$watch的oldvalue与newValue
2017/08/07 Javascript
详解使用Vue Router导航钩子与Vuex来实现后退状态保存
2017/09/11 Javascript
详解express + mock让前后台并行开发
2018/06/06 Javascript
vue实现动态列表点击各行换色的方法
2018/09/13 Javascript
[01:04:09]DOTA2-DPC中国联赛 正赛 iG vs VG BO3 第二场 2月2日
2021/03/11 DOTA
python二叉树遍历的实现方法
2013/11/21 Python
部署Python的框架下的web app的详细教程
2015/04/30 Python
python实现数据导出到excel的示例--普通格式
2018/05/03 Python
深入浅析Python2.x和3.x版本的主要区别
2018/11/30 Python
PyTorch中topk函数的用法详解
2020/01/02 Python
详解Django中views数据查询使用locals()函数进行优化
2020/08/24 Python
python 如何读、写、解析CSV文件
2021/03/03 Python
CSS3基础(RGBa、text-shadow、box-shadow、border-radius)
2012/11/13 HTML / CSS
如何让IE9以下版本(ie6/7/8)认识html5元素
2013/04/01 HTML / CSS
Bibloo罗马尼亚网站:女装、男装、童装及鞋子和配饰
2019/07/20 全球购物
蒂娜商店:Tiina the Store
2019/12/07 全球购物
飞利信loadrunner和软件测试笔试题
2012/09/22 面试题
《狼》教学反思
2014/03/02 职场文书
政法干警核心价值观心得体会
2014/09/11 职场文书
幼儿教师年度个人总结
2015/02/05 职场文书
邮政营业员岗位职责
2015/04/14 职场文书
经营场所证明范本
2015/06/19 职场文书
Flask response响应的具体使用
2021/07/15 Python
MySQL 服务和数据库管理
2021/11/11 MySQL