-->

jquery namespace: how to pass default options from

2019-05-10 14:52发布

问题:

How can I pass the default options from one method to the subsequence methods?

For instance, I have some default setting in the init method. and I want to use these settings for other methods such as show,

(function($) {
    var methods = {
        init: function(options) {
            var defaults = {
                element:    "selection"
            }

            var options =  $.extend(defaults, options);
            var o = options;

            alert(o.element);
        },
        show: function(o) {
            alert(o.element);
        },
        hide: function() {
            alert(o.element);
        }
    };

 $.fn.plugin = function( method ) {

    if ( methods[method] ) {
      return methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
    } else if ( typeof method === 'object' || ! method ) {
      return methods.init.apply( this, arguments );
    } else {
      $.error( 'Method ' +  method + ' does not exist on jQuery.tooltip' );
    }    

  };

})( jQuery );

var blah = $('#hello').plugin('show'); // TypeError: o is undefined

I would want to get selection as the answer... is it possible?

EDIT:

(function($) {

    $.fn.plugin = function( method ) {

        if ( methods[method] ) {
          return methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
        } else if ( typeof method === 'object' || ! method ) {
          return methods.init.apply( this, arguments );
        } else {
          $.error( 'Method ' +  method + ' does not exist on jQuery.tooltip' );
        }    

     }; 

     $.fn.plugin.defaults = {
        attr: 'checked',
        expected: true,
        onChange: function(){}
      }; 

    var methods = {

        init: function(options) {
            var options = $.extend({}, $.fn.plugin.defaults, options);
            var o = options;

            var $this = this;

            $this.show();
            //alert(o.attr);
        },
        show: function(options) {

            var options = $.extend({}, $.fn.plugin.defaults, options);
            var o = options;

            alert(o.expected);
        },
        hide: function(object) {
            alert(o.element);
        }
    };


})( jQuery );

reference

var blah = $('#hello').plugin('show',{expected:"#hello world"}); 

now I get #hello world (correct)

but,

var blah = $('#hello').plugin('init'); // returns nothing

I would want to get true as the answer because init is accessing show. So how do I access other methods from a method?

回答1:

It appears to me that you are trying to reinvent extensible jquery plugins (aka jQuery UI Widgets). I can walk you though a lot of how to accomplish what you are trying to do, but it really is reinventing the wheel. The jQuery UI Widget Factory is great for this type of thing.

jQuery Widget Factory -- This is their old documenation, but it outlines the widget factory better than anything else, IMHO. They have made some minor changes to it in 1.9/1.10, but most of the concepts are still the same.

Edit

Here's my modifications to your code. I believe this does what you were looking for.

(function($) {
    var methods = {
        init: function(options) {
            var defaults = {
                element:    "selection"
            }

            this.options =  $.extend(defaults, options);

            alert("init: " + this.options.element);
        },
        show: function() {
            alert("show: "  + this.options.element);
        },
        hide: function() {
            alert("hide: " + this.options.element);
        }
    };

 $.fn.plugin = function( method ) {
    if ( methods[method] ) {
      methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
    } else if ( typeof method === 'object' || ! method ) {
      methods.init.apply( this, arguments );
    } else {
      $.error( 'Method ' +  method + ' does not exist on jQuery.tooltip' );
    } 
    return this; // this is needed to ensure chainability
 };

})( jQuery );

var blah = $('#hello').plugin('init').plugin('show');​