1/** 2 * noty - jQuery Notification Plugin v2.0.3 3 * Contributors: https://github.com/needim/noty/graphs/contributors 4 * 5 * Examples and Documentation - http://needim.github.com/noty/ 6 * 7 * Licensed under the MIT licenses: 8 * http://www.opensource.org/licenses/mit-license.php 9 **/ 10 11if (typeof Object.create !== 'function') { 12 Object.create = function (o) { 13 function F() {} 14 F.prototype = o; 15 return new F(); 16 }; 17} 18 19(function ($) { 20 'use strict'; 21 22 var NotyObject = { 23 init: function (options) { 24 // Mix in the passed in options with the default options 25 this.options = $.extend({}, $.noty.defaults, options); 26 27 this.options.layout = this.options.custom ? $.noty.layouts.inline : $.noty.layouts[this.options.layout]; 28 this.options.theme = $.noty.themes[this.options.theme]; 29 30 delete options.layout; 31 delete options.theme; 32 33 this.options = $.extend({}, this.options, this.options.layout.options); 34 this.options.id = 'noty_' + (new Date().getTime() * Math.floor(Math.random() * 1000000)); 35 36 this.options = $.extend({}, this.options, options); 37 38 // Build the noty DOM initial structure 39 this._build(); 40 41 return this; // Return this for chaining 42 }, 43 44 _build: function () { 45 // Generate noty bar 46 var $bar = $('<div class="noty_bar"></div>').attr('id', this.options.id); 47 $bar.append(this.options.template).find('.noty_text').html(this.options.text); 48 49 this.$bar = this.options.layout.parent.object !== null 50 ? $(this.options.layout.parent.object).css(this.options.layout.parent.css).append($bar) 51 : $bar; 52 53 // Set buttons if available 54 if (this.options.buttons) { 55 // Disable closeWith & timeout options if buttons are present 56 this.options.closeWith = []; 57 this.options.timeout = false; 58 59 var $buttons = $('<div/>').addClass('noty_buttons'); 60 61 if (this.options.layout.parent.object !== null) { 62 this.$bar.find('.noty_bar').append($buttons); 63 } else { 64 this.$bar.append($buttons); 65 } 66 67 var self = this; 68 69 $.each(this.options.buttons, function (i, button) { 70 var $button = $('<button/>') 71 .addClass(button.addClass || 'gray') 72 .html(button.text) 73 .appendTo(self.$bar.find('.noty_buttons')) 74 .on('click', function () { 75 if ($.isFunction(button.onClick)) { 76 button.onClick.call($button, self); 77 } 78 }); 79 }); 80 } 81 82 // For easy access 83 this.$message = this.$bar.find('.noty_message'); 84 this.$closeButton = this.$bar.find('.noty_close'); 85 this.$buttons = this.$bar.find('.noty_buttons'); 86 87 $.noty.store[this.options.id] = this; // Store noty for API access 88 }, 89 90 show: function () { 91 var self = this; 92 93 $(self.options.layout.container.selector).append(self.$bar); 94 95 self.options.theme.style.apply(self); 96 97 if ($.type(self.options.layout.css) === 'function') { 98 self.options.layout.css.apply(self.$bar); 99 } else { 100 self.$bar.css(self.options.layout.css || {}); 101 } 102 103 self.$bar.addClass(self.options.layout.addClass); 104 105 self.options.layout.container.style.apply($(self.options.layout.container.selector)); 106 107 self.options.theme.callback.onShow.apply(this); 108 109 if ($.inArray('click', self.options.closeWith) > -1) { 110 self.$bar.css('cursor', 'pointer').one('click', function () { 111 self.close(); 112 }); 113 } 114 115 if ($.inArray('hover', self.options.closeWith) > -1) { 116 self.$bar.one('mouseenter', function () { 117 self.close(); 118 }); 119 } 120 121 if ($.inArray('button', self.options.closeWith) > -1) { 122 self.$closeButton.one('click', function () { 123 self.close(); 124 }); 125 } else { 126 self.$closeButton.remove(); 127 } 128 129 if (self.options.callback.onShow) { 130 self.options.callback.onShow.apply(self); 131 } 132 133 self.$bar.animate( 134 self.options.animation.open, 135 self.options.animation.speed, 136 self.options.animation.easing, 137 function () { 138 if (self.options.callback.afterShow) { 139 self.options.callback.afterShow.apply(self); 140 } 141 self.shown = true; 142 } 143 ); 144 145 // If noty has a timeout option 146 if (self.options.timeout) { 147 self.$bar.delay(self.options.timeout).promise().done(function () { 148 self.close(); 149 }); 150 } 151 152 return this; 153 }, 154 155 close: function () { 156 if (this.closed || (this.$bar && this.$bar.hasClass('i-am-closing-now'))) { 157 return; 158 } 159 160 var self = this; 161 162 if (!this.shown) { 163 // If still in the queue, remove it 164 $.noty.queue = $.noty.queue.filter(function (n) { 165 return n.options.id !== self.options.id; 166 }); 167 return; 168 } 169 170 self.$bar.addClass('i-am-closing-now'); 171 172 if (self.options.callback.onClose) { 173 self.options.callback.onClose.apply(self); 174 } 175 176 self.$bar.clearQueue().stop().animate( 177 self.options.animation.close, 178 self.options.animation.speed, 179 self.options.animation.easing, 180 function () { 181 if (self.options.callback.afterClose) { 182 self.options.callback.afterClose.apply(self); 183 } 184 } 185 ).promise().done(function () { 186 // Modal cleanup 187 if (self.options.modal) { 188 $.notyRenderer.setModalCount(-1); 189 if ($.notyRenderer.getModalCount() === 0) { 190 $('.noty_modal').fadeOut('fast', function () { 191 $(this).remove(); 192 }); 193 } 194 } 195 196 // Layout cleanup 197 $.notyRenderer.setLayoutCountFor(self, -1); 198 if ($.notyRenderer.getLayoutCountFor(self) === 0) { 199 $(self.options.layout.container.selector).remove(); 200 } 201 202 if (self.$bar) { 203 self.$bar.remove(); 204 self.$bar = null; 205 self.closed = true; 206 } 207 208 delete $.noty.store[self.options.id]; // Delete noty from store 209 210 self.options.theme.callback.onClose.apply(self); 211 212 if (!self.options.dismissQueue) { 213 // Render the next in queue 214 $.noty.ontap = true; 215 $.notyRenderer.render(); 216 } 217 }); 218 }, 219 220 setText: function (text) { 221 if (!this.closed) { 222 this.options.text = text; 223 this.$bar.find('.noty_text').html(text); 224 } 225 return this; 226 }, 227 228 setType: function (type) { 229 if (!this.closed) { 230 this.options.type = type; 231 this.options.theme.style.apply(this); 232 this.options.theme.callback.onShow.apply(this); 233 } 234 return this; 235 }, 236 237 setTimeout: function (time) { 238 if (!this.closed) { 239 var self = this; 240 this.options.timeout = time; 241 self.$bar.delay(self.options.timeout).promise().done(function () { 242 self.close(); 243 }); 244 } 245 return this; 246 }, 247
248 closed: false, 249 shown: false 250 }; 251 252 $.notyRenderer = { 253 init: function (options) { 254 var notification = Object.create(NotyObject).init(options); 255 (notification.options.force) ? $.noty.queue.unshift(notification) : $.noty.queue.push(notification); 256 $.notyRenderer.render(); 257 return ($.noty.returns === 'object') ? notification : notification.options.id; 258 }, 259 260 render: function () { 261 var instance = $.noty.queue[0]; 262 if ($.type(instance) === 'object') { 263 if (instance.options.dismissQueue) { 264 $.notyRenderer.show($.noty.queue.shift()); 265 } else { 266 if ($.noty.ontap) { 267 $.notyRenderer.show($.noty.queue.shift()); 268 $.noty.ontap = false; 269 } 270 } 271 } else { 272 $.noty.ontap = true; // Queue is over 273 } 274 }, 275 276 show: function (notification) { 277 if (notification.options.modal) { 278 $.notyRenderer.createModalFor(notification); 279 $.notyRenderer.setModalCount(+1); 280 } 281 282 if ($(notification.options.layout.container.selector).length === 0) { 283 if (notification.options.custom) { 284 notification.options.custom.append($(notification.options.layout.container.object).addClass('i-am-new')); 285 } else { 286 $('body').append($(notification.options.layout.container.object).addClass('i-am-new')); 287 } 288 } else { 289 $(notification.options.layout.container.selector).removeClass('i-am-new'); 290 } 291 292 $.notyRenderer.setLayoutCountFor(notification, +1); 293 notification.show(); 294 }, 295 296 createModalFor: function (notification) { 297 if ($('.noty_modal').length === 0) { 298 $('<div/>').addClass('noty_modal').data('noty_modal_count', 0).css(notification.options.theme.modal.css).prependTo($('body')).fadeIn('fast'); 299 } 300 }, 301 302 getLayoutCountFor: function (notification) { 303 return $(notification.options.layout.container.selector).data('noty_layout_count') || 0; 304 }, 305 306 setLayoutCountFor: function (notification, arg) { 307 return $(notification.options.layout.container.selector).data('noty_layout_count', $.notyRenderer.getLayoutCountFor(notification) + arg); 308 }, 309 310 getModalCount: function () { 311 return $('.noty_modal').data('noty_modal_count') || 0; 312 }, 313 314 setModalCount: function (arg) { 315 return $('.noty_modal').data('noty_modal_count', $.notyRenderer.getModalCount() + arg); 316 } 317 }; 318 319 // Custom container support 320 $.fn.noty = function (options) { 321 options.custom = $(this); 322 return $.notyRenderer.init(options); 323 }; 324 325 $.noty = { 326 queue: [], 327 ontap: true, 328 layouts: {}, 329 themes: {}, 330 returns: 'object', 331 store: {}, 332 333 get: function (id) { 334 return $.noty.store.hasOwnProperty(id) ? $.noty.store[id] : false; 335 }, 336 337 close: function (id) { 338 return $.noty.get(id) ? $.noty.get(id).close() : false; 339 }, 340 341 setText: function (id, text) { 342 return $.noty.get(id) ? $.noty.get(id).setText(text) : false; 343 }, 344 345 setType: function (id, type) { 346 return $.noty.get(id) ? $.noty.get(id).setType(type) : false; 347 }, 348 349 clearQueue: function () { 350 $.noty.queue = []; 351 }, 352 353 closeAll: function () { 354 $.noty.clearQueue(); 355 $.each($.noty.store, function (id, noty) { 356 noty.close(); 357 }); 358 }, 359 360 defaults: { 361 layout: 'top', 362 theme: 'defaultTheme', 363 type: 'alert', 364 text: '', 365 dismissQueue: true, 366 template: '<div class="noty_message"><span class="noty_text"></span><div class="noty_close"></div></div>', 367 animation: { 368 open: { height: 'toggle' }, 369 close: { height: 'toggle' }, 370 easing: 'swing', 371 speed: 500 372 }, 373 timeout: false, 374 force: false, 375 modal: false, 376 closeWith: ['hover'], 377 callback: { 378 onShow: function () {}, 379 afterShow: function () {}, 380 onClose: function () {}, 381 afterClose: function () {} 382 },
383 buttons: false 384 } 385 }; 386 387 $(window).on('resize', function () { 388 $.each($.noty.layouts, function (index, layout) { 389 layout.container.style.apply($(layout.container.selector)); 390 }); 391 }); 392})(jQuery); 393 394// Helpers 395function noty(options) { 396 return jQuery.notyRenderer.init(options); 397}
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.