$("a").css("color", "red");
当使用$
选择元素的时候,它会返回一个jQuery对象,这个对象中包含了你一直使用的方法(好比:.css(),.click()等)。这个jQuery对象是从$.fn
对象中获得的这些方法。$.fn
对象包含了jQuery对象的全部方法,若是想编写咱们本身的方法,也要将方法定义在$.fn
对象里面。使用这种方式编写插件,即jQuery类的实例将会拥有此功能。为何会有这种效果?简单看下源码javascript
jQuery.fn = jQuery.prototype ={ init: function( selector, context ){ //do something... };
从源码可知,当使用$.fn
的方式编写插件时,就是在jQuery的原型中绑定新的方法,因此根据原型的特性,新建立的jQuery对象天然会拥有新绑定的方法。css
目的:改变a
标签的字体颜色
作法:建立名为greenify
的方法,将其加在$.fn
里面。
如此一来,greenify
方法适用于全部的jQuery对象了html
<html> <head> <title>Title</title> <script type="text/javascript" src="../../js/jQuery-1.8.0.min.js"></script> <script type="text/javascript"> //这里使用$与jQuery均可以 $.fn.greenify = function () { /*这里使用this和$(this)均可以*/ this.css("color", "red"); }; $(function () { //$("a")即jQuery实例化对象 $("a").greenify(); }); </script> </head> <body> <a href="#">Click Me!!!</a> <a href="#">Cover Me!!!</a> </body> </html>
$.fn
还有另一种写法$.fn.extend({})
java
jQuery.fn.extend({ greenify: function () { $(this).css("color", "red"); } }); $(function () { $("a").greenify(); });
jQuery.fn.extend({ greenify: function () { $(this).css("color", "red"); //在结尾处返回this return this; } }); $(function () { $("a").greenify().addClass("greenified"); });
链式编程的好处就是当调用完一个方法后,能够在后面继续调用该对象的其余方法。jquery
$
在JavaScript库中使用是很是普遍的,若是你正在使用的其余JavaScript类库中也使用到了$
,而且你也使用了jQuery,那么你不得不使用jQuery.noConflict()
来解除冲突。显然这会破坏咱们的插件,由于它是在假设$
是jQuery函数的别名(实际上$
原本就是jQuery的别名)若是既想使用其余插件,也要使用jQuery的$
别名,咱们须要将代码放进当即执行函数(文章结尾会对其简单解释)中,而后将jQuery做为实参传递进去,$
做为形参接收。chrome
(function ( $ ) { $.fn.greenify = function() { this.css( "color", "green" ); return this; }; }( jQuery ));
因为window
,document
都是全局做用域的,而将其传入函数内部后,其在内部是做为局部变量存在的,这样作能够提升性能,减小做用域的查找时间,若是在函数内部屡次调用window
、document
,这是很高效的作法。编程
(function ( _window, _document ) { $.fn.greenify = function() { this.css( "color", "green" ); return this; }; }( window, document));
另外,存储私有变量也是使用当即执行函数的主要目的,假如想要存储一个默认的颜色,就可使用一个私有变量进行存储。浏览器
(function ($) { var defaultColor = "pink"; $.fn.extend({ setColor:function () { $(this).css("color", defaultColor); return $(this); } }) })(jQuery); $(function () { //全部div的text都会变成粉色 $("div").setColor(); });
一般在编写插件时,会在在当即执行函数前加入一个分号函数
;(function($){ //do something... })(jQuery);
做用:防止多个文件压缩合并后,前一个文件最后一行语句没加分号,而引发合并后的语法错误。
若是前面已经加了分号,此时就会多出来一个分号,但这样是不会报错的。即不怕多,就怕少。性能
;(function($, undefined){ //do something... })(jQuery)
上面代码的undefined
参数略显多余,此参数是为了解决undefined
在老一辈的浏览器(IE5)能够被赋值的问题,全局的undefined有可能会被其余函数覆盖。
var undefined = 99; alert(undefined);
以上代码若是在IE5运行,能够弹出99, 而不是undefined
,若是是这样的话,全局的undefined
就有被其余函数覆盖的危险;但以上代码在chrome运行,会弹出undefined
。
既然是插件就要考虑兼容性,因此经过在匿名函数中多定义一个undefined
的形参,因为只传入了一个实参jQuery
,从而能够保证undefined
形参未被赋值,从而最终是咱们想要的undefined
的值,什么是咱们想要的undefined
?即,undefined
没有被赋值,undefined
就是undefined
。
当使用$.fn
建立插件时,尽可能减小空间的占用,能使用参数进行区分的,就不要多定义一个方法,这样能够下降插件被覆盖的可能性。
(function( $ ) { $.fn.TurnOnLight= function() { // Turn on }; $.fn.TurnOffLight = function() { // Turn off }; }( jQuery ));
(function( $ ) { $.fn.light = function( action ) { if ( action === "turnOn") { // Turn on light code. } if ( action === "turnOff" ) { // Turn off light code. } }; }( jQuery ));
当插件愈来愈复杂时,经过接收参数选项的方式来自定义插件是一种很好的作法。
<html> <head> <title>Title</title> <script type="text/javascript" src="../../js/jquery-1.8.0.min.js"></script> <script type="text/javascript"> (function ($) { $.fn.extend({ changeColor:function (options) { var defaultColor = $.extend({ color: "red", backgroundColor:"skyblue" }, options); return $(this).css({ color:defaultColor.color, backgroundColor:defaultColor.backgroundColor }); } }); })(jQuery); $(function () { $("div").changeColor(); /*$("div").changeColor({ color:"pink", backgroundColor:"yellow" });*/ }); </script> </head> <body> <div>JavaScript</div> <div>Jquery</div> </body> </html>
调用changeColor
不传递任何参数,文本颜色默认红色,背景默认天蓝色;反之按照传入参数渲染颜色。默认的颜色被$.extned()
覆盖为其余颜色。
$.extend({ color: "red", backgroundColor:"skyblue" }, options)
以上代码执行结果:options
若是有值,那么它将覆盖第一个参数并返回options;若是为undefined
则直接返回第一个参数。
当即执行函数((Immediately-Invoked Function Expression)也称为自调用函数,函数定义好后会自动执行。(function(){})
表示一个匿名函数,后面紧跟一个()
,表示当即执行函数。
(function(){ console.log("我会当即执行"); })() (function(param){ console.log(param); //我会马上执行 })("我会马上执行");
优势:不会产生产生全局变量,不会形成变量污染。
缺点:只能执行一次,无法重复执行。
在编写插件时,使用IIFE是最合适不过的了,插件只须要引用一次,即执行一次。