1

More of a 'why', 'than it's broken'...

Can someone explain why you'd add the plugin name to the scope and set an alias here:

(function($, plugin) {
    $[plugin] = {
        timers: {}
    };
    $.fn[plugin] = function(type, msg, timeout) {
        return this.each(function() {
            var $this = $('<p class="' + type + '">' + msg + '</p>').prependTo($(this)),
                $sameMsgs = $this.siblings().filter(function() {
                    return !($(this).html() == msg);
                });
            $this.hide()[$sameMsgs.length ? 'show' : 'slideDown']();
            if ($[plugin].timers[msg]) {
                clearTimeout($[plugin].timers[msg]);
                $sameMsgs.remove();
            }
            $[plugin].timers[msg] = setTimeout(function() {
                $this.slideUp(function() {
                    $(this).remove()
                });
            }, timeout || 2500);
        });
    };
})(jQuery, "quickResponse");

What I'd like to do is write the plugin like so:

(function($) {

    $.fn.quickResponse = function(type, msg, timeout)
    {
        ....
    };

})(jQuery);
Sam Holguin
  • 553
  • 2
  • 9
  • 24
  • It means you can change the name of the plugin in just one place and have no issues at all. Personally though I'd do something like `var plugin = 'quickResponse';` at the start but that's a matter of preference. – Niet the Dark Absol Sep 21 '16 at 15:48
  • But why do it at all @NiettheDarkAbsol ??? – Sam Holguin Sep 21 '16 at 15:49
  • @SamHolguin Because otherwise you couldn't `change the name of the plugin in just one place` ... – A. Wolff Sep 21 '16 at 16:00
  • That's primarily opinion based or is my intuition? – Marcos Pérez Gude Sep 21 '16 at 16:01
  • @A.Wolff Can you show me how it could look using my desired method please? – Sam Holguin Sep 21 '16 at 16:02
  • 1
    @SamHolguin Sorry, i really don't understand your question. You ask a former question, you get your answer regarding code maintenability. Now i'm not sure anymore what you are asking. If you don't want to use any `plugin` variable, replace `$[plugin]` with `$.quickResponse` and `$.fn[plugin]` with `$.fn.quickResponse` and that's all... – A. Wolff Sep 21 '16 at 16:05
  • Thank you! I just like to fully understand what is going on... that's the answer. @A.Wolff – Sam Holguin Sep 21 '16 at 16:06
  • 1
    Maybe that was your question: http://stackoverflow.com/a/2274327/1414562 or maybe more helpful https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Working_with_Objects :) – A. Wolff Sep 21 '16 at 16:09

1 Answers1

1

If you don't do it this way, you have to repeat your plugin name throughout the code, like this:

(function($) {
    $.quickResponse = {
        timers: {}
    };
    $.fn.quickResponse = function(type, msg, timeout) {
        return this.each(function() {
            var $this = $('<p class="' + type + '">' + msg + '</p>').prependTo($(this)),
                $sameMsgs = $this.siblings().filter(function() {
                    return !($(this).html() == msg);
                });
            $this.hide()[$sameMsgs.length ? 'show' : 'slideDown']();
            if ($.quickResponse.timers[msg]) {
                clearTimeout($[plugin].timers[msg]);
                $sameMsgs.remove();
            }
            $.quickResponse.timers[msg] = setTimeout(function() {
                $this.slideUp(function() {
                    $(this).remove()
                });
            }, timeout || 2500);
        });
    };
})(jQuery);

Then if you decide to rename your plugin, you have to do a global replace of all $.quickResponse and $.fn.quickResponse to the new name.

By using the variable, you only have to change it in one place, the argument to the IIFE.

Barmar
  • 741,623
  • 53
  • 500
  • 612
  • Thank you. And as obvious as this should be, can you explain the different between `$.quickResponse` and `$.fn.quickResponse` please? – Sam Holguin Sep 21 '16 at 16:18
  • 1
    `$.quickResponse` contains an object, it's used to hold data used by the plugin. `$.fn.quickResponse` is the function used to invoke the plugin. Take a look at the first two assignments. – Barmar Sep 21 '16 at 16:21
  • Great... makes sense. Thank you! – Sam Holguin Sep 21 '16 at 16:22
  • Can you see why calling '$.fn.quickResponse' multiple times doesn't have the intended results. The error messages, if the same, still display. It looks like it creates a new `$.quickResponse = { timers: {} };` obj every time?? – Sam Holguin Sep 21 '16 at 16:31
  • It only creates a new one when you execute the IIFE, not when you call `$.fn.quickResponse`. You should only execute the IIFE once, since it's used to define the plugin. To **use** the plugin you do `$(selector).quickResponse()`. – Barmar Sep 21 '16 at 18:15