summaryrefslogtreecommitdiff
path: root/js/core/modal.js
diff options
context:
space:
mode:
Diffstat (limited to 'js/core/modal.js')
-rwxr-xr-xjs/core/modal.js393
1 files changed, 393 insertions, 0 deletions
diff --git a/js/core/modal.js b/js/core/modal.js
new file mode 100755
index 0000000..74d122d
--- /dev/null
+++ b/js/core/modal.js
@@ -0,0 +1,393 @@
1/*! UIkit 2.26.4 | http://www.getuikit.com | (c) 2014 YOOtheme | MIT License */
2(function(UI) {
3
4 "use strict";
5
6 var active = false, activeCount = 0, $html = UI.$html, body;
7
8 UI.$win.on("resize orientationchange", UI.Utils.debounce(function(){
9 UI.$('.uk-modal.uk-open').each(function(){
10 UI.$(this).data('modal').resize();
11 });
12 }, 150));
13
14 UI.component('modal', {
15
16 defaults: {
17 keyboard: true,
18 bgclose: true,
19 minScrollHeight: 150,
20 center: false,
21 modal: true
22 },
23
24 scrollable: false,
25 transition: false,
26 hasTransitioned: true,
27
28 init: function() {
29
30 if (!body) body = UI.$('body');
31
32 if (!this.element.length) return;
33
34 var $this = this;
35
36 this.paddingdir = "padding-" + (UI.langdirection == 'left' ? "right":"left");
37 this.dialog = this.find(".uk-modal-dialog");
38
39 this.active = false;
40
41 // Update ARIA
42 this.element.attr('aria-hidden', this.element.hasClass("uk-open"));
43
44 this.on("click", ".uk-modal-close", function(e) {
45 e.preventDefault();
46 $this.hide();
47 }).on("click", function(e) {
48
49 var target = UI.$(e.target);
50
51 if (target[0] == $this.element[0] && $this.options.bgclose) {
52 $this.hide();
53 }
54 });
55
56 UI.domObserve(this.element, function(e) { $this.resize(); });
57 },
58
59 toggle: function() {
60 return this[this.isActive() ? "hide" : "show"]();
61 },
62
63 show: function() {
64
65 if (!this.element.length) return;
66
67 var $this = this;
68
69 if (this.isActive()) return;
70
71 if (this.options.modal && active) {
72 active.hide(true);
73 }
74
75 this.element.removeClass("uk-open").show();
76 this.resize(true);
77
78 if (this.options.modal) {
79 active = this;
80 }
81
82 this.active = true;
83
84 activeCount++;
85
86 if (UI.support.transition) {
87 this.hasTransitioned = false;
88 this.element.one(UI.support.transition.end, function(){
89 $this.hasTransitioned = true;
90 }).addClass("uk-open");
91 } else {
92 this.element.addClass("uk-open");
93 }
94
95 $html.addClass("uk-modal-page").height(); // force browser engine redraw
96
97 // Update ARIA
98 this.element.attr('aria-hidden', 'false');
99
100 this.element.trigger("show.uk.modal");
101
102 UI.Utils.checkDisplay(this.dialog, true);
103
104 return this;
105 },
106
107 hide: function(force) {
108
109 if (!force && UI.support.transition && this.hasTransitioned) {
110
111 var $this = this;
112
113 this.one(UI.support.transition.end, function() {
114 $this._hide();
115 }).removeClass("uk-open");
116
117 } else {
118
119 this._hide();
120 }
121
122 return this;
123 },
124
125 resize: function(force) {
126
127 if (!this.isActive() && !force) return;
128
129 var bodywidth = body.width();
130
131 this.scrollbarwidth = window.innerWidth - bodywidth;
132
133 body.css(this.paddingdir, this.scrollbarwidth);
134
135 this.element.css('overflow-y', this.scrollbarwidth ? 'scroll' : 'auto');
136
137 if (!this.updateScrollable() && this.options.center) {
138
139 var dh = this.dialog.outerHeight(),
140 pad = parseInt(this.dialog.css('margin-top'), 10) + parseInt(this.dialog.css('margin-bottom'), 10);
141
142 if ((dh + pad) < window.innerHeight) {
143 this.dialog.css({'top': (window.innerHeight/2 - dh/2) - pad });
144 } else {
145 this.dialog.css({'top': ''});
146 }
147 }
148 },
149
150 updateScrollable: function() {
151
152 // has scrollable?
153 var scrollable = this.dialog.find('.uk-overflow-container:visible:first');
154
155 if (scrollable.length) {
156
157 scrollable.css('height', 0);
158
159 var offset = Math.abs(parseInt(this.dialog.css('margin-top'), 10)),
160 dh = this.dialog.outerHeight(),
161 wh = window.innerHeight,
162 h = wh - 2*(offset < 20 ? 20:offset) - dh;
163
164 scrollable.css({
165 'max-height': (h < this.options.minScrollHeight ? '':h),
166 'height':''
167 });
168
169 return true;
170 }
171
172 return false;
173 },
174
175 _hide: function() {
176
177 this.active = false;
178 if (activeCount > 0) activeCount--;
179 else activeCount = 0;
180
181 this.element.hide().removeClass('uk-open');
182
183 // Update ARIA
184 this.element.attr('aria-hidden', 'true');
185
186 if (!activeCount) {
187 $html.removeClass('uk-modal-page');
188 body.css(this.paddingdir, "");
189 }
190
191 if (active===this) active = false;
192
193 this.trigger('hide.uk.modal');
194 },
195
196 isActive: function() {
197 return this.element.hasClass('uk-open');
198 }
199
200 });
201
202 UI.component('modalTrigger', {
203
204 boot: function() {
205
206 // init code
207 UI.$html.on("click.modal.uikit", "[data-uk-modal]", function(e) {
208
209 var ele = UI.$(this);
210
211 if (ele.is("a")) {
212 e.preventDefault();
213 }
214
215 if (!ele.data("modalTrigger")) {
216 var modal = UI.modalTrigger(ele, UI.Utils.options(ele.attr("data-uk-modal")));
217 modal.show();
218 }
219
220 });
221
222 // close modal on esc button
223 UI.$html.on('keydown.modal.uikit', function (e) {
224
225 if (active && e.keyCode === 27 && active.options.keyboard) { // ESC
226 e.preventDefault();
227 active.hide();
228 }
229 });
230 },
231
232 init: function() {
233
234 var $this = this;
235
236 this.options = UI.$.extend({
237 "target": $this.element.is("a") ? $this.element.attr("href") : false
238 }, this.options);
239
240 this.modal = UI.modal(this.options.target, this.options);
241
242 this.on("click", function(e) {
243 e.preventDefault();
244 $this.show();
245 });
246
247 //methods
248 this.proxy(this.modal, "show hide isActive");
249 }
250 });
251
252 UI.modal.dialog = function(content, options) {
253
254 var modal = UI.modal(UI.$(UI.modal.dialog.template).appendTo("body"), options);
255
256 modal.on("hide.uk.modal", function(){
257 if (modal.persist) {
258 modal.persist.appendTo(modal.persist.data("modalPersistParent"));
259 modal.persist = false;
260 }
261 modal.element.remove();
262 });
263
264 setContent(content, modal);
265
266 return modal;
267 };
268
269 UI.modal.dialog.template = '<div class="uk-modal"><div class="uk-modal-dialog" style="min-height:0;"></div></div>';
270
271 UI.modal.alert = function(content, options) {
272
273 options = UI.$.extend(true, {bgclose:false, keyboard:false, modal:false, labels:UI.modal.labels}, options);
274
275 var modal = UI.modal.dialog(([
276 '<div class="uk-margin uk-modal-content">'+String(content)+'</div>',
277 '<div class="uk-modal-footer uk-text-right"><button class="uk-button uk-button-primary uk-modal-close">'+options.labels.Ok+'</button></div>'
278 ]).join(""), options);
279
280 modal.on('show.uk.modal', function(){
281 setTimeout(function(){
282 modal.element.find('button:first').focus();
283 }, 50);
284 });
285
286 return modal.show();
287 };
288
289 UI.modal.confirm = function(content, onconfirm, oncancel) {
290
291 var options = arguments.length > 1 && arguments[arguments.length-1] ? arguments[arguments.length-1] : {};
292
293 onconfirm = UI.$.isFunction(onconfirm) ? onconfirm : function(){};
294 oncancel = UI.$.isFunction(oncancel) ? oncancel : function(){};
295 options = UI.$.extend(true, {bgclose:false, keyboard:false, modal:false, labels:UI.modal.labels}, UI.$.isFunction(options) ? {}:options);
296
297 var modal = UI.modal.dialog(([
298 '<div class="uk-margin uk-modal-content">'+String(content)+'</div>',
299 '<div class="uk-modal-footer uk-text-right"><button class="uk-button js-modal-confirm-cancel">'+options.labels.Cancel+'</button> <button class="uk-button uk-button-primary js-modal-confirm">'+options.labels.Ok+'</button></div>'
300 ]).join(""), options);
301
302 modal.element.find(".js-modal-confirm, .js-modal-confirm-cancel").on("click", function(){
303 UI.$(this).is('.js-modal-confirm') ? onconfirm() : oncancel();
304 modal.hide();
305 });
306
307 modal.on('show.uk.modal', function(){
308 setTimeout(function(){
309 modal.element.find('.js-modal-confirm').focus();
310 }, 50);
311 });
312
313 return modal.show();
314 };
315
316 UI.modal.prompt = function(text, value, onsubmit, options) {
317
318 onsubmit = UI.$.isFunction(onsubmit) ? onsubmit : function(value){};
319 options = UI.$.extend(true, {bgclose:false, keyboard:false, modal:false, labels:UI.modal.labels}, options);
320
321 var modal = UI.modal.dialog(([
322 text ? '<div class="uk-modal-content uk-form">'+String(text)+'</div>':'',
323 '<div class="uk-margin-small-top uk-modal-content uk-form"><p><input type="text" class="uk-width-1-1"></p></div>',
324 '<div class="uk-modal-footer uk-text-right"><button class="uk-button uk-modal-close">'+options.labels.Cancel+'</button> <button class="uk-button uk-button-primary js-modal-ok">'+options.labels.Ok+'</button></div>'
325 ]).join(""), options),
326
327 input = modal.element.find("input[type='text']").val(value || '').on('keyup', function(e){
328 if (e.keyCode == 13) {
329 modal.element.find(".js-modal-ok").trigger('click');
330 }
331 });
332
333 modal.element.find(".js-modal-ok").on("click", function(){
334 if (onsubmit(input.val())!==false){
335 modal.hide();
336 }
337 });
338
339 modal.on('show.uk.modal', function(){
340 setTimeout(function(){
341 input.focus();
342 }, 50);
343 });
344
345 return modal.show();
346 };
347
348 UI.modal.blockUI = function(content, options) {
349
350 var modal = UI.modal.dialog(([
351 '<div class="uk-margin uk-modal-content">'+String(content || '<div class="uk-text-center">...</div>')+'</div>'
352 ]).join(""), UI.$.extend({bgclose:false, keyboard:false, modal:false}, options));
353
354 modal.content = modal.element.find('.uk-modal-content:first');
355
356 return modal.show();
357 };
358
359
360 UI.modal.labels = {
361 'Ok': 'Ok',
362 'Cancel': 'Cancel'
363 };
364
365
366 // helper functions
367 function setContent(content, modal){
368
369 if(!modal) return;
370
371 if (typeof content === 'object') {
372
373 // convert DOM object to a jQuery object
374 content = content instanceof jQuery ? content : UI.$(content);
375
376 if(content.parent().length) {
377 modal.persist = content;
378 modal.persist.data("modalPersistParent", content.parent());
379 }
380 }else if (typeof content === 'string' || typeof content === 'number') {
381 // just insert the data as innerHTML
382 content = UI.$('<div></div>').html(content);
383 }else {
384 // unsupported data type!
385 content = UI.$('<div></div>').html('UIkit.modal Error: Unsupported data type: ' + typeof content);
386 }
387
388 content.appendTo(modal.element.find('.uk-modal-dialog'));
389
390 return modal;
391 }
392
393})(UIkit);