1,开始

可以通过为jQuery.fn增加一个新的函数来编写jQuery插件。属性的名字就是你的插件的名字:

  1. jQuery.fn.myPlugin = function(){
  2. //开始写你的代码吧!
  3. };

但是,那惹人喜爱的美元符号$哪里去了?她就是jQuery,但是为了确保你的插件与其他使用$的库不冲突,最好使用一个立即执行的匿名函数,这个匿名函数的参数是jQuery,这样其他的库就可以放心的使用$符号了。

  1. (function( $ ){
  2. $.fn.myPlugin = function() {
  3. // 开始吧!
  4. };
  5. })( jQuery );

这样更好了就。在闭包内,可以放心的使用$符号了~

2,上下文

现在已经可以编写我们的代码了,但是编写之前,我必须说一说上下文。在插件内部的范围中,this关键字指向的是jQuery对象。人们很容易误解这一点,因为在正常使用jQuery的时候,this通常指向的是一个DOM元素。不了解这一点,会经常使用$又包装了一次。

  1. (function( $ ){
  2. $.fn.myPlugin = function() {
  3. // 没有必要使用$(this)
  4. // $(this) 跟 $($('#element'))是一样的
  5. this.fadeIn('normal', function(){
  6. //这里的this指的就是一个DOM元素了
  7. });
  8. };
  9. })( jQuery );
  10. $('#element').myPlugin();

3,基本开发

接下来写一个能用的插件吧。

  1. (function( $ ){
  2. $.fn.maxHeight = function() {
  3. var max = 0;
  4. this.each(function() {
  5. max = Math.max( max, $(this).height() );
  6. });
  7. return max;
  8. };
  9. })( jQuery );
  1. var tallest = $('div').maxHeight();

这是一个简单的插件,通过调用height()返回页面上height最大的div的height。

4,维护链式开发的特性

上一个例子是返回了一个整数,但是大多数情况下,一个插件紧紧是修改收集到的元素,然后返回这个元素让链条上的下一个使用。这是jQuery设计的精美之处,也是jQuery如此流行的原因之一。为了保证可链式,你必须返回this。

  1. (function( $ ){
  2. $.fn.lockDimensions = function( type ) {
  3. return this.each(function() {
  4. var $this = $(this);
  5. if ( !type || type == 'width' ) {
  6. $this.width( $this.width() );
  7. }
  8. if ( !type || type == 'height' ) {
  9. $this.height( $this.height() );
  10. }
  11. });
  12. };
  13. })( jQuery );
  1. $('div').lockDimensions('width').css('color','red');

因为该插件返回了this,所以保证了可链式,从而可以继续使用jQuery方法进行修改,如css()。如果你的插件如果不是返回一个简单值,你通常应该返回this。而且,正如你可能想到的,你传进去的参数也可以在你的插件中访问。所以在这个例子中,可以访问到type。

5,默认值和选项

为了一些复杂的,可订制的插件,最好提供一套默认值,在被调用的时候扩展默认值。这样,调用函数的时候就不用传入一大堆参数,而是传入需要被替换的参数。你可以这样做:

  1. (function( $ ){
  2. $.fn.tooltip = function( options ) {
  3. var settings = {
  4. 'location'         : 'top',
  5. 'background-color' : 'blue'
  6. };
  7. return this.each(function() {
  8. // 如果存在选项,则合并之
  9. if ( options ) {
  10. $.extend( settings, options );
  11. }
  12. // 其他代码咯
  13. });
  14. };
  15. })( jQuery );
  1. $('div').tooltip({'location':'left'});

在这个例子中,调用插件后,默认的location会被替换城'left',而background-color还是'blue'。这样可以保证高度可配置性,而不需要开发者定义所有可能的选项了。

6,命名空间

正确的命名空间对于插件开发十分重要,这样能确保你的插件不被其他插件重写,也能避免被页面上其他代码重写。命名空间可以使你更长寿,因为你能记录你自己的方法,事件,数据等。

a,插件方法

在任何情况下,都不要在一个插件中为jQuery.fn增加多个方法。如:

  1. (function( $ ){
  2. $.fn.tooltip = function( options ) { // 这样 };
  3. $.fn.tooltipShow = function( ) { // 是   };
  4. $.fn.tooltipHide = function( ) { // 不好的  };
  5. $.fn.tooltipUpdate = function( content ) { // 同学!  };
  6. })( jQuery );

不推荐这样使用,搞乱了$.fn命名空间。要纠正之,你可以把所有的方法放进一个对象中,然后通过不同的参数来调用。

  1. (function( $ ){
  2. var methods = {
  3. init : function( options ) { // THIS },
  4. show : function( ) { // IS   },
  5. hide : function( ) { // GOOD },
  6. update : function( content ) { // !!! }
  7. };
  8. $.fn.tooltip = function( method ) {
  9. // Method calling logic
  10. if ( methods[method] ) {
  11. return methods[ method ].apply( this, Array.prototype.slice.call( arguments, 1 ));
  12. } else if ( typeof method === 'object' || ! method ) {
  13. return methods.init.apply( this, arguments );
  14. } else {
  15. $.error( 'Method ' +  method + ' does not exist on jQuery.tooltip' );
  16. }
  17. };
  18. })( jQuery );
  1. $('div').tooltip({  // calls the init method
  2. foo : 'bar'
  3. });
  4. $('div').tooltip('hide'); // calls the hide method
  5. $('div').tooltip('update', 'This is the new tooltip content!'); // calls the update method

jQuery自己的扩展也是使用这种插件结构。

b,事件

绑定事件的命名空间是比较不为人知的。如果你的插件绑定了某个事件,最好将它搞到一个命名空间中。这样,如果你以后需要解绑,就不会影响到其他绑定到这个事件上的函数了。你可以使用".<namespace>"来增加命名空间。

  1. (function( $ ){
  2. var methods = {
  3. init : function( options ) {
  4. return this.each(function(){
  5. $(window).bind('resize.tooltip', methods.reposition);
  6. });
  7. },
  8. destroy : function( ) {
  9. return this.each(function(){
  10. $(window).unbind('.tooltip');
  11. })
  12. },
  13. reposition : function( ) { // ... },
  14. show : function( ) { // ... },
  15. hide : function( ) { // ... },
  16. update : function( content ) { // ...}
  17. };
  18. $.fn.tooltip = function( method ) {
  19. if ( methods[method] ) {
  20. return methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
  21. } else if ( typeof method === 'object' || ! method ) {
  22. return methods.init.apply( this, arguments );
  23. } else {
  24. $.error( 'Method ' +  method + ' does not exist on jQuery.tooltip' );
  25. }
  26. };
  27. })( jQuery );
  28. $('#fun').tooltip();
  29. // Some time later...
  30. $('#fun').tooltip('destroy');

在这个例子中,tooltip在init方法中初始化,它将reposition方法绑定到window对象的resize事件的tooltip名字空间下。稍候,如果开发者需要去掉这个tooltip,我们可以解绑这个绑定。这样就不会影响到其他绑定到window对象的resize事件的方法了。

c,数据

在开发插件的时候,你通常会有保持状态或者检查你的插件是否已经初始化的需要。使用jQuery的data方法是保持变量的很好的方法。但是,我们不把变量单独保存,而是放在一个对象中,这样就可以在一个名字空间下统一访问了。

  1. (function( $ ){
  2. var methods = {
  3. init : function( options ) {
  4. return this.each(function(){
  5. var $this = $(this),
  6. data = $this.data('tooltip'),
  7. tooltip = $('<div />', {
  8. text : $this.attr('title')
  9. });
  10. // If the plugin hasn't been initialized yet
  11. if ( ! data ) {
  12. /*
  13. Do more setup stuff here
  14. */
  15. $(this).data('tooltip', {
  16. target : $this,
  17. tooltip : tooltip
  18. });
  19. }
  20. });
  21. },
  22. destroy : function( ) {
  23. return this.each(function(){
  24. var $this = $(this),
  25. data = $this.data('tooltip');
  26. // Namespacing FTW
  27. $(window).unbind('.tooltip');
  28. data.tooltip.remove();
  29. $this.removeData('tooltip');
  30. })
  31. },
  32. reposition : function( ) { // ... },
  33. show : function( ) { // ... },
  34. hide : function( ) { // ... },
  35. update : function( content ) { // ...}
  36. };
  37. $.fn.tooltip = function( method ) {
  38. if ( methods[method] ) {
  39. return methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
  40. } else if ( typeof method === 'object' || ! method ) {
  41. return methods.init.apply( this, arguments );
  42. } else {
  43. $.error( 'Method ' +  method + ' does not exist on jQuery.tooltip' );
  44. }
  45. };
  46. })( jQuery );

使用data方法可以帮助你在插件的各个方法间保持变量和状态。将各种变量放在一个对象中,可以方便访问,也可以方便移除。

7,总结与最佳实践

编写jQuery插件可以充分利用库,将公用的函数抽象出来,“循环利用”。以下是简短的总结:

  • 使用(function($){//plugin})(jQuery);来包装你的插件
  • 不要在插件的初始范围中重复包裹
  • 除非你返回原始值,否则返回this指针来保证可链式
  • 不要用一串参数,而是使用一个对象,并且设置默认值
  • 一个插件,不要为jQuery.fn附上多个函数
  • 为你的函数,事件,数据附着到某个命名空间

jQuery插件开发--(转)的更多相关文章

  1. JavaScript学习笔记(四)——jQuery插件开发与发布

    jQuery插件就是以jQuery库为基础衍生出来的库,jQuery插件的好处是封装功能,提高了代码的复用性,加快了开发速度,现在网络上开源的jQuery插件非常多,随着版本的不停迭代越来越稳定好用, ...

  2. JavaScript学习总结(四)——jQuery插件开发与发布

    jQuery插件就是以jQuery库为基础衍生出来的库,jQuery插件的好处是封装功能,提高了代码的复用性,加快了开发速度,现在网络上开源的jQuery插件非常多,随着版本的不停迭代越来越稳定好用, ...

  3. jQuery插件开发精品教程,让你的jQuery提升一个台阶

    要说jQuery 最成功的地方,我认为是它的可扩展性吸引了众多开发者为其开发插件,从而建立起了一个生态系统.这好比大公司们争相做平台一样,得平台者得天下.苹果,微软,谷歌等巨头,都有各自的平台及生态圈 ...

  4. jquery插件开发

    jQuery是一个封装的很好的类,比如我们用语句$("#btn1") 会生成一个 jQuery类的实例. 一.jQuery插件开发注意要点 1.使用闭包,避免全局依赖,避免第三方破 ...

  5. jQuery插件开发(溢出滚动)

    声明:此程序仅针对手机端,简单的封装一个插件,意在记载插件的开发过程,如有错误及不足之处,还望即时指出. 移动开发的时候,我们经常会遇到滑动事件,众所周知手机端滑动主要依靠touch事件.最近接连遇到 ...

  6. 从零开始学jQuery插件开发

    http://www.w3cfuns.com/notes/19462/ec18ab496b4c992c437977575b12736c.html jQuery 最成功的地方,是它的可扩展性,通过吸引了 ...

  7. jquery插件开发继承了jQuery高级编程思路

    要说jQuery 最成功的地方,我认为是它的可扩展性吸引了众多开发者为其开发插件,从而建立起了一个生态系统.这好比大公司们争相做平台一样,得平台者得天下.苹果,微软,谷歌等巨头,都有各自的平台及生态圈 ...

  8. jQuery插件开发(转)

    jQuery插件开发全解析 jQuery插件的开发包括两种: 一种是类级别的插件开发,即给jQuery添加新的全局函数,相当于给jQuery类本身添加方法.jQuery的全局函数就是属于jQuery命 ...

  9. jQuery插件开发的两种方法及$.fn.extend的详解

    jQuery插件开发分为两种: 1 类级别 类级别你可以理解为拓展jquery类,最明显的例子是$.ajax(...),相当于静态方法. 开发扩展其方法时使用$.extend方法,即jQuery.ex ...

  10. Jquery插件开发学习

    一:导言 有些WEB开发者,会引用一个JQuery类库,然后在网页上写一写$("#"),$("."),写了几年就对别人说非常熟悉JQuery.我曾经也是这样的人 ...

随机推荐

  1. linux下QT Creator常见错误及解决办法

    最近因为在做一个关于linux下计算机取证的小项目,需要写一个图形界面,所以想到了用QT来写,选用了linux下的集成开发环境QT Creator5.5.1,但刚刚安装好,竟然连一个"hel ...

  2. maven加载本地lib下的jar包

    1.本地lib下有jar 2.命令: mvn install:install-file -Dfile=juh-3.0.1.jar -DgroupId=org.openoffice -Dartifact ...

  3. mybatis一对多查询

    18 <!-- 19 方式一:嵌套结果:使用嵌套结果映射来处理重复的联合结果的子集 20 封装联表查询的数据(去除重复的数据) 21 select * from class c, teacher ...

  4. Alcatraz安装在xcode7失败执行下面代码

    1.步奏rm -rf ~/Library/Application\ Support/Developer/Shared/Xcode/Plug-ins/Alcatraz.xcplugin 2.步奏 rm ...

  5. iOS开发UI篇—UIScrollView控件实现图片缩放功能

    iOS开发UI篇—UIScrollView控件实现图片缩放功能 一.缩放 1.简单说明: 有些时候,我们可能要对某些内容进行手势缩放,如下图所示 UIScrollView不仅能滚动显示大量内容,还能对 ...

  6. [Android Rro] SDK JAR

    cd ../../../outputs/aar/mkdir AAR_VERSIONmkdir JAR_VERSIONmv app-release.aar AAR_VERSION/${project_n ...

  7. Linear regression with multiple variables(多特征的线型回归)算法实例_梯度下降解法(Gradient DesentMulti)以及正规方程解法(Normal Equation)

    ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, ,, , ...

  8. web.config详解 -- asp.net夜话之十一

    1.配置文件节点说明    1.1 <appSettings>节点    1.2 <connectionStrings>节点    1.3 <compilation> ...

  9. Ubuntu开机自启动

    http://www.jb51.net/os/Ubuntu/181138.html http://blog.csdn.net/elim051/article/details/6173367

  10. 如何减少JS的全局变量污染

    A,唯一变量 B,闭包