上一篇教程,明河只是简单的贴出了colortips这个插件的示例和代码,同时提取出了jquery插件的基础模板:
- (function($){
- $.fn.插件名= function(settings){
- //默认参数
- var defaultSettings = {
- }
- /* 合并默认参数和用户自定义参数 */
- settings = $.extend(defaultSettings,settings);
- return this.each(function(){
- //代码
- });
- }
- })(jQuery);
今天明河将详解这个模板。
一、匿名函数和闭包
先来看模板中的第一行代码:
- (function($){
- })(jQuery);
如果你对匿名函数和闭包不了解,将会对这种代码非常疑惑,所以明河严重建议阅读JavaScript中的匿名函数及函数的闭包这篇文章。
这行代码其实是用于创建一个匿名函数。
1、模板中匿名函数的作用
保护“$”这个变量,避免“$”这个变量与你页面中的全局变量冲突。
这点非常重要,“$”这个变量在编程语言中使用率非常高,你无法保证你所引入的其他js都是用“$”来代表“jQuery”。明河举个例子,有用过ecshop的朋友应该有遇到一个问题,就是如果你在页面中使用jquery插件,会报”$不是一个函数”的错误,究其原因就是ecshop有个js定义了“$”作为获取dom对象的函数,如果你的插件没有使用匿名函数做包装就会报错。很多朋友喜欢$(‘[title]‘).colorTip({color:’yellow’});这样的形式调用插件,实际上也会出现冲突问题,最好的习惯是,使用jQuery(‘[title]‘).colorTip({color:’yellow’});
2、$与jQuery
jQuery是jquery库定义的一个全局变量,而$这个变量相当于jQuery的简写,$的冲突率是非常高的,不同的js框架$有不同的含义,但如果都使用jQuery,那是非常繁琐的一件事,这就是
- (function($){
- })(jQuery);
这行代码的用处,这个匿名函数创建了闭包,意味着在这个闭包内,你可以任意的使用$这个变量,不用担心冲突的问题。
3、匿名函数的函数体形式
- (function( x , y){
- alert( x + y);
- })(2 ,3 );
你可以试运行下上面的代码,再对照下模板中的第一行代码,也许你就会大致明白其形式。
- (function($){
- });
定义一个带有个名为“$”参数的匿名函数。
- (function($){
- })(jQuery);
将jQuery这个全局变量传入匿名函数,并执行匿名函数。
$.fn的含义
- (function($){
- $.fn.插件名= function(settings){
- }
- });
$.fn或者jQuery.fn本质上可以等于jQuery.prototype。prototype(原型)出现了,prototype在js中极其重要,是在javascript实现面向对象编程的关键,真的展开说,估计明河可以写好几天,这里明河推荐二本书《javascript高级编程》和《javascript设计模式》都有对prototype进行详解,你也可以看网上的教程。
以colorTip为例
- (function($){
- $.fn.colorTip= function(settings){
- alert(1);
- }
- });
实际上你就给jQuery扩展了一个名为colorTip的方法,接下来你可以如下调用执行该方法:
- (function($){
- $('a').colorTip();
- });
在$.fn.colorTip中this上下文就会指向$(‘a’)这个对象。
三、jquery的继承方法$.extend
- (function($){
- $.fn.插件名= function(settings){
- //默认参数
- var defaultSettings = {
- }
- /* 合并默认参数和用户自定义参数 */
- settings = $.extend(defaultSettings,settings);
- }
- })(jQuery);
$.extend在jquery插件开发中有个很重要的作用,就是用于合并参数。
还是以colorTip为例:
- (function($){
- $.fn.colorTip= function(settings){
- var defaultSettings = {
- //颜色
- color : 'yellow',
- //延迟
- timeout : 500
- }
- /* 合并默认参数和用户自定义参数 */
- settings = $.extend(defaultSettings,settings);
- alert(settings.color);
- }
- });
插件调用:
- $('a').colorTip({color:'blue'});
如果你运行以上代码,就会发现弹出的值为blue,而不再是默认的yellow。
$.extend(defaultSettings,settings);的含义是,使用settings来覆盖defaultSettings(同名键值)。
实际上.extend不止接受二个参数,相对于模板上的写法,明河更喜欢下面的写法:
- settings = $.extend({},defaultSettings,settings);
即不去覆盖defaultSettings(默认参数),而是合并到一个空的Object。
深层拷贝
这个知识点不是必须的,你可以略过。当$.extend的第一个参数为true时,会开启深层拷贝,代码如下:
- settings = $.extend(true,{},defaultSettings,settings);
调用之后你会发现没什么差别。
接下来我们增加个animate参数(这个参数也是个Object):
- var defaultSettings = {
- //颜色
- color : 'yellow',
- //延迟
- timeout : 500,
- animate :{type:"fade",speed:"fast"}
- }
调用如下:
- $('a').colorTip({color:'yellow',animate:{type:"slide"}});
在
- settings = $.extend({},defaultSettings,settings);
下加上:
- alert(settings.animate.speed);
按理说,应该得到的是fast,实际上却是undefined!原因是:animate是Object,不开启深度拷贝,是直接覆盖。
你可以再试下:
- settings = $.extend(true,defaultSettings,settings);
- alert(settings.animate.speed);
正确的得到fast。
推荐阅读:jQuery.extend 函数详解,这篇文章讲解的非常到位。
四、each
- return this.each(function(){
- //代码
- });
要读懂这行代码,有三个问题需要解决:
- 1、this指代什么?
- 2、为什么使用return?
- 3、为什么要使用each?
1、this指代什么?
插件的调用如下:
- $('[title]').colorTip({color:'yellow'});
那么这里this,实际上是指向$(‘[title]‘)。
2、为什么使用return?
基本上大部分的jquery插件教程都没有说到原因。明河觉得主要原因还是方便链式调用:
- return this.each(function(){
- //代码
- });
this.each()执行完返回的是this,这时候再return this.each(),返回的依旧是this,而这个this上下文又是指代$(‘[title]‘),意味着你可以在colorTip()后继续加其他方法,比如:
- $('[title]').colorTip({color:'yellow'}).size();
3、为什么使用each?
这个很容易理解。
- $('[title]').colorTip({color:'yellow'});
$(‘[title]‘)很明显是一个对象集合,我们希望所有的带有title属性的容器都能出现提示框,所以就需要遍历$(‘[title]‘)。
下一篇教程明河将讲解colorTip这个插件的代码实现,从而指出插件的不足之处,进而讲解jquery插件的高级技巧(如何开放API,如何创建自定义事件等)。
如果你遇到什么问题或发现文章有错误,可以给明河留言,谢谢!

1. (function($){
2.
3. })(jQuery);
终于看懂了这个是什么意思了,学习了,谢了。
留个脚丫 再慢慢看文章
太复杂了,不适合我 – -
呵呵其实你只要记住那个jquery插件基础模板就行了,对于原理你只要稍微理解下即可。接下来的教程我将讲解更为高级的模板。
明河 加油 支持 支持 呵呵
受益匪浅,非常感谢!!
为什么这个网站不能注册会员呢。。。难得有个心甘情愿想注册的网站
呵呵,非常非常感谢renrenqian同学,其实注册与没注册没啥区别,所以我们把注册功能关闭了。如果有兴趣可以加我们几个的微博。
勘误,在第二点的最后一句:
 在$.fn.colorTip中this上下文就会指向$(‘#a’)这个对象。
应该是指向$(‘a’)这个对象吧?
哈,的确感谢纠正,已经修正
呀个呸的,这是我看到的最详细,最perfect的文章了!!!
必须强势占座。。。