@openeuropa/bcl-bootstrap 0.24.1 → 0.26.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.
Files changed (142) hide show
  1. package/bootstrap-icons.svg +1 -1
  2. package/icons/apple.svg +2 -2
  3. package/icons/boombox-fill.svg +2 -2
  4. package/icons/cup-fill.svg +1 -1
  5. package/icons/cup.svg +1 -1
  6. package/js/dist/alert.js +3 -12
  7. package/js/dist/alert.js.map +1 -1
  8. package/js/dist/base-component.js +32 -18
  9. package/js/dist/base-component.js.map +1 -1
  10. package/js/dist/button.js +3 -12
  11. package/js/dist/button.js.map +1 -1
  12. package/js/dist/carousel.js +207 -307
  13. package/js/dist/carousel.js.map +1 -1
  14. package/js/dist/collapse.js +57 -88
  15. package/js/dist/collapse.js.map +1 -1
  16. package/js/dist/dom/data.js +1 -3
  17. package/js/dist/dom/data.js.map +1 -1
  18. package/js/dist/dom/event-handler.js +87 -106
  19. package/js/dist/dom/event-handler.js.map +1 -1
  20. package/js/dist/dom/manipulator.js +21 -25
  21. package/js/dist/dom/manipulator.js.map +1 -1
  22. package/js/dist/dom/selector-engine.js +11 -10
  23. package/js/dist/dom/selector-engine.js.map +1 -1
  24. package/js/dist/dropdown.js +83 -115
  25. package/js/dist/dropdown.js.map +1 -1
  26. package/js/dist/modal.js +95 -152
  27. package/js/dist/modal.js.map +1 -1
  28. package/js/dist/offcanvas.js +75 -58
  29. package/js/dist/offcanvas.js.map +1 -1
  30. package/js/dist/popover.js +29 -56
  31. package/js/dist/popover.js.map +1 -1
  32. package/js/dist/scrollspy.js +176 -125
  33. package/js/dist/scrollspy.js.map +1 -1
  34. package/js/dist/tab.js +207 -92
  35. package/js/dist/tab.js.map +1 -1
  36. package/js/dist/toast.js +23 -37
  37. package/js/dist/toast.js.map +1 -1
  38. package/js/dist/tooltip.js +259 -348
  39. package/js/dist/tooltip.js.map +1 -1
  40. package/js/dist/util/backdrop.js +62 -39
  41. package/js/dist/util/backdrop.js.map +1 -1
  42. package/js/dist/util/component-functions.js +1 -1
  43. package/js/dist/util/component-functions.js.map +1 -1
  44. package/js/dist/util/config.js +75 -0
  45. package/js/dist/util/config.js.map +1 -0
  46. package/js/dist/util/focustrap.js +41 -34
  47. package/js/dist/util/focustrap.js.map +1 -1
  48. package/js/dist/util/index.js +56 -52
  49. package/js/dist/util/index.js.map +1 -1
  50. package/js/dist/util/sanitizer.js +12 -19
  51. package/js/dist/util/sanitizer.js.map +1 -1
  52. package/js/dist/util/scrollbar.js +49 -34
  53. package/js/dist/util/scrollbar.js.map +1 -1
  54. package/js/dist/util/swipe.js +151 -0
  55. package/js/dist/util/swipe.js.map +1 -0
  56. package/js/dist/util/template-factory.js +173 -0
  57. package/js/dist/util/template-factory.js.map +1 -0
  58. package/js/src/alert.js +3 -15
  59. package/js/src/base-component.js +28 -18
  60. package/js/src/button.js +3 -17
  61. package/js/src/carousel.js +203 -319
  62. package/js/src/collapse.js +61 -94
  63. package/js/src/dom/data.js +1 -3
  64. package/js/src/dom/event-handler.js +80 -108
  65. package/js/src/dom/manipulator.js +22 -31
  66. package/js/src/dom/selector-engine.js +10 -19
  67. package/js/src/dropdown.js +84 -138
  68. package/js/src/modal.js +94 -158
  69. package/js/src/offcanvas.js +72 -61
  70. package/js/src/popover.js +31 -62
  71. package/js/src/scrollspy.js +166 -171
  72. package/js/src/tab.js +193 -110
  73. package/js/src/toast.js +19 -41
  74. package/js/src/tooltip.js +259 -371
  75. package/js/src/util/backdrop.js +55 -36
  76. package/js/src/util/component-functions.js +1 -1
  77. package/js/src/util/config.js +66 -0
  78. package/js/src/util/focustrap.js +38 -28
  79. package/js/src/util/index.js +67 -64
  80. package/js/src/util/sanitizer.js +11 -19
  81. package/js/src/util/scrollbar.js +47 -30
  82. package/js/src/util/swipe.js +146 -0
  83. package/js/src/util/template-factory.js +160 -0
  84. package/package.json +4 -4
  85. package/scss/_accordion.scss +52 -24
  86. package/scss/_alert.scss +18 -4
  87. package/scss/_badge.scss +14 -5
  88. package/scss/_breadcrumb.scss +22 -10
  89. package/scss/_button-group.scss +3 -0
  90. package/scss/_buttons.scss +97 -22
  91. package/scss/_card.scss +55 -37
  92. package/scss/_close.scss +1 -1
  93. package/scss/_containers.scss +1 -1
  94. package/scss/_dropdown.scss +83 -75
  95. package/scss/_functions.scss +7 -7
  96. package/scss/_grid.scss +3 -3
  97. package/scss/_helpers.scss +1 -0
  98. package/scss/_list-group.scss +44 -27
  99. package/scss/_maps.scss +54 -0
  100. package/scss/_modal.scss +71 -43
  101. package/scss/_nav.scss +53 -20
  102. package/scss/_navbar.scss +91 -150
  103. package/scss/_offcanvas.scss +119 -59
  104. package/scss/_pagination.scss +66 -21
  105. package/scss/_placeholders.scss +1 -1
  106. package/scss/_popover.scss +90 -52
  107. package/scss/_progress.scss +20 -9
  108. package/scss/_reboot.scss +25 -40
  109. package/scss/_root.scss +40 -21
  110. package/scss/_spinners.scss +38 -22
  111. package/scss/_tables.scss +32 -23
  112. package/scss/_toasts.scss +35 -16
  113. package/scss/_tooltip.scss +61 -56
  114. package/scss/_type.scss +2 -0
  115. package/scss/_utilities.scss +43 -26
  116. package/scss/_variables.scss +113 -121
  117. package/scss/bootstrap-grid.scss +3 -6
  118. package/scss/bootstrap-reboot.scss +3 -7
  119. package/scss/bootstrap-utilities.scss +3 -6
  120. package/scss/bootstrap.scss +4 -6
  121. package/scss/forms/_floating-labels.scss +14 -3
  122. package/scss/forms/_form-check.scss +28 -5
  123. package/scss/forms/_form-control.scss +12 -37
  124. package/scss/forms/_form-select.scss +0 -1
  125. package/scss/forms/_input-group.scss +15 -7
  126. package/scss/helpers/_color-bg.scss +10 -0
  127. package/scss/helpers/_colored-links.scss +2 -2
  128. package/scss/helpers/_position.scss +7 -1
  129. package/scss/helpers/_ratio.scss +2 -2
  130. package/scss/helpers/_vr.scss +1 -1
  131. package/scss/mixins/_alert.scss +7 -3
  132. package/scss/mixins/_banner.scss +9 -0
  133. package/scss/mixins/_breakpoints.scss +8 -8
  134. package/scss/mixins/_buttons.scss +32 -95
  135. package/scss/mixins/_container.scss +4 -2
  136. package/scss/mixins/_forms.scss +8 -0
  137. package/scss/mixins/_gradients.scss +1 -1
  138. package/scss/mixins/_grid.scss +12 -12
  139. package/scss/mixins/_pagination.scss +4 -25
  140. package/scss/mixins/_reset-text.scss +1 -1
  141. package/scss/mixins/_table-variants.scss +12 -9
  142. package/scss/mixins/_utilities.scss +12 -4
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * --------------------------------------------------------------------------
3
- * Bootstrap (v5.1.3): collapse.js
3
+ * Bootstrap (v5.2.0): collapse.js
4
4
  * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
5
5
  * --------------------------------------------------------------------------
6
6
  */
@@ -8,21 +8,16 @@
8
8
  import {
9
9
  defineJQueryPlugin,
10
10
  getElement,
11
- getSelectorFromElement,
12
11
  getElementFromSelector,
13
- reflow,
14
- typeCheckConfig
12
+ getSelectorFromElement,
13
+ reflow
15
14
  } from './util/index'
16
- import Data from './dom/data'
17
15
  import EventHandler from './dom/event-handler'
18
- import Manipulator from './dom/manipulator'
19
16
  import SelectorEngine from './dom/selector-engine'
20
17
  import BaseComponent from './base-component'
21
18
 
22
19
  /**
23
- * ------------------------------------------------------------------------
24
20
  * Constants
25
- * ------------------------------------------------------------------------
26
21
  */
27
22
 
28
23
  const NAME = 'collapse'
@@ -30,16 +25,6 @@ const DATA_KEY = 'bs.collapse'
30
25
  const EVENT_KEY = `.${DATA_KEY}`
31
26
  const DATA_API_KEY = '.data-api'
32
27
 
33
- const Default = {
34
- toggle: true,
35
- parent: null
36
- }
37
-
38
- const DefaultType = {
39
- toggle: 'boolean',
40
- parent: '(null|element)'
41
- }
42
-
43
28
  const EVENT_SHOW = `show${EVENT_KEY}`
44
29
  const EVENT_SHOWN = `shown${EVENT_KEY}`
45
30
  const EVENT_HIDE = `hide${EVENT_KEY}`
@@ -59,30 +44,35 @@ const HEIGHT = 'height'
59
44
  const SELECTOR_ACTIVES = '.collapse.show, .collapse.collapsing'
60
45
  const SELECTOR_DATA_TOGGLE = '[data-bs-toggle="collapse"]'
61
46
 
47
+ const Default = {
48
+ parent: null,
49
+ toggle: true
50
+ }
51
+
52
+ const DefaultType = {
53
+ parent: '(null|element)',
54
+ toggle: 'boolean'
55
+ }
56
+
62
57
  /**
63
- * ------------------------------------------------------------------------
64
- * Class Definition
65
- * ------------------------------------------------------------------------
58
+ * Class definition
66
59
  */
67
60
 
68
61
  class Collapse extends BaseComponent {
69
62
  constructor(element, config) {
70
- super(element)
63
+ super(element, config)
71
64
 
72
65
  this._isTransitioning = false
73
- this._config = this._getConfig(config)
74
66
  this._triggerArray = []
75
67
 
76
68
  const toggleList = SelectorEngine.find(SELECTOR_DATA_TOGGLE)
77
69
 
78
- for (let i = 0, len = toggleList.length; i < len; i++) {
79
- const elem = toggleList[i]
70
+ for (const elem of toggleList) {
80
71
  const selector = getSelectorFromElement(elem)
81
72
  const filterElement = SelectorEngine.find(selector)
82
- .filter(foundElem => foundElem === this._element)
73
+ .filter(foundElement => foundElement === this._element)
83
74
 
84
75
  if (selector !== null && filterElement.length) {
85
- this._selector = selector
86
76
  this._triggerArray.push(elem)
87
77
  }
88
78
  }
@@ -99,17 +89,19 @@ class Collapse extends BaseComponent {
99
89
  }
100
90
 
101
91
  // Getters
102
-
103
92
  static get Default() {
104
93
  return Default
105
94
  }
106
95
 
96
+ static get DefaultType() {
97
+ return DefaultType
98
+ }
99
+
107
100
  static get NAME() {
108
101
  return NAME
109
102
  }
110
103
 
111
104
  // Public
112
-
113
105
  toggle() {
114
106
  if (this._isShown()) {
115
107
  this.hide()
@@ -123,22 +115,17 @@ class Collapse extends BaseComponent {
123
115
  return
124
116
  }
125
117
 
126
- let actives = []
127
- let activesData
118
+ let activeChildren = []
128
119
 
120
+ // find active children
129
121
  if (this._config.parent) {
130
- const children = SelectorEngine.find(CLASS_NAME_DEEPER_CHILDREN, this._config.parent)
131
- actives = SelectorEngine.find(SELECTOR_ACTIVES, this._config.parent).filter(elem => !children.includes(elem)) // remove children if greater depth
122
+ activeChildren = this._getFirstLevelChildren(SELECTOR_ACTIVES)
123
+ .filter(element => element !== this._element)
124
+ .map(element => Collapse.getOrCreateInstance(element, { toggle: false }))
132
125
  }
133
126
 
134
- const container = SelectorEngine.findOne(this._selector)
135
- if (actives.length) {
136
- const tempActiveData = actives.find(elem => container !== elem)
137
- activesData = tempActiveData ? Collapse.getInstance(tempActiveData) : null
138
-
139
- if (activesData && activesData._isTransitioning) {
140
- return
141
- }
127
+ if (activeChildren.length && activeChildren[0]._isTransitioning) {
128
+ return
142
129
  }
143
130
 
144
131
  const startEvent = EventHandler.trigger(this._element, EVENT_SHOW)
@@ -146,15 +133,9 @@ class Collapse extends BaseComponent {
146
133
  return
147
134
  }
148
135
 
149
- actives.forEach(elemActive => {
150
- if (container !== elemActive) {
151
- Collapse.getOrCreateInstance(elemActive, { toggle: false }).hide()
152
- }
153
-
154
- if (!activesData) {
155
- Data.set(elemActive, DATA_KEY, null)
156
- }
157
- })
136
+ for (const activeInstance of activeChildren) {
137
+ activeInstance.hide()
138
+ }
158
139
 
159
140
  const dimension = this._getDimension()
160
141
 
@@ -203,12 +184,10 @@ class Collapse extends BaseComponent {
203
184
  this._element.classList.add(CLASS_NAME_COLLAPSING)
204
185
  this._element.classList.remove(CLASS_NAME_COLLAPSE, CLASS_NAME_SHOW)
205
186
 
206
- const triggerArrayLength = this._triggerArray.length
207
- for (let i = 0; i < triggerArrayLength; i++) {
208
- const trigger = this._triggerArray[i]
209
- const elem = getElementFromSelector(trigger)
187
+ for (const trigger of this._triggerArray) {
188
+ const element = getElementFromSelector(trigger)
210
189
 
211
- if (elem && !this._isShown(elem)) {
190
+ if (element && !this._isShown(element)) {
212
191
  this._addAriaAndCollapsedClass([trigger], false)
213
192
  }
214
193
  }
@@ -232,16 +211,9 @@ class Collapse extends BaseComponent {
232
211
  }
233
212
 
234
213
  // Private
235
-
236
- _getConfig(config) {
237
- config = {
238
- ...Default,
239
- ...Manipulator.getDataAttributes(this._element),
240
- ...config
241
- }
214
+ _configAfterMerge(config) {
242
215
  config.toggle = Boolean(config.toggle) // Coerce string values
243
216
  config.parent = getElement(config.parent)
244
- typeCheckConfig(NAME, config, DefaultType)
245
217
  return config
246
218
  }
247
219
 
@@ -254,15 +226,21 @@ class Collapse extends BaseComponent {
254
226
  return
255
227
  }
256
228
 
257
- const children = SelectorEngine.find(CLASS_NAME_DEEPER_CHILDREN, this._config.parent)
258
- SelectorEngine.find(SELECTOR_DATA_TOGGLE, this._config.parent).filter(elem => !children.includes(elem))
259
- .forEach(element => {
260
- const selected = getElementFromSelector(element)
229
+ const children = this._getFirstLevelChildren(SELECTOR_DATA_TOGGLE)
261
230
 
262
- if (selected) {
263
- this._addAriaAndCollapsedClass([element], this._isShown(selected))
264
- }
265
- })
231
+ for (const element of children) {
232
+ const selected = getElementFromSelector(element)
233
+
234
+ if (selected) {
235
+ this._addAriaAndCollapsedClass([element], this._isShown(selected))
236
+ }
237
+ }
238
+ }
239
+
240
+ _getFirstLevelChildren(selector) {
241
+ const children = SelectorEngine.find(CLASS_NAME_DEEPER_CHILDREN, this._config.parent)
242
+ // remove children if greater depth
243
+ return SelectorEngine.find(selector, this._config.parent).filter(element => !children.includes(element))
266
244
  }
267
245
 
268
246
  _addAriaAndCollapsedClass(triggerArray, isOpen) {
@@ -270,26 +248,20 @@ class Collapse extends BaseComponent {
270
248
  return
271
249
  }
272
250
 
273
- triggerArray.forEach(elem => {
274
- if (isOpen) {
275
- elem.classList.remove(CLASS_NAME_COLLAPSED)
276
- } else {
277
- elem.classList.add(CLASS_NAME_COLLAPSED)
278
- }
279
-
280
- elem.setAttribute('aria-expanded', isOpen)
281
- })
251
+ for (const element of triggerArray) {
252
+ element.classList.toggle(CLASS_NAME_COLLAPSED, !isOpen)
253
+ element.setAttribute('aria-expanded', isOpen)
254
+ }
282
255
  }
283
256
 
284
257
  // Static
285
-
286
258
  static jQueryInterface(config) {
287
- return this.each(function () {
288
- const _config = {}
289
- if (typeof config === 'string' && /show|hide/.test(config)) {
290
- _config.toggle = false
291
- }
259
+ const _config = {}
260
+ if (typeof config === 'string' && /show|hide/.test(config)) {
261
+ _config.toggle = false
262
+ }
292
263
 
264
+ return this.each(function () {
293
265
  const data = Collapse.getOrCreateInstance(this, _config)
294
266
 
295
267
  if (typeof config === 'string') {
@@ -304,9 +276,7 @@ class Collapse extends BaseComponent {
304
276
  }
305
277
 
306
278
  /**
307
- * ------------------------------------------------------------------------
308
- * Data Api implementation
309
- * ------------------------------------------------------------------------
279
+ * Data API implementation
310
280
  */
311
281
 
312
282
  EventHandler.on(document, EVENT_CLICK_DATA_API, SELECTOR_DATA_TOGGLE, function (event) {
@@ -318,16 +288,13 @@ EventHandler.on(document, EVENT_CLICK_DATA_API, SELECTOR_DATA_TOGGLE, function (
318
288
  const selector = getSelectorFromElement(this)
319
289
  const selectorElements = SelectorEngine.find(selector)
320
290
 
321
- selectorElements.forEach(element => {
291
+ for (const element of selectorElements) {
322
292
  Collapse.getOrCreateInstance(element, { toggle: false }).toggle()
323
- })
293
+ }
324
294
  })
325
295
 
326
296
  /**
327
- * ------------------------------------------------------------------------
328
297
  * jQuery
329
- * ------------------------------------------------------------------------
330
- * add .Collapse to jQuery only if jQuery is present
331
298
  */
332
299
 
333
300
  defineJQueryPlugin(Collapse)
@@ -1,14 +1,12 @@
1
1
  /**
2
2
  * --------------------------------------------------------------------------
3
- * Bootstrap (v5.1.3): dom/data.js
3
+ * Bootstrap (v5.2.0): dom/data.js
4
4
  * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
5
5
  * --------------------------------------------------------------------------
6
6
  */
7
7
 
8
8
  /**
9
- * ------------------------------------------------------------------------
10
9
  * Constants
11
- * ------------------------------------------------------------------------
12
10
  */
13
11
 
14
12
  const elementMap = new Map()
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * --------------------------------------------------------------------------
3
- * Bootstrap (v5.1.3): dom/event-handler.js
3
+ * Bootstrap (v5.2.0): dom/event-handler.js
4
4
  * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
5
5
  * --------------------------------------------------------------------------
6
6
  */
@@ -8,9 +8,7 @@
8
8
  import { getjQuery } from '../util/index'
9
9
 
10
10
  /**
11
- * ------------------------------------------------------------------------
12
11
  * Constants
13
- * ------------------------------------------------------------------------
14
12
  */
15
13
 
16
14
  const namespaceRegex = /[^.]*(?=\..*)\.|.*/
@@ -22,7 +20,7 @@ const customEvents = {
22
20
  mouseenter: 'mouseover',
23
21
  mouseleave: 'mouseout'
24
22
  }
25
- const customEventsRegex = /^(mouseenter|mouseleave)/i
23
+
26
24
  const nativeEvents = new Set([
27
25
  'click',
28
26
  'dblclick',
@@ -73,17 +71,15 @@ const nativeEvents = new Set([
73
71
  ])
74
72
 
75
73
  /**
76
- * ------------------------------------------------------------------------
77
74
  * Private methods
78
- * ------------------------------------------------------------------------
79
75
  */
80
76
 
81
- function getUidEvent(element, uid) {
77
+ function makeEventUid(element, uid) {
82
78
  return (uid && `${uid}::${uidEvent++}`) || element.uidEvent || uidEvent++
83
79
  }
84
80
 
85
- function getEvent(element) {
86
- const uid = getUidEvent(element)
81
+ function getElementEvents(element) {
82
+ const uid = makeEventUid(element)
87
83
 
88
84
  element.uidEvent = uid
89
85
  eventRegistry[uid] = eventRegistry[uid] || {}
@@ -93,7 +89,7 @@ function getEvent(element) {
93
89
 
94
90
  function bootstrapHandler(element, fn) {
95
91
  return function handler(event) {
96
- event.delegateTarget = element
92
+ hydrateObj(event, { delegateTarget: element })
97
93
 
98
94
  if (handler.oneOff) {
99
95
  EventHandler.off(element, event.type, fn)
@@ -108,66 +104,52 @@ function bootstrapDelegationHandler(element, selector, fn) {
108
104
  const domElements = element.querySelectorAll(selector)
109
105
 
110
106
  for (let { target } = event; target && target !== this; target = target.parentNode) {
111
- for (let i = domElements.length; i--;) {
112
- if (domElements[i] === target) {
113
- event.delegateTarget = target
107
+ for (const domElement of domElements) {
108
+ if (domElement !== target) {
109
+ continue
110
+ }
114
111
 
115
- if (handler.oneOff) {
116
- EventHandler.off(element, event.type, selector, fn)
117
- }
112
+ hydrateObj(event, { delegateTarget: target })
118
113
 
119
- return fn.apply(target, [event])
114
+ if (handler.oneOff) {
115
+ EventHandler.off(element, event.type, selector, fn)
120
116
  }
117
+
118
+ return fn.apply(target, [event])
121
119
  }
122
120
  }
123
-
124
- // To please ESLint
125
- return null
126
121
  }
127
122
  }
128
123
 
129
- function findHandler(events, handler, delegationSelector = null) {
130
- const uidEventList = Object.keys(events)
131
-
132
- for (let i = 0, len = uidEventList.length; i < len; i++) {
133
- const event = events[uidEventList[i]]
134
-
135
- if (event.originalHandler === handler && event.delegationSelector === delegationSelector) {
136
- return event
137
- }
138
- }
139
-
140
- return null
124
+ function findHandler(events, callable, delegationSelector = null) {
125
+ return Object.values(events)
126
+ .find(event => event.callable === callable && event.delegationSelector === delegationSelector)
141
127
  }
142
128
 
143
- function normalizeParams(originalTypeEvent, handler, delegationFn) {
144
- const delegation = typeof handler === 'string'
145
- const originalHandler = delegation ? delegationFn : handler
146
-
129
+ function normalizeParameters(originalTypeEvent, handler, delegationFunction) {
130
+ const isDelegated = typeof handler === 'string'
131
+ // todo: tooltip passes `false` instead of selector, so we need to check
132
+ const callable = isDelegated ? delegationFunction : (handler || delegationFunction)
147
133
  let typeEvent = getTypeEvent(originalTypeEvent)
148
- const isNative = nativeEvents.has(typeEvent)
149
134
 
150
- if (!isNative) {
135
+ if (!nativeEvents.has(typeEvent)) {
151
136
  typeEvent = originalTypeEvent
152
137
  }
153
138
 
154
- return [delegation, originalHandler, typeEvent]
139
+ return [isDelegated, callable, typeEvent]
155
140
  }
156
141
 
157
- function addHandler(element, originalTypeEvent, handler, delegationFn, oneOff) {
142
+ function addHandler(element, originalTypeEvent, handler, delegationFunction, oneOff) {
158
143
  if (typeof originalTypeEvent !== 'string' || !element) {
159
144
  return
160
145
  }
161
146
 
162
- if (!handler) {
163
- handler = delegationFn
164
- delegationFn = null
165
- }
147
+ let [isDelegated, callable, typeEvent] = normalizeParameters(originalTypeEvent, handler, delegationFunction)
166
148
 
167
149
  // in case of mouseenter or mouseleave wrap the handler within a function that checks for its DOM position
168
150
  // this prevents the handler from being dispatched the same way as mouseover or mouseout does
169
- if (customEventsRegex.test(originalTypeEvent)) {
170
- const wrapFn = fn => {
151
+ if (originalTypeEvent in customEvents) {
152
+ const wrapFunction = fn => {
171
153
  return function (event) {
172
154
  if (!event.relatedTarget || (event.relatedTarget !== event.delegateTarget && !event.delegateTarget.contains(event.relatedTarget))) {
173
155
  return fn.call(this, event)
@@ -175,36 +157,31 @@ function addHandler(element, originalTypeEvent, handler, delegationFn, oneOff) {
175
157
  }
176
158
  }
177
159
 
178
- if (delegationFn) {
179
- delegationFn = wrapFn(delegationFn)
180
- } else {
181
- handler = wrapFn(handler)
182
- }
160
+ callable = wrapFunction(callable)
183
161
  }
184
162
 
185
- const [delegation, originalHandler, typeEvent] = normalizeParams(originalTypeEvent, handler, delegationFn)
186
- const events = getEvent(element)
163
+ const events = getElementEvents(element)
187
164
  const handlers = events[typeEvent] || (events[typeEvent] = {})
188
- const previousFn = findHandler(handlers, originalHandler, delegation ? handler : null)
165
+ const previousFunction = findHandler(handlers, callable, isDelegated ? handler : null)
189
166
 
190
- if (previousFn) {
191
- previousFn.oneOff = previousFn.oneOff && oneOff
167
+ if (previousFunction) {
168
+ previousFunction.oneOff = previousFunction.oneOff && oneOff
192
169
 
193
170
  return
194
171
  }
195
172
 
196
- const uid = getUidEvent(originalHandler, originalTypeEvent.replace(namespaceRegex, ''))
197
- const fn = delegation ?
198
- bootstrapDelegationHandler(element, handler, delegationFn) :
199
- bootstrapHandler(element, handler)
173
+ const uid = makeEventUid(callable, originalTypeEvent.replace(namespaceRegex, ''))
174
+ const fn = isDelegated ?
175
+ bootstrapDelegationHandler(element, handler, callable) :
176
+ bootstrapHandler(element, callable)
200
177
 
201
- fn.delegationSelector = delegation ? handler : null
202
- fn.originalHandler = originalHandler
178
+ fn.delegationSelector = isDelegated ? handler : null
179
+ fn.callable = callable
203
180
  fn.oneOff = oneOff
204
181
  fn.uidEvent = uid
205
182
  handlers[uid] = fn
206
183
 
207
- element.addEventListener(typeEvent, fn, delegation)
184
+ element.addEventListener(typeEvent, fn, isDelegated)
208
185
  }
209
186
 
210
187
  function removeHandler(element, events, typeEvent, handler, delegationSelector) {
@@ -221,13 +198,12 @@ function removeHandler(element, events, typeEvent, handler, delegationSelector)
221
198
  function removeNamespacedHandlers(element, events, typeEvent, namespace) {
222
199
  const storeElementEvent = events[typeEvent] || {}
223
200
 
224
- Object.keys(storeElementEvent).forEach(handlerKey => {
201
+ for (const handlerKey of Object.keys(storeElementEvent)) {
225
202
  if (handlerKey.includes(namespace)) {
226
203
  const event = storeElementEvent[handlerKey]
227
-
228
- removeHandler(element, events, typeEvent, event.originalHandler, event.delegationSelector)
204
+ removeHandler(element, events, typeEvent, event.callable, event.delegationSelector)
229
205
  }
230
- })
206
+ }
231
207
  }
232
208
 
233
209
  function getTypeEvent(event) {
@@ -237,50 +213,49 @@ function getTypeEvent(event) {
237
213
  }
238
214
 
239
215
  const EventHandler = {
240
- on(element, event, handler, delegationFn) {
241
- addHandler(element, event, handler, delegationFn, false)
216
+ on(element, event, handler, delegationFunction) {
217
+ addHandler(element, event, handler, delegationFunction, false)
242
218
  },
243
219
 
244
- one(element, event, handler, delegationFn) {
245
- addHandler(element, event, handler, delegationFn, true)
220
+ one(element, event, handler, delegationFunction) {
221
+ addHandler(element, event, handler, delegationFunction, true)
246
222
  },
247
223
 
248
- off(element, originalTypeEvent, handler, delegationFn) {
224
+ off(element, originalTypeEvent, handler, delegationFunction) {
249
225
  if (typeof originalTypeEvent !== 'string' || !element) {
250
226
  return
251
227
  }
252
228
 
253
- const [delegation, originalHandler, typeEvent] = normalizeParams(originalTypeEvent, handler, delegationFn)
229
+ const [isDelegated, callable, typeEvent] = normalizeParameters(originalTypeEvent, handler, delegationFunction)
254
230
  const inNamespace = typeEvent !== originalTypeEvent
255
- const events = getEvent(element)
231
+ const events = getElementEvents(element)
232
+ const storeElementEvent = events[typeEvent] || {}
256
233
  const isNamespace = originalTypeEvent.startsWith('.')
257
234
 
258
- if (typeof originalHandler !== 'undefined') {
235
+ if (typeof callable !== 'undefined') {
259
236
  // Simplest case: handler is passed, remove that listener ONLY.
260
- if (!events || !events[typeEvent]) {
237
+ if (!Object.keys(storeElementEvent).length) {
261
238
  return
262
239
  }
263
240
 
264
- removeHandler(element, events, typeEvent, originalHandler, delegation ? handler : null)
241
+ removeHandler(element, events, typeEvent, callable, isDelegated ? handler : null)
265
242
  return
266
243
  }
267
244
 
268
245
  if (isNamespace) {
269
- Object.keys(events).forEach(elementEvent => {
246
+ for (const elementEvent of Object.keys(events)) {
270
247
  removeNamespacedHandlers(element, events, elementEvent, originalTypeEvent.slice(1))
271
- })
248
+ }
272
249
  }
273
250
 
274
- const storeElementEvent = events[typeEvent] || {}
275
- Object.keys(storeElementEvent).forEach(keyHandlers => {
251
+ for (const keyHandlers of Object.keys(storeElementEvent)) {
276
252
  const handlerKey = keyHandlers.replace(stripUidRegex, '')
277
253
 
278
254
  if (!inNamespace || originalTypeEvent.includes(handlerKey)) {
279
255
  const event = storeElementEvent[keyHandlers]
280
-
281
- removeHandler(element, events, typeEvent, event.originalHandler, event.delegationSelector)
256
+ removeHandler(element, events, typeEvent, event.callable, event.delegationSelector)
282
257
  }
283
- })
258
+ }
284
259
  },
285
260
 
286
261
  trigger(element, event, args) {
@@ -291,13 +266,11 @@ const EventHandler = {
291
266
  const $ = getjQuery()
292
267
  const typeEvent = getTypeEvent(event)
293
268
  const inNamespace = event !== typeEvent
294
- const isNative = nativeEvents.has(typeEvent)
295
269
 
296
- let jQueryEvent
270
+ let jQueryEvent = null
297
271
  let bubbles = true
298
272
  let nativeDispatch = true
299
273
  let defaultPrevented = false
300
- let evt = null
301
274
 
302
275
  if (inNamespace && $) {
303
276
  jQueryEvent = $.Event(event, args)
@@ -308,26 +281,8 @@ const EventHandler = {
308
281
  defaultPrevented = jQueryEvent.isDefaultPrevented()
309
282
  }
310
283
 
311
- if (isNative) {
312
- evt = document.createEvent('HTMLEvents')
313
- evt.initEvent(typeEvent, bubbles, true)
314
- } else {
315
- evt = new CustomEvent(event, {
316
- bubbles,
317
- cancelable: true
318
- })
319
- }
320
-
321
- // merge custom information in our event
322
- if (typeof args !== 'undefined') {
323
- Object.keys(args).forEach(key => {
324
- Object.defineProperty(evt, key, {
325
- get() {
326
- return args[key]
327
- }
328
- })
329
- })
330
- }
284
+ let evt = new Event(event, { bubbles, cancelable: true })
285
+ evt = hydrateObj(evt, args)
331
286
 
332
287
  if (defaultPrevented) {
333
288
  evt.preventDefault()
@@ -337,7 +292,7 @@ const EventHandler = {
337
292
  element.dispatchEvent(evt)
338
293
  }
339
294
 
340
- if (evt.defaultPrevented && typeof jQueryEvent !== 'undefined') {
295
+ if (evt.defaultPrevented && jQueryEvent) {
341
296
  jQueryEvent.preventDefault()
342
297
  }
343
298
 
@@ -345,4 +300,21 @@ const EventHandler = {
345
300
  }
346
301
  }
347
302
 
303
+ function hydrateObj(obj, meta) {
304
+ for (const [key, value] of Object.entries(meta || {})) {
305
+ try {
306
+ obj[key] = value
307
+ } catch {
308
+ Object.defineProperty(obj, key, {
309
+ configurable: true,
310
+ get() {
311
+ return value
312
+ }
313
+ })
314
+ }
315
+ }
316
+
317
+ return obj
318
+ }
319
+
348
320
  export default EventHandler