rails-active-ui 0.3.0 → 0.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (197) hide show
  1. checksums.yaml +4 -4
  2. data/app/javascript/ui/controllers/turbo_modal_controller.js +36 -0
  3. data/config/importmap.rb +1 -0
  4. data/formantic-ui/components/accordion.css +369 -0
  5. data/formantic-ui/components/accordion.js +595 -0
  6. data/formantic-ui/components/accordion.min.css +9 -0
  7. data/formantic-ui/components/accordion.min.js +11 -0
  8. data/formantic-ui/components/ad.css +264 -0
  9. data/formantic-ui/components/ad.min.css +10 -0
  10. data/formantic-ui/components/api.js +1225 -0
  11. data/formantic-ui/components/api.min.js +11 -0
  12. data/formantic-ui/components/breadcrumb.css +135 -0
  13. data/formantic-ui/components/breadcrumb.min.css +9 -0
  14. data/formantic-ui/components/button.css +4058 -0
  15. data/formantic-ui/components/button.min.css +9 -0
  16. data/formantic-ui/components/calendar.css +327 -0
  17. data/formantic-ui/components/calendar.js +2045 -0
  18. data/formantic-ui/components/calendar.min.css +9 -0
  19. data/formantic-ui/components/calendar.min.js +11 -0
  20. data/formantic-ui/components/card.css +1881 -0
  21. data/formantic-ui/components/card.min.css +9 -0
  22. data/formantic-ui/components/checkbox.css +785 -0
  23. data/formantic-ui/components/checkbox.js +888 -0
  24. data/formantic-ui/components/checkbox.min.css +9 -0
  25. data/formantic-ui/components/checkbox.min.js +11 -0
  26. data/formantic-ui/components/comment.css +283 -0
  27. data/formantic-ui/components/comment.min.css +9 -0
  28. data/formantic-ui/components/container.css +300 -0
  29. data/formantic-ui/components/container.min.css +9 -0
  30. data/formantic-ui/components/dimmer.css +367 -0
  31. data/formantic-ui/components/dimmer.js +732 -0
  32. data/formantic-ui/components/dimmer.min.css +9 -0
  33. data/formantic-ui/components/dimmer.min.js +11 -0
  34. data/formantic-ui/components/divider.css +287 -0
  35. data/formantic-ui/components/divider.min.css +9 -0
  36. data/formantic-ui/components/dropdown.css +2087 -0
  37. data/formantic-ui/components/dropdown.js +4432 -0
  38. data/formantic-ui/components/dropdown.min.css +9 -0
  39. data/formantic-ui/components/dropdown.min.js +11 -0
  40. data/formantic-ui/components/embed.css +155 -0
  41. data/formantic-ui/components/embed.js +688 -0
  42. data/formantic-ui/components/embed.min.css +9 -0
  43. data/formantic-ui/components/embed.min.js +11 -0
  44. data/formantic-ui/components/emoji.css +15311 -0
  45. data/formantic-ui/components/emoji.min.css +9 -0
  46. data/formantic-ui/components/feed.css +799 -0
  47. data/formantic-ui/components/feed.min.css +9 -0
  48. data/formantic-ui/components/flag.css +1149 -0
  49. data/formantic-ui/components/flag.min.css +9 -0
  50. data/formantic-ui/components/flyout.css +546 -0
  51. data/formantic-ui/components/flyout.js +1551 -0
  52. data/formantic-ui/components/flyout.min.css +9 -0
  53. data/formantic-ui/components/flyout.min.js +11 -0
  54. data/formantic-ui/components/form.css +1885 -0
  55. data/formantic-ui/components/form.js +2199 -0
  56. data/formantic-ui/components/form.min.css +9 -0
  57. data/formantic-ui/components/form.min.js +11 -0
  58. data/formantic-ui/components/grid.css +1952 -0
  59. data/formantic-ui/components/grid.min.css +9 -0
  60. data/formantic-ui/components/header.css +778 -0
  61. data/formantic-ui/components/header.min.css +9 -0
  62. data/formantic-ui/components/icon.css +7066 -0
  63. data/formantic-ui/components/icon.min.css +9 -0
  64. data/formantic-ui/components/image.css +315 -0
  65. data/formantic-ui/components/image.min.css +9 -0
  66. data/formantic-ui/components/input.css +1566 -0
  67. data/formantic-ui/components/input.min.css +9 -0
  68. data/formantic-ui/components/item.css +534 -0
  69. data/formantic-ui/components/item.min.css +9 -0
  70. data/formantic-ui/components/label.css +2114 -0
  71. data/formantic-ui/components/label.min.css +9 -0
  72. data/formantic-ui/components/list.css +955 -0
  73. data/formantic-ui/components/list.min.css +9 -0
  74. data/formantic-ui/components/loader.css +787 -0
  75. data/formantic-ui/components/loader.min.css +9 -0
  76. data/formantic-ui/components/menu.css +2131 -0
  77. data/formantic-ui/components/menu.min.css +9 -0
  78. data/formantic-ui/components/message.css +619 -0
  79. data/formantic-ui/components/message.min.css +9 -0
  80. data/formantic-ui/components/modal.css +779 -0
  81. data/formantic-ui/components/modal.js +1637 -0
  82. data/formantic-ui/components/modal.min.css +9 -0
  83. data/formantic-ui/components/modal.min.js +11 -0
  84. data/formantic-ui/components/nag.css +290 -0
  85. data/formantic-ui/components/nag.js +566 -0
  86. data/formantic-ui/components/nag.min.css +9 -0
  87. data/formantic-ui/components/nag.min.js +11 -0
  88. data/formantic-ui/components/placeholder.css +228 -0
  89. data/formantic-ui/components/placeholder.min.css +9 -0
  90. data/formantic-ui/components/popup.css +1184 -0
  91. data/formantic-ui/components/popup.js +1561 -0
  92. data/formantic-ui/components/popup.min.css +9 -0
  93. data/formantic-ui/components/popup.min.js +11 -0
  94. data/formantic-ui/components/progress.css +761 -0
  95. data/formantic-ui/components/progress.js +979 -0
  96. data/formantic-ui/components/progress.min.css +9 -0
  97. data/formantic-ui/components/progress.min.js +11 -0
  98. data/formantic-ui/components/rail.css +147 -0
  99. data/formantic-ui/components/rail.min.css +9 -0
  100. data/formantic-ui/components/rating.css +414 -0
  101. data/formantic-ui/components/rating.js +540 -0
  102. data/formantic-ui/components/rating.min.css +9 -0
  103. data/formantic-ui/components/rating.min.js +11 -0
  104. data/formantic-ui/components/reset.css +386 -0
  105. data/formantic-ui/components/reset.min.css +9 -0
  106. data/formantic-ui/components/reveal.css +277 -0
  107. data/formantic-ui/components/reveal.min.css +9 -0
  108. data/formantic-ui/components/search.css +541 -0
  109. data/formantic-ui/components/search.js +1641 -0
  110. data/formantic-ui/components/search.min.css +9 -0
  111. data/formantic-ui/components/search.min.js +11 -0
  112. data/formantic-ui/components/segment.css +1053 -0
  113. data/formantic-ui/components/segment.min.css +9 -0
  114. data/formantic-ui/components/shape.css +144 -0
  115. data/formantic-ui/components/shape.js +797 -0
  116. data/formantic-ui/components/shape.min.css +9 -0
  117. data/formantic-ui/components/shape.min.js +11 -0
  118. data/formantic-ui/components/sidebar.css +539 -0
  119. data/formantic-ui/components/sidebar.js +1054 -0
  120. data/formantic-ui/components/sidebar.min.css +9 -0
  121. data/formantic-ui/components/sidebar.min.js +11 -0
  122. data/formantic-ui/components/site.css +286 -0
  123. data/formantic-ui/components/site.js +455 -0
  124. data/formantic-ui/components/site.min.css +9 -0
  125. data/formantic-ui/components/site.min.js +11 -0
  126. data/formantic-ui/components/slider.css +926 -0
  127. data/formantic-ui/components/slider.js +1546 -0
  128. data/formantic-ui/components/slider.min.css +9 -0
  129. data/formantic-ui/components/slider.min.js +11 -0
  130. data/formantic-ui/components/state.js +697 -0
  131. data/formantic-ui/components/state.min.js +11 -0
  132. data/formantic-ui/components/statistic.css +586 -0
  133. data/formantic-ui/components/statistic.min.css +9 -0
  134. data/formantic-ui/components/step.css +1538 -0
  135. data/formantic-ui/components/step.min.css +9 -0
  136. data/formantic-ui/components/sticky.css +73 -0
  137. data/formantic-ui/components/sticky.js +917 -0
  138. data/formantic-ui/components/sticky.min.css +9 -0
  139. data/formantic-ui/components/sticky.min.js +11 -0
  140. data/formantic-ui/components/tab.css +84 -0
  141. data/formantic-ui/components/tab.js +967 -0
  142. data/formantic-ui/components/tab.min.css +9 -0
  143. data/formantic-ui/components/tab.min.js +11 -0
  144. data/formantic-ui/components/table.css +3473 -0
  145. data/formantic-ui/components/table.min.css +9 -0
  146. data/formantic-ui/components/text.css +155 -0
  147. data/formantic-ui/components/text.min.css +9 -0
  148. data/formantic-ui/components/toast.css +751 -0
  149. data/formantic-ui/components/toast.js +964 -0
  150. data/formantic-ui/components/toast.min.css +9 -0
  151. data/formantic-ui/components/toast.min.js +11 -0
  152. data/formantic-ui/components/transition.css +1148 -0
  153. data/formantic-ui/components/transition.js +1034 -0
  154. data/formantic-ui/components/transition.min.css +9 -0
  155. data/formantic-ui/components/transition.min.js +11 -0
  156. data/formantic-ui/components/visibility.js +1292 -0
  157. data/formantic-ui/components/visibility.min.js +11 -0
  158. data/formantic-ui/semantic.css +78485 -0
  159. data/formantic-ui/semantic.js +31036 -0
  160. data/formantic-ui/semantic.min.css +11 -0
  161. data/formantic-ui/semantic.min.js +11 -0
  162. data/formantic-ui/themes/basic/assets/fonts/LICENSE.txt +91 -0
  163. data/formantic-ui/themes/basic/assets/fonts/icons.woff +0 -0
  164. data/formantic-ui/themes/basic/assets/fonts/icons.woff2 +0 -0
  165. data/formantic-ui/themes/default/assets/fonts/LICENSE_Lato.txt +94 -0
  166. data/formantic-ui/themes/default/assets/fonts/LICENSE_icons.txt +165 -0
  167. data/formantic-ui/themes/default/assets/fonts/Lato-Bold.woff +0 -0
  168. data/formantic-ui/themes/default/assets/fonts/Lato-Bold.woff2 +0 -0
  169. data/formantic-ui/themes/default/assets/fonts/Lato-BoldItalic.woff +0 -0
  170. data/formantic-ui/themes/default/assets/fonts/Lato-BoldItalic.woff2 +0 -0
  171. data/formantic-ui/themes/default/assets/fonts/Lato-Italic.woff +0 -0
  172. data/formantic-ui/themes/default/assets/fonts/Lato-Italic.woff2 +0 -0
  173. data/formantic-ui/themes/default/assets/fonts/Lato-Regular.woff +0 -0
  174. data/formantic-ui/themes/default/assets/fonts/Lato-Regular.woff2 +0 -0
  175. data/formantic-ui/themes/default/assets/fonts/LatoLatin-Bold.woff +0 -0
  176. data/formantic-ui/themes/default/assets/fonts/LatoLatin-Bold.woff2 +0 -0
  177. data/formantic-ui/themes/default/assets/fonts/LatoLatin-BoldItalic.woff +0 -0
  178. data/formantic-ui/themes/default/assets/fonts/LatoLatin-BoldItalic.woff2 +0 -0
  179. data/formantic-ui/themes/default/assets/fonts/LatoLatin-Italic.woff +0 -0
  180. data/formantic-ui/themes/default/assets/fonts/LatoLatin-Italic.woff2 +0 -0
  181. data/formantic-ui/themes/default/assets/fonts/LatoLatin-Regular.woff +0 -0
  182. data/formantic-ui/themes/default/assets/fonts/LatoLatin-Regular.woff2 +0 -0
  183. data/formantic-ui/themes/default/assets/fonts/brand-icons.woff +0 -0
  184. data/formantic-ui/themes/default/assets/fonts/brand-icons.woff2 +0 -0
  185. data/formantic-ui/themes/default/assets/fonts/icons.woff +0 -0
  186. data/formantic-ui/themes/default/assets/fonts/icons.woff2 +0 -0
  187. data/formantic-ui/themes/default/assets/fonts/outline-icons.woff +0 -0
  188. data/formantic-ui/themes/default/assets/fonts/outline-icons.woff2 +0 -0
  189. data/formantic-ui/themes/famfamfam/assets/images/flags.png +0 -0
  190. data/formantic-ui/themes/github/assets/fonts/LICENSE.txt +94 -0
  191. data/formantic-ui/themes/github/assets/fonts/octicons.woff +0 -0
  192. data/formantic-ui/themes/github/assets/fonts/octicons.woff2 +0 -0
  193. data/formantic-ui/themes/material/assets/fonts/LICENSE.txt +202 -0
  194. data/formantic-ui/themes/material/assets/fonts/icons.woff +0 -0
  195. data/formantic-ui/themes/material/assets/fonts/icons.woff2 +0 -0
  196. data/lib/ui/version.rb +1 -1
  197. metadata +194 -1
@@ -0,0 +1,1561 @@
1
+ /*!
2
+ * # Fomantic-UI 2.9.4 - Popup
3
+ * https://github.com/fomantic/Fomantic-UI/
4
+ *
5
+ *
6
+ * Released under the MIT license
7
+ * https://opensource.org/licenses/MIT
8
+ *
9
+ */
10
+
11
+ (function ($, window, document) {
12
+ 'use strict';
13
+
14
+ function isFunction(obj) {
15
+ return typeof obj === 'function' && typeof obj.nodeType !== 'number';
16
+ }
17
+
18
+ window = window !== undefined && window.Math === Math
19
+ ? window
20
+ : globalThis;
21
+
22
+ $.fn.popup = function (parameters) {
23
+ var
24
+ $allModules = $(this),
25
+ $document = $(document),
26
+ $window = $(window),
27
+ $body = $('body'),
28
+
29
+ clickEvent = 'ontouchstart' in document.documentElement
30
+ ? 'touchstart'
31
+ : 'click',
32
+
33
+ time = Date.now(),
34
+ performance = [],
35
+
36
+ query = arguments[0],
37
+ methodInvoked = typeof query === 'string',
38
+ queryArguments = [].slice.call(arguments, 1),
39
+ contextCheck = function (context, win) {
40
+ var $context;
41
+ if ([window, document].indexOf(context) >= 0) {
42
+ $context = $(context);
43
+ } else {
44
+ $context = $(win.document).find(context);
45
+ if ($context.length === 0) {
46
+ $context = win.frameElement ? contextCheck(context, win.parent) : $body;
47
+ }
48
+ }
49
+
50
+ return $context;
51
+ },
52
+
53
+ returnedValue
54
+ ;
55
+ $allModules.each(function () {
56
+ var
57
+ settings = $.isPlainObject(parameters)
58
+ ? $.extend(true, {}, $.fn.popup.settings, parameters)
59
+ : $.extend({}, $.fn.popup.settings),
60
+
61
+ selector = settings.selector,
62
+ className = settings.className,
63
+ error = settings.error,
64
+ metadata = settings.metadata,
65
+ namespace = settings.namespace,
66
+
67
+ eventNamespace = '.' + settings.namespace,
68
+ moduleNamespace = 'module-' + namespace,
69
+
70
+ $module = $(this),
71
+ $context = contextCheck(settings.context, window),
72
+ $scrollContext = contextCheck(settings.scrollContext, window),
73
+ $boundary = contextCheck(settings.boundary, window),
74
+ $target = settings.target ? contextCheck(settings.target, window) : $module,
75
+
76
+ $popup,
77
+ $offsetParent,
78
+
79
+ searchDepth = 0,
80
+ triedPositions = false,
81
+ openedWithTouch = false,
82
+
83
+ element = this,
84
+ instance = $module.data(moduleNamespace),
85
+
86
+ documentObserver,
87
+ elementNamespace,
88
+ id,
89
+ module
90
+ ;
91
+
92
+ module = {
93
+
94
+ // binds events
95
+ initialize: function () {
96
+ module.debug('Initializing', $module);
97
+ module.createID();
98
+ module.bind.events();
99
+ if (!module.exists() && settings.preserve) {
100
+ module.create();
101
+ }
102
+ if (settings.observeChanges) {
103
+ module.observeChanges();
104
+ }
105
+ module.instantiate();
106
+ },
107
+
108
+ instantiate: function () {
109
+ module.verbose('Storing instance', module);
110
+ instance = module;
111
+ $module
112
+ .data(moduleNamespace, instance)
113
+ ;
114
+ },
115
+
116
+ observeChanges: function () {
117
+ if ('MutationObserver' in window) {
118
+ documentObserver = new MutationObserver(module.event.documentChanged);
119
+ documentObserver.observe(document, {
120
+ childList: true,
121
+ subtree: true,
122
+ });
123
+ module.debug('Setting up mutation observer', documentObserver);
124
+ }
125
+ },
126
+
127
+ refresh: function () {
128
+ if (settings.popup) {
129
+ $popup = $document.find(settings.popup).eq(0);
130
+ } else {
131
+ if (settings.inline) {
132
+ $popup = $target.nextAll(selector.popup).eq(0);
133
+ settings.popup = $popup;
134
+ }
135
+ }
136
+ if (settings.popup) {
137
+ module.set.invisible();
138
+ $offsetParent = module.get.offsetParent();
139
+ module.remove.invisible();
140
+ if (settings.movePopup && module.has.popup() && module.get.offsetParent($popup)[0] !== $offsetParent[0]) {
141
+ module.debug('Moving popup to the same offset parent as target');
142
+ $popup
143
+ .detach()
144
+ .appendTo($offsetParent)
145
+ ;
146
+ }
147
+ } else {
148
+ $offsetParent = settings.inline
149
+ ? module.get.offsetParent($target)
150
+ : (module.has.popup()
151
+ ? module.get.offsetParent($popup)
152
+ : $body);
153
+ }
154
+ if ($offsetParent.is('html') && $offsetParent[0] !== $body[0]) {
155
+ module.debug('Setting page as offset parent');
156
+ $offsetParent = $body;
157
+ }
158
+ if (module.get.variation()) {
159
+ module.set.variation();
160
+ }
161
+ },
162
+
163
+ reposition: function () {
164
+ module.refresh();
165
+ module.set.position();
166
+ },
167
+
168
+ destroy: function () {
169
+ module.debug('Destroying previous module');
170
+ if (documentObserver) {
171
+ documentObserver.disconnect();
172
+ }
173
+ // remove element only if was created dynamically
174
+ if ($popup && !settings.preserve) {
175
+ module.removePopup();
176
+ }
177
+ // clear all timeouts
178
+ clearTimeout(module.hideTimer);
179
+ clearTimeout(module.showTimer);
180
+ // remove events
181
+ module.unbind.close();
182
+ module.unbind.events();
183
+ $module
184
+ .removeData(moduleNamespace)
185
+ ;
186
+ },
187
+
188
+ event: {
189
+ start: function (event) {
190
+ var
191
+ delay = $.isPlainObject(settings.delay)
192
+ ? settings.delay.show
193
+ : settings.delay
194
+ ;
195
+ clearTimeout(module.hideTimer);
196
+ if (!openedWithTouch || (openedWithTouch && settings.addTouchEvents)) {
197
+ module.showTimer = setTimeout(function () {
198
+ module.show();
199
+ }, delay);
200
+ }
201
+ },
202
+ end: function () {
203
+ var
204
+ delay = $.isPlainObject(settings.delay)
205
+ ? settings.delay.hide
206
+ : settings.delay
207
+ ;
208
+ clearTimeout(module.showTimer);
209
+ module.hideTimer = setTimeout(function () {
210
+ module.hide();
211
+ }, delay);
212
+ },
213
+ touchstart: function (event) {
214
+ openedWithTouch = true;
215
+ if (settings.addTouchEvents) {
216
+ module.show();
217
+ }
218
+ },
219
+ resize: function () {
220
+ if (module.is.visible()) {
221
+ module.set.position();
222
+ }
223
+ },
224
+ documentChanged: function (mutations) {
225
+ [].forEach.call(mutations, function (mutation) {
226
+ if (mutation.removedNodes) {
227
+ [].forEach.call(mutation.removedNodes, function (node) {
228
+ if (node === element || $(node).find(element).length > 0) {
229
+ module.debug('Element removed from DOM, tearing down events');
230
+ module.destroy();
231
+ }
232
+ });
233
+ }
234
+ });
235
+ },
236
+ hideGracefully: function (event) {
237
+ var
238
+ $target = $(event.target),
239
+ isInDOM = $.contains(document.documentElement, event.target),
240
+ inPopup = $target.closest(selector.popup).length > 0
241
+ ;
242
+ // don't close on clicks inside popup
243
+ if (event && !inPopup && isInDOM) {
244
+ module.debug('Click occurred outside popup hiding popup');
245
+ module.hide();
246
+ } else {
247
+ module.debug('Click was inside popup, keeping popup open');
248
+ }
249
+ },
250
+ },
251
+
252
+ // generates popup html from metadata
253
+ create: function () {
254
+ var
255
+ targetSibling = $target.next(selector.popup),
256
+ contentFallback = !settings.popup && targetSibling.length === 0 ? $module.attr('title') : false,
257
+ html = module.get.html(),
258
+ title = module.get.title(),
259
+ content = module.get.content(contentFallback)
260
+ ;
261
+
262
+ if (html || content || title) {
263
+ module.debug('Creating pop-up html');
264
+ if (!html) {
265
+ html = settings.templates.popup({
266
+ title: title,
267
+ content: content,
268
+ });
269
+ }
270
+ $popup = $('<div/>')
271
+ .addClass(className.popup)
272
+ .data(metadata.activator, $module)
273
+ .html(html)
274
+ ;
275
+ if (settings.inline) {
276
+ module.verbose('Inserting popup element inline', $popup);
277
+ $popup
278
+ .insertAfter($module)
279
+ ;
280
+ } else {
281
+ module.verbose('Appending popup element to body', $popup);
282
+ $popup
283
+ .appendTo($context)
284
+ ;
285
+ }
286
+ module.refresh();
287
+ module.set.variation();
288
+
289
+ if (settings.hoverable) {
290
+ module.bind.popup();
291
+ }
292
+ settings.onCreate.call($popup, element);
293
+ } else if (settings.popup) {
294
+ $document.find(settings.popup).data(metadata.activator, $module);
295
+ module.verbose('Used popup specified in settings');
296
+ module.refresh();
297
+ if (settings.hoverable) {
298
+ module.bind.popup();
299
+ }
300
+ } else if (targetSibling.length > 0) {
301
+ module.verbose('Pre-existing popup found');
302
+ settings.inline = true;
303
+ settings.popup = targetSibling.data(metadata.activator, $module);
304
+ module.refresh();
305
+ if (settings.hoverable) {
306
+ module.bind.popup();
307
+ }
308
+ } else {
309
+ module.debug('No content specified skipping display', element);
310
+ }
311
+ },
312
+
313
+ createID: function () {
314
+ id = (Math.random().toString(16) + '000000000').slice(2, 10);
315
+ elementNamespace = '.' + id;
316
+ module.verbose('Creating unique id for element', id);
317
+ },
318
+
319
+ // determines popup state
320
+ toggle: function () {
321
+ module.debug('Toggling pop-up');
322
+ if (module.is.hidden()) {
323
+ module.debug('Popup is hidden, showing pop-up');
324
+ module.unbind.close();
325
+ module.show();
326
+ } else {
327
+ module.debug('Popup is visible, hiding pop-up');
328
+ module.hide();
329
+ }
330
+ },
331
+
332
+ show: function (callback) {
333
+ callback = callback || function () {};
334
+ module.debug('Showing pop-up', settings.transition);
335
+ if (module.is.hidden() && !(module.is.active() && module.is.dropdown())) {
336
+ if (!module.exists()) {
337
+ module.create();
338
+ }
339
+ if (settings.onShow.call($popup, element) === false) {
340
+ module.debug('onShow callback returned false, cancelling popup animation');
341
+
342
+ return;
343
+ }
344
+ if (!settings.preserve && !settings.popup) {
345
+ module.refresh();
346
+ }
347
+ if ($popup && module.set.position()) {
348
+ module.save.conditions();
349
+ if (settings.exclusive) {
350
+ module.hideAll();
351
+ }
352
+ module.animate.show(callback);
353
+ }
354
+ }
355
+ },
356
+
357
+ hide: function (callback) {
358
+ callback = callback || function () {};
359
+ if (module.is.visible() || module.is.animating()) {
360
+ if (settings.onHide.call($popup, element) === false) {
361
+ module.debug('onHide callback returned false, cancelling popup animation');
362
+
363
+ return;
364
+ }
365
+ module.remove.visible();
366
+ module.unbind.close();
367
+ module.restore.conditions();
368
+ module.animate.hide(callback);
369
+ }
370
+ },
371
+
372
+ hideAll: function () {
373
+ $document.find(selector.popup)
374
+ .filter('.' + className.popupVisible)
375
+ .each(function () {
376
+ $(this)
377
+ .data(metadata.activator)
378
+ .popup('hide')
379
+ ;
380
+ })
381
+ ;
382
+ },
383
+ exists: function () {
384
+ if (!$popup) {
385
+ return false;
386
+ }
387
+ if (settings.inline || settings.popup) {
388
+ return module.has.popup();
389
+ }
390
+
391
+ return $popup.closest($context).length > 0;
392
+ },
393
+
394
+ removePopup: function () {
395
+ if (module.has.popup() && !settings.popup) {
396
+ module.debug('Removing popup', $popup);
397
+ $popup.remove();
398
+ $popup = undefined;
399
+ settings.onRemove.call($popup, element);
400
+ }
401
+ },
402
+
403
+ save: {
404
+ conditions: function () {
405
+ module.cache = {
406
+ title: $module.attr('title'),
407
+ };
408
+ if (module.cache.title) {
409
+ $module.removeAttr('title');
410
+ }
411
+ module.verbose('Saving original attributes', module.cache.title);
412
+ },
413
+ },
414
+ restore: {
415
+ conditions: function () {
416
+ if (module.cache && module.cache.title) {
417
+ $module.attr('title', module.cache.title);
418
+ module.verbose('Restoring original attributes', module.cache.title);
419
+ }
420
+
421
+ return true;
422
+ },
423
+ },
424
+ supports: {
425
+ svg: function () {
426
+ return typeof SVGGraphicsElement !== 'undefined';
427
+ },
428
+ },
429
+ animate: {
430
+ show: function (callback) {
431
+ callback = isFunction(callback) ? callback : function () {};
432
+ if (settings.transition && module.can.useElement('transition')) {
433
+ module.set.visible();
434
+ $popup
435
+ .transition({
436
+ animation: (settings.transition.showMethod || settings.transition) + ' in',
437
+ queue: false,
438
+ debug: settings.debug,
439
+ verbose: settings.verbose,
440
+ silent: settings.silent,
441
+ duration: settings.transition.showDuration || settings.duration,
442
+ onComplete: function () {
443
+ module.bind.close();
444
+ callback.call($popup, element);
445
+ settings.onVisible.call($popup, element);
446
+ },
447
+ })
448
+ ;
449
+ }
450
+ },
451
+ hide: function (callback) {
452
+ callback = isFunction(callback) ? callback : function () {};
453
+ module.debug('Hiding pop-up');
454
+ if (settings.transition && $.fn.transition !== undefined) {
455
+ $popup
456
+ .transition({
457
+ animation: (settings.transition.hideMethod || settings.transition) + ' out',
458
+ queue: false,
459
+ duration: settings.transition.hideDuration || settings.duration,
460
+ debug: settings.debug,
461
+ verbose: settings.verbose,
462
+ silent: settings.silent,
463
+ onComplete: function () {
464
+ module.reset();
465
+ callback.call($popup, element);
466
+ settings.onHidden.call($popup, element);
467
+ },
468
+ })
469
+ ;
470
+ } else {
471
+ module.error(error.noTransition);
472
+ }
473
+ },
474
+ },
475
+
476
+ change: {
477
+ content: function (html) {
478
+ $popup.html(html);
479
+ },
480
+ },
481
+
482
+ get: {
483
+ html: function () {
484
+ $module.removeData(metadata.html);
485
+
486
+ return $module.data(metadata.html) || settings.html;
487
+ },
488
+ title: function () {
489
+ $module.removeData(metadata.title);
490
+
491
+ return $module.data(metadata.title) || settings.title;
492
+ },
493
+ content: function (fallback) {
494
+ $module.removeData(metadata.content);
495
+
496
+ return $module.data(metadata.content) || settings.content || fallback;
497
+ },
498
+ variation: function () {
499
+ $module.removeData(metadata.variation);
500
+
501
+ return $module.data(metadata.variation) || settings.variation;
502
+ },
503
+ popup: function () {
504
+ return $popup;
505
+ },
506
+ popupOffset: function () {
507
+ return $popup.offset();
508
+ },
509
+ calculations: function () {
510
+ var
511
+ $popupOffsetParent = module.get.offsetParent($popup),
512
+ targetElement = $target[0],
513
+ isWindowEl = $boundary[0] === window,
514
+ targetOffset = $target.offset(),
515
+ parentOffset = settings.inline || (settings.popup && settings.movePopup)
516
+ ? $target.offsetParent().offset()
517
+ : { top: 0, left: 0 },
518
+ screenPosition = isWindowEl
519
+ ? { top: 0, left: 0 }
520
+ : $boundary.offset(),
521
+ calculations = {},
522
+ scroll = isWindowEl
523
+ ? { top: $window.scrollTop(), left: $window.scrollLeft() }
524
+ : { top: 0, left: 0 },
525
+ screen
526
+ ;
527
+ calculations = {
528
+ // element which is launching popup
529
+ target: {
530
+ element: $target[0],
531
+ width: $target.outerWidth(),
532
+ height: $target.outerHeight(),
533
+ top: targetOffset.top - parentOffset.top,
534
+ left: targetOffset.left - parentOffset.left,
535
+ margin: {},
536
+ },
537
+ // popup itself
538
+ popup: {
539
+ width: $popup.outerWidth(),
540
+ height: $popup.outerHeight(),
541
+ },
542
+ // offset container (or 3d context)
543
+ parent: {
544
+ width: $offsetParent.outerWidth(),
545
+ height: $offsetParent.outerHeight(),
546
+ },
547
+ // screen boundaries
548
+ screen: {
549
+ top: screenPosition.top,
550
+ left: screenPosition.left,
551
+ scroll: {
552
+ top: scroll.top,
553
+ left: scroll.left,
554
+ },
555
+ width: $boundary.width(),
556
+ height: $boundary.height(),
557
+ },
558
+ };
559
+
560
+ // if popup offset context is not same as target, then adjust calculations
561
+ if ($popupOffsetParent[0] !== $offsetParent[0]) {
562
+ var
563
+ popupOffset = $popupOffsetParent.offset()
564
+ ;
565
+ calculations.target.top -= popupOffset.top;
566
+ calculations.target.left -= popupOffset.left;
567
+ calculations.parent.width = $popupOffsetParent.outerWidth();
568
+ calculations.parent.height = $popupOffsetParent.outerHeight();
569
+ }
570
+
571
+ // add in container calcs if fluid
572
+ if (settings.setFluidWidth && module.is.fluid()) {
573
+ calculations.container = {
574
+ width: $popup.parent().outerWidth(),
575
+ };
576
+ calculations.popup.width = calculations.container.width;
577
+ }
578
+
579
+ // add in margins if inline
580
+ calculations.target.margin.top = settings.inline
581
+ ? parseInt(window.getComputedStyle(targetElement).getPropertyValue('margin-top'), 10)
582
+ : 0;
583
+ calculations.target.margin.left = settings.inline
584
+ ? (module.is.rtl()
585
+ ? parseInt(window.getComputedStyle(targetElement).getPropertyValue('margin-right'), 10)
586
+ : parseInt(window.getComputedStyle(targetElement).getPropertyValue('margin-left'), 10))
587
+ : 0;
588
+ // calculate screen boundaries
589
+ screen = calculations.screen;
590
+ calculations.boundary = {
591
+ top: screen.top + screen.scroll.top,
592
+ bottom: screen.top + screen.scroll.top + screen.height,
593
+ left: screen.left + screen.scroll.left,
594
+ right: screen.left + screen.scroll.left + screen.width,
595
+ };
596
+
597
+ return calculations;
598
+ },
599
+ id: function () {
600
+ return id;
601
+ },
602
+ startEvent: function () {
603
+ if (settings.on === 'hover') {
604
+ return 'mouseenter';
605
+ }
606
+ if (settings.on === 'focus') {
607
+ return 'focus';
608
+ }
609
+
610
+ return false;
611
+ },
612
+ scrollEvent: function () {
613
+ return 'scroll';
614
+ },
615
+ endEvent: function () {
616
+ if (settings.on === 'hover') {
617
+ return 'mouseleave';
618
+ }
619
+ if (settings.on === 'focus') {
620
+ return 'blur';
621
+ }
622
+
623
+ return false;
624
+ },
625
+ distanceFromBoundary: function (offset, calculations) {
626
+ var
627
+ distanceFromBoundary = {},
628
+ popup,
629
+ boundary
630
+ ;
631
+ calculations = calculations || module.get.calculations();
632
+
633
+ // shorthand
634
+ popup = calculations.popup;
635
+ boundary = calculations.boundary;
636
+
637
+ if (offset) {
638
+ distanceFromBoundary = {
639
+ top: offset.top - boundary.top,
640
+ left: offset.left - boundary.left,
641
+ right: boundary.right - (offset.left + popup.width),
642
+ bottom: boundary.bottom - (offset.top + popup.height),
643
+ };
644
+ module.verbose('Distance from boundaries determined', offset, distanceFromBoundary);
645
+ }
646
+
647
+ return distanceFromBoundary;
648
+ },
649
+ offsetParent: function ($element) {
650
+ var
651
+ element = $element !== undefined
652
+ ? $element[0]
653
+ : $target[0],
654
+ parentNode = element.parentNode,
655
+ $node = $(parentNode)
656
+ ;
657
+ if (parentNode) {
658
+ var
659
+ is2D = $node.css('transform') === 'none',
660
+ isStatic = $node.css('position') === 'static',
661
+ isBody = $node.is('body')
662
+ ;
663
+ while (parentNode && !isBody && isStatic && is2D) {
664
+ parentNode = parentNode.parentNode;
665
+ $node = $(parentNode);
666
+ is2D = $node.css('transform') === 'none';
667
+ isStatic = $node.css('position') === 'static';
668
+ isBody = $node.is('body');
669
+ }
670
+ }
671
+
672
+ return $node && $node.length > 0
673
+ ? $node
674
+ : $();
675
+ },
676
+ positions: function () {
677
+ return {
678
+ 'top left': false,
679
+ 'top center': false,
680
+ 'top right': false,
681
+ 'bottom left': false,
682
+ 'bottom center': false,
683
+ 'bottom right': false,
684
+ 'left center': false,
685
+ 'right center': false,
686
+ };
687
+ },
688
+ nextPosition: function (position) {
689
+ var
690
+ positions = position.split(' '),
691
+ verticalPosition = positions[0],
692
+ horizontalPosition = positions[1],
693
+ opposite = {
694
+ top: 'bottom',
695
+ bottom: 'top',
696
+ left: 'right',
697
+ right: 'left',
698
+ },
699
+ adjacent = {
700
+ left: 'center',
701
+ center: 'right',
702
+ right: 'left',
703
+ },
704
+ backup = {
705
+ 'top left': 'top center',
706
+ 'top center': 'top right',
707
+ 'top right': 'right center',
708
+ 'right center': 'bottom right',
709
+ 'bottom right': 'bottom center',
710
+ 'bottom center': 'bottom left',
711
+ 'bottom left': 'left center',
712
+ 'left center': 'top left',
713
+ },
714
+ adjacentsAvailable = verticalPosition === 'top' || verticalPosition === 'bottom',
715
+ oppositeTried = false,
716
+ adjacentTried = false,
717
+ nextPosition = false
718
+ ;
719
+ if (!triedPositions) {
720
+ module.verbose('All available positions available');
721
+ triedPositions = module.get.positions();
722
+ }
723
+
724
+ module.debug('Recording last position tried', position);
725
+ triedPositions[position] = true;
726
+
727
+ if (settings.prefer === 'opposite') {
728
+ nextPosition = [opposite[verticalPosition], horizontalPosition];
729
+ nextPosition = nextPosition.join(' ');
730
+ oppositeTried = triedPositions[nextPosition] === true;
731
+ module.debug('Trying opposite strategy', nextPosition);
732
+ }
733
+ if ((settings.prefer === 'adjacent') && adjacentsAvailable) {
734
+ nextPosition = [verticalPosition, adjacent[horizontalPosition]];
735
+ nextPosition = nextPosition.join(' ');
736
+ adjacentTried = triedPositions[nextPosition] === true;
737
+ module.debug('Trying adjacent strategy', nextPosition);
738
+ }
739
+ if (adjacentTried || oppositeTried) {
740
+ module.debug('Using backup position', nextPosition);
741
+ nextPosition = backup[position];
742
+ }
743
+
744
+ return nextPosition;
745
+ },
746
+ },
747
+
748
+ set: {
749
+ position: function (position, calculations) {
750
+ // exit conditions
751
+ if ($target.length === 0 || $popup.length === 0) {
752
+ module.error(error.notFound);
753
+
754
+ return;
755
+ }
756
+ var
757
+ offset,
758
+ distanceAway,
759
+ target,
760
+ popup,
761
+ parent,
762
+ positioning,
763
+ popupOffset,
764
+ distanceFromBoundary
765
+ ;
766
+
767
+ calculations = calculations || module.get.calculations();
768
+ position = position || $module.data(metadata.position) || settings.position;
769
+
770
+ offset = $module.data(metadata.offset) || settings.offset;
771
+ distanceAway = settings.distanceAway;
772
+
773
+ // shorthand
774
+ target = calculations.target;
775
+ popup = calculations.popup;
776
+ parent = calculations.parent;
777
+
778
+ if (module.should.centerArrow(calculations)) {
779
+ module.verbose('Adjusting offset to center arrow on small target element');
780
+ if (position === 'top left' || position === 'bottom left') {
781
+ offset += target.width / 2;
782
+ offset -= settings.arrowPixelsFromEdge;
783
+ }
784
+ if (position === 'top right' || position === 'bottom right') {
785
+ offset -= target.width / 2;
786
+ offset += settings.arrowPixelsFromEdge;
787
+ }
788
+ }
789
+
790
+ if (target.width === 0 && target.height === 0 && !module.is.svg(target.element)) {
791
+ module.debug('Popup target is hidden, no action taken');
792
+
793
+ return false;
794
+ }
795
+
796
+ if (settings.inline) {
797
+ module.debug('Adding margin to calculation', target.margin);
798
+ if (position === 'left center' || position === 'right center') {
799
+ offset += target.margin.top;
800
+ distanceAway += -target.margin.left;
801
+ } else if (position === 'top left' || position === 'top center' || position === 'top right') {
802
+ offset += target.margin.left;
803
+ distanceAway -= target.margin.top;
804
+ } else {
805
+ offset += target.margin.left;
806
+ distanceAway += target.margin.top;
807
+ }
808
+ }
809
+
810
+ module.debug('Determining popup position from calculations', position, calculations);
811
+
812
+ if (module.is.rtl()) {
813
+ position = position.replace(/left|right/g, function (match) {
814
+ return match === 'left'
815
+ ? 'right'
816
+ : 'left';
817
+ });
818
+ module.debug('RTL: Popup position updated', position);
819
+ }
820
+
821
+ // if last attempt use specified last resort position
822
+ if (searchDepth === settings.maxSearchDepth && typeof settings.lastResort === 'string') {
823
+ position = settings.lastResort;
824
+ }
825
+
826
+ switch (position) {
827
+ case 'top left': {
828
+ positioning = {
829
+ top: 'auto',
830
+ bottom: parent.height - target.top + distanceAway,
831
+ left: target.left + offset,
832
+ right: 'auto',
833
+ };
834
+
835
+ break;
836
+ }
837
+ case 'top center': {
838
+ positioning = {
839
+ bottom: parent.height - target.top + distanceAway,
840
+ left: target.left + (target.width / 2) - (popup.width / 2) + offset,
841
+ top: 'auto',
842
+ right: 'auto',
843
+ };
844
+
845
+ break;
846
+ }
847
+ case 'top right': {
848
+ positioning = {
849
+ bottom: parent.height - target.top + distanceAway,
850
+ right: parent.width - target.left - target.width - offset,
851
+ top: 'auto',
852
+ left: 'auto',
853
+ };
854
+
855
+ break;
856
+ }
857
+ case 'left center': {
858
+ positioning = {
859
+ top: target.top + (target.height / 2) - (popup.height / 2) + offset,
860
+ right: parent.width - target.left + distanceAway,
861
+ left: 'auto',
862
+ bottom: 'auto',
863
+ };
864
+
865
+ break;
866
+ }
867
+ case 'right center': {
868
+ positioning = {
869
+ top: target.top + (target.height / 2) - (popup.height / 2) + offset,
870
+ left: target.left + target.width + distanceAway,
871
+ bottom: 'auto',
872
+ right: 'auto',
873
+ };
874
+
875
+ break;
876
+ }
877
+ case 'bottom left': {
878
+ positioning = {
879
+ top: target.top + target.height + distanceAway,
880
+ left: target.left + offset,
881
+ bottom: 'auto',
882
+ right: 'auto',
883
+ };
884
+
885
+ break;
886
+ }
887
+ case 'bottom center': {
888
+ positioning = {
889
+ top: target.top + target.height + distanceAway,
890
+ left: target.left + (target.width / 2) - (popup.width / 2) + offset,
891
+ bottom: 'auto',
892
+ right: 'auto',
893
+ };
894
+
895
+ break;
896
+ }
897
+ case 'bottom right': {
898
+ positioning = {
899
+ top: target.top + target.height + distanceAway,
900
+ right: parent.width - target.left - target.width - offset,
901
+ left: 'auto',
902
+ bottom: 'auto',
903
+ };
904
+
905
+ break;
906
+ }
907
+ }
908
+ if (positioning === undefined) {
909
+ module.error(error.invalidPosition, position);
910
+ }
911
+
912
+ module.debug('Calculated popup positioning values', positioning);
913
+
914
+ // tentatively place on stage
915
+ $popup
916
+ .css(positioning)
917
+ .removeClass(className.position)
918
+ .addClass(position)
919
+ ;
920
+ module.set.invisible();
921
+
922
+ popupOffset = module.get.popupOffset();
923
+
924
+ // see if any boundaries are surpassed with this tentative position
925
+ distanceFromBoundary = module.get.distanceFromBoundary(popupOffset, calculations);
926
+
927
+ if (!settings.forcePosition && module.is.offstage(distanceFromBoundary, position)) {
928
+ module.debug('Position is outside viewport', position);
929
+ if (searchDepth < settings.maxSearchDepth) {
930
+ searchDepth++;
931
+ position = module.get.nextPosition(position);
932
+ module.debug('Trying new position', position);
933
+
934
+ return $popup
935
+ ? module.set.position(position, calculations)
936
+ : false;
937
+ }
938
+ if (settings.lastResort) {
939
+ module.debug('No position found, showing with last position');
940
+ } else {
941
+ module.debug('Popup could not find a position to display', $popup);
942
+ module.error(error.cannotPlace, element);
943
+ module.remove.attempts();
944
+ module.remove.invisible();
945
+ module.reset();
946
+ settings.onUnplaceable.call($popup, element);
947
+
948
+ return false;
949
+ }
950
+ }
951
+ module.debug('Position is on stage', position);
952
+ module.remove.attempts();
953
+ module.remove.invisible();
954
+ if (settings.setFluidWidth && module.is.fluid()) {
955
+ module.set.fluidWidth(calculations);
956
+ }
957
+
958
+ return true;
959
+ },
960
+
961
+ fluidWidth: function (calculations) {
962
+ calculations = calculations || module.get.calculations();
963
+ module.debug('Automatically setting element width to parent width', calculations.parent.width);
964
+ $popup.css('width', calculations.container.width);
965
+ },
966
+
967
+ loading: function () {
968
+ $popup.addClass(className.loading);
969
+ },
970
+
971
+ invisible: function () {
972
+ $popup.addClass(className.invisible);
973
+ },
974
+
975
+ variation: function (variation) {
976
+ variation = variation || module.get.variation();
977
+ if (variation && module.has.popup()) {
978
+ module.verbose('Adding variation to popup', variation);
979
+ $popup.addClass(variation);
980
+ }
981
+ },
982
+
983
+ visible: function () {
984
+ $module.addClass(className.visible);
985
+ },
986
+ },
987
+
988
+ remove: {
989
+ loading: function () {
990
+ $popup.removeClass(className.loading);
991
+ },
992
+ invisible: function () {
993
+ $popup.removeClass(className.invisible);
994
+ },
995
+ variation: function (variation) {
996
+ variation = variation || module.get.variation();
997
+ if (variation) {
998
+ module.verbose('Removing variation', variation);
999
+ $popup.removeClass(variation);
1000
+ }
1001
+ },
1002
+ visible: function () {
1003
+ $module.removeClass(className.visible);
1004
+ },
1005
+ attempts: function () {
1006
+ module.verbose('Resetting all searched positions');
1007
+ searchDepth = 0;
1008
+ triedPositions = false;
1009
+ },
1010
+ },
1011
+
1012
+ bind: {
1013
+ events: function () {
1014
+ module.debug('Binding popup events to module');
1015
+ if (settings.on === 'click') {
1016
+ $module
1017
+ .on(clickEvent + eventNamespace, module.toggle)
1018
+ ;
1019
+ }
1020
+ if (settings.on === 'hover') {
1021
+ $module
1022
+ .on('touchstart' + eventNamespace, module.event.touchstart)
1023
+ ;
1024
+ }
1025
+ if (module.get.startEvent()) {
1026
+ $module
1027
+ .on(module.get.startEvent() + eventNamespace, module.event.start)
1028
+ .on(module.get.endEvent() + eventNamespace, module.event.end)
1029
+ ;
1030
+ }
1031
+ if (settings.target) {
1032
+ module.debug('Target set to element', $target);
1033
+ }
1034
+ $window.on('resize' + elementNamespace, module.event.resize);
1035
+ },
1036
+ popup: function () {
1037
+ module.verbose('Allowing hover events on popup to prevent closing');
1038
+ if ($popup && module.has.popup()) {
1039
+ $popup
1040
+ .on('mouseenter' + eventNamespace, module.event.start)
1041
+ .on('mouseleave' + eventNamespace, module.event.end)
1042
+ ;
1043
+ }
1044
+ },
1045
+ close: function () {
1046
+ if (settings.hideOnScroll === true || (settings.hideOnScroll === 'auto' && settings.on !== 'click')) {
1047
+ module.bind.closeOnScroll();
1048
+ }
1049
+ if (module.is.closable()) {
1050
+ module.bind.clickaway();
1051
+ } else if (settings.on === 'hover' && openedWithTouch) {
1052
+ module.bind.touchClose();
1053
+ }
1054
+ },
1055
+ closeOnScroll: function () {
1056
+ module.verbose('Binding scroll close event to document');
1057
+ $scrollContext
1058
+ .one(module.get.scrollEvent() + elementNamespace, module.event.hideGracefully)
1059
+ ;
1060
+ },
1061
+ touchClose: function () {
1062
+ module.verbose('Binding popup touchclose event to document');
1063
+ $document
1064
+ .on('touchstart' + elementNamespace, function (event) {
1065
+ module.verbose('Touched away from popup');
1066
+ module.event.hideGracefully.call(element, event);
1067
+ })
1068
+ ;
1069
+ },
1070
+ clickaway: function () {
1071
+ module.verbose('Binding popup close event to document');
1072
+ $document
1073
+ .on(clickEvent + elementNamespace, function (event) {
1074
+ module.verbose('Clicked away from popup');
1075
+ module.event.hideGracefully.call(element, event);
1076
+ })
1077
+ ;
1078
+ },
1079
+ },
1080
+
1081
+ unbind: {
1082
+ events: function () {
1083
+ $window
1084
+ .off(elementNamespace)
1085
+ ;
1086
+ $module
1087
+ .off(eventNamespace)
1088
+ ;
1089
+ },
1090
+ close: function () {
1091
+ $document
1092
+ .off(elementNamespace)
1093
+ ;
1094
+ $scrollContext
1095
+ .off(elementNamespace)
1096
+ ;
1097
+ },
1098
+ },
1099
+
1100
+ can: {
1101
+ useElement: function (element) {
1102
+ if ($.fn[element] !== undefined) {
1103
+ return true;
1104
+ }
1105
+ module.error(error.noElement.replace('{element}', element));
1106
+
1107
+ return false;
1108
+ },
1109
+ },
1110
+
1111
+ has: {
1112
+ popup: function () {
1113
+ return $popup && $popup.length > 0;
1114
+ },
1115
+ },
1116
+
1117
+ should: {
1118
+ centerArrow: function (calculations) {
1119
+ return !module.is.basic() && calculations.target.width <= (settings.arrowPixelsFromEdge * 2);
1120
+ },
1121
+ },
1122
+
1123
+ is: {
1124
+ closable: function () {
1125
+ if (settings.closable === 'auto') {
1126
+ return settings.on !== 'hover';
1127
+ }
1128
+
1129
+ return settings.closable;
1130
+ },
1131
+ offstage: function (distanceFromBoundary, position) {
1132
+ var
1133
+ offstage = []
1134
+ ;
1135
+ // return boundaries that have been surpassed
1136
+ $.each(distanceFromBoundary, function (direction, distance) {
1137
+ if (distance < -settings.jitter) {
1138
+ module.debug('Position exceeds allowable distance from edge', direction, distance, position);
1139
+ offstage.push(direction);
1140
+ }
1141
+ });
1142
+
1143
+ return offstage.length > 0;
1144
+ },
1145
+ svg: function (element) {
1146
+ return module.supports.svg() && (element instanceof SVGGraphicsElement);
1147
+ },
1148
+ basic: function () {
1149
+ return $module.hasClass(className.basic);
1150
+ },
1151
+ active: function () {
1152
+ return $module.hasClass(className.active);
1153
+ },
1154
+ animating: function () {
1155
+ return $popup !== undefined && $popup.hasClass(className.animating);
1156
+ },
1157
+ fluid: function () {
1158
+ return $popup !== undefined && $popup.hasClass(className.fluid);
1159
+ },
1160
+ visible: function () {
1161
+ return $popup !== undefined && $popup.hasClass(className.popupVisible);
1162
+ },
1163
+ dropdown: function () {
1164
+ return $module.hasClass(className.dropdown);
1165
+ },
1166
+ hidden: function () {
1167
+ return !module.is.visible();
1168
+ },
1169
+ rtl: function () {
1170
+ return $module.attr('dir') === 'rtl' || $module.css('direction') === 'rtl' || $body.attr('dir') === 'rtl' || $body.css('direction') === 'rtl' || $context.attr('dir') === 'rtl' || $context.css('direction') === 'rtl';
1171
+ },
1172
+ },
1173
+
1174
+ reset: function () {
1175
+ module.remove.visible();
1176
+ if (settings.preserve) {
1177
+ if ($.fn.transition !== undefined) {
1178
+ $popup
1179
+ .transition('remove transition')
1180
+ ;
1181
+ }
1182
+ } else {
1183
+ module.removePopup();
1184
+ }
1185
+ },
1186
+
1187
+ setting: function (name, value) {
1188
+ if ($.isPlainObject(name)) {
1189
+ $.extend(true, settings, name);
1190
+ } else if (value !== undefined) {
1191
+ settings[name] = value;
1192
+ } else {
1193
+ return settings[name];
1194
+ }
1195
+ },
1196
+ internal: function (name, value) {
1197
+ if ($.isPlainObject(name)) {
1198
+ $.extend(true, module, name);
1199
+ } else if (value !== undefined) {
1200
+ module[name] = value;
1201
+ } else {
1202
+ return module[name];
1203
+ }
1204
+ },
1205
+ debug: function () {
1206
+ if (!settings.silent && settings.debug) {
1207
+ if (settings.performance) {
1208
+ module.performance.log(arguments);
1209
+ } else {
1210
+ module.debug = Function.prototype.bind.call(console.info, console, settings.name + ':');
1211
+ module.debug.apply(console, arguments);
1212
+ }
1213
+ }
1214
+ },
1215
+ verbose: function () {
1216
+ if (!settings.silent && settings.verbose && settings.debug) {
1217
+ if (settings.performance) {
1218
+ module.performance.log(arguments);
1219
+ } else {
1220
+ module.verbose = Function.prototype.bind.call(console.info, console, settings.name + ':');
1221
+ module.verbose.apply(console, arguments);
1222
+ }
1223
+ }
1224
+ },
1225
+ error: function () {
1226
+ if (!settings.silent) {
1227
+ module.error = Function.prototype.bind.call(console.error, console, settings.name + ':');
1228
+ module.error.apply(console, arguments);
1229
+ }
1230
+ },
1231
+ performance: {
1232
+ log: function (message) {
1233
+ var
1234
+ currentTime,
1235
+ executionTime,
1236
+ previousTime
1237
+ ;
1238
+ if (settings.performance) {
1239
+ currentTime = Date.now();
1240
+ previousTime = time || currentTime;
1241
+ executionTime = currentTime - previousTime;
1242
+ time = currentTime;
1243
+ performance.push({
1244
+ Name: message[0],
1245
+ Arguments: [].slice.call(message, 1) || '',
1246
+ Element: element,
1247
+ 'Execution Time': executionTime,
1248
+ });
1249
+ }
1250
+ clearTimeout(module.performance.timer);
1251
+ module.performance.timer = setTimeout(function () {
1252
+ module.performance.display();
1253
+ }, 500);
1254
+ },
1255
+ display: function () {
1256
+ var
1257
+ title = settings.name + ':',
1258
+ totalTime = 0
1259
+ ;
1260
+ time = false;
1261
+ clearTimeout(module.performance.timer);
1262
+ $.each(performance, function (index, data) {
1263
+ totalTime += data['Execution Time'];
1264
+ });
1265
+ title += ' ' + totalTime + 'ms';
1266
+ if (performance.length > 0) {
1267
+ console.groupCollapsed(title);
1268
+ if (console.table) {
1269
+ console.table(performance);
1270
+ } else {
1271
+ $.each(performance, function (index, data) {
1272
+ console.log(data.Name + ': ' + data['Execution Time'] + 'ms');
1273
+ });
1274
+ }
1275
+ console.groupEnd();
1276
+ }
1277
+ performance = [];
1278
+ },
1279
+ },
1280
+ invoke: function (query, passedArguments, context) {
1281
+ var
1282
+ object = instance,
1283
+ maxDepth,
1284
+ found,
1285
+ response
1286
+ ;
1287
+ passedArguments = passedArguments || queryArguments;
1288
+ context = context || element;
1289
+ if (typeof query === 'string' && object !== undefined) {
1290
+ query = query.split(/[ .]/);
1291
+ maxDepth = query.length - 1;
1292
+ $.each(query, function (depth, value) {
1293
+ var camelCaseValue = depth !== maxDepth
1294
+ ? value + query[depth + 1].charAt(0).toUpperCase() + query[depth + 1].slice(1)
1295
+ : query
1296
+ ;
1297
+ if ($.isPlainObject(object[camelCaseValue]) && (depth !== maxDepth)) {
1298
+ object = object[camelCaseValue];
1299
+ } else if (object[camelCaseValue] !== undefined) {
1300
+ found = object[camelCaseValue];
1301
+
1302
+ return false;
1303
+ } else if ($.isPlainObject(object[value]) && (depth !== maxDepth)) {
1304
+ object = object[value];
1305
+ } else if (object[value] !== undefined) {
1306
+ found = object[value];
1307
+
1308
+ return false;
1309
+ } else {
1310
+ module.error(error.method, query);
1311
+
1312
+ return false;
1313
+ }
1314
+ });
1315
+ }
1316
+ if (isFunction(found)) {
1317
+ response = found.apply(context, passedArguments);
1318
+ } else if (found !== undefined) {
1319
+ response = found;
1320
+ }
1321
+ if (Array.isArray(returnedValue)) {
1322
+ returnedValue.push(response);
1323
+ } else if (returnedValue !== undefined) {
1324
+ returnedValue = [returnedValue, response];
1325
+ } else if (response !== undefined) {
1326
+ returnedValue = response;
1327
+ }
1328
+
1329
+ return found;
1330
+ },
1331
+ };
1332
+
1333
+ if (methodInvoked) {
1334
+ if (instance === undefined) {
1335
+ module.initialize();
1336
+ }
1337
+ module.invoke(query);
1338
+ } else {
1339
+ if (instance !== undefined) {
1340
+ instance.invoke('destroy');
1341
+ }
1342
+ module.initialize();
1343
+ }
1344
+ });
1345
+
1346
+ return returnedValue !== undefined
1347
+ ? returnedValue
1348
+ : this;
1349
+ };
1350
+
1351
+ $.fn.popup.settings = {
1352
+
1353
+ name: 'Popup',
1354
+
1355
+ // module settings
1356
+ silent: false,
1357
+ debug: false,
1358
+ verbose: false,
1359
+ performance: true,
1360
+ namespace: 'popup',
1361
+
1362
+ // whether it should use dom mutation observers
1363
+ observeChanges: true,
1364
+
1365
+ // callback only when element added to dom
1366
+ onCreate: function () {},
1367
+
1368
+ // callback before element removed from dom
1369
+ onRemove: function () {},
1370
+
1371
+ // callback before show animation
1372
+ onShow: function () {},
1373
+
1374
+ // callback after show animation
1375
+ onVisible: function () {},
1376
+
1377
+ // callback before hide animation
1378
+ onHide: function () {},
1379
+
1380
+ // callback when popup cannot be positioned in visible screen
1381
+ onUnplaceable: function () {},
1382
+
1383
+ // callback after hide animation
1384
+ onHidden: function () {},
1385
+
1386
+ // when to show popup
1387
+ on: 'hover',
1388
+
1389
+ // element to use to determine if popup is out of boundary
1390
+ boundary: window,
1391
+
1392
+ // whether to add touchstart events when using hover
1393
+ addTouchEvents: true,
1394
+
1395
+ // default position relative to element
1396
+ position: 'top left',
1397
+
1398
+ // if given position should be used regardless if popup fits
1399
+ forcePosition: false,
1400
+
1401
+ // name of variation to use
1402
+ variation: '',
1403
+
1404
+ // whether popup should be moved to context
1405
+ movePopup: true,
1406
+
1407
+ // element which popup should be relative to
1408
+ target: false,
1409
+
1410
+ // jq selector or element that should be used as popup
1411
+ popup: false,
1412
+
1413
+ // popup should remain inline next to activator
1414
+ inline: false,
1415
+
1416
+ // popup should be removed from page on hide
1417
+ preserve: false,
1418
+
1419
+ // popup should not close when being hovered on
1420
+ hoverable: false,
1421
+
1422
+ // explicitly set content
1423
+ content: false,
1424
+
1425
+ // explicitly set html
1426
+ html: false,
1427
+
1428
+ // explicitly set title
1429
+ title: false,
1430
+
1431
+ // whether automatically close on clickaway when on click
1432
+ closable: true,
1433
+
1434
+ // automatically hide on scroll
1435
+ hideOnScroll: 'auto',
1436
+
1437
+ // hide other popups on show
1438
+ exclusive: false,
1439
+
1440
+ // context to attach popups
1441
+ context: 'body',
1442
+
1443
+ // context for binding scroll events
1444
+ scrollContext: window,
1445
+
1446
+ // position to prefer when calculating new position
1447
+ prefer: 'opposite',
1448
+
1449
+ // specify position to appear even if it doesn't fit
1450
+ lastResort: false,
1451
+
1452
+ // number of pixels from edge of popup to pointing arrow center (used from centering)
1453
+ arrowPixelsFromEdge: 20,
1454
+
1455
+ // delay used to prevent accidental refiring of animations due to user error
1456
+ delay: {
1457
+ show: 50,
1458
+ hide: 70,
1459
+ },
1460
+
1461
+ // whether fluid variation should assign width explicitly
1462
+ setFluidWidth: true,
1463
+
1464
+ // transition settings
1465
+ duration: 200,
1466
+ transition: 'scale',
1467
+
1468
+ // distance away from activating element in px
1469
+ distanceAway: 0,
1470
+
1471
+ // number of pixels an element is allowed to be "offstage" for a position to be chosen (allows for rounding)
1472
+ jitter: 2,
1473
+
1474
+ // offset on aligning axis from calculated position
1475
+ offset: 0,
1476
+
1477
+ // maximum times to look for a position before failing (9 positions total)
1478
+ maxSearchDepth: 15,
1479
+
1480
+ error: {
1481
+ invalidPosition: 'The position you specified is not a valid position',
1482
+ cannotPlace: 'Popup does not fit within the boundaries of the viewport',
1483
+ method: 'The method you called is not defined.',
1484
+ noElement: 'This module requires ui {element}',
1485
+ notFound: 'The target or popup you specified does not exist on the page',
1486
+ },
1487
+
1488
+ metadata: {
1489
+ activator: 'activator',
1490
+ content: 'content',
1491
+ html: 'html',
1492
+ offset: 'offset',
1493
+ position: 'position',
1494
+ title: 'title',
1495
+ variation: 'variation',
1496
+ },
1497
+
1498
+ className: {
1499
+ active: 'active',
1500
+ basic: 'basic',
1501
+ animating: 'animating',
1502
+ dropdown: 'dropdown',
1503
+ invisible: 'invisible',
1504
+ fluid: 'fluid',
1505
+ loading: 'loading',
1506
+ popup: 'ui popup',
1507
+ position: 'top left center bottom right',
1508
+ visible: 'visible',
1509
+ popupVisible: 'visible',
1510
+ },
1511
+
1512
+ selector: {
1513
+ popup: '.ui.popup',
1514
+ },
1515
+
1516
+ templates: {
1517
+ escape: function (string) {
1518
+ var
1519
+ badChars = /["'<>`]/g,
1520
+ shouldEscape = /["&'<>`]/,
1521
+ escape = {
1522
+ '<': '&lt;',
1523
+ '>': '&gt;',
1524
+ '"': '&quot;',
1525
+ "'": '&#x27;',
1526
+ '`': '&#x60;',
1527
+ },
1528
+ escapedChar = function (chr) {
1529
+ return escape[chr];
1530
+ }
1531
+ ;
1532
+ if (shouldEscape.test(string)) {
1533
+ string = string.replace(/&(?![\d#a-z]{1,12};)/gi, '&amp;');
1534
+
1535
+ return string.replace(badChars, escapedChar);
1536
+ }
1537
+
1538
+ return string;
1539
+ },
1540
+ popup: function (text) {
1541
+ var
1542
+ html = '',
1543
+ escape = $.fn.popup.settings.templates.escape
1544
+ ;
1545
+ if (text !== undefined) {
1546
+ if (text.title) {
1547
+ text.title = escape(text.title);
1548
+ html += '<div class="header">' + text.title + '</div>';
1549
+ }
1550
+ if (text.content) {
1551
+ text.content = escape(text.content);
1552
+ html += '<div class="content">' + text.content + '</div>';
1553
+ }
1554
+ }
1555
+
1556
+ return html;
1557
+ },
1558
+ },
1559
+
1560
+ };
1561
+ })(jQuery, window, document);