bootstrap 5.0.1 → 5.1.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.
- checksums.yaml +4 -4
- data/README.md +2 -2
- data/assets/javascripts/bootstrap/alert.js +89 -58
- data/assets/javascripts/bootstrap/base-component.js +53 -39
- data/assets/javascripts/bootstrap/button.js +31 -25
- data/assets/javascripts/bootstrap/carousel.js +126 -89
- data/assets/javascripts/bootstrap/collapse.js +125 -133
- data/assets/javascripts/bootstrap/dom/data.js +5 -5
- data/assets/javascripts/bootstrap/dom/event-handler.js +11 -5
- data/assets/javascripts/bootstrap/dom/manipulator.js +6 -6
- data/assets/javascripts/bootstrap/dom/selector-engine.js +49 -7
- data/assets/javascripts/bootstrap/dropdown.js +147 -140
- data/assets/javascripts/bootstrap/modal.js +397 -180
- data/assets/javascripts/bootstrap/offcanvas.js +333 -138
- data/assets/javascripts/bootstrap/popover.js +36 -54
- data/assets/javascripts/bootstrap/scrollspy.js +58 -68
- data/assets/javascripts/bootstrap/tab.js +53 -26
- data/assets/javascripts/bootstrap/toast.js +138 -41
- data/assets/javascripts/bootstrap/tooltip.js +137 -120
- data/assets/javascripts/bootstrap-sprockets.js +8 -8
- data/assets/javascripts/bootstrap.js +937 -886
- data/assets/javascripts/bootstrap.min.js +2 -2
- data/assets/stylesheets/_bootstrap-grid.scss +3 -1
- data/assets/stylesheets/_bootstrap-reboot.scss +2 -4
- data/assets/stylesheets/_bootstrap.scss +2 -1
- data/assets/stylesheets/bootstrap/_buttons.scss +1 -0
- data/assets/stylesheets/bootstrap/_card.scss +7 -6
- data/assets/stylesheets/bootstrap/_carousel.scss +2 -2
- data/assets/stylesheets/bootstrap/_dropdown.scss +4 -4
- data/assets/stylesheets/bootstrap/_functions.scss +100 -3
- data/assets/stylesheets/bootstrap/_grid.scss +11 -0
- data/assets/stylesheets/bootstrap/_helpers.scss +2 -0
- data/assets/stylesheets/bootstrap/_images.scss +1 -1
- data/assets/stylesheets/bootstrap/_mixins.scss +1 -0
- data/assets/stylesheets/bootstrap/_modal.scss +5 -15
- data/assets/stylesheets/bootstrap/_navbar.scss +30 -1
- data/assets/stylesheets/bootstrap/_offcanvas.scss +8 -2
- data/assets/stylesheets/bootstrap/_placeholders.scss +51 -0
- data/assets/stylesheets/bootstrap/_popover.scss +10 -10
- data/assets/stylesheets/bootstrap/_reboot.scss +12 -8
- data/assets/stylesheets/bootstrap/_root.scss +40 -2
- data/assets/stylesheets/bootstrap/_tables.scss +9 -5
- data/assets/stylesheets/bootstrap/_toasts.scss +3 -3
- data/assets/stylesheets/bootstrap/_tooltip.scss +4 -4
- data/assets/stylesheets/bootstrap/_transitions.scss +6 -0
- data/assets/stylesheets/bootstrap/_utilities.scss +44 -8
- data/assets/stylesheets/bootstrap/_variables.scss +206 -29
- data/assets/stylesheets/bootstrap/bootstrap-utilities.scss +1 -1
- data/assets/stylesheets/bootstrap/forms/_floating-labels.scss +3 -1
- data/assets/stylesheets/bootstrap/forms/_form-check.scss +1 -1
- data/assets/stylesheets/bootstrap/forms/_form-control.scss +1 -1
- data/assets/stylesheets/bootstrap/forms/_form-range.scss +1 -1
- data/assets/stylesheets/bootstrap/forms/_form-select.scss +5 -0
- data/assets/stylesheets/bootstrap/helpers/_stacks.scss +15 -0
- data/assets/stylesheets/bootstrap/helpers/_vr.scss +8 -0
- data/assets/stylesheets/bootstrap/mixins/_backdrop.scss +14 -0
- data/assets/stylesheets/bootstrap/mixins/_buttons.scss +1 -1
- data/assets/stylesheets/bootstrap/mixins/_grid.scss +35 -9
- data/assets/stylesheets/bootstrap/mixins/_utilities.scss +27 -6
- data/assets/stylesheets/bootstrap/mixins/_visually-hidden.scss +1 -1
- data/assets/stylesheets/bootstrap/vendor/_rfs.scss +55 -13
- data/bootstrap.gemspec +3 -3
- data/lib/bootstrap/version.rb +2 -2
- data/tasks/updater/js.rb +6 -2
- metadata +12 -8
@@ -1,21 +1,27 @@
|
|
1
1
|
/*!
|
2
|
-
* Bootstrap modal.js v5.
|
2
|
+
* Bootstrap modal.js v5.1.2 (https://getbootstrap.com/)
|
3
3
|
* Copyright 2011-2021 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors)
|
4
4
|
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
5
5
|
*/
|
6
6
|
(function (global, factory) {
|
7
|
-
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory(require('./dom/
|
8
|
-
typeof define === 'function' && define.amd ? define(['./dom/
|
9
|
-
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, global.Modal = factory(global.
|
10
|
-
}(this, (function (
|
7
|
+
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory(require('./dom/event-handler.js'), require('./dom/manipulator.js'), require('./dom/selector-engine.js'), require('./base-component.js')) :
|
8
|
+
typeof define === 'function' && define.amd ? define(['./dom/event-handler', './dom/manipulator', './dom/selector-engine', './base-component'], factory) :
|
9
|
+
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, global.Modal = factory(global.EventHandler, global.Manipulator, global.SelectorEngine, global.Base));
|
10
|
+
})(this, (function (EventHandler, Manipulator, SelectorEngine, BaseComponent) { 'use strict';
|
11
11
|
|
12
|
-
|
12
|
+
const _interopDefaultLegacy = e => e && typeof e === 'object' && 'default' in e ? e : { default: e };
|
13
13
|
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
14
|
+
const EventHandler__default = /*#__PURE__*/_interopDefaultLegacy(EventHandler);
|
15
|
+
const Manipulator__default = /*#__PURE__*/_interopDefaultLegacy(Manipulator);
|
16
|
+
const SelectorEngine__default = /*#__PURE__*/_interopDefaultLegacy(SelectorEngine);
|
17
|
+
const BaseComponent__default = /*#__PURE__*/_interopDefaultLegacy(BaseComponent);
|
18
18
|
|
19
|
+
/**
|
20
|
+
* --------------------------------------------------------------------------
|
21
|
+
* Bootstrap (v5.1.2): util/index.js
|
22
|
+
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
23
|
+
* --------------------------------------------------------------------------
|
24
|
+
*/
|
19
25
|
const MILLISECONDS_MULTIPLIER = 1000;
|
20
26
|
const TRANSITION_END = 'transitionend'; // Shoutout AngusCroll (https://goo.gl/pxwQGp)
|
21
27
|
|
@@ -95,22 +101,17 @@
|
|
95
101
|
return typeof obj.nodeType !== 'undefined';
|
96
102
|
};
|
97
103
|
|
98
|
-
const
|
99
|
-
|
100
|
-
|
101
|
-
|
104
|
+
const getElement = obj => {
|
105
|
+
if (isElement(obj)) {
|
106
|
+
// it's a jQuery object or a node element
|
107
|
+
return obj.jquery ? obj[0] : obj;
|
108
|
+
}
|
102
109
|
|
103
|
-
|
104
|
-
|
105
|
-
element.removeEventListener(TRANSITION_END, listener);
|
110
|
+
if (typeof obj === 'string' && obj.length > 0) {
|
111
|
+
return document.querySelector(obj);
|
106
112
|
}
|
107
113
|
|
108
|
-
|
109
|
-
setTimeout(() => {
|
110
|
-
if (!called) {
|
111
|
-
triggerTransitionEnd(element);
|
112
|
-
}
|
113
|
-
}, emulatedDuration);
|
114
|
+
return null;
|
114
115
|
};
|
115
116
|
|
116
117
|
const typeCheckConfig = (componentName, config, configTypes) => {
|
@@ -126,20 +127,42 @@
|
|
126
127
|
};
|
127
128
|
|
128
129
|
const isVisible = element => {
|
129
|
-
if (!element) {
|
130
|
+
if (!isElement(element) || element.getClientRects().length === 0) {
|
130
131
|
return false;
|
131
132
|
}
|
132
133
|
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
134
|
+
return getComputedStyle(element).getPropertyValue('visibility') === 'visible';
|
135
|
+
};
|
136
|
+
|
137
|
+
const isDisabled = element => {
|
138
|
+
if (!element || element.nodeType !== Node.ELEMENT_NODE) {
|
139
|
+
return true;
|
140
|
+
}
|
141
|
+
|
142
|
+
if (element.classList.contains('disabled')) {
|
143
|
+
return true;
|
137
144
|
}
|
138
145
|
|
139
|
-
|
146
|
+
if (typeof element.disabled !== 'undefined') {
|
147
|
+
return element.disabled;
|
148
|
+
}
|
149
|
+
|
150
|
+
return element.hasAttribute('disabled') && element.getAttribute('disabled') !== 'false';
|
140
151
|
};
|
152
|
+
/**
|
153
|
+
* Trick to restart an element's animation
|
154
|
+
*
|
155
|
+
* @param {HTMLElement} element
|
156
|
+
* @return void
|
157
|
+
*
|
158
|
+
* @see https://www.charistheo.io/blog/2021/02/restart-a-css-animation-with-javascript/#restarting-a-css-animation
|
159
|
+
*/
|
160
|
+
|
141
161
|
|
142
|
-
const reflow = element =>
|
162
|
+
const reflow = element => {
|
163
|
+
// eslint-disable-next-line no-unused-expressions
|
164
|
+
element.offsetHeight;
|
165
|
+
};
|
143
166
|
|
144
167
|
const getjQuery = () => {
|
145
168
|
const {
|
@@ -153,9 +176,18 @@
|
|
153
176
|
return null;
|
154
177
|
};
|
155
178
|
|
179
|
+
const DOMContentLoadedCallbacks = [];
|
180
|
+
|
156
181
|
const onDOMContentLoaded = callback => {
|
157
182
|
if (document.readyState === 'loading') {
|
158
|
-
document
|
183
|
+
// add listener on the first call when the document is in loading state
|
184
|
+
if (!DOMContentLoadedCallbacks.length) {
|
185
|
+
document.addEventListener('DOMContentLoaded', () => {
|
186
|
+
DOMContentLoadedCallbacks.forEach(callback => callback());
|
187
|
+
});
|
188
|
+
}
|
189
|
+
|
190
|
+
DOMContentLoadedCallbacks.push(callback);
|
159
191
|
} else {
|
160
192
|
callback();
|
161
193
|
}
|
@@ -188,105 +220,166 @@
|
|
188
220
|
}
|
189
221
|
};
|
190
222
|
|
223
|
+
const executeAfterTransition = (callback, transitionElement, waitForTransition = true) => {
|
224
|
+
if (!waitForTransition) {
|
225
|
+
execute(callback);
|
226
|
+
return;
|
227
|
+
}
|
228
|
+
|
229
|
+
const durationPadding = 5;
|
230
|
+
const emulatedDuration = getTransitionDurationFromElement(transitionElement) + durationPadding;
|
231
|
+
let called = false;
|
232
|
+
|
233
|
+
const handler = ({
|
234
|
+
target
|
235
|
+
}) => {
|
236
|
+
if (target !== transitionElement) {
|
237
|
+
return;
|
238
|
+
}
|
239
|
+
|
240
|
+
called = true;
|
241
|
+
transitionElement.removeEventListener(TRANSITION_END, handler);
|
242
|
+
execute(callback);
|
243
|
+
};
|
244
|
+
|
245
|
+
transitionElement.addEventListener(TRANSITION_END, handler);
|
246
|
+
setTimeout(() => {
|
247
|
+
if (!called) {
|
248
|
+
triggerTransitionEnd(transitionElement);
|
249
|
+
}
|
250
|
+
}, emulatedDuration);
|
251
|
+
};
|
252
|
+
|
191
253
|
/**
|
192
254
|
* --------------------------------------------------------------------------
|
193
|
-
* Bootstrap (v5.
|
255
|
+
* Bootstrap (v5.1.2): util/scrollBar.js
|
194
256
|
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
195
257
|
* --------------------------------------------------------------------------
|
196
258
|
*/
|
197
259
|
const SELECTOR_FIXED_CONTENT = '.fixed-top, .fixed-bottom, .is-fixed, .sticky-top';
|
198
260
|
const SELECTOR_STICKY_CONTENT = '.sticky-top';
|
199
261
|
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
};
|
262
|
+
class ScrollBarHelper {
|
263
|
+
constructor() {
|
264
|
+
this._element = document.body;
|
265
|
+
}
|
205
266
|
|
206
|
-
|
207
|
-
|
267
|
+
getWidth() {
|
268
|
+
// https://developer.mozilla.org/en-US/docs/Web/API/Window/innerWidth#usage_notes
|
269
|
+
const documentWidth = document.documentElement.clientWidth;
|
270
|
+
return Math.abs(window.innerWidth - documentWidth);
|
271
|
+
}
|
208
272
|
|
273
|
+
hide() {
|
274
|
+
const width = this.getWidth();
|
209
275
|
|
210
|
-
|
276
|
+
this._disableOverFlow(); // give padding to element to balance the hidden scrollbar width
|
211
277
|
|
212
278
|
|
213
|
-
|
279
|
+
this._setElementAttributes(this._element, 'paddingRight', calculatedValue => calculatedValue + width); // trick: We adjust positive paddingRight and negative marginRight to sticky-top elements to keep showing fullwidth
|
214
280
|
|
215
|
-
_setElementAttributes(SELECTOR_STICKY_CONTENT, 'marginRight', calculatedValue => calculatedValue - width);
|
216
|
-
};
|
217
281
|
|
218
|
-
|
219
|
-
const actualValue = document.body.style.overflow;
|
282
|
+
this._setElementAttributes(SELECTOR_FIXED_CONTENT, 'paddingRight', calculatedValue => calculatedValue + width);
|
220
283
|
|
221
|
-
|
222
|
-
Manipulator__default['default'].setDataAttribute(document.body, 'overflow', actualValue);
|
284
|
+
this._setElementAttributes(SELECTOR_STICKY_CONTENT, 'marginRight', calculatedValue => calculatedValue - width);
|
223
285
|
}
|
224
286
|
|
225
|
-
|
226
|
-
|
287
|
+
_disableOverFlow() {
|
288
|
+
this._saveInitialAttribute(this._element, 'overflow');
|
227
289
|
|
228
|
-
|
229
|
-
|
230
|
-
SelectorEngine__default['default'].find(selector).forEach(element => {
|
231
|
-
if (element !== document.body && window.innerWidth > element.clientWidth + scrollbarWidth) {
|
232
|
-
return;
|
233
|
-
}
|
290
|
+
this._element.style.overflow = 'hidden';
|
291
|
+
}
|
234
292
|
|
235
|
-
|
236
|
-
const
|
237
|
-
Manipulator__default['default'].setDataAttribute(element, styleProp, actualValue);
|
238
|
-
element.style[styleProp] = `${callback(Number.parseFloat(calculatedValue))}px`;
|
239
|
-
});
|
240
|
-
};
|
293
|
+
_setElementAttributes(selector, styleProp, callback) {
|
294
|
+
const scrollbarWidth = this.getWidth();
|
241
295
|
|
242
|
-
|
243
|
-
|
296
|
+
const manipulationCallBack = element => {
|
297
|
+
if (element !== this._element && window.innerWidth > element.clientWidth + scrollbarWidth) {
|
298
|
+
return;
|
299
|
+
}
|
300
|
+
|
301
|
+
this._saveInitialAttribute(element, styleProp);
|
244
302
|
|
245
|
-
|
303
|
+
const calculatedValue = window.getComputedStyle(element)[styleProp];
|
304
|
+
element.style[styleProp] = `${callback(Number.parseFloat(calculatedValue))}px`;
|
305
|
+
};
|
246
306
|
|
247
|
-
|
307
|
+
this._applyManipulationCallback(selector, manipulationCallBack);
|
308
|
+
}
|
248
309
|
|
249
|
-
|
250
|
-
|
310
|
+
reset() {
|
311
|
+
this._resetElementAttributes(this._element, 'overflow');
|
251
312
|
|
252
|
-
|
253
|
-
|
254
|
-
|
313
|
+
this._resetElementAttributes(this._element, 'paddingRight');
|
314
|
+
|
315
|
+
this._resetElementAttributes(SELECTOR_FIXED_CONTENT, 'paddingRight');
|
316
|
+
|
317
|
+
this._resetElementAttributes(SELECTOR_STICKY_CONTENT, 'marginRight');
|
318
|
+
}
|
319
|
+
|
320
|
+
_saveInitialAttribute(element, styleProp) {
|
321
|
+
const actualValue = element.style[styleProp];
|
322
|
+
|
323
|
+
if (actualValue) {
|
324
|
+
Manipulator__default.default.setDataAttribute(element, styleProp, actualValue);
|
325
|
+
}
|
326
|
+
}
|
327
|
+
|
328
|
+
_resetElementAttributes(selector, styleProp) {
|
329
|
+
const manipulationCallBack = element => {
|
330
|
+
const value = Manipulator__default.default.getDataAttribute(element, styleProp);
|
331
|
+
|
332
|
+
if (typeof value === 'undefined') {
|
333
|
+
element.style.removeProperty(styleProp);
|
334
|
+
} else {
|
335
|
+
Manipulator__default.default.removeDataAttribute(element, styleProp);
|
336
|
+
element.style[styleProp] = value;
|
337
|
+
}
|
338
|
+
};
|
255
339
|
|
256
|
-
|
257
|
-
|
340
|
+
this._applyManipulationCallback(selector, manipulationCallBack);
|
341
|
+
}
|
342
|
+
|
343
|
+
_applyManipulationCallback(selector, callBack) {
|
344
|
+
if (isElement(selector)) {
|
345
|
+
callBack(selector);
|
258
346
|
} else {
|
259
|
-
|
260
|
-
element.style[styleProp] = value;
|
347
|
+
SelectorEngine__default.default.find(selector, this._element).forEach(callBack);
|
261
348
|
}
|
262
|
-
}
|
263
|
-
|
349
|
+
}
|
350
|
+
|
351
|
+
isOverflowing() {
|
352
|
+
return this.getWidth() > 0;
|
353
|
+
}
|
354
|
+
|
355
|
+
}
|
264
356
|
|
265
357
|
/**
|
266
358
|
* --------------------------------------------------------------------------
|
267
|
-
* Bootstrap (v5.
|
268
|
-
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/
|
359
|
+
* Bootstrap (v5.1.2): util/backdrop.js
|
360
|
+
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
269
361
|
* --------------------------------------------------------------------------
|
270
362
|
*/
|
271
|
-
const Default$
|
363
|
+
const Default$2 = {
|
364
|
+
className: 'modal-backdrop',
|
272
365
|
isVisible: true,
|
273
366
|
// if false, we use the backdrop helper without adding any element to the dom
|
274
367
|
isAnimated: false,
|
275
|
-
rootElement:
|
368
|
+
rootElement: 'body',
|
276
369
|
// give the choice to place backdrop under different elements
|
277
370
|
clickCallback: null
|
278
371
|
};
|
279
|
-
const DefaultType$
|
372
|
+
const DefaultType$2 = {
|
373
|
+
className: 'string',
|
280
374
|
isVisible: 'boolean',
|
281
375
|
isAnimated: 'boolean',
|
282
|
-
rootElement: 'element',
|
376
|
+
rootElement: '(element|string)',
|
283
377
|
clickCallback: '(function|null)'
|
284
378
|
};
|
285
|
-
const NAME$
|
286
|
-
const CLASS_NAME_BACKDROP = 'modal-backdrop';
|
379
|
+
const NAME$2 = 'backdrop';
|
287
380
|
const CLASS_NAME_FADE$1 = 'fade';
|
288
381
|
const CLASS_NAME_SHOW$1 = 'show';
|
289
|
-
const EVENT_MOUSEDOWN = `mousedown.bs.${NAME$
|
382
|
+
const EVENT_MOUSEDOWN = `mousedown.bs.${NAME$2}`;
|
290
383
|
|
291
384
|
class Backdrop {
|
292
385
|
constructor(config) {
|
@@ -332,7 +425,7 @@
|
|
332
425
|
_getElement() {
|
333
426
|
if (!this._element) {
|
334
427
|
const backdrop = document.createElement('div');
|
335
|
-
backdrop.className =
|
428
|
+
backdrop.className = this._config.className;
|
336
429
|
|
337
430
|
if (this._config.isAnimated) {
|
338
431
|
backdrop.classList.add(CLASS_NAME_FADE$1);
|
@@ -345,11 +438,12 @@
|
|
345
438
|
}
|
346
439
|
|
347
440
|
_getConfig(config) {
|
348
|
-
config = { ...Default$
|
441
|
+
config = { ...Default$2,
|
349
442
|
...(typeof config === 'object' ? config : {})
|
350
|
-
};
|
351
|
-
|
352
|
-
|
443
|
+
}; // use getElement() with the default "body" to get a fresh Element on each instantiation
|
444
|
+
|
445
|
+
config.rootElement = getElement(config.rootElement);
|
446
|
+
typeCheckConfig(NAME$2, config, DefaultType$2);
|
353
447
|
return config;
|
354
448
|
}
|
355
449
|
|
@@ -358,9 +452,9 @@
|
|
358
452
|
return;
|
359
453
|
}
|
360
454
|
|
361
|
-
this._config.rootElement.
|
455
|
+
this._config.rootElement.append(this._getElement());
|
362
456
|
|
363
|
-
EventHandler__default
|
457
|
+
EventHandler__default.default.on(this._getElement(), EVENT_MOUSEDOWN, () => {
|
364
458
|
execute(this._config.clickCallback);
|
365
459
|
});
|
366
460
|
this._isAppended = true;
|
@@ -371,29 +465,151 @@
|
|
371
465
|
return;
|
372
466
|
}
|
373
467
|
|
374
|
-
EventHandler__default
|
468
|
+
EventHandler__default.default.off(this._element, EVENT_MOUSEDOWN);
|
375
469
|
|
376
|
-
this.
|
470
|
+
this._element.remove();
|
377
471
|
|
378
472
|
this._isAppended = false;
|
379
473
|
}
|
380
474
|
|
381
475
|
_emulateAnimation(callback) {
|
382
|
-
|
383
|
-
|
476
|
+
executeAfterTransition(callback, this._getElement(), this._config.isAnimated);
|
477
|
+
}
|
478
|
+
|
479
|
+
}
|
480
|
+
|
481
|
+
/**
|
482
|
+
* --------------------------------------------------------------------------
|
483
|
+
* Bootstrap (v5.1.2): util/focustrap.js
|
484
|
+
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
485
|
+
* --------------------------------------------------------------------------
|
486
|
+
*/
|
487
|
+
const Default$1 = {
|
488
|
+
trapElement: null,
|
489
|
+
// The element to trap focus inside of
|
490
|
+
autofocus: true
|
491
|
+
};
|
492
|
+
const DefaultType$1 = {
|
493
|
+
trapElement: 'element',
|
494
|
+
autofocus: 'boolean'
|
495
|
+
};
|
496
|
+
const NAME$1 = 'focustrap';
|
497
|
+
const DATA_KEY$1 = 'bs.focustrap';
|
498
|
+
const EVENT_KEY$1 = `.${DATA_KEY$1}`;
|
499
|
+
const EVENT_FOCUSIN = `focusin${EVENT_KEY$1}`;
|
500
|
+
const EVENT_KEYDOWN_TAB = `keydown.tab${EVENT_KEY$1}`;
|
501
|
+
const TAB_KEY = 'Tab';
|
502
|
+
const TAB_NAV_FORWARD = 'forward';
|
503
|
+
const TAB_NAV_BACKWARD = 'backward';
|
504
|
+
|
505
|
+
class FocusTrap {
|
506
|
+
constructor(config) {
|
507
|
+
this._config = this._getConfig(config);
|
508
|
+
this._isActive = false;
|
509
|
+
this._lastTabNavDirection = null;
|
510
|
+
}
|
511
|
+
|
512
|
+
activate() {
|
513
|
+
const {
|
514
|
+
trapElement,
|
515
|
+
autofocus
|
516
|
+
} = this._config;
|
517
|
+
|
518
|
+
if (this._isActive) {
|
384
519
|
return;
|
385
520
|
}
|
386
521
|
|
387
|
-
|
388
|
-
|
389
|
-
|
522
|
+
if (autofocus) {
|
523
|
+
trapElement.focus();
|
524
|
+
}
|
525
|
+
|
526
|
+
EventHandler__default.default.off(document, EVENT_KEY$1); // guard against infinite focus loop
|
527
|
+
|
528
|
+
EventHandler__default.default.on(document, EVENT_FOCUSIN, event => this._handleFocusin(event));
|
529
|
+
EventHandler__default.default.on(document, EVENT_KEYDOWN_TAB, event => this._handleKeydown(event));
|
530
|
+
this._isActive = true;
|
531
|
+
}
|
532
|
+
|
533
|
+
deactivate() {
|
534
|
+
if (!this._isActive) {
|
535
|
+
return;
|
536
|
+
}
|
537
|
+
|
538
|
+
this._isActive = false;
|
539
|
+
EventHandler__default.default.off(document, EVENT_KEY$1);
|
540
|
+
} // Private
|
541
|
+
|
542
|
+
|
543
|
+
_handleFocusin(event) {
|
544
|
+
const {
|
545
|
+
target
|
546
|
+
} = event;
|
547
|
+
const {
|
548
|
+
trapElement
|
549
|
+
} = this._config;
|
550
|
+
|
551
|
+
if (target === document || target === trapElement || trapElement.contains(target)) {
|
552
|
+
return;
|
553
|
+
}
|
554
|
+
|
555
|
+
const elements = SelectorEngine__default.default.focusableChildren(trapElement);
|
556
|
+
|
557
|
+
if (elements.length === 0) {
|
558
|
+
trapElement.focus();
|
559
|
+
} else if (this._lastTabNavDirection === TAB_NAV_BACKWARD) {
|
560
|
+
elements[elements.length - 1].focus();
|
561
|
+
} else {
|
562
|
+
elements[0].focus();
|
563
|
+
}
|
564
|
+
}
|
565
|
+
|
566
|
+
_handleKeydown(event) {
|
567
|
+
if (event.key !== TAB_KEY) {
|
568
|
+
return;
|
569
|
+
}
|
570
|
+
|
571
|
+
this._lastTabNavDirection = event.shiftKey ? TAB_NAV_BACKWARD : TAB_NAV_FORWARD;
|
572
|
+
}
|
573
|
+
|
574
|
+
_getConfig(config) {
|
575
|
+
config = { ...Default$1,
|
576
|
+
...(typeof config === 'object' ? config : {})
|
577
|
+
};
|
578
|
+
typeCheckConfig(NAME$1, config, DefaultType$1);
|
579
|
+
return config;
|
390
580
|
}
|
391
581
|
|
392
582
|
}
|
393
583
|
|
394
584
|
/**
|
395
585
|
* --------------------------------------------------------------------------
|
396
|
-
* Bootstrap (v5.
|
586
|
+
* Bootstrap (v5.1.2): util/component-functions.js
|
587
|
+
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
588
|
+
* --------------------------------------------------------------------------
|
589
|
+
*/
|
590
|
+
|
591
|
+
const enableDismissTrigger = (component, method = 'hide') => {
|
592
|
+
const clickEvent = `click.dismiss${component.EVENT_KEY}`;
|
593
|
+
const name = component.NAME;
|
594
|
+
EventHandler__default.default.on(document, clickEvent, `[data-bs-dismiss="${name}"]`, function (event) {
|
595
|
+
if (['A', 'AREA'].includes(this.tagName)) {
|
596
|
+
event.preventDefault();
|
597
|
+
}
|
598
|
+
|
599
|
+
if (isDisabled(this)) {
|
600
|
+
return;
|
601
|
+
}
|
602
|
+
|
603
|
+
const target = getElementFromSelector(this) || this.closest(`.${name}`);
|
604
|
+
const instance = component.getOrCreateInstance(target); // Method argument is left, for Alert and only, as it doesn't implement the 'hide' method
|
605
|
+
|
606
|
+
instance[method]();
|
607
|
+
});
|
608
|
+
};
|
609
|
+
|
610
|
+
/**
|
611
|
+
* --------------------------------------------------------------------------
|
612
|
+
* Bootstrap (v5.1.2): modal.js
|
397
613
|
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
|
398
614
|
* --------------------------------------------------------------------------
|
399
615
|
*/
|
@@ -423,7 +639,6 @@
|
|
423
639
|
const EVENT_HIDDEN = `hidden${EVENT_KEY}`;
|
424
640
|
const EVENT_SHOW = `show${EVENT_KEY}`;
|
425
641
|
const EVENT_SHOWN = `shown${EVENT_KEY}`;
|
426
|
-
const EVENT_FOCUSIN = `focusin${EVENT_KEY}`;
|
427
642
|
const EVENT_RESIZE = `resize${EVENT_KEY}`;
|
428
643
|
const EVENT_CLICK_DISMISS = `click.dismiss${EVENT_KEY}`;
|
429
644
|
const EVENT_KEYDOWN_DISMISS = `keydown.dismiss${EVENT_KEY}`;
|
@@ -434,25 +649,27 @@
|
|
434
649
|
const CLASS_NAME_FADE = 'fade';
|
435
650
|
const CLASS_NAME_SHOW = 'show';
|
436
651
|
const CLASS_NAME_STATIC = 'modal-static';
|
652
|
+
const OPEN_SELECTOR = '.modal.show';
|
437
653
|
const SELECTOR_DIALOG = '.modal-dialog';
|
438
654
|
const SELECTOR_MODAL_BODY = '.modal-body';
|
439
655
|
const SELECTOR_DATA_TOGGLE = '[data-bs-toggle="modal"]';
|
440
|
-
const SELECTOR_DATA_DISMISS = '[data-bs-dismiss="modal"]';
|
441
656
|
/**
|
442
657
|
* ------------------------------------------------------------------------
|
443
658
|
* Class Definition
|
444
659
|
* ------------------------------------------------------------------------
|
445
660
|
*/
|
446
661
|
|
447
|
-
class Modal extends BaseComponent__default
|
662
|
+
class Modal extends BaseComponent__default.default {
|
448
663
|
constructor(element, config) {
|
449
664
|
super(element);
|
450
665
|
this._config = this._getConfig(config);
|
451
|
-
this._dialog = SelectorEngine__default
|
666
|
+
this._dialog = SelectorEngine__default.default.findOne(SELECTOR_DIALOG, this._element);
|
452
667
|
this._backdrop = this._initializeBackDrop();
|
668
|
+
this._focustrap = this._initializeFocusTrap();
|
453
669
|
this._isShown = false;
|
454
670
|
this._ignoreBackdropClick = false;
|
455
671
|
this._isTransitioning = false;
|
672
|
+
this._scrollBar = new ScrollBarHelper();
|
456
673
|
} // Getters
|
457
674
|
|
458
675
|
|
@@ -474,20 +691,22 @@
|
|
474
691
|
return;
|
475
692
|
}
|
476
693
|
|
477
|
-
|
478
|
-
this._isTransitioning = true;
|
479
|
-
}
|
480
|
-
|
481
|
-
const showEvent = EventHandler__default['default'].trigger(this._element, EVENT_SHOW, {
|
694
|
+
const showEvent = EventHandler__default.default.trigger(this._element, EVENT_SHOW, {
|
482
695
|
relatedTarget
|
483
696
|
});
|
484
697
|
|
485
|
-
if (
|
698
|
+
if (showEvent.defaultPrevented) {
|
486
699
|
return;
|
487
700
|
}
|
488
701
|
|
489
702
|
this._isShown = true;
|
490
|
-
|
703
|
+
|
704
|
+
if (this._isAnimated()) {
|
705
|
+
this._isTransitioning = true;
|
706
|
+
}
|
707
|
+
|
708
|
+
this._scrollBar.hide();
|
709
|
+
|
491
710
|
document.body.classList.add(CLASS_NAME_OPEN);
|
492
711
|
|
493
712
|
this._adjustDialog();
|
@@ -496,9 +715,8 @@
|
|
496
715
|
|
497
716
|
this._setResizeEvent();
|
498
717
|
|
499
|
-
EventHandler__default
|
500
|
-
|
501
|
-
EventHandler__default['default'].one(this._element, EVENT_MOUSEUP_DISMISS, event => {
|
718
|
+
EventHandler__default.default.on(this._dialog, EVENT_MOUSEDOWN_DISMISS, () => {
|
719
|
+
EventHandler__default.default.one(this._element, EVENT_MOUSEUP_DISMISS, event => {
|
502
720
|
if (event.target === this._element) {
|
503
721
|
this._ignoreBackdropClick = true;
|
504
722
|
}
|
@@ -508,16 +726,12 @@
|
|
508
726
|
this._showBackdrop(() => this._showElement(relatedTarget));
|
509
727
|
}
|
510
728
|
|
511
|
-
hide(
|
512
|
-
if (event) {
|
513
|
-
event.preventDefault();
|
514
|
-
}
|
515
|
-
|
729
|
+
hide() {
|
516
730
|
if (!this._isShown || this._isTransitioning) {
|
517
731
|
return;
|
518
732
|
}
|
519
733
|
|
520
|
-
const hideEvent = EventHandler__default
|
734
|
+
const hideEvent = EventHandler__default.default.trigger(this._element, EVENT_HIDE);
|
521
735
|
|
522
736
|
if (hideEvent.defaultPrevented) {
|
523
737
|
return;
|
@@ -535,29 +749,24 @@
|
|
535
749
|
|
536
750
|
this._setResizeEvent();
|
537
751
|
|
538
|
-
|
752
|
+
this._focustrap.deactivate();
|
539
753
|
|
540
754
|
this._element.classList.remove(CLASS_NAME_SHOW);
|
541
755
|
|
542
|
-
EventHandler__default
|
543
|
-
EventHandler__default
|
756
|
+
EventHandler__default.default.off(this._element, EVENT_CLICK_DISMISS);
|
757
|
+
EventHandler__default.default.off(this._dialog, EVENT_MOUSEDOWN_DISMISS);
|
544
758
|
|
545
759
|
this._queueCallback(() => this._hideModal(), this._element, isAnimated);
|
546
760
|
}
|
547
761
|
|
548
762
|
dispose() {
|
549
|
-
[window, this._dialog].forEach(htmlElement => EventHandler__default
|
763
|
+
[window, this._dialog].forEach(htmlElement => EventHandler__default.default.off(htmlElement, EVENT_KEY));
|
550
764
|
|
551
765
|
this._backdrop.dispose();
|
552
766
|
|
553
|
-
|
554
|
-
/**
|
555
|
-
* `document` has 2 events `EVENT_FOCUSIN` and `EVENT_CLICK_DATA_API`
|
556
|
-
* Do not move `document` in `htmlElements` array
|
557
|
-
* It will remove `EVENT_CLICK_DATA_API` event that should remain
|
558
|
-
*/
|
767
|
+
this._focustrap.deactivate();
|
559
768
|
|
560
|
-
|
769
|
+
super.dispose();
|
561
770
|
}
|
562
771
|
|
563
772
|
handleUpdate() {
|
@@ -573,10 +782,16 @@
|
|
573
782
|
});
|
574
783
|
}
|
575
784
|
|
785
|
+
_initializeFocusTrap() {
|
786
|
+
return new FocusTrap({
|
787
|
+
trapElement: this._element
|
788
|
+
});
|
789
|
+
}
|
790
|
+
|
576
791
|
_getConfig(config) {
|
577
792
|
config = { ...Default,
|
578
|
-
...Manipulator__default
|
579
|
-
...config
|
793
|
+
...Manipulator__default.default.getDataAttributes(this._element),
|
794
|
+
...(typeof config === 'object' ? config : {})
|
580
795
|
};
|
581
796
|
typeCheckConfig(NAME, config, DefaultType);
|
582
797
|
return config;
|
@@ -585,11 +800,11 @@
|
|
585
800
|
_showElement(relatedTarget) {
|
586
801
|
const isAnimated = this._isAnimated();
|
587
802
|
|
588
|
-
const modalBody = SelectorEngine__default
|
803
|
+
const modalBody = SelectorEngine__default.default.findOne(SELECTOR_MODAL_BODY, this._dialog);
|
589
804
|
|
590
805
|
if (!this._element.parentNode || this._element.parentNode.nodeType !== Node.ELEMENT_NODE) {
|
591
806
|
// Don't move modal's DOM position
|
592
|
-
document.body.
|
807
|
+
document.body.append(this._element);
|
593
808
|
}
|
594
809
|
|
595
810
|
this._element.style.display = 'block';
|
@@ -612,17 +827,13 @@
|
|
612
827
|
|
613
828
|
this._element.classList.add(CLASS_NAME_SHOW);
|
614
829
|
|
615
|
-
if (this._config.focus) {
|
616
|
-
this._enforceFocus();
|
617
|
-
}
|
618
|
-
|
619
830
|
const transitionComplete = () => {
|
620
831
|
if (this._config.focus) {
|
621
|
-
this.
|
832
|
+
this._focustrap.activate();
|
622
833
|
}
|
623
834
|
|
624
835
|
this._isTransitioning = false;
|
625
|
-
EventHandler__default
|
836
|
+
EventHandler__default.default.trigger(this._element, EVENT_SHOWN, {
|
626
837
|
relatedTarget
|
627
838
|
});
|
628
839
|
};
|
@@ -630,19 +841,9 @@
|
|
630
841
|
this._queueCallback(transitionComplete, this._dialog, isAnimated);
|
631
842
|
}
|
632
843
|
|
633
|
-
_enforceFocus() {
|
634
|
-
EventHandler__default['default'].off(document, EVENT_FOCUSIN); // guard against infinite focus loop
|
635
|
-
|
636
|
-
EventHandler__default['default'].on(document, EVENT_FOCUSIN, event => {
|
637
|
-
if (document !== event.target && this._element !== event.target && !this._element.contains(event.target)) {
|
638
|
-
this._element.focus();
|
639
|
-
}
|
640
|
-
});
|
641
|
-
}
|
642
|
-
|
643
844
|
_setEscapeEvent() {
|
644
845
|
if (this._isShown) {
|
645
|
-
EventHandler__default
|
846
|
+
EventHandler__default.default.on(this._element, EVENT_KEYDOWN_DISMISS, event => {
|
646
847
|
if (this._config.keyboard && event.key === ESCAPE_KEY) {
|
647
848
|
event.preventDefault();
|
648
849
|
this.hide();
|
@@ -651,15 +852,15 @@
|
|
651
852
|
}
|
652
853
|
});
|
653
854
|
} else {
|
654
|
-
EventHandler__default
|
855
|
+
EventHandler__default.default.off(this._element, EVENT_KEYDOWN_DISMISS);
|
655
856
|
}
|
656
857
|
}
|
657
858
|
|
658
859
|
_setResizeEvent() {
|
659
860
|
if (this._isShown) {
|
660
|
-
EventHandler__default
|
861
|
+
EventHandler__default.default.on(window, EVENT_RESIZE, () => this._adjustDialog());
|
661
862
|
} else {
|
662
|
-
EventHandler__default
|
863
|
+
EventHandler__default.default.off(window, EVENT_RESIZE);
|
663
864
|
}
|
664
865
|
}
|
665
866
|
|
@@ -679,13 +880,14 @@
|
|
679
880
|
|
680
881
|
this._resetAdjustments();
|
681
882
|
|
682
|
-
reset();
|
683
|
-
|
883
|
+
this._scrollBar.reset();
|
884
|
+
|
885
|
+
EventHandler__default.default.trigger(this._element, EVENT_HIDDEN);
|
684
886
|
});
|
685
887
|
}
|
686
888
|
|
687
889
|
_showBackdrop(callback) {
|
688
|
-
EventHandler__default
|
890
|
+
EventHandler__default.default.on(this._element, EVENT_CLICK_DISMISS, event => {
|
689
891
|
if (this._ignoreBackdropClick) {
|
690
892
|
this._ignoreBackdropClick = false;
|
691
893
|
return;
|
@@ -710,33 +912,38 @@
|
|
710
912
|
}
|
711
913
|
|
712
914
|
_triggerBackdropTransition() {
|
713
|
-
const hideEvent = EventHandler__default
|
915
|
+
const hideEvent = EventHandler__default.default.trigger(this._element, EVENT_HIDE_PREVENTED);
|
714
916
|
|
715
917
|
if (hideEvent.defaultPrevented) {
|
716
918
|
return;
|
717
919
|
}
|
718
920
|
|
719
|
-
const
|
921
|
+
const {
|
922
|
+
classList,
|
923
|
+
scrollHeight,
|
924
|
+
style
|
925
|
+
} = this._element;
|
926
|
+
const isModalOverflowing = scrollHeight > document.documentElement.clientHeight; // return if the following background transition hasn't yet completed
|
927
|
+
|
928
|
+
if (!isModalOverflowing && style.overflowY === 'hidden' || classList.contains(CLASS_NAME_STATIC)) {
|
929
|
+
return;
|
930
|
+
}
|
720
931
|
|
721
932
|
if (!isModalOverflowing) {
|
722
|
-
|
933
|
+
style.overflowY = 'hidden';
|
723
934
|
}
|
724
935
|
|
725
|
-
|
936
|
+
classList.add(CLASS_NAME_STATIC);
|
726
937
|
|
727
|
-
|
728
|
-
|
729
|
-
EventHandler__default['default'].one(this._element, 'transitionend', () => {
|
730
|
-
this._element.classList.remove(CLASS_NAME_STATIC);
|
938
|
+
this._queueCallback(() => {
|
939
|
+
classList.remove(CLASS_NAME_STATIC);
|
731
940
|
|
732
941
|
if (!isModalOverflowing) {
|
733
|
-
|
734
|
-
|
735
|
-
});
|
736
|
-
emulateTransitionEnd(this._element, modalTransitionDuration);
|
942
|
+
this._queueCallback(() => {
|
943
|
+
style.overflowY = '';
|
944
|
+
}, this._dialog);
|
737
945
|
}
|
738
|
-
});
|
739
|
-
emulateTransitionEnd(this._element, modalTransitionDuration);
|
946
|
+
}, this._dialog);
|
740
947
|
|
741
948
|
this._element.focus();
|
742
949
|
} // ----------------------------------------------------------------------
|
@@ -746,7 +953,9 @@
|
|
746
953
|
|
747
954
|
_adjustDialog() {
|
748
955
|
const isModalOverflowing = this._element.scrollHeight > document.documentElement.clientHeight;
|
749
|
-
|
956
|
+
|
957
|
+
const scrollbarWidth = this._scrollBar.getWidth();
|
958
|
+
|
750
959
|
const isBodyOverflowing = scrollbarWidth > 0;
|
751
960
|
|
752
961
|
if (!isBodyOverflowing && isModalOverflowing && !isRTL() || isBodyOverflowing && !isModalOverflowing && isRTL()) {
|
@@ -766,7 +975,7 @@
|
|
766
975
|
|
767
976
|
static jQueryInterface(config, relatedTarget) {
|
768
977
|
return this.each(function () {
|
769
|
-
const data = Modal.
|
978
|
+
const data = Modal.getOrCreateInstance(this, config);
|
770
979
|
|
771
980
|
if (typeof config !== 'string') {
|
772
981
|
return;
|
@@ -788,28 +997,36 @@
|
|
788
997
|
*/
|
789
998
|
|
790
999
|
|
791
|
-
EventHandler__default
|
1000
|
+
EventHandler__default.default.on(document, EVENT_CLICK_DATA_API, SELECTOR_DATA_TOGGLE, function (event) {
|
792
1001
|
const target = getElementFromSelector(this);
|
793
1002
|
|
794
1003
|
if (['A', 'AREA'].includes(this.tagName)) {
|
795
1004
|
event.preventDefault();
|
796
1005
|
}
|
797
1006
|
|
798
|
-
EventHandler__default
|
1007
|
+
EventHandler__default.default.one(target, EVENT_SHOW, showEvent => {
|
799
1008
|
if (showEvent.defaultPrevented) {
|
800
1009
|
// only register focus restorer if modal will actually get shown
|
801
1010
|
return;
|
802
1011
|
}
|
803
1012
|
|
804
|
-
EventHandler__default
|
1013
|
+
EventHandler__default.default.one(target, EVENT_HIDDEN, () => {
|
805
1014
|
if (isVisible(this)) {
|
806
1015
|
this.focus();
|
807
1016
|
}
|
808
1017
|
});
|
809
|
-
});
|
810
|
-
|
1018
|
+
}); // avoid conflict when clicking moddal toggler while another one is open
|
1019
|
+
|
1020
|
+
const allReadyOpen = SelectorEngine__default.default.findOne(OPEN_SELECTOR);
|
1021
|
+
|
1022
|
+
if (allReadyOpen) {
|
1023
|
+
Modal.getInstance(allReadyOpen).hide();
|
1024
|
+
}
|
1025
|
+
|
1026
|
+
const data = Modal.getOrCreateInstance(target);
|
811
1027
|
data.toggle(this);
|
812
1028
|
});
|
1029
|
+
enableDismissTrigger(Modal);
|
813
1030
|
/**
|
814
1031
|
* ------------------------------------------------------------------------
|
815
1032
|
* jQuery
|
@@ -821,4 +1038,4 @@
|
|
821
1038
|
|
822
1039
|
return Modal;
|
823
1040
|
|
824
|
-
}))
|
1041
|
+
}));
|