2013-03-21 37 views
12

我想創建帶有配置的jQuery插件(例如插件myplugin)。 比打電話$(elem).myplugin(config);之後,我想調用這個插件的方法,如$(elem).myplugin().method()已經存儲的配置。將jquery插件配置存儲在數據中是一個好習慣嗎?

我的報價是類似的東西:

(function($) { 
    $.fn.myplugin = function(options) { 
     var $this = $(this); 

     var getOptions = function() { 
      return $this.data('myplugin'); 
     }; 

     var initOptions = function(opt) { 
      $this.data('myplugin', opt); 
     }; 

     var setOption = function(key, value) { 
      $this.data('myplugin')[key] = value; 
     } 

     var updateBorderWidth = function() { 
      $this.css('border-width', 
         getOptions().borderWidth * getOptions().coeficient); 
     }; 

     var init = function(opt) { 
      initOptions(opt); 
      updateBorderWidth(); 
     }   

     function changeBorder(width) {    
      setOption('borderWidth', width) 
      updateBorderWidth(); 
     } 

     if(options) { 
      init(options);    
     }   

     return { 
      changeBorder : changeBorder 
     }; 
    }   
})(jQuery); 

與用法:

$(function() { 
    var item1 = $('#test1').myplugin({ coeficient: 1, borderWidth: 1 }); 
    var item1 = $('#test2').myplugin({ coeficient: 2, borderWidth: 1 }); 

    $('#btn').click(updateBorder);  
}); 

function updateBorder() { 
    $('#test1').myplugin().changeBorder($('#inpt').val()); 
    $('#test2').myplugin().changeBorder($('#inpt').val()); 
} 

例子:http://jsfiddle.net/inser/zQumX/4/

我的問題:它是一個很好的做法,這樣做呢?

可能是不正確的做法。你能提供更好的解決方案?

+0

的最佳解決方案! – whatswrong 2013-03-21 10:08:57

回答

2

編輯:

jQuery plugin template搜索線程後,我發現這些Boilerplate templates這比我所提供的以下更靈活和廣泛的設計。最終你選擇什麼取決於你的需求。 Boilerplate模板涵蓋了比我的產品更多的用例,但根據需求,每個模板都有其自身的優點和注意事項。當一個值傳遞給它們作爲


通常jQuery插件要麼返回一個jQuery對象:

.wrap(html) // returns a jQuery object 

,或者當沒有參數在

.width() // returns a value 

.height() // also returns a value 

傳遞它們返回一個值

要閱讀您的示例調用約定:

$('#test1').myplugin().changeBorder($('#inpt').val());

它會出現,給誰用了jQuery,就好像是一前一後正在使用兩個單獨的插件,其中一個將承擔將返回一個jQuery對象與執行一些默認的DOM maniplulation任何開發,第一.myplugin()#test1,然後是.changeBorder($('#inpt').val()),它也可能會返回一個jQuery對象,但在您的示例中,整行不會分配給變量,因此不使用任何返回值 - 它看起來像是DOM操作。但是你的設計並沒有遵循我所描述的標準調用約定,所以任何人如果不熟悉你的插件,看看你的代碼中的實際內容可能會有些困惑。


我有,在過去,認爲類似的問題和使用情況您所描述的一個,我喜歡有用於調用與插件相關的獨立功能的便利公約的想法。這個選擇完全取決於你 - 這是你的插件,你需要根據誰來使用它,但我已經解決的方式是簡單地傳遞函數的名稱,它的參數要麼作爲一個單獨的.myplugin(name, parameters)或作爲.myplugin(object)的對象。

我通常做它像這樣:

(function($) { 
    $.fn.myplugin = function(fn, o) { // both fn and o are [optional] 
     return this.each(function(){ // each() allows you to keep internal data separate for each DOM object that's being manipulated in case the jQuery object (from the original selector that generated this jQuery) is being referenced for later use 
      var $this = $(this); // in case $this is referenced in the short cuts 

      // short cut methods 
      if(fn==="method1") { 
       if ($this.data("method1")) // if not initialized method invocation fails 
        $this.data("method1")() // the() invokes the method passing user options 
      } else if(fn==="method2") { 
       if ($this.data("method2")) 
        $this.data("method2")() 
      } else if(fn==="method3") { 
       if ($this.data("method3")) 
        $this.data("method3")(o) // passing the user options to the method 
      } else if(fn==="destroy") { 
       if ($this.data("destroy")) 
        $this.data("destroy")() 
      } 
      // continue with initial configuration 

      var _data1, 
       _data2, 
       _default = { // contains all default parameters for any functions that may be called 
        param1: "value #1", 
        param2: "value #2", 
       }, 
       _options = { 
        param1: (o===undefined) ? _default.param1 : (o.param1===undefined) ? _default.param1 : o.param1, 
        param2: (o===undefined) ? _default.param2 : (o.param2===undefined) ? _default.param2 : o.param2, 

       } 
       method1 = function(){ 
        // do something that requires no parameters 
        return; 
       }, 
       method2 = function(){ 
        // do some other thing that requires no parameters 
        return; 
       }, 
       method3 = function(){ 
        // does something with param1 
        // _options can be reset from the user options parameter - (o) - from within any of these methods as is done above 
        return; 
       }, 
       initialize = function(){ 
        // may or may not use data1, data2, param1 and param2 
        $this 
         .data("method1", method1) 
         .data("method2", method2) 
         .data("method3", method3) 
         .data("destroy", destroy); 
       }, 
       destroy = function(){ 
        // be sure to unbind any events that were bound in initialize(), then: 
        $this 
         .removeData("method1", method1) 
         .removeData("method2", method2) 
         .removeData("method3", method3) 
         .removeData("destroy", destroy); 
       } 
      initialize(); 
     }) // end of each() 
    } // end of function   
})(jQuery); 

和使用:

var $test = $('#test').myplugin(false, {param1: 'first value', param2: 'second value'}); // initializes the object 
$test.myplugin('method3', {param1: 'some new value', param2: 'second new value'}); // change some values (method invocation with params) 

,或者你可以只說:

$('#test').myplugin(); // assume defaults and initialize the selector 
2

通過數據屬性將參數傳遞給javascript是一個很好的模式,因爲它有效地分離了Javascript代碼和服務器端代碼。它也不會對Javascript代碼的可測試性產生負面影響,這是許多其他解決方案的副作用。

我會盡可能地說服務器端代碼與Web應用程序中的客戶端代碼進行通信的最佳方式。

相關問題