Pierre de LESPINAY
Pierre de LESPINAY

Reputation: 46168

jQuery - plugin methods call

I'm trying to create a jQuery plugin following some official best practices

(function($){

  var methods = {
    init : function( options ) {
      this.options = options;
    }
  , add_that: function (elem) {
      this.append(elem);
      return (this);
    }
  , add_this: function (elem) {
      return (methods.add_that(elem));
    }
  };

  $.fn.test = 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.test' );
    }    
  };

})(jQuery);

I'd like the method add_that to be able to append things to the matched element(s).
Now this method is called from add_this.

$('#test').test('add_this', $('<div />'));

TypeError: this.append is not a function

Why can't I access to the plugin (this) from add_that ?

Upvotes: 3

Views: 3267

Answers (2)

Jamiec
Jamiec

Reputation: 136074

Because the scope has changed when you've called it from add_this. Notice that the original call used Function.apply to scope the call to this.

if ( methods[method] ) {
  return methods[ method ].apply( this, Array.prototype.slice.call( arguments, 1 ));
}

So you can presumably get around the issue by using apply again in your method:

add_this: function (elem) {
  return methods.add_that.apply(this,[elem]);
}

Live example: http://jsfiddle.net/XaUHV/

Upvotes: 6

Brian
Brian

Reputation: 3023

In the context you're using it "this" refers to methods.add_that

Since methods.add_that is a function there is no method on it called "append" by default.

Upvotes: 2

Related Questions