rails_shepherd 1.0.1 → 1.1.0
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.
- checksums.yaml +4 -4
- data/README.md +3 -1
- data/lib/rails_shepherd/version.rb +1 -1
- data/vendor/assets/javascripts/popper.js +2612 -0
- data/vendor/assets/javascripts/tippy.js +1915 -0
- metadata +4 -6
- data/vendor/assets/javascripts/shepherd.esm.js +0 -7713
- data/vendor/assets/javascripts/shepherd.esm.js.map +0 -1
- data/vendor/assets/javascripts/shepherd.esm.min.js +0 -4
- data/vendor/assets/javascripts/shepherd.esm.min.js.map +0 -1
|
@@ -0,0 +1,1915 @@
|
|
|
1
|
+
/**!
|
|
2
|
+
* tippy.js v4.3.4
|
|
3
|
+
* (c) 2017-2019 atomiks
|
|
4
|
+
* MIT License
|
|
5
|
+
*/
|
|
6
|
+
(function (global, factory) {
|
|
7
|
+
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory(require('popper.js')) :
|
|
8
|
+
typeof define === 'function' && define.amd ? define(['popper.js'], factory) :
|
|
9
|
+
(global = global || self, global.tippy = factory(global.Popper));
|
|
10
|
+
}(this, function (Popper) { 'use strict';
|
|
11
|
+
|
|
12
|
+
Popper = Popper && Popper.hasOwnProperty('default') ? Popper['default'] : Popper;
|
|
13
|
+
|
|
14
|
+
function _extends() {
|
|
15
|
+
_extends = Object.assign || function (target) {
|
|
16
|
+
for (var i = 1; i < arguments.length; i++) {
|
|
17
|
+
var source = arguments[i];
|
|
18
|
+
|
|
19
|
+
for (var key in source) {
|
|
20
|
+
if (Object.prototype.hasOwnProperty.call(source, key)) {
|
|
21
|
+
target[key] = source[key];
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
return target;
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
return _extends.apply(this, arguments);
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
var version = "4.3.4";
|
|
33
|
+
|
|
34
|
+
var isBrowser = typeof window !== 'undefined' && typeof document !== 'undefined';
|
|
35
|
+
var ua = isBrowser ? navigator.userAgent : '';
|
|
36
|
+
var isIE = /MSIE |Trident\//.test(ua);
|
|
37
|
+
var isUCBrowser = /UCBrowser\//.test(ua);
|
|
38
|
+
var isIOS = isBrowser && /iPhone|iPad|iPod/.test(navigator.platform) && !window.MSStream;
|
|
39
|
+
|
|
40
|
+
var defaultProps = {
|
|
41
|
+
a11y: true,
|
|
42
|
+
allowHTML: true,
|
|
43
|
+
animateFill: true,
|
|
44
|
+
animation: 'shift-away',
|
|
45
|
+
appendTo: function appendTo() {
|
|
46
|
+
return document.body;
|
|
47
|
+
},
|
|
48
|
+
aria: 'describedby',
|
|
49
|
+
arrow: false,
|
|
50
|
+
arrowType: 'sharp',
|
|
51
|
+
boundary: 'scrollParent',
|
|
52
|
+
content: '',
|
|
53
|
+
delay: 0,
|
|
54
|
+
distance: 10,
|
|
55
|
+
duration: [325, 275],
|
|
56
|
+
flip: true,
|
|
57
|
+
flipBehavior: 'flip',
|
|
58
|
+
flipOnUpdate: false,
|
|
59
|
+
followCursor: false,
|
|
60
|
+
hideOnClick: true,
|
|
61
|
+
ignoreAttributes: false,
|
|
62
|
+
inertia: false,
|
|
63
|
+
interactive: false,
|
|
64
|
+
interactiveBorder: 2,
|
|
65
|
+
interactiveDebounce: 0,
|
|
66
|
+
lazy: true,
|
|
67
|
+
maxWidth: 350,
|
|
68
|
+
multiple: false,
|
|
69
|
+
offset: 0,
|
|
70
|
+
onHidden: function onHidden() {},
|
|
71
|
+
onHide: function onHide() {},
|
|
72
|
+
onMount: function onMount() {},
|
|
73
|
+
onShow: function onShow() {},
|
|
74
|
+
onShown: function onShown() {},
|
|
75
|
+
onTrigger: function onTrigger() {},
|
|
76
|
+
placement: 'top',
|
|
77
|
+
popperOptions: {},
|
|
78
|
+
role: 'tooltip',
|
|
79
|
+
showOnInit: false,
|
|
80
|
+
size: 'regular',
|
|
81
|
+
sticky: false,
|
|
82
|
+
target: '',
|
|
83
|
+
theme: 'dark',
|
|
84
|
+
touch: true,
|
|
85
|
+
touchHold: false,
|
|
86
|
+
trigger: 'mouseenter focus',
|
|
87
|
+
triggerTarget: null,
|
|
88
|
+
updateDuration: 0,
|
|
89
|
+
wait: null,
|
|
90
|
+
zIndex: 9999
|
|
91
|
+
/**
|
|
92
|
+
* If the set() method encounters one of these, the popperInstance must be
|
|
93
|
+
* recreated
|
|
94
|
+
*/
|
|
95
|
+
|
|
96
|
+
};
|
|
97
|
+
var POPPER_INSTANCE_DEPENDENCIES = ['arrow', 'arrowType', 'boundary', 'distance', 'flip', 'flipBehavior', 'flipOnUpdate', 'offset', 'placement', 'popperOptions'];
|
|
98
|
+
|
|
99
|
+
var elementProto = isBrowser ? Element.prototype : {};
|
|
100
|
+
var matches = elementProto.matches || elementProto.matchesSelector || elementProto.webkitMatchesSelector || elementProto.mozMatchesSelector || elementProto.msMatchesSelector;
|
|
101
|
+
/**
|
|
102
|
+
* Ponyfill for Array.from - converts iterable values to an array
|
|
103
|
+
*/
|
|
104
|
+
|
|
105
|
+
function arrayFrom(value) {
|
|
106
|
+
return [].slice.call(value);
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* Ponyfill for Element.prototype.closest
|
|
110
|
+
*/
|
|
111
|
+
|
|
112
|
+
function closest(element, selector) {
|
|
113
|
+
return closestCallback(element, function (el) {
|
|
114
|
+
return matches.call(el, selector);
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* Works like Element.prototype.closest, but uses a callback instead
|
|
119
|
+
*/
|
|
120
|
+
|
|
121
|
+
function closestCallback(element, callback) {
|
|
122
|
+
while (element) {
|
|
123
|
+
if (callback(element)) {
|
|
124
|
+
return element;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
element = element.parentElement;
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
return null;
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
// Passive event listener config
|
|
134
|
+
var PASSIVE = {
|
|
135
|
+
passive: true // Popper `preventOverflow` padding
|
|
136
|
+
|
|
137
|
+
};
|
|
138
|
+
var PADDING = 4; // Popper attributes
|
|
139
|
+
// In Popper v2 these will be `data-*` instead of `x-*` to adhere to HTML5 spec
|
|
140
|
+
|
|
141
|
+
var PLACEMENT_ATTRIBUTE = 'x-placement';
|
|
142
|
+
var OUT_OF_BOUNDARIES_ATTRIBUTE = 'x-out-of-boundaries'; // Classes
|
|
143
|
+
|
|
144
|
+
var IOS_CLASS = "tippy-iOS";
|
|
145
|
+
var ACTIVE_CLASS = "tippy-active";
|
|
146
|
+
var POPPER_CLASS = "tippy-popper";
|
|
147
|
+
var TOOLTIP_CLASS = "tippy-tooltip";
|
|
148
|
+
var CONTENT_CLASS = "tippy-content";
|
|
149
|
+
var BACKDROP_CLASS = "tippy-backdrop";
|
|
150
|
+
var ARROW_CLASS = "tippy-arrow";
|
|
151
|
+
var ROUND_ARROW_CLASS = "tippy-roundarrow"; // Selectors
|
|
152
|
+
|
|
153
|
+
var POPPER_SELECTOR = ".".concat(POPPER_CLASS);
|
|
154
|
+
var TOOLTIP_SELECTOR = ".".concat(TOOLTIP_CLASS);
|
|
155
|
+
var CONTENT_SELECTOR = ".".concat(CONTENT_CLASS);
|
|
156
|
+
var BACKDROP_SELECTOR = ".".concat(BACKDROP_CLASS);
|
|
157
|
+
var ARROW_SELECTOR = ".".concat(ARROW_CLASS);
|
|
158
|
+
var ROUND_ARROW_SELECTOR = ".".concat(ROUND_ARROW_CLASS);
|
|
159
|
+
|
|
160
|
+
var isUsingTouch = false;
|
|
161
|
+
function onDocumentTouch() {
|
|
162
|
+
if (isUsingTouch) {
|
|
163
|
+
return;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
isUsingTouch = true;
|
|
167
|
+
|
|
168
|
+
if (isIOS) {
|
|
169
|
+
document.body.classList.add(IOS_CLASS);
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
if (window.performance) {
|
|
173
|
+
document.addEventListener('mousemove', onDocumentMouseMove);
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
var lastMouseMoveTime = 0;
|
|
177
|
+
function onDocumentMouseMove() {
|
|
178
|
+
var now = performance.now(); // Chrome 60+ is 1 mousemove per animation frame, use 20ms time difference
|
|
179
|
+
|
|
180
|
+
if (now - lastMouseMoveTime < 20) {
|
|
181
|
+
isUsingTouch = false;
|
|
182
|
+
document.removeEventListener('mousemove', onDocumentMouseMove);
|
|
183
|
+
|
|
184
|
+
if (!isIOS) {
|
|
185
|
+
document.body.classList.remove(IOS_CLASS);
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
lastMouseMoveTime = now;
|
|
190
|
+
}
|
|
191
|
+
function onWindowBlur() {
|
|
192
|
+
var _document = document,
|
|
193
|
+
activeElement = _document.activeElement;
|
|
194
|
+
|
|
195
|
+
if (activeElement && activeElement.blur && activeElement._tippy) {
|
|
196
|
+
activeElement.blur();
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
/**
|
|
200
|
+
* Adds the needed global event listeners
|
|
201
|
+
*/
|
|
202
|
+
|
|
203
|
+
function bindGlobalEventListeners() {
|
|
204
|
+
document.addEventListener('touchstart', onDocumentTouch, PASSIVE);
|
|
205
|
+
window.addEventListener('blur', onWindowBlur);
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
var keys = Object.keys(defaultProps);
|
|
209
|
+
/**
|
|
210
|
+
* Returns an object of optional props from data-tippy-* attributes
|
|
211
|
+
*/
|
|
212
|
+
|
|
213
|
+
function getDataAttributeOptions(reference) {
|
|
214
|
+
return keys.reduce(function (acc, key) {
|
|
215
|
+
var valueAsString = (reference.getAttribute("data-tippy-".concat(key)) || '').trim();
|
|
216
|
+
|
|
217
|
+
if (!valueAsString) {
|
|
218
|
+
return acc;
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
if (key === 'content') {
|
|
222
|
+
acc[key] = valueAsString;
|
|
223
|
+
} else {
|
|
224
|
+
try {
|
|
225
|
+
acc[key] = JSON.parse(valueAsString);
|
|
226
|
+
} catch (e) {
|
|
227
|
+
acc[key] = valueAsString;
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
return acc;
|
|
232
|
+
}, {});
|
|
233
|
+
}
|
|
234
|
+
/**
|
|
235
|
+
* Polyfills the virtual reference (plain object) with Element.prototype props
|
|
236
|
+
* Mutating because DOM elements are mutated, adds `_tippy` property
|
|
237
|
+
*/
|
|
238
|
+
|
|
239
|
+
function polyfillElementPrototypeProperties(virtualReference) {
|
|
240
|
+
var polyfills = {
|
|
241
|
+
isVirtual: true,
|
|
242
|
+
attributes: virtualReference.attributes || {},
|
|
243
|
+
contains: function contains() {},
|
|
244
|
+
setAttribute: function setAttribute(key, value) {
|
|
245
|
+
virtualReference.attributes[key] = value;
|
|
246
|
+
},
|
|
247
|
+
getAttribute: function getAttribute(key) {
|
|
248
|
+
return virtualReference.attributes[key];
|
|
249
|
+
},
|
|
250
|
+
removeAttribute: function removeAttribute(key) {
|
|
251
|
+
delete virtualReference.attributes[key];
|
|
252
|
+
},
|
|
253
|
+
hasAttribute: function hasAttribute(key) {
|
|
254
|
+
return key in virtualReference.attributes;
|
|
255
|
+
},
|
|
256
|
+
addEventListener: function addEventListener() {},
|
|
257
|
+
removeEventListener: function removeEventListener() {},
|
|
258
|
+
classList: {
|
|
259
|
+
classNames: {},
|
|
260
|
+
add: function add(key) {
|
|
261
|
+
virtualReference.classList.classNames[key] = true;
|
|
262
|
+
},
|
|
263
|
+
remove: function remove(key) {
|
|
264
|
+
delete virtualReference.classList.classNames[key];
|
|
265
|
+
},
|
|
266
|
+
contains: function contains(key) {
|
|
267
|
+
return key in virtualReference.classList.classNames;
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
};
|
|
271
|
+
|
|
272
|
+
for (var key in polyfills) {
|
|
273
|
+
virtualReference[key] = polyfills[key];
|
|
274
|
+
}
|
|
275
|
+
}
|
|
276
|
+
|
|
277
|
+
/**
|
|
278
|
+
* Determines if a value is a "bare" virtual element (before mutations done
|
|
279
|
+
* by `polyfillElementPrototypeProperties()`). JSDOM elements show up as
|
|
280
|
+
* [object Object], we can check if the value is "element-like" if it has
|
|
281
|
+
* `addEventListener`
|
|
282
|
+
*/
|
|
283
|
+
|
|
284
|
+
function isBareVirtualElement(value) {
|
|
285
|
+
return {}.toString.call(value) === '[object Object]' && !value.addEventListener;
|
|
286
|
+
}
|
|
287
|
+
/**
|
|
288
|
+
* Determines if the value is a reference element
|
|
289
|
+
*/
|
|
290
|
+
|
|
291
|
+
function isReferenceElement(value) {
|
|
292
|
+
return !!value._tippy && !matches.call(value, POPPER_SELECTOR);
|
|
293
|
+
}
|
|
294
|
+
/**
|
|
295
|
+
* Safe .hasOwnProperty check, for prototype-less objects
|
|
296
|
+
*/
|
|
297
|
+
|
|
298
|
+
function hasOwnProperty(obj, key) {
|
|
299
|
+
return {}.hasOwnProperty.call(obj, key);
|
|
300
|
+
}
|
|
301
|
+
/**
|
|
302
|
+
* Returns an array of elements based on the value
|
|
303
|
+
*/
|
|
304
|
+
|
|
305
|
+
function getArrayOfElements(value) {
|
|
306
|
+
if (isSingular(value)) {
|
|
307
|
+
// TODO: VirtualReference is not compatible to type Element
|
|
308
|
+
return [value];
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
if (value instanceof NodeList) {
|
|
312
|
+
return arrayFrom(value);
|
|
313
|
+
}
|
|
314
|
+
|
|
315
|
+
if (Array.isArray(value)) {
|
|
316
|
+
return value;
|
|
317
|
+
}
|
|
318
|
+
|
|
319
|
+
try {
|
|
320
|
+
return arrayFrom(document.querySelectorAll(value));
|
|
321
|
+
} catch (e) {
|
|
322
|
+
return [];
|
|
323
|
+
}
|
|
324
|
+
}
|
|
325
|
+
/**
|
|
326
|
+
* Returns a value at a given index depending on if it's an array or number
|
|
327
|
+
*/
|
|
328
|
+
|
|
329
|
+
function getValue(value, index, defaultValue) {
|
|
330
|
+
if (Array.isArray(value)) {
|
|
331
|
+
var v = value[index];
|
|
332
|
+
return v == null ? defaultValue : v;
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
return value;
|
|
336
|
+
}
|
|
337
|
+
/**
|
|
338
|
+
* Debounce utility. To avoid bloating bundle size, we're only passing 1
|
|
339
|
+
* argument here, a more generic function would pass all arguments. Only
|
|
340
|
+
* `onMouseMove` uses this which takes the event object for now.
|
|
341
|
+
*/
|
|
342
|
+
|
|
343
|
+
function debounce(fn, ms) {
|
|
344
|
+
// Avoid wrapping in `setTimeout` if ms is 0 anyway
|
|
345
|
+
if (ms === 0) {
|
|
346
|
+
return fn;
|
|
347
|
+
}
|
|
348
|
+
|
|
349
|
+
var timeout;
|
|
350
|
+
return function (arg) {
|
|
351
|
+
clearTimeout(timeout);
|
|
352
|
+
timeout = setTimeout(function () {
|
|
353
|
+
fn(arg);
|
|
354
|
+
}, ms);
|
|
355
|
+
};
|
|
356
|
+
}
|
|
357
|
+
/**
|
|
358
|
+
* Prevents errors from being thrown while accessing nested modifier objects
|
|
359
|
+
* in `popperOptions`
|
|
360
|
+
*/
|
|
361
|
+
|
|
362
|
+
function getModifier(obj, key) {
|
|
363
|
+
return obj && obj.modifiers && obj.modifiers[key];
|
|
364
|
+
}
|
|
365
|
+
/**
|
|
366
|
+
* Determines if an array or string includes a value
|
|
367
|
+
*/
|
|
368
|
+
|
|
369
|
+
function includes(a, b) {
|
|
370
|
+
return a.indexOf(b) > -1;
|
|
371
|
+
}
|
|
372
|
+
/**
|
|
373
|
+
* Determines if the value is a real element
|
|
374
|
+
*/
|
|
375
|
+
|
|
376
|
+
function isRealElement(value) {
|
|
377
|
+
return value instanceof Element;
|
|
378
|
+
}
|
|
379
|
+
/**
|
|
380
|
+
* Determines if the value is singular-like
|
|
381
|
+
*/
|
|
382
|
+
|
|
383
|
+
function isSingular(value) {
|
|
384
|
+
return !!(value && hasOwnProperty(value, 'isVirtual')) || isRealElement(value);
|
|
385
|
+
}
|
|
386
|
+
/**
|
|
387
|
+
* Firefox extensions don't allow setting .innerHTML directly, this will trick it
|
|
388
|
+
*/
|
|
389
|
+
|
|
390
|
+
function innerHTML() {
|
|
391
|
+
return 'innerHTML';
|
|
392
|
+
}
|
|
393
|
+
/**
|
|
394
|
+
* Evaluates a function if one, or returns the value
|
|
395
|
+
*/
|
|
396
|
+
|
|
397
|
+
function invokeWithArgsOrReturn(value, args) {
|
|
398
|
+
return typeof value === 'function' ? value.apply(null, args) : value;
|
|
399
|
+
}
|
|
400
|
+
/**
|
|
401
|
+
* Sets a popperInstance `flip` modifier's enabled state
|
|
402
|
+
*/
|
|
403
|
+
|
|
404
|
+
function setFlipModifierEnabled(modifiers, value) {
|
|
405
|
+
modifiers.filter(function (m) {
|
|
406
|
+
return m.name === 'flip';
|
|
407
|
+
})[0].enabled = value;
|
|
408
|
+
}
|
|
409
|
+
/**
|
|
410
|
+
* Determines if an element can receive focus
|
|
411
|
+
* Always returns true for virtual objects
|
|
412
|
+
*/
|
|
413
|
+
|
|
414
|
+
function canReceiveFocus(element) {
|
|
415
|
+
return isRealElement(element) ? matches.call(element, 'a[href],area[href],button,details,input,textarea,select,iframe,[tabindex]') && !element.hasAttribute('disabled') : true;
|
|
416
|
+
}
|
|
417
|
+
/**
|
|
418
|
+
* Returns a new `div` element
|
|
419
|
+
*/
|
|
420
|
+
|
|
421
|
+
function div() {
|
|
422
|
+
return document.createElement('div');
|
|
423
|
+
}
|
|
424
|
+
/**
|
|
425
|
+
* Applies a transition duration to a list of elements
|
|
426
|
+
*/
|
|
427
|
+
|
|
428
|
+
function setTransitionDuration(els, value) {
|
|
429
|
+
els.forEach(function (el) {
|
|
430
|
+
if (el) {
|
|
431
|
+
el.style.transitionDuration = "".concat(value, "ms");
|
|
432
|
+
}
|
|
433
|
+
});
|
|
434
|
+
}
|
|
435
|
+
/**
|
|
436
|
+
* Sets the visibility state to elements so they can begin to transition
|
|
437
|
+
*/
|
|
438
|
+
|
|
439
|
+
function setVisibilityState(els, state) {
|
|
440
|
+
els.forEach(function (el) {
|
|
441
|
+
if (el) {
|
|
442
|
+
el.setAttribute('data-state', state);
|
|
443
|
+
}
|
|
444
|
+
});
|
|
445
|
+
}
|
|
446
|
+
/**
|
|
447
|
+
* Evaluates the props object by merging data attributes and
|
|
448
|
+
* disabling conflicting options where necessary
|
|
449
|
+
*/
|
|
450
|
+
|
|
451
|
+
function evaluateProps(reference, props) {
|
|
452
|
+
var out = _extends({}, props, {
|
|
453
|
+
content: invokeWithArgsOrReturn(props.content, [reference])
|
|
454
|
+
}, props.ignoreAttributes ? {} : getDataAttributeOptions(reference));
|
|
455
|
+
|
|
456
|
+
if (out.arrow || isUCBrowser) {
|
|
457
|
+
out.animateFill = false;
|
|
458
|
+
}
|
|
459
|
+
|
|
460
|
+
return out;
|
|
461
|
+
}
|
|
462
|
+
/**
|
|
463
|
+
* Validates an object of options with the valid default props object
|
|
464
|
+
*/
|
|
465
|
+
|
|
466
|
+
function validateOptions(options, defaultProps) {
|
|
467
|
+
Object.keys(options).forEach(function (option) {
|
|
468
|
+
if (!hasOwnProperty(defaultProps, option)) {
|
|
469
|
+
throw new Error("[tippy]: `".concat(option, "` is not a valid option"));
|
|
470
|
+
}
|
|
471
|
+
});
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
/**
|
|
475
|
+
* Sets the innerHTML of an element
|
|
476
|
+
*/
|
|
477
|
+
|
|
478
|
+
function setInnerHTML(element, html) {
|
|
479
|
+
element[innerHTML()] = isRealElement(html) ? html[innerHTML()] : html;
|
|
480
|
+
}
|
|
481
|
+
/**
|
|
482
|
+
* Sets the content of a tooltip
|
|
483
|
+
*/
|
|
484
|
+
|
|
485
|
+
function setContent(contentEl, props) {
|
|
486
|
+
if (isRealElement(props.content)) {
|
|
487
|
+
setInnerHTML(contentEl, '');
|
|
488
|
+
contentEl.appendChild(props.content);
|
|
489
|
+
} else if (typeof props.content !== 'function') {
|
|
490
|
+
var key = props.allowHTML ? 'innerHTML' : 'textContent';
|
|
491
|
+
contentEl[key] = props.content;
|
|
492
|
+
}
|
|
493
|
+
}
|
|
494
|
+
/**
|
|
495
|
+
* Returns the child elements of a popper element
|
|
496
|
+
*/
|
|
497
|
+
|
|
498
|
+
function getChildren(popper) {
|
|
499
|
+
return {
|
|
500
|
+
tooltip: popper.querySelector(TOOLTIP_SELECTOR),
|
|
501
|
+
backdrop: popper.querySelector(BACKDROP_SELECTOR),
|
|
502
|
+
content: popper.querySelector(CONTENT_SELECTOR),
|
|
503
|
+
arrow: popper.querySelector(ARROW_SELECTOR) || popper.querySelector(ROUND_ARROW_SELECTOR)
|
|
504
|
+
};
|
|
505
|
+
}
|
|
506
|
+
/**
|
|
507
|
+
* Adds `data-inertia` attribute
|
|
508
|
+
*/
|
|
509
|
+
|
|
510
|
+
function addInertia(tooltip) {
|
|
511
|
+
tooltip.setAttribute('data-inertia', '');
|
|
512
|
+
}
|
|
513
|
+
/**
|
|
514
|
+
* Removes `data-inertia` attribute
|
|
515
|
+
*/
|
|
516
|
+
|
|
517
|
+
function removeInertia(tooltip) {
|
|
518
|
+
tooltip.removeAttribute('data-inertia');
|
|
519
|
+
}
|
|
520
|
+
/**
|
|
521
|
+
* Creates an arrow element and returns it
|
|
522
|
+
*/
|
|
523
|
+
|
|
524
|
+
function createArrowElement(arrowType) {
|
|
525
|
+
var arrow = div();
|
|
526
|
+
|
|
527
|
+
if (arrowType === 'round') {
|
|
528
|
+
arrow.className = ROUND_ARROW_CLASS;
|
|
529
|
+
setInnerHTML(arrow, '<svg viewBox="0 0 18 7" xmlns="http://www.w3.org/2000/svg"><path d="M0 7s2.021-.015 5.253-4.218C6.584 1.051 7.797.007 9 0c1.203-.007 2.416 1.035 3.761 2.782C16.012 7.005 18 7 18 7H0z"/></svg>');
|
|
530
|
+
} else {
|
|
531
|
+
arrow.className = ARROW_CLASS;
|
|
532
|
+
}
|
|
533
|
+
|
|
534
|
+
return arrow;
|
|
535
|
+
}
|
|
536
|
+
/**
|
|
537
|
+
* Creates a backdrop element and returns it
|
|
538
|
+
*/
|
|
539
|
+
|
|
540
|
+
function createBackdropElement() {
|
|
541
|
+
var backdrop = div();
|
|
542
|
+
backdrop.className = BACKDROP_CLASS;
|
|
543
|
+
backdrop.setAttribute('data-state', 'hidden');
|
|
544
|
+
return backdrop;
|
|
545
|
+
}
|
|
546
|
+
/**
|
|
547
|
+
* Adds interactive-related attributes
|
|
548
|
+
*/
|
|
549
|
+
|
|
550
|
+
function addInteractive(popper, tooltip) {
|
|
551
|
+
popper.setAttribute('tabindex', '-1');
|
|
552
|
+
tooltip.setAttribute('data-interactive', '');
|
|
553
|
+
}
|
|
554
|
+
/**
|
|
555
|
+
* Removes interactive-related attributes
|
|
556
|
+
*/
|
|
557
|
+
|
|
558
|
+
function removeInteractive(popper, tooltip) {
|
|
559
|
+
popper.removeAttribute('tabindex');
|
|
560
|
+
tooltip.removeAttribute('data-interactive');
|
|
561
|
+
}
|
|
562
|
+
/**
|
|
563
|
+
* Add/remove transitionend listener from tooltip
|
|
564
|
+
*/
|
|
565
|
+
|
|
566
|
+
function updateTransitionEndListener(tooltip, action, listener) {
|
|
567
|
+
// UC Browser hasn't adopted the `transitionend` event despite supporting
|
|
568
|
+
// unprefixed transitions...
|
|
569
|
+
var eventName = isUCBrowser && document.body.style.webkitTransition !== undefined ? 'webkitTransitionEnd' : 'transitionend';
|
|
570
|
+
tooltip[action + 'EventListener'](eventName, listener);
|
|
571
|
+
}
|
|
572
|
+
/**
|
|
573
|
+
* Returns the popper's placement, ignoring shifting (top-start, etc)
|
|
574
|
+
*/
|
|
575
|
+
|
|
576
|
+
function getBasicPlacement(popper) {
|
|
577
|
+
var fullPlacement = popper.getAttribute(PLACEMENT_ATTRIBUTE);
|
|
578
|
+
return fullPlacement ? fullPlacement.split('-')[0] : '';
|
|
579
|
+
}
|
|
580
|
+
/**
|
|
581
|
+
* Triggers reflow
|
|
582
|
+
*/
|
|
583
|
+
|
|
584
|
+
function reflow(popper) {
|
|
585
|
+
void popper.offsetHeight;
|
|
586
|
+
}
|
|
587
|
+
/**
|
|
588
|
+
* Adds/removes theme from tooltip's classList
|
|
589
|
+
*/
|
|
590
|
+
|
|
591
|
+
function updateTheme(tooltip, action, theme) {
|
|
592
|
+
theme.split(' ').forEach(function (themeName) {
|
|
593
|
+
tooltip.classList[action](themeName + '-theme');
|
|
594
|
+
});
|
|
595
|
+
}
|
|
596
|
+
/**
|
|
597
|
+
* Constructs the popper element and returns it
|
|
598
|
+
*/
|
|
599
|
+
|
|
600
|
+
function createPopperElement(id, props) {
|
|
601
|
+
var popper = div();
|
|
602
|
+
popper.className = POPPER_CLASS;
|
|
603
|
+
popper.id = "tippy-".concat(id);
|
|
604
|
+
popper.style.zIndex = '' + props.zIndex;
|
|
605
|
+
popper.style.position = 'absolute';
|
|
606
|
+
popper.style.top = '0';
|
|
607
|
+
popper.style.left = '0';
|
|
608
|
+
|
|
609
|
+
if (props.role) {
|
|
610
|
+
popper.setAttribute('role', props.role);
|
|
611
|
+
}
|
|
612
|
+
|
|
613
|
+
var tooltip = div();
|
|
614
|
+
tooltip.className = TOOLTIP_CLASS;
|
|
615
|
+
tooltip.style.maxWidth = props.maxWidth + (typeof props.maxWidth === 'number' ? 'px' : '');
|
|
616
|
+
tooltip.setAttribute('data-size', props.size);
|
|
617
|
+
tooltip.setAttribute('data-animation', props.animation);
|
|
618
|
+
tooltip.setAttribute('data-state', 'hidden');
|
|
619
|
+
updateTheme(tooltip, 'add', props.theme);
|
|
620
|
+
var content = div();
|
|
621
|
+
content.className = CONTENT_CLASS;
|
|
622
|
+
content.setAttribute('data-state', 'hidden');
|
|
623
|
+
|
|
624
|
+
if (props.interactive) {
|
|
625
|
+
addInteractive(popper, tooltip);
|
|
626
|
+
}
|
|
627
|
+
|
|
628
|
+
if (props.arrow) {
|
|
629
|
+
tooltip.appendChild(createArrowElement(props.arrowType));
|
|
630
|
+
}
|
|
631
|
+
|
|
632
|
+
if (props.animateFill) {
|
|
633
|
+
tooltip.appendChild(createBackdropElement());
|
|
634
|
+
tooltip.setAttribute('data-animatefill', '');
|
|
635
|
+
}
|
|
636
|
+
|
|
637
|
+
if (props.inertia) {
|
|
638
|
+
addInertia(tooltip);
|
|
639
|
+
}
|
|
640
|
+
|
|
641
|
+
setContent(content, props);
|
|
642
|
+
tooltip.appendChild(content);
|
|
643
|
+
popper.appendChild(tooltip);
|
|
644
|
+
return popper;
|
|
645
|
+
}
|
|
646
|
+
/**
|
|
647
|
+
* Updates the popper element based on the new props
|
|
648
|
+
*/
|
|
649
|
+
|
|
650
|
+
function updatePopperElement(popper, prevProps, nextProps) {
|
|
651
|
+
var _getChildren = getChildren(popper),
|
|
652
|
+
tooltip = _getChildren.tooltip,
|
|
653
|
+
content = _getChildren.content,
|
|
654
|
+
backdrop = _getChildren.backdrop,
|
|
655
|
+
arrow = _getChildren.arrow;
|
|
656
|
+
|
|
657
|
+
popper.style.zIndex = '' + nextProps.zIndex;
|
|
658
|
+
tooltip.setAttribute('data-size', nextProps.size);
|
|
659
|
+
tooltip.setAttribute('data-animation', nextProps.animation);
|
|
660
|
+
tooltip.style.maxWidth = nextProps.maxWidth + (typeof nextProps.maxWidth === 'number' ? 'px' : '');
|
|
661
|
+
|
|
662
|
+
if (nextProps.role) {
|
|
663
|
+
popper.setAttribute('role', nextProps.role);
|
|
664
|
+
} else {
|
|
665
|
+
popper.removeAttribute('role');
|
|
666
|
+
}
|
|
667
|
+
|
|
668
|
+
if (prevProps.content !== nextProps.content) {
|
|
669
|
+
setContent(content, nextProps);
|
|
670
|
+
} // animateFill
|
|
671
|
+
|
|
672
|
+
|
|
673
|
+
if (!prevProps.animateFill && nextProps.animateFill) {
|
|
674
|
+
tooltip.appendChild(createBackdropElement());
|
|
675
|
+
tooltip.setAttribute('data-animatefill', '');
|
|
676
|
+
} else if (prevProps.animateFill && !nextProps.animateFill) {
|
|
677
|
+
tooltip.removeChild(backdrop);
|
|
678
|
+
tooltip.removeAttribute('data-animatefill');
|
|
679
|
+
} // arrow
|
|
680
|
+
|
|
681
|
+
|
|
682
|
+
if (!prevProps.arrow && nextProps.arrow) {
|
|
683
|
+
tooltip.appendChild(createArrowElement(nextProps.arrowType));
|
|
684
|
+
} else if (prevProps.arrow && !nextProps.arrow) {
|
|
685
|
+
tooltip.removeChild(arrow);
|
|
686
|
+
} // arrowType
|
|
687
|
+
|
|
688
|
+
|
|
689
|
+
if (prevProps.arrow && nextProps.arrow && prevProps.arrowType !== nextProps.arrowType) {
|
|
690
|
+
tooltip.replaceChild(createArrowElement(nextProps.arrowType), arrow);
|
|
691
|
+
} // interactive
|
|
692
|
+
|
|
693
|
+
|
|
694
|
+
if (!prevProps.interactive && nextProps.interactive) {
|
|
695
|
+
addInteractive(popper, tooltip);
|
|
696
|
+
} else if (prevProps.interactive && !nextProps.interactive) {
|
|
697
|
+
removeInteractive(popper, tooltip);
|
|
698
|
+
} // inertia
|
|
699
|
+
|
|
700
|
+
|
|
701
|
+
if (!prevProps.inertia && nextProps.inertia) {
|
|
702
|
+
addInertia(tooltip);
|
|
703
|
+
} else if (prevProps.inertia && !nextProps.inertia) {
|
|
704
|
+
removeInertia(tooltip);
|
|
705
|
+
} // theme
|
|
706
|
+
|
|
707
|
+
|
|
708
|
+
if (prevProps.theme !== nextProps.theme) {
|
|
709
|
+
updateTheme(tooltip, 'remove', prevProps.theme);
|
|
710
|
+
updateTheme(tooltip, 'add', nextProps.theme);
|
|
711
|
+
}
|
|
712
|
+
}
|
|
713
|
+
/**
|
|
714
|
+
* Hides all visible poppers on the document
|
|
715
|
+
*/
|
|
716
|
+
|
|
717
|
+
function hideAll() {
|
|
718
|
+
var _ref = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {},
|
|
719
|
+
excludedReferenceOrInstance = _ref.exclude,
|
|
720
|
+
duration = _ref.duration;
|
|
721
|
+
|
|
722
|
+
arrayFrom(document.querySelectorAll(POPPER_SELECTOR)).forEach(function (popper) {
|
|
723
|
+
var instance = popper._tippy;
|
|
724
|
+
|
|
725
|
+
if (instance) {
|
|
726
|
+
var isExcluded = false;
|
|
727
|
+
|
|
728
|
+
if (excludedReferenceOrInstance) {
|
|
729
|
+
isExcluded = isReferenceElement(excludedReferenceOrInstance) ? instance.reference === excludedReferenceOrInstance : popper === excludedReferenceOrInstance.popper;
|
|
730
|
+
}
|
|
731
|
+
|
|
732
|
+
if (!isExcluded) {
|
|
733
|
+
instance.hide(duration);
|
|
734
|
+
}
|
|
735
|
+
}
|
|
736
|
+
});
|
|
737
|
+
}
|
|
738
|
+
/**
|
|
739
|
+
* Determines if the mouse cursor is outside of the popper's interactive border
|
|
740
|
+
* region
|
|
741
|
+
*/
|
|
742
|
+
|
|
743
|
+
function isCursorOutsideInteractiveBorder(popperPlacement, popperRect, event, props) {
|
|
744
|
+
if (!popperPlacement) {
|
|
745
|
+
return true;
|
|
746
|
+
}
|
|
747
|
+
|
|
748
|
+
var x = event.clientX,
|
|
749
|
+
y = event.clientY;
|
|
750
|
+
var interactiveBorder = props.interactiveBorder,
|
|
751
|
+
distance = props.distance;
|
|
752
|
+
var exceedsTop = popperRect.top - y > (popperPlacement === 'top' ? interactiveBorder + distance : interactiveBorder);
|
|
753
|
+
var exceedsBottom = y - popperRect.bottom > (popperPlacement === 'bottom' ? interactiveBorder + distance : interactiveBorder);
|
|
754
|
+
var exceedsLeft = popperRect.left - x > (popperPlacement === 'left' ? interactiveBorder + distance : interactiveBorder);
|
|
755
|
+
var exceedsRight = x - popperRect.right > (popperPlacement === 'right' ? interactiveBorder + distance : interactiveBorder);
|
|
756
|
+
return exceedsTop || exceedsBottom || exceedsLeft || exceedsRight;
|
|
757
|
+
}
|
|
758
|
+
/**
|
|
759
|
+
* Returns the distance offset, taking into account the default offset due to
|
|
760
|
+
* the transform: translate() rule (10px) in CSS
|
|
761
|
+
*/
|
|
762
|
+
|
|
763
|
+
function getOffsetDistanceInPx(distance) {
|
|
764
|
+
return -(distance - 10) + 'px';
|
|
765
|
+
}
|
|
766
|
+
|
|
767
|
+
var idCounter = 1; // Workaround for IE11's lack of new MouseEvent constructor
|
|
768
|
+
|
|
769
|
+
var mouseMoveListeners = [];
|
|
770
|
+
/**
|
|
771
|
+
* Creates and returns a Tippy object. We're using a closure pattern instead of
|
|
772
|
+
* a class so that the exposed object API is clean without private members
|
|
773
|
+
* prefixed with `_`.
|
|
774
|
+
*/
|
|
775
|
+
|
|
776
|
+
function createTippy(reference, collectionProps) {
|
|
777
|
+
var props = evaluateProps(reference, collectionProps); // If the reference shouldn't have multiple tippys, return null early
|
|
778
|
+
|
|
779
|
+
if (!props.multiple && reference._tippy) {
|
|
780
|
+
return null;
|
|
781
|
+
}
|
|
782
|
+
/* ======================= 🔒 Private members 🔒 ======================= */
|
|
783
|
+
|
|
784
|
+
|
|
785
|
+
var lastTriggerEventType;
|
|
786
|
+
var lastMouseMoveEvent;
|
|
787
|
+
var showTimeoutId;
|
|
788
|
+
var hideTimeoutId;
|
|
789
|
+
var scheduleHideAnimationFrameId;
|
|
790
|
+
var isScheduledToShow = false;
|
|
791
|
+
var isBeingDestroyed = false;
|
|
792
|
+
var previousPlacement;
|
|
793
|
+
var wasVisibleDuringPreviousUpdate = false;
|
|
794
|
+
var hasMountCallbackRun = false;
|
|
795
|
+
var currentMountCallback;
|
|
796
|
+
var currentTransitionEndListener;
|
|
797
|
+
var listeners = [];
|
|
798
|
+
var currentComputedPadding;
|
|
799
|
+
var debouncedOnMouseMove = debounce(onMouseMove, props.interactiveDebounce);
|
|
800
|
+
/* ======================= 🔑 Public members 🔑 ======================= */
|
|
801
|
+
|
|
802
|
+
var id = idCounter++;
|
|
803
|
+
var popper = createPopperElement(id, props);
|
|
804
|
+
var popperChildren = getChildren(popper);
|
|
805
|
+
var popperInstance = null;
|
|
806
|
+
var state = {
|
|
807
|
+
// Is the instance currently enabled?
|
|
808
|
+
isEnabled: true,
|
|
809
|
+
// Is the tippy currently showing and not transitioning out?
|
|
810
|
+
isVisible: false,
|
|
811
|
+
// Has the instance been destroyed?
|
|
812
|
+
isDestroyed: false,
|
|
813
|
+
// Is the tippy currently mounted to the DOM?
|
|
814
|
+
isMounted: false,
|
|
815
|
+
// Has the tippy finished transitioning in?
|
|
816
|
+
isShown: false
|
|
817
|
+
};
|
|
818
|
+
var instance = {
|
|
819
|
+
// properties
|
|
820
|
+
id: id,
|
|
821
|
+
reference: reference,
|
|
822
|
+
popper: popper,
|
|
823
|
+
popperChildren: popperChildren,
|
|
824
|
+
popperInstance: popperInstance,
|
|
825
|
+
props: props,
|
|
826
|
+
state: state,
|
|
827
|
+
// methods
|
|
828
|
+
clearDelayTimeouts: clearDelayTimeouts,
|
|
829
|
+
set: set,
|
|
830
|
+
setContent: setContent,
|
|
831
|
+
show: show,
|
|
832
|
+
hide: hide,
|
|
833
|
+
enable: enable,
|
|
834
|
+
disable: disable,
|
|
835
|
+
destroy: destroy
|
|
836
|
+
/* ==================== Initial instance mutations =================== */
|
|
837
|
+
|
|
838
|
+
};
|
|
839
|
+
reference._tippy = instance;
|
|
840
|
+
popper._tippy = instance;
|
|
841
|
+
addTriggersToReference();
|
|
842
|
+
|
|
843
|
+
if (!props.lazy) {
|
|
844
|
+
createPopperInstance();
|
|
845
|
+
}
|
|
846
|
+
|
|
847
|
+
if (props.showOnInit) {
|
|
848
|
+
scheduleShow();
|
|
849
|
+
} // Ensure the event listeners target can receive focus
|
|
850
|
+
|
|
851
|
+
|
|
852
|
+
if (props.a11y && !props.target && !canReceiveFocus(getEventListenersTarget())) {
|
|
853
|
+
getEventListenersTarget().setAttribute('tabindex', '0');
|
|
854
|
+
} // Prevent a tippy with a delay from hiding if the cursor left then returned
|
|
855
|
+
// before it started hiding
|
|
856
|
+
|
|
857
|
+
|
|
858
|
+
popper.addEventListener('mouseenter', function (event) {
|
|
859
|
+
if (instance.props.interactive && instance.state.isVisible && lastTriggerEventType === 'mouseenter') {
|
|
860
|
+
// We don't want props.onTrigger() to be called here, since the `event`
|
|
861
|
+
// object is not related to the reference element
|
|
862
|
+
scheduleShow(event, true);
|
|
863
|
+
}
|
|
864
|
+
});
|
|
865
|
+
popper.addEventListener('mouseleave', function () {
|
|
866
|
+
if (instance.props.interactive && lastTriggerEventType === 'mouseenter') {
|
|
867
|
+
document.addEventListener('mousemove', debouncedOnMouseMove);
|
|
868
|
+
}
|
|
869
|
+
});
|
|
870
|
+
return instance;
|
|
871
|
+
/* ======================= 🔒 Private methods 🔒 ======================= */
|
|
872
|
+
|
|
873
|
+
/**
|
|
874
|
+
* Removes the follow cursor listener
|
|
875
|
+
*/
|
|
876
|
+
|
|
877
|
+
function removeFollowCursorListener() {
|
|
878
|
+
document.removeEventListener('mousemove', positionVirtualReferenceNearCursor);
|
|
879
|
+
}
|
|
880
|
+
/**
|
|
881
|
+
* Cleans up interactive mouse listeners
|
|
882
|
+
*/
|
|
883
|
+
|
|
884
|
+
|
|
885
|
+
function cleanupInteractiveMouseListeners() {
|
|
886
|
+
document.body.removeEventListener('mouseleave', scheduleHide);
|
|
887
|
+
document.removeEventListener('mousemove', debouncedOnMouseMove);
|
|
888
|
+
mouseMoveListeners = mouseMoveListeners.filter(function (listener) {
|
|
889
|
+
return listener !== debouncedOnMouseMove;
|
|
890
|
+
});
|
|
891
|
+
}
|
|
892
|
+
/**
|
|
893
|
+
* Returns correct target used for event listeners
|
|
894
|
+
*/
|
|
895
|
+
|
|
896
|
+
|
|
897
|
+
function getEventListenersTarget() {
|
|
898
|
+
return instance.props.triggerTarget || reference;
|
|
899
|
+
}
|
|
900
|
+
/**
|
|
901
|
+
* Adds the document click event listener for the instance
|
|
902
|
+
*/
|
|
903
|
+
|
|
904
|
+
|
|
905
|
+
function addDocumentClickListener() {
|
|
906
|
+
document.addEventListener('click', onDocumentClick, true);
|
|
907
|
+
}
|
|
908
|
+
/**
|
|
909
|
+
* Removes the document click event listener for the instance
|
|
910
|
+
*/
|
|
911
|
+
|
|
912
|
+
|
|
913
|
+
function removeDocumentClickListener() {
|
|
914
|
+
document.removeEventListener('click', onDocumentClick, true);
|
|
915
|
+
}
|
|
916
|
+
/**
|
|
917
|
+
* Returns transitionable inner elements used in show/hide methods
|
|
918
|
+
*/
|
|
919
|
+
|
|
920
|
+
|
|
921
|
+
function getTransitionableElements() {
|
|
922
|
+
return [instance.popperChildren.tooltip, instance.popperChildren.backdrop, instance.popperChildren.content];
|
|
923
|
+
}
|
|
924
|
+
/**
|
|
925
|
+
* Determines if the instance is in `followCursor` mode.
|
|
926
|
+
* NOTE: in v5, touch devices will use `initial` behavior no matter the value.
|
|
927
|
+
*/
|
|
928
|
+
|
|
929
|
+
|
|
930
|
+
function getIsInLooseFollowCursorMode() {
|
|
931
|
+
var followCursor = instance.props.followCursor;
|
|
932
|
+
return followCursor && lastTriggerEventType !== 'focus' || isUsingTouch && followCursor === 'initial';
|
|
933
|
+
}
|
|
934
|
+
/**
|
|
935
|
+
* Updates the tooltip's position on each animation frame
|
|
936
|
+
*/
|
|
937
|
+
|
|
938
|
+
|
|
939
|
+
function makeSticky() {
|
|
940
|
+
setTransitionDuration([popper], isIE ? 0 : instance.props.updateDuration);
|
|
941
|
+
|
|
942
|
+
function updatePosition() {
|
|
943
|
+
instance.popperInstance.scheduleUpdate();
|
|
944
|
+
|
|
945
|
+
if (instance.state.isMounted) {
|
|
946
|
+
requestAnimationFrame(updatePosition);
|
|
947
|
+
} else {
|
|
948
|
+
setTransitionDuration([popper], 0);
|
|
949
|
+
}
|
|
950
|
+
}
|
|
951
|
+
|
|
952
|
+
updatePosition();
|
|
953
|
+
}
|
|
954
|
+
/**
|
|
955
|
+
* Invokes a callback once the tooltip has fully transitioned out
|
|
956
|
+
*/
|
|
957
|
+
|
|
958
|
+
|
|
959
|
+
function onTransitionedOut(duration, callback) {
|
|
960
|
+
onTransitionEnd(duration, function () {
|
|
961
|
+
if (!instance.state.isVisible && popper.parentNode && popper.parentNode.contains(popper)) {
|
|
962
|
+
callback();
|
|
963
|
+
}
|
|
964
|
+
});
|
|
965
|
+
}
|
|
966
|
+
/**
|
|
967
|
+
* Invokes a callback once the tooltip has fully transitioned in
|
|
968
|
+
*/
|
|
969
|
+
|
|
970
|
+
|
|
971
|
+
function onTransitionedIn(duration, callback) {
|
|
972
|
+
onTransitionEnd(duration, callback);
|
|
973
|
+
}
|
|
974
|
+
/**
|
|
975
|
+
* Invokes a callback once the tooltip's CSS transition ends
|
|
976
|
+
*/
|
|
977
|
+
|
|
978
|
+
|
|
979
|
+
function onTransitionEnd(duration, callback) {
|
|
980
|
+
var tooltip = instance.popperChildren.tooltip;
|
|
981
|
+
/**
|
|
982
|
+
* Listener added as the `transitionend` handler
|
|
983
|
+
*/
|
|
984
|
+
|
|
985
|
+
function listener(event) {
|
|
986
|
+
if (event.target === tooltip) {
|
|
987
|
+
updateTransitionEndListener(tooltip, 'remove', listener);
|
|
988
|
+
callback();
|
|
989
|
+
}
|
|
990
|
+
} // Make callback synchronous if duration is 0
|
|
991
|
+
// `transitionend` won't fire otherwise
|
|
992
|
+
|
|
993
|
+
|
|
994
|
+
if (duration === 0) {
|
|
995
|
+
return callback();
|
|
996
|
+
}
|
|
997
|
+
|
|
998
|
+
updateTransitionEndListener(tooltip, 'remove', currentTransitionEndListener);
|
|
999
|
+
updateTransitionEndListener(tooltip, 'add', listener);
|
|
1000
|
+
currentTransitionEndListener = listener;
|
|
1001
|
+
}
|
|
1002
|
+
/**
|
|
1003
|
+
* Adds an event listener to the reference and stores it in `listeners`
|
|
1004
|
+
*/
|
|
1005
|
+
|
|
1006
|
+
|
|
1007
|
+
function on(eventType, handler) {
|
|
1008
|
+
var options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : false;
|
|
1009
|
+
getEventListenersTarget().addEventListener(eventType, handler, options);
|
|
1010
|
+
listeners.push({
|
|
1011
|
+
eventType: eventType,
|
|
1012
|
+
handler: handler,
|
|
1013
|
+
options: options
|
|
1014
|
+
});
|
|
1015
|
+
}
|
|
1016
|
+
/**
|
|
1017
|
+
* Adds event listeners to the reference based on the `trigger` prop
|
|
1018
|
+
*/
|
|
1019
|
+
|
|
1020
|
+
|
|
1021
|
+
function addTriggersToReference() {
|
|
1022
|
+
if (instance.props.touchHold && !instance.props.target) {
|
|
1023
|
+
on('touchstart', onTrigger, PASSIVE);
|
|
1024
|
+
on('touchend', onMouseLeave, PASSIVE);
|
|
1025
|
+
}
|
|
1026
|
+
|
|
1027
|
+
instance.props.trigger.trim().split(' ').forEach(function (eventType) {
|
|
1028
|
+
if (eventType === 'manual') {
|
|
1029
|
+
return;
|
|
1030
|
+
} // Non-delegates
|
|
1031
|
+
|
|
1032
|
+
|
|
1033
|
+
if (!instance.props.target) {
|
|
1034
|
+
on(eventType, onTrigger);
|
|
1035
|
+
|
|
1036
|
+
switch (eventType) {
|
|
1037
|
+
case 'mouseenter':
|
|
1038
|
+
on('mouseleave', onMouseLeave);
|
|
1039
|
+
break;
|
|
1040
|
+
|
|
1041
|
+
case 'focus':
|
|
1042
|
+
on(isIE ? 'focusout' : 'blur', onBlur);
|
|
1043
|
+
break;
|
|
1044
|
+
}
|
|
1045
|
+
} else {
|
|
1046
|
+
// Delegates
|
|
1047
|
+
switch (eventType) {
|
|
1048
|
+
case 'mouseenter':
|
|
1049
|
+
on('mouseover', onDelegateShow);
|
|
1050
|
+
on('mouseout', onDelegateHide);
|
|
1051
|
+
break;
|
|
1052
|
+
|
|
1053
|
+
case 'focus':
|
|
1054
|
+
on('focusin', onDelegateShow);
|
|
1055
|
+
on('focusout', onDelegateHide);
|
|
1056
|
+
break;
|
|
1057
|
+
|
|
1058
|
+
case 'click':
|
|
1059
|
+
on(eventType, onDelegateShow);
|
|
1060
|
+
break;
|
|
1061
|
+
}
|
|
1062
|
+
}
|
|
1063
|
+
});
|
|
1064
|
+
}
|
|
1065
|
+
/**
|
|
1066
|
+
* Removes event listeners from the reference
|
|
1067
|
+
*/
|
|
1068
|
+
|
|
1069
|
+
|
|
1070
|
+
function removeTriggersFromReference() {
|
|
1071
|
+
listeners.forEach(function (_ref) {
|
|
1072
|
+
var eventType = _ref.eventType,
|
|
1073
|
+
handler = _ref.handler,
|
|
1074
|
+
options = _ref.options;
|
|
1075
|
+
getEventListenersTarget().removeEventListener(eventType, handler, options);
|
|
1076
|
+
});
|
|
1077
|
+
listeners = [];
|
|
1078
|
+
}
|
|
1079
|
+
/**
|
|
1080
|
+
* Positions the virtual reference near the cursor
|
|
1081
|
+
*/
|
|
1082
|
+
|
|
1083
|
+
|
|
1084
|
+
function positionVirtualReferenceNearCursor(event) {
|
|
1085
|
+
var _lastMouseMoveEvent = lastMouseMoveEvent = event,
|
|
1086
|
+
x = _lastMouseMoveEvent.clientX,
|
|
1087
|
+
y = _lastMouseMoveEvent.clientY; // Gets set once popperInstance `onCreate` has been called
|
|
1088
|
+
|
|
1089
|
+
|
|
1090
|
+
if (!currentComputedPadding) {
|
|
1091
|
+
return;
|
|
1092
|
+
} // If the instance is interactive, avoid updating the position unless it's
|
|
1093
|
+
// over the reference element
|
|
1094
|
+
|
|
1095
|
+
|
|
1096
|
+
var isCursorOverReference = closestCallback(event.target, function (el) {
|
|
1097
|
+
return el === reference;
|
|
1098
|
+
});
|
|
1099
|
+
var rect = reference.getBoundingClientRect();
|
|
1100
|
+
var followCursor = instance.props.followCursor;
|
|
1101
|
+
var isHorizontal = followCursor === 'horizontal';
|
|
1102
|
+
var isVertical = followCursor === 'vertical'; // The virtual reference needs some size to prevent itself from overflowing
|
|
1103
|
+
|
|
1104
|
+
var isVerticalPlacement = includes(['top', 'bottom'], getBasicPlacement(popper));
|
|
1105
|
+
var fullPlacement = popper.getAttribute(PLACEMENT_ATTRIBUTE);
|
|
1106
|
+
var isVariation = fullPlacement ? !!fullPlacement.split('-')[1] : false;
|
|
1107
|
+
var size = isVerticalPlacement ? popper.offsetWidth : popper.offsetHeight;
|
|
1108
|
+
var halfSize = size / 2;
|
|
1109
|
+
var verticalIncrease = isVerticalPlacement ? 0 : isVariation ? size : halfSize;
|
|
1110
|
+
var horizontalIncrease = isVerticalPlacement ? isVariation ? size : halfSize : 0;
|
|
1111
|
+
|
|
1112
|
+
if (isCursorOverReference || !instance.props.interactive) {
|
|
1113
|
+
instance.popperInstance.reference = _extends({}, instance.popperInstance.reference, {
|
|
1114
|
+
// These `client` values don't get used by Popper.js if they are 0
|
|
1115
|
+
clientWidth: 0,
|
|
1116
|
+
clientHeight: 0,
|
|
1117
|
+
getBoundingClientRect: function getBoundingClientRect() {
|
|
1118
|
+
return {
|
|
1119
|
+
width: isVerticalPlacement ? size : 0,
|
|
1120
|
+
height: isVerticalPlacement ? 0 : size,
|
|
1121
|
+
top: (isHorizontal ? rect.top : y) - verticalIncrease,
|
|
1122
|
+
bottom: (isHorizontal ? rect.bottom : y) + verticalIncrease,
|
|
1123
|
+
left: (isVertical ? rect.left : x) - horizontalIncrease,
|
|
1124
|
+
right: (isVertical ? rect.right : x) + horizontalIncrease
|
|
1125
|
+
};
|
|
1126
|
+
}
|
|
1127
|
+
});
|
|
1128
|
+
instance.popperInstance.update();
|
|
1129
|
+
}
|
|
1130
|
+
|
|
1131
|
+
if (followCursor === 'initial' && instance.state.isVisible) {
|
|
1132
|
+
removeFollowCursorListener();
|
|
1133
|
+
}
|
|
1134
|
+
}
|
|
1135
|
+
/**
|
|
1136
|
+
* Creates the tippy instance for a delegate when it's been triggered
|
|
1137
|
+
*/
|
|
1138
|
+
|
|
1139
|
+
|
|
1140
|
+
function createDelegateChildTippy(event) {
|
|
1141
|
+
if (event) {
|
|
1142
|
+
var targetEl = closest(event.target, instance.props.target);
|
|
1143
|
+
|
|
1144
|
+
if (targetEl && !targetEl._tippy) {
|
|
1145
|
+
createTippy(targetEl, _extends({}, instance.props, {
|
|
1146
|
+
content: invokeWithArgsOrReturn(collectionProps.content, [targetEl]),
|
|
1147
|
+
appendTo: collectionProps.appendTo,
|
|
1148
|
+
target: '',
|
|
1149
|
+
showOnInit: true
|
|
1150
|
+
}));
|
|
1151
|
+
}
|
|
1152
|
+
}
|
|
1153
|
+
}
|
|
1154
|
+
/**
|
|
1155
|
+
* Event listener invoked upon trigger
|
|
1156
|
+
*/
|
|
1157
|
+
|
|
1158
|
+
|
|
1159
|
+
function onTrigger(event) {
|
|
1160
|
+
if (!instance.state.isEnabled || isEventListenerStopped(event)) {
|
|
1161
|
+
return;
|
|
1162
|
+
}
|
|
1163
|
+
|
|
1164
|
+
if (!instance.state.isVisible) {
|
|
1165
|
+
lastTriggerEventType = event.type;
|
|
1166
|
+
|
|
1167
|
+
if (event instanceof MouseEvent) {
|
|
1168
|
+
lastMouseMoveEvent = event; // If scrolling, `mouseenter` events can be fired if the cursor lands
|
|
1169
|
+
// over a new target, but `mousemove` events don't get fired. This
|
|
1170
|
+
// causes interactive tooltips to get stuck open until the cursor is
|
|
1171
|
+
// moved
|
|
1172
|
+
|
|
1173
|
+
mouseMoveListeners.forEach(function (listener) {
|
|
1174
|
+
return listener(event);
|
|
1175
|
+
});
|
|
1176
|
+
}
|
|
1177
|
+
} // Toggle show/hide when clicking click-triggered tooltips
|
|
1178
|
+
|
|
1179
|
+
|
|
1180
|
+
if (event.type === 'click' && instance.props.hideOnClick !== false && instance.state.isVisible) {
|
|
1181
|
+
scheduleHide();
|
|
1182
|
+
} else {
|
|
1183
|
+
scheduleShow(event);
|
|
1184
|
+
}
|
|
1185
|
+
}
|
|
1186
|
+
/**
|
|
1187
|
+
* Event listener used for interactive tooltips to detect when they should
|
|
1188
|
+
* hide
|
|
1189
|
+
*/
|
|
1190
|
+
|
|
1191
|
+
|
|
1192
|
+
function onMouseMove(event) {
|
|
1193
|
+
var isCursorOverPopper = closest(event.target, POPPER_SELECTOR) === popper;
|
|
1194
|
+
var isCursorOverReference = closestCallback(event.target, function (el) {
|
|
1195
|
+
return el === reference;
|
|
1196
|
+
});
|
|
1197
|
+
|
|
1198
|
+
if (isCursorOverPopper || isCursorOverReference) {
|
|
1199
|
+
return;
|
|
1200
|
+
}
|
|
1201
|
+
|
|
1202
|
+
if (isCursorOutsideInteractiveBorder(getBasicPlacement(popper), popper.getBoundingClientRect(), event, instance.props)) {
|
|
1203
|
+
cleanupInteractiveMouseListeners();
|
|
1204
|
+
scheduleHide();
|
|
1205
|
+
}
|
|
1206
|
+
}
|
|
1207
|
+
/**
|
|
1208
|
+
* Event listener invoked upon mouseleave
|
|
1209
|
+
*/
|
|
1210
|
+
|
|
1211
|
+
|
|
1212
|
+
function onMouseLeave(event) {
|
|
1213
|
+
if (isEventListenerStopped(event)) {
|
|
1214
|
+
return;
|
|
1215
|
+
}
|
|
1216
|
+
|
|
1217
|
+
if (instance.props.interactive) {
|
|
1218
|
+
document.body.addEventListener('mouseleave', scheduleHide);
|
|
1219
|
+
document.addEventListener('mousemove', debouncedOnMouseMove);
|
|
1220
|
+
mouseMoveListeners.push(debouncedOnMouseMove);
|
|
1221
|
+
return;
|
|
1222
|
+
}
|
|
1223
|
+
|
|
1224
|
+
scheduleHide();
|
|
1225
|
+
}
|
|
1226
|
+
/**
|
|
1227
|
+
* Event listener invoked upon blur
|
|
1228
|
+
*/
|
|
1229
|
+
|
|
1230
|
+
|
|
1231
|
+
function onBlur(event) {
|
|
1232
|
+
if (event.target !== getEventListenersTarget()) {
|
|
1233
|
+
return;
|
|
1234
|
+
}
|
|
1235
|
+
|
|
1236
|
+
if (instance.props.interactive && event.relatedTarget && popper.contains(event.relatedTarget)) {
|
|
1237
|
+
return;
|
|
1238
|
+
}
|
|
1239
|
+
|
|
1240
|
+
scheduleHide();
|
|
1241
|
+
}
|
|
1242
|
+
/**
|
|
1243
|
+
* Event listener invoked when a child target is triggered
|
|
1244
|
+
*/
|
|
1245
|
+
|
|
1246
|
+
|
|
1247
|
+
function onDelegateShow(event) {
|
|
1248
|
+
if (closest(event.target, instance.props.target)) {
|
|
1249
|
+
scheduleShow(event);
|
|
1250
|
+
}
|
|
1251
|
+
}
|
|
1252
|
+
/**
|
|
1253
|
+
* Event listener invoked when a child target should hide
|
|
1254
|
+
*/
|
|
1255
|
+
|
|
1256
|
+
|
|
1257
|
+
function onDelegateHide(event) {
|
|
1258
|
+
if (closest(event.target, instance.props.target)) {
|
|
1259
|
+
scheduleHide();
|
|
1260
|
+
}
|
|
1261
|
+
}
|
|
1262
|
+
/**
|
|
1263
|
+
* Determines if an event listener should stop further execution due to the
|
|
1264
|
+
* `touchHold` option
|
|
1265
|
+
*/
|
|
1266
|
+
|
|
1267
|
+
|
|
1268
|
+
function isEventListenerStopped(event) {
|
|
1269
|
+
var supportsTouch = 'ontouchstart' in window;
|
|
1270
|
+
var isTouchEvent = includes(event.type, 'touch');
|
|
1271
|
+
var touchHold = instance.props.touchHold;
|
|
1272
|
+
return supportsTouch && isUsingTouch && touchHold && !isTouchEvent || isUsingTouch && !touchHold && isTouchEvent;
|
|
1273
|
+
}
|
|
1274
|
+
/**
|
|
1275
|
+
* Runs the mount callback
|
|
1276
|
+
*/
|
|
1277
|
+
|
|
1278
|
+
|
|
1279
|
+
function runMountCallback() {
|
|
1280
|
+
if (!hasMountCallbackRun && currentMountCallback) {
|
|
1281
|
+
hasMountCallbackRun = true;
|
|
1282
|
+
reflow(popper);
|
|
1283
|
+
currentMountCallback();
|
|
1284
|
+
}
|
|
1285
|
+
}
|
|
1286
|
+
/**
|
|
1287
|
+
* Creates the popper instance for the instance
|
|
1288
|
+
*/
|
|
1289
|
+
|
|
1290
|
+
|
|
1291
|
+
function createPopperInstance() {
|
|
1292
|
+
var popperOptions = instance.props.popperOptions;
|
|
1293
|
+
var _instance$popperChild = instance.popperChildren,
|
|
1294
|
+
tooltip = _instance$popperChild.tooltip,
|
|
1295
|
+
arrow = _instance$popperChild.arrow;
|
|
1296
|
+
var preventOverflowModifier = getModifier(popperOptions, 'preventOverflow');
|
|
1297
|
+
|
|
1298
|
+
function applyMutations(data) {
|
|
1299
|
+
if (instance.props.flip && !instance.props.flipOnUpdate) {
|
|
1300
|
+
if (data.flipped) {
|
|
1301
|
+
instance.popperInstance.options.placement = data.placement;
|
|
1302
|
+
}
|
|
1303
|
+
|
|
1304
|
+
setFlipModifierEnabled(instance.popperInstance.modifiers, false);
|
|
1305
|
+
} // Apply all of the popper's attributes to the tootip node as well.
|
|
1306
|
+
// Allows users to avoid using the .tippy-popper selector for themes.
|
|
1307
|
+
|
|
1308
|
+
|
|
1309
|
+
tooltip.setAttribute(PLACEMENT_ATTRIBUTE, data.placement);
|
|
1310
|
+
|
|
1311
|
+
if (data.attributes[OUT_OF_BOUNDARIES_ATTRIBUTE] !== false) {
|
|
1312
|
+
tooltip.setAttribute(OUT_OF_BOUNDARIES_ATTRIBUTE, '');
|
|
1313
|
+
} else {
|
|
1314
|
+
tooltip.removeAttribute(OUT_OF_BOUNDARIES_ATTRIBUTE);
|
|
1315
|
+
} // Prevents a transition when changing placements (while tippy is visible)
|
|
1316
|
+
// for scroll/resize updates
|
|
1317
|
+
|
|
1318
|
+
|
|
1319
|
+
if (previousPlacement && previousPlacement !== data.placement && wasVisibleDuringPreviousUpdate) {
|
|
1320
|
+
tooltip.style.transition = 'none';
|
|
1321
|
+
requestAnimationFrame(function () {
|
|
1322
|
+
tooltip.style.transition = '';
|
|
1323
|
+
});
|
|
1324
|
+
}
|
|
1325
|
+
|
|
1326
|
+
previousPlacement = data.placement;
|
|
1327
|
+
wasVisibleDuringPreviousUpdate = instance.state.isVisible;
|
|
1328
|
+
var basicPlacement = getBasicPlacement(popper);
|
|
1329
|
+
var styles = tooltip.style; // Account for the `distance` offset
|
|
1330
|
+
|
|
1331
|
+
styles.top = styles.bottom = styles.left = styles.right = '';
|
|
1332
|
+
styles[basicPlacement] = getOffsetDistanceInPx(instance.props.distance);
|
|
1333
|
+
var padding = preventOverflowModifier && preventOverflowModifier.padding !== undefined ? preventOverflowModifier.padding : PADDING;
|
|
1334
|
+
var isPaddingNumber = typeof padding === 'number';
|
|
1335
|
+
|
|
1336
|
+
var computedPadding = _extends({
|
|
1337
|
+
top: isPaddingNumber ? padding : padding.top,
|
|
1338
|
+
bottom: isPaddingNumber ? padding : padding.bottom,
|
|
1339
|
+
left: isPaddingNumber ? padding : padding.left,
|
|
1340
|
+
right: isPaddingNumber ? padding : padding.right
|
|
1341
|
+
}, !isPaddingNumber && padding);
|
|
1342
|
+
|
|
1343
|
+
computedPadding[basicPlacement] = isPaddingNumber ? padding + instance.props.distance : (padding[basicPlacement] || 0) + instance.props.distance;
|
|
1344
|
+
instance.popperInstance.modifiers.filter(function (m) {
|
|
1345
|
+
return m.name === 'preventOverflow';
|
|
1346
|
+
})[0].padding = computedPadding;
|
|
1347
|
+
currentComputedPadding = computedPadding;
|
|
1348
|
+
}
|
|
1349
|
+
|
|
1350
|
+
var config = _extends({
|
|
1351
|
+
eventsEnabled: false,
|
|
1352
|
+
placement: instance.props.placement
|
|
1353
|
+
}, popperOptions, {
|
|
1354
|
+
modifiers: _extends({}, popperOptions ? popperOptions.modifiers : {}, {
|
|
1355
|
+
preventOverflow: _extends({
|
|
1356
|
+
boundariesElement: instance.props.boundary,
|
|
1357
|
+
padding: PADDING
|
|
1358
|
+
}, preventOverflowModifier),
|
|
1359
|
+
arrow: _extends({
|
|
1360
|
+
element: arrow,
|
|
1361
|
+
enabled: !!arrow
|
|
1362
|
+
}, getModifier(popperOptions, 'arrow')),
|
|
1363
|
+
flip: _extends({
|
|
1364
|
+
enabled: instance.props.flip,
|
|
1365
|
+
// The tooltip is offset by 10px from the popper in CSS,
|
|
1366
|
+
// we need to account for its distance
|
|
1367
|
+
padding: instance.props.distance + PADDING,
|
|
1368
|
+
behavior: instance.props.flipBehavior
|
|
1369
|
+
}, getModifier(popperOptions, 'flip')),
|
|
1370
|
+
offset: _extends({
|
|
1371
|
+
offset: instance.props.offset
|
|
1372
|
+
}, getModifier(popperOptions, 'offset'))
|
|
1373
|
+
}),
|
|
1374
|
+
onCreate: function onCreate(data) {
|
|
1375
|
+
applyMutations(data);
|
|
1376
|
+
runMountCallback();
|
|
1377
|
+
|
|
1378
|
+
if (popperOptions && popperOptions.onCreate) {
|
|
1379
|
+
popperOptions.onCreate(data);
|
|
1380
|
+
}
|
|
1381
|
+
},
|
|
1382
|
+
onUpdate: function onUpdate(data) {
|
|
1383
|
+
applyMutations(data);
|
|
1384
|
+
runMountCallback();
|
|
1385
|
+
|
|
1386
|
+
if (popperOptions && popperOptions.onUpdate) {
|
|
1387
|
+
popperOptions.onUpdate(data);
|
|
1388
|
+
}
|
|
1389
|
+
}
|
|
1390
|
+
});
|
|
1391
|
+
|
|
1392
|
+
instance.popperInstance = new Popper(reference, popper, config);
|
|
1393
|
+
}
|
|
1394
|
+
/**
|
|
1395
|
+
* Mounts the tooltip to the DOM
|
|
1396
|
+
*/
|
|
1397
|
+
|
|
1398
|
+
|
|
1399
|
+
function mount() {
|
|
1400
|
+
hasMountCallbackRun = false;
|
|
1401
|
+
var isInLooseFollowCursorMode = getIsInLooseFollowCursorMode();
|
|
1402
|
+
|
|
1403
|
+
if (instance.popperInstance) {
|
|
1404
|
+
setFlipModifierEnabled(instance.popperInstance.modifiers, instance.props.flip);
|
|
1405
|
+
|
|
1406
|
+
if (!isInLooseFollowCursorMode) {
|
|
1407
|
+
instance.popperInstance.reference = reference;
|
|
1408
|
+
instance.popperInstance.enableEventListeners();
|
|
1409
|
+
}
|
|
1410
|
+
|
|
1411
|
+
instance.popperInstance.scheduleUpdate();
|
|
1412
|
+
} else {
|
|
1413
|
+
createPopperInstance();
|
|
1414
|
+
|
|
1415
|
+
if (!isInLooseFollowCursorMode) {
|
|
1416
|
+
instance.popperInstance.enableEventListeners();
|
|
1417
|
+
}
|
|
1418
|
+
}
|
|
1419
|
+
|
|
1420
|
+
var appendTo = instance.props.appendTo;
|
|
1421
|
+
var parentNode = appendTo === 'parent' ? reference.parentNode : invokeWithArgsOrReturn(appendTo, [reference]);
|
|
1422
|
+
|
|
1423
|
+
if (!parentNode.contains(popper)) {
|
|
1424
|
+
parentNode.appendChild(popper);
|
|
1425
|
+
instance.props.onMount(instance);
|
|
1426
|
+
instance.state.isMounted = true;
|
|
1427
|
+
}
|
|
1428
|
+
}
|
|
1429
|
+
/**
|
|
1430
|
+
* Setup before show() is invoked (delays, etc.)
|
|
1431
|
+
*/
|
|
1432
|
+
|
|
1433
|
+
|
|
1434
|
+
function scheduleShow(event, shouldAvoidCallingOnTrigger) {
|
|
1435
|
+
clearDelayTimeouts();
|
|
1436
|
+
|
|
1437
|
+
if (instance.state.isVisible) {
|
|
1438
|
+
return;
|
|
1439
|
+
} // Is a delegate, create an instance for the child target
|
|
1440
|
+
|
|
1441
|
+
|
|
1442
|
+
if (instance.props.target) {
|
|
1443
|
+
return createDelegateChildTippy(event);
|
|
1444
|
+
}
|
|
1445
|
+
|
|
1446
|
+
isScheduledToShow = true;
|
|
1447
|
+
|
|
1448
|
+
if (event && !shouldAvoidCallingOnTrigger) {
|
|
1449
|
+
instance.props.onTrigger(instance, event);
|
|
1450
|
+
}
|
|
1451
|
+
|
|
1452
|
+
if (instance.props.wait) {
|
|
1453
|
+
return instance.props.wait(instance, event);
|
|
1454
|
+
} // If the tooltip has a delay, we need to be listening to the mousemove as
|
|
1455
|
+
// soon as the trigger event is fired, so that it's in the correct position
|
|
1456
|
+
// upon mount.
|
|
1457
|
+
// Edge case: if the tooltip is still mounted, but then scheduleShow() is
|
|
1458
|
+
// called, it causes a jump.
|
|
1459
|
+
|
|
1460
|
+
|
|
1461
|
+
if (getIsInLooseFollowCursorMode() && !instance.state.isMounted) {
|
|
1462
|
+
if (!instance.popperInstance) {
|
|
1463
|
+
createPopperInstance();
|
|
1464
|
+
}
|
|
1465
|
+
|
|
1466
|
+
document.addEventListener('mousemove', positionVirtualReferenceNearCursor);
|
|
1467
|
+
}
|
|
1468
|
+
|
|
1469
|
+
addDocumentClickListener();
|
|
1470
|
+
var delay = getValue(instance.props.delay, 0, defaultProps.delay);
|
|
1471
|
+
|
|
1472
|
+
if (delay) {
|
|
1473
|
+
showTimeoutId = setTimeout(function () {
|
|
1474
|
+
show();
|
|
1475
|
+
}, delay);
|
|
1476
|
+
} else {
|
|
1477
|
+
show();
|
|
1478
|
+
}
|
|
1479
|
+
}
|
|
1480
|
+
/**
|
|
1481
|
+
* Setup before hide() is invoked (delays, etc.)
|
|
1482
|
+
*/
|
|
1483
|
+
|
|
1484
|
+
|
|
1485
|
+
function scheduleHide() {
|
|
1486
|
+
clearDelayTimeouts();
|
|
1487
|
+
|
|
1488
|
+
if (!instance.state.isVisible) {
|
|
1489
|
+
return removeFollowCursorListener();
|
|
1490
|
+
}
|
|
1491
|
+
|
|
1492
|
+
isScheduledToShow = false;
|
|
1493
|
+
var delay = getValue(instance.props.delay, 1, defaultProps.delay);
|
|
1494
|
+
|
|
1495
|
+
if (delay) {
|
|
1496
|
+
hideTimeoutId = setTimeout(function () {
|
|
1497
|
+
if (instance.state.isVisible) {
|
|
1498
|
+
hide();
|
|
1499
|
+
}
|
|
1500
|
+
}, delay);
|
|
1501
|
+
} else {
|
|
1502
|
+
// Fixes a `transitionend` problem when it fires 1 frame too
|
|
1503
|
+
// late sometimes, we don't want hide() to be called.
|
|
1504
|
+
scheduleHideAnimationFrameId = requestAnimationFrame(function () {
|
|
1505
|
+
hide();
|
|
1506
|
+
});
|
|
1507
|
+
}
|
|
1508
|
+
}
|
|
1509
|
+
/**
|
|
1510
|
+
* Listener to handle clicks on the document to determine if the
|
|
1511
|
+
* instance should hide
|
|
1512
|
+
*/
|
|
1513
|
+
|
|
1514
|
+
|
|
1515
|
+
function onDocumentClick(event) {
|
|
1516
|
+
// Clicked on interactive popper
|
|
1517
|
+
if (instance.props.interactive && popper.contains(event.target)) {
|
|
1518
|
+
return;
|
|
1519
|
+
} // Clicked on the event listeners target
|
|
1520
|
+
|
|
1521
|
+
|
|
1522
|
+
if (getEventListenersTarget().contains(event.target)) {
|
|
1523
|
+
if (isUsingTouch) {
|
|
1524
|
+
return;
|
|
1525
|
+
}
|
|
1526
|
+
|
|
1527
|
+
if (instance.state.isVisible && includes(instance.props.trigger, 'click')) {
|
|
1528
|
+
return;
|
|
1529
|
+
}
|
|
1530
|
+
}
|
|
1531
|
+
|
|
1532
|
+
if (instance.props.hideOnClick === true) {
|
|
1533
|
+
clearDelayTimeouts();
|
|
1534
|
+
hide();
|
|
1535
|
+
}
|
|
1536
|
+
}
|
|
1537
|
+
/* ======================= 🔑 Public methods 🔑 ======================= */
|
|
1538
|
+
|
|
1539
|
+
/**
|
|
1540
|
+
* Enables the instance to allow it to show or hide
|
|
1541
|
+
*/
|
|
1542
|
+
|
|
1543
|
+
|
|
1544
|
+
function enable() {
|
|
1545
|
+
instance.state.isEnabled = true;
|
|
1546
|
+
}
|
|
1547
|
+
/**
|
|
1548
|
+
* Disables the instance to disallow it to show or hide
|
|
1549
|
+
*/
|
|
1550
|
+
|
|
1551
|
+
|
|
1552
|
+
function disable() {
|
|
1553
|
+
instance.state.isEnabled = false;
|
|
1554
|
+
}
|
|
1555
|
+
/**
|
|
1556
|
+
* Clears pending timeouts related to the `delay` prop if any
|
|
1557
|
+
*/
|
|
1558
|
+
|
|
1559
|
+
|
|
1560
|
+
function clearDelayTimeouts() {
|
|
1561
|
+
clearTimeout(showTimeoutId);
|
|
1562
|
+
clearTimeout(hideTimeoutId);
|
|
1563
|
+
cancelAnimationFrame(scheduleHideAnimationFrameId);
|
|
1564
|
+
}
|
|
1565
|
+
/**
|
|
1566
|
+
* Sets new props for the instance and redraws the tooltip
|
|
1567
|
+
*/
|
|
1568
|
+
|
|
1569
|
+
|
|
1570
|
+
function set(options) {
|
|
1571
|
+
// Backwards-compatible after TypeScript change
|
|
1572
|
+
options = options || {};
|
|
1573
|
+
validateOptions(options, defaultProps);
|
|
1574
|
+
removeTriggersFromReference();
|
|
1575
|
+
var prevProps = instance.props;
|
|
1576
|
+
var nextProps = evaluateProps(reference, _extends({}, instance.props, options, {
|
|
1577
|
+
ignoreAttributes: true
|
|
1578
|
+
}));
|
|
1579
|
+
nextProps.ignoreAttributes = hasOwnProperty(options, 'ignoreAttributes') ? options.ignoreAttributes || false : prevProps.ignoreAttributes;
|
|
1580
|
+
instance.props = nextProps;
|
|
1581
|
+
addTriggersToReference();
|
|
1582
|
+
cleanupInteractiveMouseListeners();
|
|
1583
|
+
debouncedOnMouseMove = debounce(onMouseMove, nextProps.interactiveDebounce);
|
|
1584
|
+
updatePopperElement(popper, prevProps, nextProps);
|
|
1585
|
+
instance.popperChildren = getChildren(popper);
|
|
1586
|
+
|
|
1587
|
+
if (instance.popperInstance) {
|
|
1588
|
+
if (POPPER_INSTANCE_DEPENDENCIES.some(function (prop) {
|
|
1589
|
+
return hasOwnProperty(options, prop) && options[prop] !== prevProps[prop];
|
|
1590
|
+
})) {
|
|
1591
|
+
instance.popperInstance.destroy();
|
|
1592
|
+
createPopperInstance();
|
|
1593
|
+
|
|
1594
|
+
if (instance.state.isVisible) {
|
|
1595
|
+
instance.popperInstance.enableEventListeners();
|
|
1596
|
+
}
|
|
1597
|
+
|
|
1598
|
+
if (instance.props.followCursor && lastMouseMoveEvent) {
|
|
1599
|
+
positionVirtualReferenceNearCursor(lastMouseMoveEvent);
|
|
1600
|
+
}
|
|
1601
|
+
} else {
|
|
1602
|
+
instance.popperInstance.update();
|
|
1603
|
+
}
|
|
1604
|
+
}
|
|
1605
|
+
}
|
|
1606
|
+
/**
|
|
1607
|
+
* Shortcut for .set({ content: newContent })
|
|
1608
|
+
*/
|
|
1609
|
+
|
|
1610
|
+
|
|
1611
|
+
function setContent(content) {
|
|
1612
|
+
set({
|
|
1613
|
+
content: content
|
|
1614
|
+
});
|
|
1615
|
+
}
|
|
1616
|
+
/**
|
|
1617
|
+
* Shows the tooltip
|
|
1618
|
+
*/
|
|
1619
|
+
|
|
1620
|
+
|
|
1621
|
+
function show() {
|
|
1622
|
+
var duration = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : getValue(instance.props.duration, 0, defaultProps.duration[1]);
|
|
1623
|
+
|
|
1624
|
+
if (instance.state.isDestroyed || !instance.state.isEnabled || isUsingTouch && !instance.props.touch) {
|
|
1625
|
+
return;
|
|
1626
|
+
} // Standardize `disabled` behavior across browsers.
|
|
1627
|
+
// Firefox allows events on disabled elements, but Chrome doesn't.
|
|
1628
|
+
// Using a wrapper element (i.e. <span>) is recommended.
|
|
1629
|
+
|
|
1630
|
+
|
|
1631
|
+
if (getEventListenersTarget().hasAttribute('disabled')) {
|
|
1632
|
+
return;
|
|
1633
|
+
}
|
|
1634
|
+
|
|
1635
|
+
if (instance.props.onShow(instance) === false) {
|
|
1636
|
+
return;
|
|
1637
|
+
}
|
|
1638
|
+
|
|
1639
|
+
addDocumentClickListener();
|
|
1640
|
+
popper.style.visibility = 'visible';
|
|
1641
|
+
instance.state.isVisible = true;
|
|
1642
|
+
|
|
1643
|
+
if (instance.props.interactive) {
|
|
1644
|
+
getEventListenersTarget().classList.add(ACTIVE_CLASS);
|
|
1645
|
+
} // Prevent a transition if the popper is at the opposite placement
|
|
1646
|
+
|
|
1647
|
+
|
|
1648
|
+
var transitionableElements = getTransitionableElements();
|
|
1649
|
+
setTransitionDuration(transitionableElements.concat(popper), 0);
|
|
1650
|
+
|
|
1651
|
+
currentMountCallback = function currentMountCallback() {
|
|
1652
|
+
if (!instance.state.isVisible) {
|
|
1653
|
+
return;
|
|
1654
|
+
}
|
|
1655
|
+
|
|
1656
|
+
var isInLooseFollowCursorMode = getIsInLooseFollowCursorMode();
|
|
1657
|
+
|
|
1658
|
+
if (isInLooseFollowCursorMode && lastMouseMoveEvent) {
|
|
1659
|
+
positionVirtualReferenceNearCursor(lastMouseMoveEvent);
|
|
1660
|
+
} else if (!isInLooseFollowCursorMode) {
|
|
1661
|
+
// Double update will apply correct mutations
|
|
1662
|
+
instance.popperInstance.update();
|
|
1663
|
+
}
|
|
1664
|
+
|
|
1665
|
+
if (instance.popperChildren.backdrop) {
|
|
1666
|
+
instance.popperChildren.content.style.transitionDelay = Math.round(duration / 12) + 'ms';
|
|
1667
|
+
}
|
|
1668
|
+
|
|
1669
|
+
if (instance.props.sticky) {
|
|
1670
|
+
makeSticky();
|
|
1671
|
+
}
|
|
1672
|
+
|
|
1673
|
+
setTransitionDuration([popper], instance.props.updateDuration);
|
|
1674
|
+
setTransitionDuration(transitionableElements, duration);
|
|
1675
|
+
setVisibilityState(transitionableElements, 'visible');
|
|
1676
|
+
onTransitionedIn(duration, function () {
|
|
1677
|
+
if (instance.props.aria) {
|
|
1678
|
+
getEventListenersTarget().setAttribute("aria-".concat(instance.props.aria), popper.id);
|
|
1679
|
+
}
|
|
1680
|
+
|
|
1681
|
+
instance.props.onShown(instance);
|
|
1682
|
+
instance.state.isShown = true;
|
|
1683
|
+
});
|
|
1684
|
+
};
|
|
1685
|
+
|
|
1686
|
+
mount();
|
|
1687
|
+
}
|
|
1688
|
+
/**
|
|
1689
|
+
* Hides the tooltip
|
|
1690
|
+
*/
|
|
1691
|
+
|
|
1692
|
+
|
|
1693
|
+
function hide() {
|
|
1694
|
+
var duration = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : getValue(instance.props.duration, 1, defaultProps.duration[1]);
|
|
1695
|
+
|
|
1696
|
+
if (instance.state.isDestroyed || !instance.state.isEnabled && !isBeingDestroyed) {
|
|
1697
|
+
return;
|
|
1698
|
+
}
|
|
1699
|
+
|
|
1700
|
+
if (instance.props.onHide(instance) === false && !isBeingDestroyed) {
|
|
1701
|
+
return;
|
|
1702
|
+
}
|
|
1703
|
+
|
|
1704
|
+
removeDocumentClickListener();
|
|
1705
|
+
popper.style.visibility = 'hidden';
|
|
1706
|
+
instance.state.isVisible = false;
|
|
1707
|
+
instance.state.isShown = false;
|
|
1708
|
+
wasVisibleDuringPreviousUpdate = false;
|
|
1709
|
+
|
|
1710
|
+
if (instance.props.interactive) {
|
|
1711
|
+
getEventListenersTarget().classList.remove(ACTIVE_CLASS);
|
|
1712
|
+
}
|
|
1713
|
+
|
|
1714
|
+
var transitionableElements = getTransitionableElements();
|
|
1715
|
+
setTransitionDuration(transitionableElements, duration);
|
|
1716
|
+
setVisibilityState(transitionableElements, 'hidden');
|
|
1717
|
+
onTransitionedOut(duration, function () {
|
|
1718
|
+
if (!isScheduledToShow) {
|
|
1719
|
+
removeFollowCursorListener();
|
|
1720
|
+
}
|
|
1721
|
+
|
|
1722
|
+
if (instance.props.aria) {
|
|
1723
|
+
getEventListenersTarget().removeAttribute("aria-".concat(instance.props.aria));
|
|
1724
|
+
}
|
|
1725
|
+
|
|
1726
|
+
instance.popperInstance.disableEventListeners();
|
|
1727
|
+
instance.popperInstance.options.placement = instance.props.placement;
|
|
1728
|
+
popper.parentNode.removeChild(popper);
|
|
1729
|
+
instance.props.onHidden(instance);
|
|
1730
|
+
instance.state.isMounted = false;
|
|
1731
|
+
});
|
|
1732
|
+
}
|
|
1733
|
+
/**
|
|
1734
|
+
* Destroys the tooltip
|
|
1735
|
+
*/
|
|
1736
|
+
|
|
1737
|
+
|
|
1738
|
+
function destroy(destroyTargetInstances) {
|
|
1739
|
+
if (instance.state.isDestroyed) {
|
|
1740
|
+
return;
|
|
1741
|
+
}
|
|
1742
|
+
|
|
1743
|
+
isBeingDestroyed = true; // If the popper is currently mounted to the DOM, we want to ensure it gets
|
|
1744
|
+
// hidden and unmounted instantly upon destruction
|
|
1745
|
+
|
|
1746
|
+
if (instance.state.isMounted) {
|
|
1747
|
+
hide(0);
|
|
1748
|
+
}
|
|
1749
|
+
|
|
1750
|
+
removeTriggersFromReference();
|
|
1751
|
+
delete reference._tippy;
|
|
1752
|
+
var target = instance.props.target;
|
|
1753
|
+
|
|
1754
|
+
if (target && destroyTargetInstances && isRealElement(reference)) {
|
|
1755
|
+
arrayFrom(reference.querySelectorAll(target)).forEach(function (child) {
|
|
1756
|
+
if (child._tippy) {
|
|
1757
|
+
child._tippy.destroy();
|
|
1758
|
+
}
|
|
1759
|
+
});
|
|
1760
|
+
}
|
|
1761
|
+
|
|
1762
|
+
if (instance.popperInstance) {
|
|
1763
|
+
instance.popperInstance.destroy();
|
|
1764
|
+
}
|
|
1765
|
+
|
|
1766
|
+
isBeingDestroyed = false;
|
|
1767
|
+
instance.state.isDestroyed = true;
|
|
1768
|
+
}
|
|
1769
|
+
}
|
|
1770
|
+
|
|
1771
|
+
/**
|
|
1772
|
+
* Groups an array of instances by taking control of their props during
|
|
1773
|
+
* certain lifecycles.
|
|
1774
|
+
*/
|
|
1775
|
+
function group(instances) {
|
|
1776
|
+
var _ref = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {},
|
|
1777
|
+
_ref$delay = _ref.delay,
|
|
1778
|
+
delay = _ref$delay === void 0 ? instances[0].props.delay : _ref$delay,
|
|
1779
|
+
_ref$duration = _ref.duration,
|
|
1780
|
+
duration = _ref$duration === void 0 ? 0 : _ref$duration;
|
|
1781
|
+
|
|
1782
|
+
var isAnyTippyOpen = false;
|
|
1783
|
+
instances.forEach(function (instance) {
|
|
1784
|
+
if (instance._originalProps) {
|
|
1785
|
+
instance.set(instance._originalProps);
|
|
1786
|
+
} else {
|
|
1787
|
+
instance._originalProps = _extends({}, instance.props);
|
|
1788
|
+
}
|
|
1789
|
+
});
|
|
1790
|
+
|
|
1791
|
+
function setIsAnyTippyOpen(value) {
|
|
1792
|
+
isAnyTippyOpen = value;
|
|
1793
|
+
updateInstances();
|
|
1794
|
+
}
|
|
1795
|
+
|
|
1796
|
+
function onShow(instance) {
|
|
1797
|
+
instance._originalProps.onShow(instance);
|
|
1798
|
+
|
|
1799
|
+
instances.forEach(function (instance) {
|
|
1800
|
+
instance.set({
|
|
1801
|
+
duration: duration
|
|
1802
|
+
});
|
|
1803
|
+
|
|
1804
|
+
if (instance.state.isVisible) {
|
|
1805
|
+
instance.hide();
|
|
1806
|
+
}
|
|
1807
|
+
});
|
|
1808
|
+
setIsAnyTippyOpen(true);
|
|
1809
|
+
}
|
|
1810
|
+
|
|
1811
|
+
function onHide(instance) {
|
|
1812
|
+
instance._originalProps.onHide(instance);
|
|
1813
|
+
|
|
1814
|
+
setIsAnyTippyOpen(false);
|
|
1815
|
+
}
|
|
1816
|
+
|
|
1817
|
+
function onShown(instance) {
|
|
1818
|
+
instance._originalProps.onShown(instance);
|
|
1819
|
+
|
|
1820
|
+
instance.set({
|
|
1821
|
+
duration: instance._originalProps.duration
|
|
1822
|
+
});
|
|
1823
|
+
}
|
|
1824
|
+
|
|
1825
|
+
function updateInstances() {
|
|
1826
|
+
instances.forEach(function (instance) {
|
|
1827
|
+
instance.set({
|
|
1828
|
+
onShow: onShow,
|
|
1829
|
+
onShown: onShown,
|
|
1830
|
+
onHide: onHide,
|
|
1831
|
+
delay: isAnyTippyOpen ? [0, Array.isArray(delay) ? delay[1] : delay] : delay,
|
|
1832
|
+
duration: isAnyTippyOpen ? duration : instance._originalProps.duration
|
|
1833
|
+
});
|
|
1834
|
+
});
|
|
1835
|
+
}
|
|
1836
|
+
|
|
1837
|
+
updateInstances();
|
|
1838
|
+
}
|
|
1839
|
+
|
|
1840
|
+
var globalEventListenersBound = false;
|
|
1841
|
+
/**
|
|
1842
|
+
* Exported module
|
|
1843
|
+
*/
|
|
1844
|
+
|
|
1845
|
+
function tippy(targets, options) {
|
|
1846
|
+
validateOptions(options || {}, defaultProps);
|
|
1847
|
+
|
|
1848
|
+
if (!globalEventListenersBound) {
|
|
1849
|
+
bindGlobalEventListeners();
|
|
1850
|
+
globalEventListenersBound = true;
|
|
1851
|
+
}
|
|
1852
|
+
|
|
1853
|
+
var props = _extends({}, defaultProps, options); // If they are specifying a virtual positioning reference, we need to polyfill
|
|
1854
|
+
// some native DOM props
|
|
1855
|
+
|
|
1856
|
+
|
|
1857
|
+
if (isBareVirtualElement(targets)) {
|
|
1858
|
+
polyfillElementPrototypeProperties(targets);
|
|
1859
|
+
}
|
|
1860
|
+
|
|
1861
|
+
var instances = getArrayOfElements(targets).reduce(function (acc, reference) {
|
|
1862
|
+
var instance = reference && createTippy(reference, props);
|
|
1863
|
+
|
|
1864
|
+
if (instance) {
|
|
1865
|
+
acc.push(instance);
|
|
1866
|
+
}
|
|
1867
|
+
|
|
1868
|
+
return acc;
|
|
1869
|
+
}, []);
|
|
1870
|
+
return isSingular(targets) ? instances[0] : instances;
|
|
1871
|
+
}
|
|
1872
|
+
/**
|
|
1873
|
+
* Static props
|
|
1874
|
+
*/
|
|
1875
|
+
|
|
1876
|
+
|
|
1877
|
+
tippy.version = version;
|
|
1878
|
+
tippy.defaults = defaultProps;
|
|
1879
|
+
/**
|
|
1880
|
+
* Static methods
|
|
1881
|
+
*/
|
|
1882
|
+
|
|
1883
|
+
tippy.setDefaults = function (partialDefaults) {
|
|
1884
|
+
Object.keys(partialDefaults).forEach(function (key) {
|
|
1885
|
+
// @ts-ignore
|
|
1886
|
+
defaultProps[key] = partialDefaults[key];
|
|
1887
|
+
});
|
|
1888
|
+
};
|
|
1889
|
+
|
|
1890
|
+
tippy.hideAll = hideAll;
|
|
1891
|
+
tippy.group = group;
|
|
1892
|
+
/**
|
|
1893
|
+
* Auto-init tooltips for elements with a `data-tippy="..."` attribute
|
|
1894
|
+
*/
|
|
1895
|
+
|
|
1896
|
+
function autoInit() {
|
|
1897
|
+
arrayFrom(document.querySelectorAll('[data-tippy]')).forEach(function (el) {
|
|
1898
|
+
var content = el.getAttribute('data-tippy');
|
|
1899
|
+
|
|
1900
|
+
if (content) {
|
|
1901
|
+
tippy(el, {
|
|
1902
|
+
content: content
|
|
1903
|
+
});
|
|
1904
|
+
}
|
|
1905
|
+
});
|
|
1906
|
+
}
|
|
1907
|
+
|
|
1908
|
+
if (isBrowser) {
|
|
1909
|
+
setTimeout(autoInit);
|
|
1910
|
+
}
|
|
1911
|
+
|
|
1912
|
+
return tippy;
|
|
1913
|
+
|
|
1914
|
+
}));
|
|
1915
|
+
//# sourceMappingURL=index.js.map
|