О шаблоне плагина jQuery от Addy Osmani: вызов функций

0

Я использую превосходный шаблон плагина jQuery Addy Osmani для написания плагина jQuery (http://addyosmani.com/resources/essentialjsdesignpatterns/book/#jquerypluginpatterns), но там что-то меня смущает о том, как он добавляет функции прототипу:

// The actual plugin constructor
function Plugin( element, options ) {
    this.element = element;

    // jQuery has an extend method that merges the
    // contents of two or more objects, storing the
    // result in the first object. The first object
    // is generally empty because we don't want to alter
    // the default options for future instances of the plugin
    this.options = $.extend( {}, defaults, options) ;

    this._defaults = defaults;
    this._name = pluginName;

    this.init();
}

Plugin.prototype.init = function () {
    // Place initialization logic here
    // We already have access to the DOM element and
    // the options via the instance, e.g. this.element
    // and this.options
};

В этом разделе он называет "this.init()", который является функцией, добавленной в прототип плагина, но если я добавлю свои собственные функции в прототип, я не могу назвать его нигде, где "это" изменяет область видимости.

Например

Plugin.prototype.foo = function() {};

не может быть вызван из:

$('.some-class).each(function() {
  this.foo();
});

потому что "это" относится к каждому элементу в выборе.

Как я могу стандартным образом вызвать методы и функции из плагина? Эти подходы также не работают:

Plugin.foo();
this.foo();

Изменение: действительный код:

;(function ($, window, document, undefined) {

    var pluginName = 'slider',
        defaults = {
            speed: 1000,
            pause: 5000
        };


    function Plugin(element, options) {

        this.element = element;
        this.options = $.extend( {}, defaults, options) ;

        this._defaults = defaults;
        this._name = pluginName;

        this.init();
    }


    Plugin.prototype.init = function () {

        var $slider,
            $controls;

        $slider = $(this.element);
        $controls = $slider.find('.slider__controls');

        $controls.each(function(index) {

            // How do I call 'showControl();'?

        });

    };


    Plugin.prototype.showControl = function() {

        // Do things.

    };


    $.fn[pluginName] = function (options) {
        return this.each(function () {
            if (!$.data(this, "plugin_" + pluginName)) {
                $.data(this, "plugin_" + pluginName, new Plugin(this, options));
            }
        });
    }

})(jQuery, window, document);
  • 1
    Вы также не можете вызвать init из jQuery each() . Вы также можете вызывать ваши методы из конструктора.
  • 0
    Где вы создали new Plugin экземпляр new Plugin ? Покажите нам свой полный код, пожалуйста.
Показать ещё 1 комментарий
Теги:
design-patterns

1 ответ

1
Лучший ответ

См. Как получить доступ к правильному "этому" контексту внутри обратного вызова? :

Plugin.prototype.init = function () {
    var $slider = $(this.element),
        $controls = $slider.find('.slider__controls'),
        pluginInstance = this;

    $controls.each(function(index) {
        pluginInstance.showControl(this);
    });
};
  • 0
    Отлично, это трюк. я знал, что это проблема с этим, но, будучи новичком в этом паттерне, я не до конца понял, почему ;-)

Ещё вопросы

Сообщество Overcoder
Наверх
Меню