一个简单的jQuery插件制作 学习过程及实例


Posted in Javascript onApril 25, 2010

一,首先,制作jQuery插件需要一个闭包

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

这是来自jQuery官方的插件开发规范要求,使用这种编写方式有什么好处呢?
a) 避免全局依赖。
b) 避免第三方破坏。
c) 兼容jQuery操作符'$'和'jQuery '

二,有了闭包,在其中加入插件的骨架

$.fn.dBox = function (options) { 
var defaults = { 
//各种属性及其默认值 
}; 
var opts = $.extend(defaults, options); 
//function codes in here 
};

在这里dBox是我为这个弹出层插件的命名

三,为dBox建立起属性及其默认值

$.fn.dBox = function (options) { 
var defaults = { 
opacity: 0.6, //for mask layer 
drag: true, 
title: 'dBox', 
content: '', 
left: 400, 
top: 200, 
width: 600, 
height: 300, 
setPos: false, //if use the customer's left and top 
overlay: true, //if use the mask layer 
loadStr: 'Loading', 
ajaxSrc: '', 
iframeSrc: '' 
}; 
var opts = $.extend(defaults, options); 
//function codes in here 
};

四,既然是弹出窗体,那么要先设计好一个div窗体和遮罩层,在这里我将样式也直接写进去了,在function codes区域中输入如下:
//build html code of the dBox 
var dBoxHtml = "<div id='dBox' style='background-color:#FFF;border:solid 2px #00E;position:absolute;z-index:100;'>"; 
dBoxHtml += "<div id='d_head' style='width:100%;height:20px;border-bottom:solid 1px #00E;'>"; 
dBoxHtml += "<div id='d_title' style='float:left;width:90%;color:#00E'>" + opts.title + "</div>"; 
dBoxHtml += "<div id='d_close' style='float:right;cursor:pointer;margin-right:5px;color:#00E'>[x]</div>"; 
dBoxHtml += "</div>"; 
dBoxHtml += "<div id='d_content' style='width:100%;height:100%;padding:3px;'>" + opts.content + "</div>"; 
dBoxHtml += "</div>"; 
var dBoxBG = "<iframe id='d_iframebg' style='position:absolute;top:0;left:0;width:0;height:0;border:none;'></iframe><div id='d_bg' style='background-color:#000;z-index:99;position:absolute;top:0;left:0;'></div>"; 
var loading = "<div id='d_loading' style='position:fixed;top:48%;left:48%;z-index:100;border:solid 1px #000;'>" + opts.loadStr + "</div>";

在IE6中,z-index对下拉列表不会起作用,所以这里遮罩层中加入id为d_iframebg的iframe作为遮罩层,这样,大体已经制作好了框架。
五,现在我们考虑要实现什么功能了
首先,如何出现弹出窗体,一般都是点击,这里仍然使用点击事件
//click event 
$(this).click(function () { 
$("body").append(dBoxHtml); 
//case ajax 
if (opts.ajaxSrc != "") { 
$("#d_content").append("<div id='d_ajax' style='width:" + (opts.width - 6) + "px;height:" + (opts.height - 26) + "px;overflow:scroll;'><div id='d_ajaxcontent'></div></div>"); 
$("#d_ajaxcontent").load(opts.ajaxSrc); 
} 
//case iframe 
else if (opts.iframeSrc != "") { 
$("#d_content").append("<iframe frameborder='0' width='" + (opts.width - 6) + "' height='" + (opts.height - 26) + "' src='" + opts.iframeSrc + "'>"); 
} 
addCSS(); 
//case drag 
if (opts.drag == true) { 
drag(); 
} 
$("#d_close").click(dBoxRemove); 
return false; 
});

最后一个return false可以去掉浏览器默认的点击事件,如在一个a标记上绑定点击事件,将不会造成默认的跳转效果
在这个点击事件中,先将dBox的框架载入了页面,然后判断内容的加载方式,分别处理,最后有三个事件
1,addCSS()此事件处理遮罩层大小,弹出层的位置
2,drag()此事件处理弹出层的拖曳
3,dBoxRemove()此事件处理弹出层的关闭
有了这三个事件,整个插件就基本完成了

六,这里贴出如上三个事件的代码
1,addCSS():

//add css to the dBox 
function addCSS() { 
var pos = setPosition(); 
$("#dBox").css({ "left": pos[0], "top": pos[1], "width": opts.width + "px", "height": opts.height + "px" }); 
if (opts.overlay) { 
var wh = getPageSize(); 
$(dBoxBG).appendTo("body").css({ "opacity": opts.opacity, "width": wh[0], "height": wh[1] }); 
} 
}

在这个addCSS中,还有两个功能需要实现,以下代码:
//calc the size of the page to put the mask layer cover the whole document 
function getPageSize() { 
if ($(window).height() > $(document).height()) { 
h = $(window).height(); 
} else { 
h = $(document).height(); 
} 
w = $(window).width(); 
return Array(w, h); 
} 
//calc the position of the dBox to put the dBox in the center of current window 
function setPosition() { 
if (opts.setPos) { 
l = opts.left; 
t = opts.top; 
} else { 
var w = opts.width; 
var h = opts.height; 
var width = $(document).width(); 
var height = $(window).height(); 
var left = $(document).scrollLeft(); 
var top = $(document).scrollTop(); 
var t = top + (height / 2) - (h / 2); 
var l = left + (width / 2) - (w / 2); 
} 
return Array(l, t); 
}

2,drag():

//drag the dBox 
//this event contains four events(handle.mousedown,move,out,up) 
function drag() { 
var dx, dy, moveout; 
var handle = $("#dBox").find("#d_head>#d_title").css('cursor', 'move'); 
handle.mousedown(function (e) { 
//cal the distance between e and dBox 
dx = e.clientX - parseInt($("#dBox").css("left")); 
dy = e.clientY - parseInt($("#dBox").css("top")); 
//bind mousemove event and mouseout event to the dBox 
$("#dBox").mousemove(move).mouseout(out).css({ "opacity": opts.opacity }); 
handle.mouseup(up); 
}); 
move = function (e) { 
moveout = false; 
win = $(window); 
var x, y; 
if (e.clientX - dx < 0) { 
x = 0; 
} else { 
if (e.clientX - dx > (win.width() - $("#dBox").width())) { 
x = win.width() - $("#dBox").width(); 
} else { 
x = e.clientX - dx; 
} 
} 
if (e.clientY - dy < 0) { 
y = 0; 
} else { 
y = e.clientY - dy; 
} 
$("#dBox").css({ 
left: x, 
top: y 
}); 
} 
out = function (e) { 
moveout = true; 
setTimeout(function () { 
moveout && up(e); 
}, 10); 
} 
up = function (e) { 
$("#dBox").unbind("mousemove", move).unbind("mouseout", out).css("opacity", 1); 
handle.unbind("mouseup", up); 
} 
}

3,dBoxRemove():
//close the dBox 
function dBoxRemove() { 
if ($("#dBox")) { 
$("#dBox").stop().fadeOut(200, function () { 
$("#dBox").remove(); 
if (opts.overlay) { 
$("#d_bg").remove(); 
$("#d_iframebg").remove(); 
} 
}); 
} 
}

到这里,插件制作基本完成,不过loading这个东东没有加上去。。。
另外还发现在ie6中,弹出的iframe高度和宽度都少了点,还有就是有遮罩层时,移动的时候不顺畅
还有其它问题欢迎讨论!
在线演示地址 http://demo.3water.com/js/dBox/dBox.htm
打包下载地址 http://xiazai.3water.com/201004/yuanma/dBox.rar

Javascript 相关文章推荐
javascript innerText和innerHtml应用
Jan 28 Javascript
基于jquery的inputlimiter 实现字数限制功能
May 30 Javascript
jQuery.Autocomplete实现自动完成功能(详解)
Jul 13 Javascript
js URL参数的拼接方法比较
Feb 15 Javascript
学习使用grunt来打包JavaScript和CSS程序的教程
Jan 04 Javascript
JS实现二叉查找树的建立以及一些遍历方法实现
Apr 17 Javascript
JS非行间样式获取函数的实例代码
Jun 05 Javascript
vue-cli2打包前和打包后的css前缀不一致的问题解决
Aug 24 Javascript
详解React之key的使用和实践
Sep 29 Javascript
微信小程序下拉框组件使用方法详解
Dec 28 Javascript
解决vue组件props传值对象获取不到的问题
Jun 06 Javascript
JavaScript中的惰性载入函数及优势
Feb 18 Javascript
Javascript中的相等与不等运算
Apr 25 #Javascript
下载网站打开页面后间隔多少时间才显示下载链接地址的代码
Apr 25 #Javascript
jQuery 打造动态渐变按钮 详细图文教程
Apr 25 #Javascript
javascript之学会吝啬 精简代码
Apr 25 #Javascript
一些相见恨晚的 JavaScript 技巧
Apr 25 #Javascript
Javascript 中的 &amp;&amp; 和 || 使用小结
Apr 25 #Javascript
js 禁用只读文本框获得焦点时的退格键
Apr 25 #Javascript
You might like
linux下删除7天前日志的代码(php+shell)
2011/01/02 PHP
PHP开发中四种查询返回结果分析
2011/01/02 PHP
php查看请求头信息获取远程图片大小的方法分享
2013/12/25 PHP
PHP实现批量修改文件后缀名的方法
2015/07/30 PHP
php die()与exit()的区别实例详解
2016/12/03 PHP
js 动态添加标签(新增一行,其实很简单,就是几个函数的应用)
2009/03/26 Javascript
Mootools 1.2教程(21)——类(二)
2009/09/15 Javascript
javascript 面向对象编程  function是方法(函数)
2009/09/17 Javascript
用JS写的一个TableView控件代码
2010/01/23 Javascript
javascript 数组学习资料收集
2010/04/11 Javascript
jquery.simple.tree插件 更简单,兼容性更好的无限树插件
2010/09/03 Javascript
基于jquery tab切换(防止页面刷新)
2012/05/23 Javascript
jquery不会自动回收xmlHttpRequest对象 导致了内存溢出
2012/06/18 Javascript
javascript读取xml实现javascript分页
2013/12/13 Javascript
JS中表单的使用小结
2014/01/11 Javascript
jquery单行文字向上滚动效果的实现代码
2014/09/05 Javascript
nodejs爬虫抓取数据乱码问题总结
2015/07/03 NodeJs
jquery实现隐藏在左侧的弹性弹出菜单效果
2015/09/18 Javascript
ui组件之input多选下拉实现方法(带有搜索功能)
2016/07/14 Javascript
javascript轮播图算法
2016/10/21 Javascript
JS实现的表头列头固定页面功能示例
2017/01/10 Javascript
在小程序中使用Echart图表的示例代码
2018/08/02 Javascript
Vue实现星级评价效果实例详解
2019/12/30 Javascript
JavaScript中交换值的10种方法总结
2020/08/18 Javascript
深入Python函数编程的一些特性
2015/04/13 Python
python pandas 如何替换某列的一个值
2018/06/09 Python
Python实现FM算法解析
2019/06/18 Python
Django models文件模型变更错误解决
2020/05/11 Python
OpenCV图片漫画效果的实现示例
2020/08/18 Python
英国Office鞋店德国网站:在线购买鞋子、靴子和运动鞋
2018/12/19 全球购物
临床医学应届生求职信
2013/11/06 职场文书
专业幼师实习生自我鉴定范文
2013/12/08 职场文书
关于爱情的广播稿
2014/01/16 职场文书
加入学生会演讲稿
2014/04/24 职场文书
大学团日活动总结书
2015/05/11 职场文书
2016高校自主招生自荐信范文
2016/01/28 职场文书