@studiometa/js-toolkit 1.7.2 → 2.0.0-alpha.10

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 (237) hide show
  1. package/Base/index.d.ts +217 -0
  2. package/Base/index.js +237 -0
  3. package/Base/managers/ChildrenManager.d.ts +108 -0
  4. package/Base/managers/ChildrenManager.js +124 -0
  5. package/Base/managers/EventsManager.d.ts +190 -0
  6. package/Base/managers/EventsManager.js +195 -0
  7. package/Base/managers/OptionsManager.d.ts +120 -0
  8. package/Base/managers/OptionsManager.js +180 -0
  9. package/Base/managers/RefsManager.d.ts +84 -0
  10. package/Base/managers/RefsManager.js +83 -0
  11. package/{abstracts/Base/classes/Services.d.ts → Base/managers/ServicesManager.d.ts} +22 -7
  12. package/Base/managers/ServicesManager.js +115 -0
  13. package/{abstracts/Base → Base}/utils.d.ts +0 -30
  14. package/Base/utils.js +43 -0
  15. package/README.md +12 -70
  16. package/decorators/index.js +1 -2
  17. package/decorators/withBreakpointManager.d.ts +5 -5
  18. package/decorators/withBreakpointManager.js +41 -79
  19. package/decorators/withBreakpointObserver.d.ts +4 -4
  20. package/decorators/withBreakpointObserver.js +54 -77
  21. package/decorators/withDrag.d.ts +6 -6
  22. package/decorators/withDrag.js +17 -41
  23. package/decorators/withExtraConfig.d.ts +6 -6
  24. package/decorators/withExtraConfig.js +2 -24
  25. package/decorators/withIntersectionObserver.d.ts +4 -4
  26. package/decorators/withIntersectionObserver.js +17 -60
  27. package/decorators/withMountWhenInView.d.ts +8 -8
  28. package/decorators/withMountWhenInView.js +23 -51
  29. package/helpers/createApp.d.ts +4 -4
  30. package/helpers/createApp.js +10 -12
  31. package/helpers/importOnInteraction.d.ts +6 -6
  32. package/helpers/importOnInteraction.js +7 -8
  33. package/helpers/importWhenIdle.d.ts +4 -4
  34. package/helpers/importWhenIdle.js +7 -8
  35. package/helpers/importWhenVisible.d.ts +6 -6
  36. package/helpers/importWhenVisible.js +9 -16
  37. package/helpers/index.d.ts +1 -3
  38. package/helpers/index.js +1 -4
  39. package/helpers/utils.js +2 -3
  40. package/index.d.ts +19 -5
  41. package/index.js +5 -6
  42. package/index.modern.js +1 -3230
  43. package/index.umd.js +1 -3586
  44. package/package.json +3 -6
  45. package/{abstracts → services}/Service.d.ts +0 -0
  46. package/services/Service.js +63 -0
  47. package/services/drag.js +144 -180
  48. package/services/index.js +1 -2
  49. package/services/key.js +56 -98
  50. package/services/load.d.ts +1 -1
  51. package/services/load.js +22 -51
  52. package/services/pointer.js +118 -157
  53. package/services/raf.js +37 -65
  54. package/services/resize.js +46 -98
  55. package/services/scroll.js +81 -120
  56. package/utils/collide/boundingRectToCircle.js +7 -6
  57. package/utils/collide/collideCircleCircle.js +1 -2
  58. package/utils/collide/collideCircleRect.js +1 -2
  59. package/utils/collide/collidePointCircle.js +1 -2
  60. package/utils/collide/collidePointRect.js +1 -2
  61. package/utils/collide/collideRectRect.js +1 -2
  62. package/utils/collide/index.js +1 -2
  63. package/utils/css/classes.js +2 -3
  64. package/utils/css/index.js +1 -2
  65. package/utils/css/matrix.js +1 -2
  66. package/utils/css/styles.js +3 -8
  67. package/utils/css/transition.js +67 -140
  68. package/utils/debounce.js +3 -4
  69. package/utils/focusTrap.js +4 -5
  70. package/utils/history.js +12 -19
  71. package/utils/index.d.ts +2 -1
  72. package/utils/index.js +2 -2
  73. package/utils/keyCodes.js +1 -2
  74. package/utils/math/clamp.js +1 -2
  75. package/utils/math/clamp01.js +1 -2
  76. package/utils/math/damp.js +1 -2
  77. package/utils/math/index.js +1 -2
  78. package/utils/math/inertiaFinalValue.js +1 -2
  79. package/utils/math/lerp.js +1 -2
  80. package/utils/math/map.js +1 -2
  81. package/utils/math/round.js +1 -2
  82. package/utils/memoize.d.ts +30 -0
  83. package/utils/memoize.js +30 -0
  84. package/utils/nextFrame.js +4 -9
  85. package/utils/object/autoBind.js +11 -19
  86. package/utils/object/getAllProperties.d.ts +6 -3
  87. package/utils/object/getAllProperties.js +10 -8
  88. package/utils/object/index.js +1 -2
  89. package/utils/object/isObject.js +2 -4
  90. package/utils/string/index.js +1 -2
  91. package/utils/string/withLeadingCharacters.js +1 -2
  92. package/utils/string/withLeadingSlash.js +1 -2
  93. package/utils/string/withTrailingCharacters.js +1 -2
  94. package/utils/string/withTrailingSlash.js +1 -2
  95. package/utils/string/withoutLeadingCharacters.js +1 -2
  96. package/utils/string/withoutLeadingCharactersRecursive.js +1 -2
  97. package/utils/string/withoutLeadingSlash.js +1 -2
  98. package/utils/string/withoutTrailingCharacters.js +1 -2
  99. package/utils/string/withoutTrailingCharactersRecursive.js +1 -2
  100. package/utils/string/withoutTrailingSlash.js +1 -2
  101. package/utils/throttle.js +2 -3
  102. package/abstracts/Base/children.d.ts +0 -16
  103. package/abstracts/Base/children.js +0 -66
  104. package/abstracts/Base/children.js.map +0 -1
  105. package/abstracts/Base/classes/Options.d.ts +0 -37
  106. package/abstracts/Base/classes/Options.js +0 -182
  107. package/abstracts/Base/classes/Options.js.map +0 -1
  108. package/abstracts/Base/classes/Services.js +0 -120
  109. package/abstracts/Base/classes/Services.js.map +0 -1
  110. package/abstracts/Base/components.d.ts +0 -22
  111. package/abstracts/Base/components.js +0 -67
  112. package/abstracts/Base/components.js.map +0 -1
  113. package/abstracts/Base/events.d.ts +0 -8
  114. package/abstracts/Base/events.js +0 -185
  115. package/abstracts/Base/events.js.map +0 -1
  116. package/abstracts/Base/index.d.ts +0 -176
  117. package/abstracts/Base/index.js +0 -215
  118. package/abstracts/Base/index.js.map +0 -1
  119. package/abstracts/Base/options.d.ts +0 -17
  120. package/abstracts/Base/options.js +0 -112
  121. package/abstracts/Base/options.js.map +0 -1
  122. package/abstracts/Base/refs.d.ts +0 -30
  123. package/abstracts/Base/refs.js +0 -60
  124. package/abstracts/Base/refs.js.map +0 -1
  125. package/abstracts/Base/utils.js +0 -102
  126. package/abstracts/Base/utils.js.map +0 -1
  127. package/abstracts/EventManager.d.ts +0 -41
  128. package/abstracts/EventManager.js +0 -88
  129. package/abstracts/EventManager.js.map +0 -1
  130. package/abstracts/Service.js +0 -82
  131. package/abstracts/Service.js.map +0 -1
  132. package/abstracts/index.d.ts +0 -4
  133. package/abstracts/index.js +0 -5
  134. package/abstracts/index.js.map +0 -1
  135. package/components/Accordion/Accordion.d.ts +0 -83
  136. package/components/Accordion/Accordion.js +0 -121
  137. package/components/Accordion/Accordion.js.map +0 -1
  138. package/components/Accordion/AccordionItem.d.ts +0 -122
  139. package/components/Accordion/AccordionItem.js +0 -327
  140. package/components/Accordion/AccordionItem.js.map +0 -1
  141. package/components/Accordion/index.d.ts +0 -27
  142. package/components/Accordion/index.js +0 -39
  143. package/components/Accordion/index.js.map +0 -1
  144. package/components/Cursor.d.ts +0 -138
  145. package/components/Cursor.js +0 -167
  146. package/components/Cursor.js.map +0 -1
  147. package/components/Draggable.d.ts +0 -49
  148. package/components/Draggable.js +0 -77
  149. package/components/Draggable.js.map +0 -1
  150. package/components/Modal.d.ts +0 -158
  151. package/components/Modal.js +0 -270
  152. package/components/Modal.js.map +0 -1
  153. package/components/Tabs.d.ts +0 -108
  154. package/components/Tabs.js +0 -195
  155. package/components/Tabs.js.map +0 -1
  156. package/components/index.d.ts +0 -6
  157. package/components/index.js +0 -7
  158. package/components/index.js.map +0 -1
  159. package/decorators/index.js.map +0 -1
  160. package/decorators/withBreakpointManager.js.map +0 -1
  161. package/decorators/withBreakpointObserver.js.map +0 -1
  162. package/decorators/withDrag.js.map +0 -1
  163. package/decorators/withExtraConfig.js.map +0 -1
  164. package/decorators/withIntersectionObserver.js.map +0 -1
  165. package/decorators/withMountWhenInView.js.map +0 -1
  166. package/full.d.ts +0 -10
  167. package/full.js +0 -12
  168. package/full.js.map +0 -1
  169. package/full.modern.js +0 -7523
  170. package/full.modern.js.map +0 -1
  171. package/full.umd.js +0 -8277
  172. package/full.umd.js.map +0 -1
  173. package/helpers/createApp.js.map +0 -1
  174. package/helpers/createBase.d.ts +0 -7
  175. package/helpers/createBase.js +0 -7
  176. package/helpers/createBase.js.map +0 -1
  177. package/helpers/defineComponent.d.ts +0 -11
  178. package/helpers/defineComponent.js +0 -68
  179. package/helpers/defineComponent.js.map +0 -1
  180. package/helpers/importOnInteraction.js.map +0 -1
  181. package/helpers/importWhenIdle.js.map +0 -1
  182. package/helpers/importWhenVisible.js.map +0 -1
  183. package/helpers/index.js.map +0 -1
  184. package/helpers/utils.js.map +0 -1
  185. package/index.js.map +0 -1
  186. package/index.modern.js.map +0 -1
  187. package/index.umd.js.map +0 -1
  188. package/services/drag.js.map +0 -1
  189. package/services/index.js.map +0 -1
  190. package/services/key.js.map +0 -1
  191. package/services/load.js.map +0 -1
  192. package/services/pointer.js.map +0 -1
  193. package/services/raf.js.map +0 -1
  194. package/services/resize.js.map +0 -1
  195. package/services/scroll.js.map +0 -1
  196. package/utils/collide/boundingRectToCircle.js.map +0 -1
  197. package/utils/collide/collideCircleCircle.js.map +0 -1
  198. package/utils/collide/collideCircleRect.js.map +0 -1
  199. package/utils/collide/collidePointCircle.js.map +0 -1
  200. package/utils/collide/collidePointRect.js.map +0 -1
  201. package/utils/collide/collideRectRect.js.map +0 -1
  202. package/utils/collide/index.js.map +0 -1
  203. package/utils/css/classes.js.map +0 -1
  204. package/utils/css/index.js.map +0 -1
  205. package/utils/css/matrix.js.map +0 -1
  206. package/utils/css/styles.js.map +0 -1
  207. package/utils/css/transition.js.map +0 -1
  208. package/utils/debounce.js.map +0 -1
  209. package/utils/focusTrap.js.map +0 -1
  210. package/utils/history.js.map +0 -1
  211. package/utils/index.js.map +0 -1
  212. package/utils/keyCodes.js.map +0 -1
  213. package/utils/math/clamp.js.map +0 -1
  214. package/utils/math/clamp01.js.map +0 -1
  215. package/utils/math/damp.js.map +0 -1
  216. package/utils/math/index.js.map +0 -1
  217. package/utils/math/inertiaFinalValue.js.map +0 -1
  218. package/utils/math/lerp.js.map +0 -1
  219. package/utils/math/map.js.map +0 -1
  220. package/utils/math/round.js.map +0 -1
  221. package/utils/nextFrame.js.map +0 -1
  222. package/utils/object/autoBind.js.map +0 -1
  223. package/utils/object/getAllProperties.js.map +0 -1
  224. package/utils/object/index.js.map +0 -1
  225. package/utils/object/isObject.js.map +0 -1
  226. package/utils/string/index.js.map +0 -1
  227. package/utils/string/withLeadingCharacters.js.map +0 -1
  228. package/utils/string/withLeadingSlash.js.map +0 -1
  229. package/utils/string/withTrailingCharacters.js.map +0 -1
  230. package/utils/string/withTrailingSlash.js.map +0 -1
  231. package/utils/string/withoutLeadingCharacters.js.map +0 -1
  232. package/utils/string/withoutLeadingCharactersRecursive.js.map +0 -1
  233. package/utils/string/withoutLeadingSlash.js.map +0 -1
  234. package/utils/string/withoutTrailingCharacters.js.map +0 -1
  235. package/utils/string/withoutTrailingCharactersRecursive.js.map +0 -1
  236. package/utils/string/withoutTrailingSlash.js.map +0 -1
  237. package/utils/throttle.js.map +0 -1
package/index.modern.js CHANGED
@@ -1,3230 +1 @@
1
- /**
2
- * Gets all non-builtin properties up the prototype chain.
3
- *
4
- * @param {Object} object The object to get the propeties from.
5
- * @param {Array=} [props=[]] The already existing properties.
6
- * @return {Array<[String, Object]>} An array of properties and the prototype they belong to.
7
- */
8
- function getAllProperties(object, props = []) {
9
- const proto = Object.getPrototypeOf(object);
10
-
11
- if (proto === Object.prototype) {
12
- return props;
13
- }
14
-
15
- return getAllProperties(proto, Object.getOwnPropertyNames(proto).map(name => [name, proto]).reduce((acc, val) => [...acc, val], props));
16
- }
17
-
18
- /**
19
- * Auto-bind methods to an instance.
20
- *
21
- * @param {Object} instance The instance.
22
- * @param {Object} options Define specific methods to include or exlude.
23
- * @param {Array<String|RegExp>} [options.include] Methods to include.
24
- * @param {Array<String|RegExp>} [options.exclude] Methods to exclude.
25
- * @return {Object} The instance.
26
- */
27
-
28
- function autoBind(instance, options) {
29
- const {
30
- exclude,
31
- include
32
- } = options || {};
33
-
34
- const filter = key => {
35
- const match = pattern => typeof pattern === 'string' ? key === pattern : pattern.test(key);
36
-
37
- if (include) {
38
- return include.some(match);
39
- }
40
-
41
- if (exclude) {
42
- return !exclude.some(match);
43
- }
44
-
45
- return true;
46
- };
47
-
48
- getAllProperties(instance).filter(([key]) => key !== 'constructor' && filter(key)).forEach(([key, object]) => {
49
- const descriptor = Object.getOwnPropertyDescriptor(object, key);
50
-
51
- if (descriptor && typeof descriptor.value === 'function') {
52
- instance[key] = instance[key].bind(instance);
53
- }
54
- });
55
- return instance;
56
- }
57
-
58
- /* eslint no-underscore-dangle: ["error", { "allow": ["_events"] }] */
59
-
60
- /**
61
- * Event management class.
62
- */
63
- class EventManager {
64
- constructor() {
65
- this._events = {};
66
- }
67
-
68
- /**
69
- * Bind a listener function to an event.
70
- *
71
- * @param {String} event Name of the event.
72
- * @param {Function} listener Function to be called.
73
- * @return {Function} A function to unbind the listener.
74
- */
75
- $on(event, listener) {
76
- if (!Array.isArray(this._events[event])) {
77
- this._events[event] = [];
78
- }
79
-
80
- this._events[event].push(listener);
81
-
82
- return () => {
83
- this.$off(event, listener);
84
- };
85
- }
86
- /**
87
- * Unbind a listener function from an event.
88
- *
89
- * @param {String} event Name of the event.
90
- * @param {Function} listener Function to be removed.
91
- * @return {EventManager} The current instance.
92
- */
93
-
94
-
95
- $off(event, listener) {
96
- // If no event specified, we remove them all.
97
- if (!event) {
98
- this._events = {};
99
- return this;
100
- } // If no listener have been specified, we remove all
101
- // the listeners for the given event.
102
-
103
-
104
- if (!listener) {
105
- this._events[event] = [];
106
- return this;
107
- }
108
-
109
- const index = this._events[event].indexOf(listener);
110
-
111
- if (index > -1) {
112
- this._events[event].splice(index, 1);
113
- }
114
-
115
- return this;
116
- }
117
- /**
118
- * Emits an event.
119
- *
120
- * @param {String} event Name of the event.
121
- * @param {Array} args The arguments to apply to the functions bound to this event.
122
- * @return {EventManager} The current instance.
123
- */
124
-
125
-
126
- $emit(event, ...args) {
127
- if (!Array.isArray(this._events[event])) {
128
- return this;
129
- }
130
-
131
- this._events[event].forEach(listener => {
132
- listener.apply(this, args);
133
- });
134
-
135
- return this;
136
- }
137
- /**
138
- * Bind a listener function to an event for one execution only.
139
- *
140
- * @param {String} event Name of the event.
141
- * @param {Function} listener Function to be called.
142
- * @return {EventManager} The current instance.
143
- */
144
-
145
-
146
- $once(event, listener) {
147
- const instance = this;
148
- this.$on(event,
149
- /**
150
- * @param {...any} args
151
- */
152
- function handler(...args) {
153
- instance.$off(event, handler);
154
- listener.apply(instance, args);
155
- });
156
- return this;
157
- }
158
-
159
- }
160
-
161
- /**
162
- * @typedef {import('./index.js').default} Base
163
- * @typedef {import('./index.js').BaseConfig} BaseConfig
164
- */
165
-
166
- /**
167
- * Get the config from a Base instance, either the new static one or the old getter one.
168
- *
169
- * @param {Base} instance The instance to get the config from.
170
- * @return {BaseConfig} A Base class configuration object.
171
- */
172
- function getConfig(instance) {
173
- // @ts-ignore
174
- const config = instance.constructor.config || instance.config;
175
-
176
- if (!config) {
177
- throw new Error('The `config` property must be defined.');
178
- }
179
-
180
- if (!config.name) {
181
- throw new Error('The `config.name` property is required.');
182
- } // @ts-ignore
183
-
184
-
185
- if (instance.config && !instance.constructor.config) {
186
- console.warn(`[${config.name}]`, 'Defining the `config` as a getter is deprecated, replace it with a static property.');
187
- }
188
-
189
- return config;
190
- }
191
- /**
192
- * Display a console warning for the given instance.
193
- *
194
- * @param {Base} instance A Base instance.
195
- * @param {...String} msg Values to display in the console.
196
- */
197
-
198
- function warn(instance, ...msg) {
199
- const {
200
- name
201
- } = getConfig(instance);
202
- console.warn(`[${name}]`, ...msg);
203
- }
204
- /**
205
- * Display a console log for the given instance.
206
- *
207
- * @param {Base} instance The instance to log information from.
208
- * @param {...any} msg The data to print to the console.
209
- */
210
-
211
- function log(instance, ...msg) {
212
- const {
213
- name
214
- } = getConfig(instance);
215
- console.log(`[${name}]`, ...msg);
216
- }
217
- /**
218
- * Verbose debug for the component.
219
- *
220
- * @param {Base} instance The instance to debug.
221
- * @param {...any} args The data to print.
222
- */
223
-
224
- function debug(instance, ...args) {
225
- if (instance.$options.debug) {
226
- log(instance, '[debug]', ...args);
227
- }
228
- }
229
- /**
230
- * Test if an object has a method.
231
- *
232
- * @param {Object} obj The object to test
233
- * @param {String} name The method's name
234
- * @return {Boolean}
235
- */
236
-
237
- function hasMethod(obj, name) {
238
- return typeof obj[name] === 'function';
239
- }
240
- /**
241
- * Call the given method while applying the given arguments.
242
- *
243
- * @param {Base} instance The Base instance on which to trigger the method.
244
- * @param {String} method The method to call.
245
- * @param {...any} args The arguments to pass to the method.
246
- */
247
-
248
- function callMethod(instance, method, ...args) {
249
- if (__DEV__) {
250
- debug(instance, 'callMethod', method, ...args);
251
- } // Prevent duplicate call of `mounted` and `destroyed`
252
- // methods based on the component status
253
-
254
-
255
- if (method === 'destroyed' && !instance.$isMounted || method === 'mounted' && instance.$isMounted) {
256
- if (__DEV__) {
257
- debug(instance, 'not', method, 'because the method has already been triggered once.');
258
- }
259
-
260
- return instance;
261
- }
262
-
263
- instance.$emit(method, ...args); // We always emit an event, but we do not call the method if it does not exist
264
-
265
- if (!hasMethod(instance, method)) {
266
- return instance;
267
- }
268
-
269
- instance[method].call(instance, ...args);
270
-
271
- if (__DEV__) {
272
- debug(instance, method, instance, ...args);
273
- }
274
-
275
- return instance;
276
- }
277
- /**
278
- * Get a list of elements based on the name of a component.
279
- *
280
- * @param {String} nameOrSelector
281
- * The name or selector to used for this component.
282
- * @param {HTMLElement|Document} element
283
- * The root element on which to query the selector, defaults to `document`.
284
- * @return {Array<HTMLElement>}
285
- * A list of elements on which the component should be mounted.
286
- */
287
-
288
- function getComponentElements(nameOrSelector, element = document) {
289
- const selector = `[data-component="${nameOrSelector}"]`;
290
- let elements = [];
291
-
292
- try {
293
- elements = Array.from(element.querySelectorAll(selector)); // eslint-disable-next-line no-empty
294
- } catch (_unused) {} // If no child component found with the default selector, try a classic DOM selector
295
-
296
-
297
- if (elements.length === 0) {
298
- elements = Array.from(element.querySelectorAll(nameOrSelector));
299
- }
300
-
301
- return elements;
302
- }
303
-
304
- /**
305
- * @typedef {import('./index.js').default} Base
306
- * @typedef {import('./index.js').BaseComponent} BaseComponent
307
- * @typedef {import('./index.js').BaseAsyncComponent} BaseAsyncComponent
308
- * @typedef {import('./index.js').BaseConfigComponents} BaseConfigComponents
309
- */
310
-
311
- /**
312
- * Get a child component.
313
- *
314
- * @param {HTMLElement & { __base__?: Base | 'terminated' }} el
315
- * The root element of the child component.
316
- * @param {BaseComponent|BaseAsyncComponent} ComponentClass
317
- * A Base class or a Promise for async components.
318
- * @param {Base} parent
319
- * The parent component instance.
320
- * @return {Base|Promise|'terminated'}
321
- * A Base instance or a Promise resolving to a Base instance.
322
- */
323
-
324
- function getChild(el, ComponentClass, parent) {
325
- // Return existing instance if it exists
326
- if (el.__base__) {
327
- return el.__base__;
328
- } // Return a new instance if the component class is a child of the Base class
329
-
330
-
331
- if ('$isBase' in ComponentClass) {
332
- const child = new ComponentClass(el);
333
- Object.defineProperty(child, '$parent', {
334
- get: () => parent
335
- });
336
- return child;
337
- } // Resolve async components
338
-
339
-
340
- return ComponentClass(parent).then(module => {
341
- var _module$default;
342
-
343
- // @ts-ignore
344
- return getChild(el, (_module$default = module.default) != null ? _module$default : module, parent);
345
- });
346
- }
347
- /**
348
- * Get child components.
349
- * @param {Base} instance The component's instance.
350
- * @param {HTMLElement} element The component's root element
351
- * @param {BaseConfigComponents} components The children components' classes
352
- * @return {null|Object} Returns `null` if no child components are defined or an object of all child component instances
353
- */
354
-
355
-
356
- function getChildren(instance, element, components) {
357
- if (__DEV__) {
358
- debug(instance, 'before:getChildren', element, components);
359
- }
360
-
361
- const children = Object.entries(components).reduce((acc, [name, ComponentClass]) => {
362
- Object.defineProperty(acc, name, {
363
- get() {
364
- const elements = getComponentElements(name, element);
365
-
366
- if (elements.length === 0) {
367
- return [];
368
- }
369
-
370
- return elements.map(el => getChild(el, ComponentClass, instance)) // Filter out terminated children
371
- // @ts-ignore
372
- .filter(el => el !== 'terminated');
373
- },
374
-
375
- enumerable: true,
376
- configurable: true
377
- });
378
- return acc;
379
- }, {});
380
- instance.$emit('get:children', children);
381
-
382
- if (__DEV__) {
383
- debug(instance, 'after:getChildren', children);
384
- }
385
-
386
- return children;
387
- }
388
-
389
- function _extends() {
390
- _extends = Object.assign || function (target) {
391
- for (var i = 1; i < arguments.length; i++) {
392
- var source = arguments[i];
393
-
394
- for (var key in source) {
395
- if (Object.prototype.hasOwnProperty.call(source, key)) {
396
- target[key] = source[key];
397
- }
398
- }
399
- }
400
-
401
- return target;
402
- };
403
-
404
- return _extends.apply(this, arguments);
405
- }
406
-
407
- function _objectWithoutPropertiesLoose(source, excluded) {
408
- if (source == null) return {};
409
- var target = {};
410
- var sourceKeys = Object.keys(source);
411
- var key, i;
412
-
413
- for (i = 0; i < sourceKeys.length; i++) {
414
- key = sourceKeys[i];
415
- if (excluded.indexOf(key) >= 0) continue;
416
- target[key] = source[key];
417
- }
418
-
419
- return target;
420
- }
421
-
422
- var id$1 = 0;
423
-
424
- function _classPrivateFieldLooseKey(name) {
425
- return "__private_" + id$1++ + "_" + name;
426
- }
427
-
428
- function _classPrivateFieldLooseBase(receiver, privateKey) {
429
- if (!Object.prototype.hasOwnProperty.call(receiver, privateKey)) {
430
- throw new TypeError("attempted to use private field on non-instance");
431
- }
432
-
433
- return receiver;
434
- }
435
-
436
- var isMergeableObject = function isMergeableObject(value) {
437
- return isNonNullObject(value)
438
- && !isSpecial(value)
439
- };
440
-
441
- function isNonNullObject(value) {
442
- return !!value && typeof value === 'object'
443
- }
444
-
445
- function isSpecial(value) {
446
- var stringValue = Object.prototype.toString.call(value);
447
-
448
- return stringValue === '[object RegExp]'
449
- || stringValue === '[object Date]'
450
- || isReactElement(value)
451
- }
452
-
453
- // see https://github.com/facebook/react/blob/b5ac963fb791d1298e7f396236383bc955f916c1/src/isomorphic/classic/element/ReactElement.js#L21-L25
454
- var canUseSymbol = typeof Symbol === 'function' && Symbol.for;
455
- var REACT_ELEMENT_TYPE = canUseSymbol ? Symbol.for('react.element') : 0xeac7;
456
-
457
- function isReactElement(value) {
458
- return value.$$typeof === REACT_ELEMENT_TYPE
459
- }
460
-
461
- function emptyTarget(val) {
462
- return Array.isArray(val) ? [] : {}
463
- }
464
-
465
- function cloneUnlessOtherwiseSpecified(value, options) {
466
- return (options.clone !== false && options.isMergeableObject(value))
467
- ? deepmerge(emptyTarget(value), value, options)
468
- : value
469
- }
470
-
471
- function defaultArrayMerge(target, source, options) {
472
- return target.concat(source).map(function(element) {
473
- return cloneUnlessOtherwiseSpecified(element, options)
474
- })
475
- }
476
-
477
- function getMergeFunction(key, options) {
478
- if (!options.customMerge) {
479
- return deepmerge
480
- }
481
- var customMerge = options.customMerge(key);
482
- return typeof customMerge === 'function' ? customMerge : deepmerge
483
- }
484
-
485
- function getEnumerableOwnPropertySymbols(target) {
486
- return Object.getOwnPropertySymbols
487
- ? Object.getOwnPropertySymbols(target).filter(function(symbol) {
488
- return target.propertyIsEnumerable(symbol)
489
- })
490
- : []
491
- }
492
-
493
- function getKeys(target) {
494
- return Object.keys(target).concat(getEnumerableOwnPropertySymbols(target))
495
- }
496
-
497
- function propertyIsOnObject(object, property) {
498
- try {
499
- return property in object
500
- } catch(_) {
501
- return false
502
- }
503
- }
504
-
505
- // Protects from prototype poisoning and unexpected merging up the prototype chain.
506
- function propertyIsUnsafe(target, key) {
507
- return propertyIsOnObject(target, key) // Properties are safe to merge if they don't exist in the target yet,
508
- && !(Object.hasOwnProperty.call(target, key) // unsafe if they exist up the prototype chain,
509
- && Object.propertyIsEnumerable.call(target, key)) // and also unsafe if they're nonenumerable.
510
- }
511
-
512
- function mergeObject(target, source, options) {
513
- var destination = {};
514
- if (options.isMergeableObject(target)) {
515
- getKeys(target).forEach(function(key) {
516
- destination[key] = cloneUnlessOtherwiseSpecified(target[key], options);
517
- });
518
- }
519
- getKeys(source).forEach(function(key) {
520
- if (propertyIsUnsafe(target, key)) {
521
- return
522
- }
523
-
524
- if (propertyIsOnObject(target, key) && options.isMergeableObject(source[key])) {
525
- destination[key] = getMergeFunction(key, options)(target[key], source[key], options);
526
- } else {
527
- destination[key] = cloneUnlessOtherwiseSpecified(source[key], options);
528
- }
529
- });
530
- return destination
531
- }
532
-
533
- function deepmerge(target, source, options) {
534
- options = options || {};
535
- options.arrayMerge = options.arrayMerge || defaultArrayMerge;
536
- options.isMergeableObject = options.isMergeableObject || isMergeableObject;
537
- // cloneUnlessOtherwiseSpecified is added to `options` so that custom arrayMerge()
538
- // implementations can use it. The caller may not replace it.
539
- options.cloneUnlessOtherwiseSpecified = cloneUnlessOtherwiseSpecified;
540
-
541
- var sourceIsArray = Array.isArray(source);
542
- var targetIsArray = Array.isArray(target);
543
- var sourceAndTargetTypesMatch = sourceIsArray === targetIsArray;
544
-
545
- if (!sourceAndTargetTypesMatch) {
546
- return cloneUnlessOtherwiseSpecified(source, options)
547
- } else if (sourceIsArray) {
548
- return options.arrayMerge(target, source, options)
549
- } else {
550
- return mergeObject(target, source, options)
551
- }
552
- }
553
-
554
- deepmerge.all = function deepmergeAll(array, options) {
555
- if (!Array.isArray(array)) {
556
- throw new Error('first argument should be an array')
557
- }
558
-
559
- return array.reduce(function(prev, next) {
560
- return deepmerge(prev, next, options)
561
- }, {})
562
- };
563
-
564
- var deepmerge_1 = deepmerge;
565
-
566
- var cjs = deepmerge_1;
567
-
568
- /**
569
- * Source: ftp://ftp.unicode.org/Public/UCD/latest/ucd/SpecialCasing.txt
570
- */
571
- /**
572
- * Lower case as a function.
573
- */
574
- function lowerCase(str) {
575
- return str.toLowerCase();
576
- }
577
-
578
- // Support camel case ("camelCase" -> "camel Case" and "CAMELCase" -> "CAMEL Case").
579
- var DEFAULT_SPLIT_REGEXP = [/([a-z0-9])([A-Z])/g, /([A-Z])([A-Z][a-z])/g];
580
- // Remove all non-word characters.
581
- var DEFAULT_STRIP_REGEXP = /[^A-Z0-9]+/gi;
582
- /**
583
- * Normalize the string into something other libraries can manipulate easier.
584
- */
585
- function noCase(input, options) {
586
- if (options === void 0) { options = {}; }
587
- var _a = options.splitRegexp, splitRegexp = _a === void 0 ? DEFAULT_SPLIT_REGEXP : _a, _b = options.stripRegexp, stripRegexp = _b === void 0 ? DEFAULT_STRIP_REGEXP : _b, _c = options.transform, transform = _c === void 0 ? lowerCase : _c, _d = options.delimiter, delimiter = _d === void 0 ? " " : _d;
588
- var result = replace(replace(input, splitRegexp, "$1\0$2"), stripRegexp, "\0");
589
- var start = 0;
590
- var end = result.length;
591
- // Trim the delimiter from around the output string.
592
- while (result.charAt(start) === "\0")
593
- start++;
594
- while (result.charAt(end - 1) === "\0")
595
- end--;
596
- // Transform each token independently.
597
- return result.slice(start, end).split("\0").map(transform).join(delimiter);
598
- }
599
- /**
600
- * Replace `re` in the input string with the replacement value.
601
- */
602
- function replace(input, re, value) {
603
- if (re instanceof RegExp)
604
- return input.replace(re, value);
605
- return re.reduce(function (input, re) { return input.replace(re, value); }, input);
606
- }
607
-
608
- const copyProperty = (to, from, property, ignoreNonConfigurable) => {
609
- // `Function#length` should reflect the parameters of `to` not `from` since we keep its body.
610
- // `Function#prototype` is non-writable and non-configurable so can never be modified.
611
- if (property === 'length' || property === 'prototype') {
612
- return;
613
- } // `Function#arguments` and `Function#caller` should not be copied. They were reported to be present in `Reflect.ownKeys` for some devices in React Native (#41), so we explicitly ignore them here.
614
-
615
-
616
- if (property === 'arguments' || property === 'caller') {
617
- return;
618
- }
619
-
620
- const toDescriptor = Object.getOwnPropertyDescriptor(to, property);
621
- const fromDescriptor = Object.getOwnPropertyDescriptor(from, property);
622
-
623
- if (!canCopyProperty(toDescriptor, fromDescriptor) && ignoreNonConfigurable) {
624
- return;
625
- }
626
-
627
- Object.defineProperty(to, property, fromDescriptor);
628
- }; // `Object.defineProperty()` throws if the property exists, is not configurable and either:
629
- // - one its descriptors is changed
630
- // - it is non-writable and its value is changed
631
-
632
-
633
- const canCopyProperty = function canCopyProperty(toDescriptor, fromDescriptor) {
634
- return toDescriptor === undefined || toDescriptor.configurable || toDescriptor.writable === fromDescriptor.writable && toDescriptor.enumerable === fromDescriptor.enumerable && toDescriptor.configurable === fromDescriptor.configurable && (toDescriptor.writable || toDescriptor.value === fromDescriptor.value);
635
- };
636
-
637
- const changePrototype = (to, from) => {
638
- const fromPrototype = Object.getPrototypeOf(from);
639
-
640
- if (fromPrototype === Object.getPrototypeOf(to)) {
641
- return;
642
- }
643
-
644
- Object.setPrototypeOf(to, fromPrototype);
645
- };
646
-
647
- const wrappedToString = (withName, fromBody) => `/* Wrapped ${withName}*/\n${fromBody}`;
648
-
649
- const toStringDescriptor = Object.getOwnPropertyDescriptor(Function.prototype, 'toString');
650
- const toStringName = Object.getOwnPropertyDescriptor(Function.prototype.toString, 'name'); // We call `from.toString()` early (not lazily) to ensure `from` can be garbage collected.
651
- // We use `bind()` instead of a closure for the same reason.
652
- // Calling `from.toString()` early also allows caching it in case `to.toString()` is called several times.
653
-
654
- const changeToString = (to, from, name) => {
655
- const withName = name === '' ? '' : `with ${name.trim()}() `;
656
- const newToString = wrappedToString.bind(null, withName, from.toString()); // Ensure `to.toString.toString` is non-enumerable and has the same `same`
657
-
658
- Object.defineProperty(newToString, 'name', toStringName);
659
- Object.defineProperty(to, 'toString', _extends({}, toStringDescriptor, {
660
- value: newToString
661
- }));
662
- };
663
-
664
- function mimicFunction(to, from, {
665
- ignoreNonConfigurable = false
666
- } = {}) {
667
- const {
668
- name
669
- } = to;
670
-
671
- for (const property of Reflect.ownKeys(from)) {
672
- copyProperty(to, from, property, ignoreNonConfigurable);
673
- }
674
-
675
- changePrototype(to, from);
676
- changeToString(to, from, name);
677
- return to;
678
- }
679
-
680
- var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
681
-
682
- function getDefaultExportFromCjs (x) {
683
- return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x;
684
- }
685
-
686
- function createCommonjsModule(fn) {
687
- var module = { exports: {} };
688
- return fn(module, module.exports), module.exports;
689
- }
690
-
691
- var pDefer = () => {
692
- const ret = {};
693
-
694
- ret.promise = new Promise((resolve, reject) => {
695
- ret.resolve = resolve;
696
- ret.reject = reject;
697
- });
698
-
699
- return ret;
700
- };
701
-
702
- var dist = createCommonjsModule(function (module, exports) {
703
- var __awaiter = (commonjsGlobal && commonjsGlobal.__awaiter) || function (thisArg, _arguments, P, generator) {
704
- return new (P || (P = Promise))(function (resolve, reject) {
705
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
706
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
707
- function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
708
- step((generator = generator.apply(thisArg, _arguments || [])).next());
709
- });
710
- };
711
- var __importDefault = (commonjsGlobal && commonjsGlobal.__importDefault) || function (mod) {
712
- return (mod && mod.__esModule) ? mod : { "default": mod };
713
- };
714
- Object.defineProperty(exports, "__esModule", { value: true });
715
- const p_defer_1 = __importDefault(pDefer);
716
- function mapAgeCleaner(map, property = 'maxAge') {
717
- let processingKey;
718
- let processingTimer;
719
- let processingDeferred;
720
- const cleanup = () => __awaiter(this, void 0, void 0, function* () {
721
- if (processingKey !== undefined) {
722
- // If we are already processing an item, we can safely exit
723
- return;
724
- }
725
- const setupTimer = (item) => __awaiter(this, void 0, void 0, function* () {
726
- processingDeferred = p_defer_1.default();
727
- const delay = item[1][property] - Date.now();
728
- if (delay <= 0) {
729
- // Remove the item immediately if the delay is equal to or below 0
730
- map.delete(item[0]);
731
- processingDeferred.resolve();
732
- return;
733
- }
734
- // Keep track of the current processed key
735
- processingKey = item[0];
736
- processingTimer = setTimeout(() => {
737
- // Remove the item when the timeout fires
738
- map.delete(item[0]);
739
- if (processingDeferred) {
740
- processingDeferred.resolve();
741
- }
742
- }, delay);
743
- // tslint:disable-next-line:strict-type-predicates
744
- if (typeof processingTimer.unref === 'function') {
745
- // Don't hold up the process from exiting
746
- processingTimer.unref();
747
- }
748
- return processingDeferred.promise;
749
- });
750
- try {
751
- for (const entry of map) {
752
- yield setupTimer(entry);
753
- }
754
- }
755
- catch (_a) {
756
- // Do nothing if an error occurs, this means the timer was cleaned up and we should stop processing
757
- }
758
- processingKey = undefined;
759
- });
760
- const reset = () => {
761
- processingKey = undefined;
762
- if (processingTimer !== undefined) {
763
- clearTimeout(processingTimer);
764
- processingTimer = undefined;
765
- }
766
- if (processingDeferred !== undefined) { // tslint:disable-line:early-exit
767
- processingDeferred.reject(undefined);
768
- processingDeferred = undefined;
769
- }
770
- };
771
- const originalSet = map.set.bind(map);
772
- map.set = (key, value) => {
773
- if (map.has(key)) {
774
- // If the key already exist, remove it so we can add it back at the end of the map.
775
- map.delete(key);
776
- }
777
- // Call the original `map.set`
778
- const result = originalSet(key, value);
779
- // If we are already processing a key and the key added is the current processed key, stop processing it
780
- if (processingKey && processingKey === key) {
781
- reset();
782
- }
783
- // Always run the cleanup method in case it wasn't started yet
784
- cleanup(); // tslint:disable-line:no-floating-promises
785
- return result;
786
- };
787
- cleanup(); // tslint:disable-line:no-floating-promises
788
- return map;
789
- }
790
- exports.default = mapAgeCleaner;
791
- // Add support for CJS
792
- module.exports = mapAgeCleaner;
793
- module.exports.default = mapAgeCleaner;
794
- });
795
-
796
- var mapAgeCleaner = /*@__PURE__*/getDefaultExportFromCjs(dist);
797
-
798
- const cacheStore = new WeakMap();
799
- /**
800
- [Memoize](https://en.wikipedia.org/wiki/Memoization) functions - An optimization used to speed up consecutive function calls by caching the result of calls with identical input.
801
-
802
- @param fn - Function to be memoized.
803
-
804
- @example
805
- ```
806
- import mem from 'mem';
807
-
808
- let index = 0;
809
- const counter = () => ++index;
810
- const memoized = mem(counter);
811
-
812
- memoized('foo');
813
- //=> 1
814
-
815
- // Cached as it's the same argument
816
- memoized('foo');
817
- //=> 1
818
-
819
- // Not cached anymore as the arguments changed
820
- memoized('bar');
821
- //=> 2
822
-
823
- memoized('bar');
824
- //=> 2
825
- ```
826
- */
827
-
828
- function mem(fn, {
829
- cacheKey,
830
- cache = new Map(),
831
- maxAge
832
- } = {}) {
833
- if (typeof maxAge === 'number') {
834
- mapAgeCleaner(cache);
835
- }
836
-
837
- const memoized = function memoized(...arguments_) {
838
- const key = cacheKey ? cacheKey(arguments_) : arguments_[0];
839
- const cacheItem = cache.get(key);
840
-
841
- if (cacheItem) {
842
- return cacheItem.data; // eslint-disable-line @typescript-eslint/no-unsafe-return
843
- }
844
-
845
- const result = fn.apply(this, arguments_);
846
- cache.set(key, {
847
- data: result,
848
- maxAge: maxAge ? Date.now() + maxAge : Number.POSITIVE_INFINITY
849
- });
850
- return result; // eslint-disable-line @typescript-eslint/no-unsafe-return
851
- };
852
-
853
- mimicFunction(memoized, fn, {
854
- ignoreNonConfigurable: true
855
- });
856
- cacheStore.set(memoized, cache);
857
- return memoized;
858
- }
859
-
860
- /**
861
- * Test if the given value is an object.
862
- *
863
- * @param {*} value The value to test.
864
- * @return {Boolean} Whether or not the value is an object.
865
- */
866
- function isObject(value) {
867
- return typeof value === 'object' && !!value && value.toString() === '[object Object]';
868
- }
869
-
870
- /**
871
- * @typedef {StringConstructor|NumberConstructor|BooleanConstructor|ArrayConstructor|ObjectConstructor} OptionType
872
- * @typedef {{ [name:string]: OptionType | { type: OptionType, default: String|Number|Boolean|(() => Array|Object)} }} OptionsSchema
873
- * @typedef {{ [optionName:string]: any }} OptionsInterface
874
- */
875
-
876
- /**
877
- * Get the attribute name based on the given option name.
878
- * @param {String} name The option name.
879
- */
880
-
881
- function getAttributeName(name) {
882
- return `data-option-${noCase(name, {
883
- delimiter: '-'
884
- })}`;
885
- }
886
-
887
- const memoizedGetAttributeName = mem(getAttributeName);
888
- /**
889
- * Class options to manage options as data attributes on an HTML element.
890
- * @augments {OptionsInterface}
891
- */
892
-
893
- var _element = /*#__PURE__*/_classPrivateFieldLooseKey("element");
894
-
895
- var _values = /*#__PURE__*/_classPrivateFieldLooseKey("values");
896
-
897
- var _defaultValues = /*#__PURE__*/_classPrivateFieldLooseKey("defaultValues");
898
-
899
- class Options {
900
- /** @type {HTMLElement} The HTML element holding the options attributes. */
901
-
902
- /** @type {Object} An object to store Array and Object values for reference. */
903
-
904
- /** @type {Array} List of allowed types. */
905
-
906
- /**
907
- * The default values to return for each available type.
908
- * @type {Object}
909
- */
910
-
911
- /**
912
- * Class constructor.
913
- *
914
- * @param {HTMLElement} element The HTML element storing the options.
915
- * @param {OptionsSchema} schema A Base class config.
916
- */
917
- constructor(element, schema) {
918
- Object.defineProperty(this, _element, {
919
- writable: true,
920
- value: void 0
921
- });
922
- Object.defineProperty(this, _values, {
923
- writable: true,
924
- value: {}
925
- });
926
- Object.defineProperty(this, _defaultValues, {
927
- writable: true,
928
- value: {
929
- String: '',
930
- Number: 0,
931
- Boolean: false,
932
- Array: () => [],
933
- Object: () => ({})
934
- }
935
- });
936
- _classPrivateFieldLooseBase(this, _element)[_element] = element;
937
- Object.entries(schema).forEach(([name, config]) => {
938
- const isObjectConfig = !Options.types.includes(config);
939
- /** @type {OptionType} */
940
- // @ts-ignore
941
-
942
- const type = isObjectConfig ? config.type : config;
943
-
944
- if (!Options.types.includes(type)) {
945
- throw new Error(`The "${name}" option has an invalid type. The allowed types are: String, Number, Boolean, Array and Object.`);
946
- } // @ts-ignore
947
-
948
-
949
- const defaultValue = isObjectConfig ? config.default : _classPrivateFieldLooseBase(this, _defaultValues)[_defaultValues][type.name];
950
-
951
- if ((type === Array || type === Object) && typeof defaultValue !== 'function') {
952
- throw new Error(`The default value for options of type "${type.name}" must be returned by a function.`);
953
- }
954
-
955
- Object.defineProperty(this, name, {
956
- get() {
957
- return this.get(name, type, defaultValue);
958
- },
959
-
960
- set(value) {
961
- this.set(name, type, value, defaultValue);
962
- },
963
-
964
- enumerable: true
965
- });
966
- });
967
- return this;
968
- }
969
- /**
970
- * Get an option value.
971
- *
972
- * @param {String} name The option name.
973
- * @param {ArrayConstructor|ObjectConstructor|StringConstructor|NumberConstructor|BooleanConstructor} type The option data's type.
974
- * @param {any} defaultValue The default value for this option.
975
- */
976
-
977
-
978
- get(name, type, defaultValue) {
979
- const attributeName = memoizedGetAttributeName(name);
980
-
981
- const hasAttribute = _classPrivateFieldLooseBase(this, _element)[_element].hasAttribute(attributeName);
982
-
983
- if (type === Boolean) {
984
- if (defaultValue) {
985
- const negatedAttributeName = memoizedGetAttributeName(`no-${name}`);
986
-
987
- const hasNegatedAttribute = _classPrivateFieldLooseBase(this, _element)[_element].hasAttribute(negatedAttributeName);
988
-
989
- return !hasNegatedAttribute;
990
- }
991
-
992
- return hasAttribute || defaultValue;
993
- }
994
-
995
- const value = _classPrivateFieldLooseBase(this, _element)[_element].getAttribute(attributeName);
996
-
997
- if (type === Number) {
998
- return hasAttribute ? Number(value) : defaultValue;
999
- }
1000
-
1001
- if (type === Array || type === Object) {
1002
- const val = cjs(defaultValue(), hasAttribute ? JSON.parse(value) : _classPrivateFieldLooseBase(this, _defaultValues)[_defaultValues][type.name]());
1003
-
1004
- if (!_classPrivateFieldLooseBase(this, _values)[_values][name]) {
1005
- _classPrivateFieldLooseBase(this, _values)[_values][name] = val;
1006
- } else if (val !== _classPrivateFieldLooseBase(this, _values)[_values][name]) {
1007
- // When getting the value, wait for the next loop to update the data attribute
1008
- // with the new value. This is a simple trick to avoid using a Proxy to watch
1009
- // for any deep changes on an array or object. It should not break anything as
1010
- // the original value is read once from the data attribute and is then read from
1011
- // the private property `#values`.
1012
- setTimeout(() => {
1013
- _classPrivateFieldLooseBase(this, _element)[_element].setAttribute(attributeName, JSON.stringify(_classPrivateFieldLooseBase(this, _values)[_values][name]));
1014
- }, 0);
1015
- }
1016
-
1017
- return _classPrivateFieldLooseBase(this, _values)[_values][name];
1018
- }
1019
-
1020
- return hasAttribute ? value : defaultValue;
1021
- }
1022
- /**
1023
- * Set an option value.
1024
- *
1025
- * @param {String} name The option name.
1026
- * @param {ArrayConstructor|ObjectConstructor|StringConstructor|NumberConstructor|BooleanConstructor} type The option data's type.
1027
- * @param {any} value The new value for this option.
1028
- */
1029
-
1030
-
1031
- set(name, type, value, defaultValue) {
1032
- const attributeName = memoizedGetAttributeName(name);
1033
-
1034
- if (value.constructor.name !== type.name) {
1035
- const val = Array.isArray(value) || isObject(value) ? JSON.stringify(value) : value;
1036
- throw new TypeError(`The "${val}" value for the "${name}" option must be of type "${type.name}"`);
1037
- }
1038
-
1039
- switch (type) {
1040
- case Boolean:
1041
- if (defaultValue) {
1042
- const negatedAttributeName = memoizedGetAttributeName(`no-${name}`);
1043
-
1044
- if (value) {
1045
- _classPrivateFieldLooseBase(this, _element)[_element].removeAttribute(negatedAttributeName);
1046
- } else {
1047
- _classPrivateFieldLooseBase(this, _element)[_element].setAttribute(negatedAttributeName, '');
1048
- }
1049
- } else if (value) {
1050
- _classPrivateFieldLooseBase(this, _element)[_element].setAttribute(attributeName, '');
1051
- } else {
1052
- _classPrivateFieldLooseBase(this, _element)[_element].removeAttribute(attributeName);
1053
- }
1054
-
1055
- break;
1056
-
1057
- case Array:
1058
- case Object:
1059
- _classPrivateFieldLooseBase(this, _values)[_values][name] = value;
1060
-
1061
- _classPrivateFieldLooseBase(this, _element)[_element].setAttribute(attributeName, JSON.stringify(value));
1062
-
1063
- break;
1064
-
1065
- default:
1066
- _classPrivateFieldLooseBase(this, _element)[_element].setAttribute(attributeName, value);
1067
-
1068
- }
1069
- }
1070
-
1071
- }
1072
- Options.types = [String, Number, Boolean, Array, Object];
1073
-
1074
- /**
1075
- * @typedef {import('./index.js').default} Base
1076
- * @typedef {import('./index.js').BaseOptions} BaseOptions
1077
- * @typedef {import('./classes/Options.js').OptionsSchema} OptionsSchema
1078
- */
1079
-
1080
- /**
1081
- * Get the legacy options from the `config` properties.
1082
- *
1083
- * @param {Base} instance The component's instance.
1084
- * @param {Object} config The component's config.
1085
- * @return {OptionsSchema}
1086
- */
1087
-
1088
- function getLegacyOptionsSchema(instance, config) {
1089
- // Add legacy options to the schema
1090
- const propsToExclude = ['name', 'log', 'debug', 'components', 'refs', 'options'];
1091
- return Object.keys(config).reduce(
1092
- /**
1093
- * @param {OptionsSchema} schema
1094
- * @param {String} propName
1095
- */
1096
- (schema, propName) => {
1097
- if (propsToExclude.includes(propName)) {
1098
- return schema;
1099
- }
1100
-
1101
- const value = config[propName];
1102
- let type = value === null || value === undefined ? Object : value.constructor; // Default to object type as it should work for any values.
1103
-
1104
- if (!Options.types.includes(type)) {
1105
- type = Object;
1106
- }
1107
-
1108
- warn(instance, '\n Options must be defined in the `config.options` property.', `\n Consider moving the \`config.${propName}\` option to \`config.options.${propName}\`.`);
1109
-
1110
- if (type === Array || type === Object) {
1111
- schema[propName] = {
1112
- type,
1113
- default: () => value
1114
- };
1115
- } else {
1116
- schema[propName] = {
1117
- type,
1118
- default: value
1119
- };
1120
- }
1121
-
1122
- return schema;
1123
- }, {});
1124
- }
1125
- /**
1126
- * Get the inherited options values from the current instance parent classes.
1127
- * @param {Base} instance The component's instance.
1128
- * @return {OptionsSchema}
1129
- */
1130
-
1131
-
1132
- function getParentOptionsSchema(instance) {
1133
- /** @type {OptionsSchema} [description] */
1134
- let schema = {};
1135
- /** @type {Base|false} Merge inherited options. */
1136
-
1137
- let prototype = instance;
1138
-
1139
- while (prototype) {
1140
- const getterConfig = prototype.config; // @ts-ignore
1141
-
1142
- const staticConfig = prototype.constructor.config;
1143
-
1144
- if (getterConfig || staticConfig) {
1145
- schema = Object.assign((getterConfig || {}).options || {}, (staticConfig || {}).options || {}, schema);
1146
- prototype = Object.getPrototypeOf(prototype);
1147
- } else {
1148
- prototype = false;
1149
- }
1150
- }
1151
-
1152
- return schema;
1153
- }
1154
- /**
1155
- * Update an Options object with the legacy values from the element's `data-options` attribute.
1156
- *
1157
- * @param {Base} instance The component's instance.
1158
- * @param {HTMLElement} element The component's root element.
1159
- * @param {Options} options The component's options.
1160
- */
1161
-
1162
-
1163
- function updateOptionsWithLegacyValues(instance, element, options) {
1164
- // Update legacy options with value from the `data-options` attribute
1165
- let legacyOptionsValues = {};
1166
-
1167
- if (element.dataset.options) {
1168
- warn(instance, 'The `data-options` attribute usage is deprecated, use multiple `data-option-...` attributes instead.');
1169
-
1170
- try {
1171
- legacyOptionsValues = JSON.parse(element.dataset.options);
1172
- } catch (err) {
1173
- throw new Error('Can not parse the `data-options` attribute. Is it a valid JSON string?');
1174
- }
1175
- }
1176
-
1177
- Object.entries(legacyOptionsValues).forEach(([optionName, optionValue]) => {
1178
- options[optionName] = optionValue;
1179
- });
1180
- }
1181
- /**
1182
- * Get a component's options.
1183
- *
1184
- * @param {Base} instance The component's instance.
1185
- * @param {HTMLElement} element The component's root element.
1186
- * @param {Object} config The component's default config.
1187
- * @return {Options & BaseOptions} The component's merged options.
1188
- */
1189
-
1190
-
1191
- function getOptions(instance, element, config) {
1192
- var _config$log, _config$debug;
1193
-
1194
- /** @type {OptionsSchema} */
1195
- const schema = _extends({
1196
- name: {
1197
- type: String,
1198
- default: config.name
1199
- },
1200
- log: {
1201
- type: Boolean,
1202
- default: (_config$log = config.log) != null ? _config$log : false
1203
- },
1204
- debug: {
1205
- type: Boolean,
1206
- default: (_config$debug = config.debug) != null ? _config$debug : false
1207
- }
1208
- }, getParentOptionsSchema(instance), getLegacyOptionsSchema(instance, config), config.options || {});
1209
-
1210
- const options = new Options(element, schema);
1211
- updateOptionsWithLegacyValues(instance, element, options);
1212
- instance.$emit('get:options', options);
1213
- return options;
1214
- }
1215
-
1216
- /**
1217
- * @typedef {import('./index.js').default} Base
1218
- */
1219
-
1220
- /**
1221
- * A ponyfill for the CSS `:scope` selector which is not supported in IE11.
1222
- * The following method will return an array of elements similare to the
1223
- * `:scope ${selector}` selector.
1224
- *
1225
- * @see https://developer.mozilla.org/en-US/docs/Web/CSS/:scope
1226
- * @see https://github.com/jonathantneal/element-qsa-scope
1227
- *
1228
- * @param {HTMLElement} element The element from which the scope is taken.
1229
- * @param {String} selector The children selector.
1230
- * @param {String} uniqId A uniq ID to prefix the selector with.
1231
- * @return {Array} A list of elements.
1232
- */
1233
-
1234
- function scopeSelectorPonyfill(element, selector, uniqId) {
1235
- let list = [];
1236
-
1237
- try {
1238
- list = Array.from(element.querySelectorAll(`:scope ${selector}`));
1239
- } catch (err) {
1240
- const attr = `data-uniq-id`;
1241
- const scopedSelector = `[${attr}="${uniqId}"] ${selector}`;
1242
- element.setAttribute(attr, uniqId);
1243
- list = Array.from(element.querySelectorAll(scopedSelector));
1244
- element.removeAttribute(attr);
1245
- }
1246
-
1247
- return list;
1248
- }
1249
- /**
1250
- * Get all refs of a component.
1251
- *
1252
- * @param {Base} instance The component's instance.
1253
- * @param {HTMLElement} element The component's root element.
1254
- * @return {Object} Return an object containing all the component's refs.
1255
- */
1256
-
1257
- function getRefs(instance, element) {
1258
- const definedRefs = getConfig(instance).refs || [];
1259
- /** @type {Array<HTMLElement>} */
1260
-
1261
- const allRefs = Array.from(element.querySelectorAll(`[data-ref]`));
1262
- const childrenRefs = scopeSelectorPonyfill(element, '[data-component] [data-ref]', instance.$id);
1263
- const elements = allRefs.filter(ref => !childrenRefs.includes(ref));
1264
- const refs = elements.reduce(
1265
- /**
1266
- * @param {Object} $refs
1267
- * @param {HTMLElement & {__base__?: Base}} $ref
1268
- */
1269
- ($refs, $ref) => {
1270
- let refName = $ref.dataset.ref;
1271
-
1272
- if (!definedRefs.includes(refName)) {
1273
- warn(instance, `The "${refName}" ref is not defined in the class configuration.`, 'Did you forgot to define it?');
1274
- }
1275
-
1276
- const $realRef = $ref.__base__ ? $ref.__base__ : $ref;
1277
-
1278
- if (refName.endsWith('[]')) {
1279
- refName = refName.replace(/\[\]$/, '');
1280
-
1281
- if (!$refs[refName]) {
1282
- $refs[refName] = [];
1283
- }
1284
- }
1285
-
1286
- if ($refs[refName]) {
1287
- if (Array.isArray($refs[refName])) {
1288
- $refs[refName].push($realRef);
1289
- } else {
1290
- $refs[refName] = [$refs[refName], $realRef];
1291
- warn(instance, `The "${refName}" ref has been found multiple times.`, 'Did you forgot to add the `[]` suffix to its name?');
1292
- }
1293
- } else {
1294
- $refs[refName] = $realRef;
1295
- }
1296
-
1297
- return $refs;
1298
- }, {});
1299
- instance.$emit('get:refs', refs);
1300
- return refs;
1301
- }
1302
-
1303
- /**
1304
- * @typedef {import('./index.js').default} Base
1305
- */
1306
-
1307
- /**
1308
- * Mount a given component which might be async.
1309
- *
1310
- * @param {Base|Promise<Base>} component The component to mount.
1311
- * @return {void}
1312
- */
1313
-
1314
- function mountComponent(component) {
1315
- if (component instanceof Promise) {
1316
- component.then(instance => instance.$mount());
1317
- } else {
1318
- component.$mount();
1319
- }
1320
- }
1321
- /**
1322
- * Mount children components of a given instance.
1323
- *
1324
- * @param {Base} instance The parent component's instance.
1325
- * @return {void}
1326
- */
1327
-
1328
-
1329
- function mountComponents(instance) {
1330
- if (__DEV__) {
1331
- debug(instance, 'mountComponents', instance.$children);
1332
- }
1333
-
1334
- Object.values(instance.$children).forEach($child => {
1335
- if (__DEV__) {
1336
- debug(instance, 'mountComponent', $child);
1337
- }
1338
-
1339
- $child.forEach(mountComponent);
1340
- });
1341
- }
1342
- /**
1343
- * Mount or update the given component.
1344
- *
1345
- * @param {Base|Promise<Base>} component [description]
1346
- * @return {void}
1347
- */
1348
-
1349
- function mountOrUpdateComponent(component) {
1350
- if (component instanceof Promise) {
1351
- component.then(instance => instance.$isMounted ? instance.$update() : instance.$mount());
1352
- } else {
1353
- const method = component.$isMounted ? '$update' : '$mount';
1354
- component[method]();
1355
- }
1356
- }
1357
- /**
1358
- * Mount or updte children components of the given instance.
1359
- *
1360
- * @param {Base} instance The parent component's instance.
1361
- * @return {void}
1362
- */
1363
-
1364
-
1365
- function mountOrUpdateComponents(instance) {
1366
- if (__DEV__) {
1367
- debug(instance, 'mountComponents', instance.$children);
1368
- }
1369
-
1370
- Object.values(instance.$children).forEach($child => {
1371
- $child.forEach(mountOrUpdateComponent);
1372
- });
1373
- }
1374
- /**
1375
- * Destroy a given component which might be async.
1376
- *
1377
- * @param {Base|Promise} component The component to destroy.
1378
- * @return {void}
1379
- */
1380
-
1381
- function destroyComponent(component) {
1382
- if (component instanceof Promise) {
1383
- component.then(instance => instance.$destroy());
1384
- } else {
1385
- component.$destroy();
1386
- }
1387
- }
1388
- /**
1389
- * Destroy children components of a given instance.
1390
- *
1391
- * @param {Base} instance The parent component's instance.
1392
- * @return {void}
1393
- */
1394
-
1395
-
1396
- function destroyComponents(instance) {
1397
- if (__DEV__) {
1398
- debug(instance, 'destroyComponents', instance.$children);
1399
- }
1400
-
1401
- Object.values(instance.$children).forEach(
1402
- /**
1403
- * @param {Array<Base>} $child
1404
- */
1405
- $child => {
1406
- $child.forEach(destroyComponent);
1407
- });
1408
- }
1409
-
1410
- /**
1411
- * Service abstract class
1412
- */
1413
- class Service {
1414
- /**
1415
- * Class constructor, used to test the abstract class implementation.
1416
- */
1417
- constructor() {
1418
- this.callbacks = new Map();
1419
- this.isInit = false;
1420
- }
1421
- /**
1422
- * Getter to get the services properties.
1423
- * This getter MUST be implementer by the service extending this class.
1424
- * @return {Object}
1425
- */
1426
-
1427
-
1428
- get props() {
1429
- throw new Error('The `props` getter must be implemented.');
1430
- }
1431
- /**
1432
- * Method to initialize the service behaviors.
1433
- * This method MUST be implemented by the service extending this class.
1434
- *
1435
- * @return {Service} The current instance
1436
- */
1437
-
1438
-
1439
- init() {
1440
- throw new Error('The `init` method must be implemented.');
1441
- }
1442
- /**
1443
- * Method to kill the service behaviors.
1444
- * This method MUST be implemented by the service extending this class.
1445
- *
1446
- * @return {Service} The current instance
1447
- */
1448
-
1449
-
1450
- kill() {
1451
- throw new Error('The `kill` method must be implemented.');
1452
- }
1453
- /**
1454
- * Add a callback.
1455
- *
1456
- * @param {String} key The callback's identifier
1457
- * @param {Function} callback The callback function
1458
- * @return {this} The current instance
1459
- */
1460
-
1461
-
1462
- add(key, callback) {
1463
- if (this.has(key)) {
1464
- throw new Error(`A callback with the key \`${key}\` has already been registered.`);
1465
- } // Initialize the service when we add the first callback
1466
-
1467
-
1468
- if (this.callbacks.size === 0 && !this.isInit) {
1469
- this.init();
1470
- this.isInit = true;
1471
- }
1472
-
1473
- this.callbacks.set(key, callback);
1474
- return this;
1475
- }
1476
- /**
1477
- * Test if a callback with the given key has already been added.
1478
- *
1479
- * @param {String} key The identifier to test
1480
- * @return {Boolean} Whether or not the identifier already exists
1481
- */
1482
-
1483
-
1484
- has(key) {
1485
- return this.callbacks.has(key);
1486
- }
1487
- /**
1488
- * Get the callback tied to the given key.
1489
- *
1490
- * @param {String} key The identifier to get
1491
- * @return {Function} The callback function
1492
- */
1493
-
1494
-
1495
- get(key) {
1496
- return this.callbacks.get(key);
1497
- }
1498
- /**
1499
- * Remove the callback tied to the given key.
1500
- *
1501
- * @param {String} key The identifier to remove
1502
- * @return {Service} The current instance
1503
- */
1504
-
1505
-
1506
- remove(key) {
1507
- this.callbacks.delete(key); // Kill the service when we remove the last callback
1508
-
1509
- if (this.callbacks.size === 0 && this.isInit) {
1510
- this.kill();
1511
- this.isInit = false;
1512
- }
1513
-
1514
- return this;
1515
- }
1516
- /**
1517
- * Trigger each added callback with the given arguments.
1518
- *
1519
- * @param {Array} args All the arguments to apply to the callback
1520
- * @return {Service} The current instance
1521
- */
1522
-
1523
-
1524
- trigger(...args) {
1525
- this.callbacks.forEach(function forEachCallback(callback) {
1526
- callback(...args);
1527
- });
1528
- return this;
1529
- }
1530
-
1531
- }
1532
-
1533
- /**
1534
- * @typedef {import('./index').ServiceInterface} ServiceInterface
1535
- */
1536
-
1537
- /**
1538
- * @typedef {Object} PointerServiceProps
1539
- * @property {MouseEvent | TouchEvent} event
1540
- * @property {Boolean} isDown
1541
- * @property {Number} x
1542
- * @property {Number} y
1543
- * @property {{ x: Boolean, y: Boolean }} changed
1544
- * @property {{ x: Number, y: Number }} last
1545
- * @property {{ x: Number, y: Number }} delta
1546
- * @property {{ x: Number, y: Number }} progress
1547
- * @property {{ x: Number, y: Number }} max
1548
- */
1549
-
1550
- /**
1551
- * @typedef {Object} PointerService
1552
- * @property {(key:String, callback:(props:PointerServiceProps) => void) => void} add
1553
- * Add a function to the resize service. The key must be uniq.
1554
- * @property {() => PointerServiceProps} props
1555
- * Get the current values of the resize service props.
1556
- */
1557
-
1558
- /**
1559
- * Test if an event is an instance of TouchEvent.
1560
- *
1561
- * @param {TouchEvent|MouseEvent} event The event instance to test.
1562
- * @return {Boolean} Is it a TouchEvent?
1563
- */
1564
-
1565
- function isTouchEvent(event) {
1566
- return typeof TouchEvent !== 'undefined' && event instanceof TouchEvent;
1567
- }
1568
- /**
1569
- * Pointer service
1570
- */
1571
-
1572
-
1573
- class Pointer extends Service {
1574
- constructor(...args) {
1575
- super(...args);
1576
- this.isDown = false;
1577
- this.y = window.innerHeight / 2;
1578
- this.yLast = window.innerHeight / 2;
1579
- this.x = window.innerWidth / 2;
1580
- this.xLast = window.innerWidth / 2;
1581
- this.hasRaf = false;
1582
- }
1583
-
1584
- /**
1585
- * Bind the handler to the mousemove and touchmove events.
1586
- * Bind the up and down handler to the mousedown, mouseup, touchstart and touchend events.
1587
- *
1588
- * @return {Pointer}
1589
- */
1590
- init() {
1591
- document.documentElement.addEventListener('mouseenter', this, {
1592
- once: true,
1593
- capture: true
1594
- });
1595
- const options = {
1596
- passive: true,
1597
- capture: true
1598
- };
1599
- document.addEventListener('mousemove', this, options);
1600
- document.addEventListener('touchmove', this, options);
1601
- document.addEventListener('mousedown', this, options);
1602
- document.addEventListener('touchstart', this, options);
1603
- document.addEventListener('mouseup', this, options);
1604
- document.addEventListener('touchend', this, options);
1605
- return this;
1606
- }
1607
- /**
1608
- * Handle events.
1609
- * @param {MouseEvent|TouchEvent} event The event object.
1610
- */
1611
-
1612
-
1613
- handleEvent(event) {
1614
- // eslint-disable-next-line default-case
1615
- switch (event.type) {
1616
- case 'mouseenter':
1617
- case 'mousemove':
1618
- case 'touchmove':
1619
- this.handler(event);
1620
- break;
1621
-
1622
- case 'mousedown':
1623
- case 'touchstart':
1624
- this.downHandler();
1625
- break;
1626
-
1627
- case 'mouseup':
1628
- case 'touchend':
1629
- this.upHandler();
1630
- break;
1631
- }
1632
- }
1633
- /**
1634
- * Unbind all handlers from their bounded event.
1635
- *
1636
- * @return {Pointer}
1637
- */
1638
-
1639
-
1640
- kill() {
1641
- document.removeEventListener('mousemove', this);
1642
- document.removeEventListener('touchmove', this);
1643
- document.removeEventListener('mousedown', this);
1644
- document.removeEventListener('touchstart', this);
1645
- document.removeEventListener('mouseup', this);
1646
- document.removeEventListener('touchend', this);
1647
- return this;
1648
- }
1649
- /**
1650
- * The service handler.
1651
- * @param {MouseEvent|TouchEvent} event The mouse event object.
1652
- */
1653
-
1654
-
1655
- handler(event) {
1656
- this.updateValues(event);
1657
- this.trigger(this.props);
1658
- }
1659
- /**
1660
- * Handler for the pointer's down action.
1661
- *
1662
- * @return {void}
1663
- */
1664
-
1665
-
1666
- downHandler() {
1667
- this.isDown = true;
1668
- this.trigger(this.props);
1669
- }
1670
- /**
1671
- * Handler for the pointer's up action.
1672
- *
1673
- * @return {void}
1674
- */
1675
-
1676
-
1677
- upHandler() {
1678
- this.isDown = false;
1679
- this.trigger(this.props);
1680
- }
1681
- /**
1682
- * Update the pointer positions.
1683
- *
1684
- * @param {MouseEvent|TouchEvent} event The event object.
1685
- * @return {void}
1686
- */
1687
-
1688
-
1689
- updateValues(event) {
1690
- var _event$touches$, _event$touches$2;
1691
-
1692
- this.event = event;
1693
- this.yLast = this.y;
1694
- this.xLast = this.x; // Check pointer Y
1695
- // We either get data from a touch event `event.touches[0].clientY` or from
1696
- // a mouse event `event.clientY`.
1697
-
1698
- const y = isTouchEvent(event) ?
1699
- /** @type {TouchEvent} */
1700
- (_event$touches$ = event.touches[0]) == null ? void 0 : _event$touches$.clientY :
1701
- /** @type {MouseEvent} */
1702
- event.clientY;
1703
-
1704
- if (y !== this.y) {
1705
- this.y = y;
1706
- } // Check pointer X
1707
- // We either get data from a touch event `event.touches[0].clientX` or from
1708
- // a mouse event `event.clientX`.
1709
-
1710
-
1711
- const x = isTouchEvent(event) ?
1712
- /** @type {TouchEvent} */
1713
- (_event$touches$2 = event.touches[0]) == null ? void 0 : _event$touches$2.clientX :
1714
- /** @type {MouseEvent} */
1715
- event.clientX;
1716
-
1717
- if (x !== this.x) {
1718
- this.x = x;
1719
- }
1720
- }
1721
- /**
1722
- * Get the pointer props.
1723
- *
1724
- * @type {Object}
1725
- */
1726
-
1727
-
1728
- get props() {
1729
- return {
1730
- event: this.event,
1731
- isDown: this.isDown,
1732
- x: this.x,
1733
- y: this.y,
1734
- changed: {
1735
- x: this.x !== this.xLast,
1736
- y: this.y !== this.yLast
1737
- },
1738
- last: {
1739
- x: this.xLast,
1740
- y: this.yLast
1741
- },
1742
- delta: {
1743
- x: this.x - this.xLast,
1744
- y: this.y - this.yLast
1745
- },
1746
- progress: {
1747
- x: this.x / window.innerWidth,
1748
- y: this.y / window.innerHeight
1749
- },
1750
- max: {
1751
- x: window.innerWidth,
1752
- y: window.innerHeight
1753
- }
1754
- };
1755
- }
1756
-
1757
- }
1758
-
1759
- let pointer = null;
1760
- /**
1761
- * Use the pointer.
1762
- *
1763
- * ```js
1764
- * import usePointer from '@studiometa/js-toolkit/services';
1765
- * const { add, remove, props } = usePointer();
1766
- * add('id', () => {});
1767
- * remove('id');
1768
- * props();
1769
- * ```
1770
- *
1771
- * @return {ServiceInterface & PointerService}
1772
- */
1773
-
1774
- function usePointer() {
1775
- if (!pointer) {
1776
- pointer = new Pointer();
1777
- }
1778
-
1779
- const add = pointer.add.bind(pointer);
1780
- const remove = pointer.remove.bind(pointer);
1781
- const has = pointer.has.bind(pointer);
1782
-
1783
- const props = () => pointer.props;
1784
-
1785
- return {
1786
- add,
1787
- remove,
1788
- has,
1789
- props
1790
- };
1791
- }
1792
-
1793
- /**
1794
- * RequestAnimation frame polyfill.
1795
- * @see https://github.com/vuejs/vue/blob/ec78fc8b6d03e59da669be1adf4b4b5abf670a34/dist/vue.runtime.esm.js#L7355
1796
- * @return {(handler: Function) => number}
1797
- */
1798
- function getRaf() {
1799
- return typeof window !== 'undefined' && window.requestAnimationFrame ? window.requestAnimationFrame.bind(window) : setTimeout;
1800
- }
1801
- /**
1802
- * Get a function to cancel the method returned by `getRaf()`.
1803
- *
1804
- * @return {(id:number) => void}
1805
- */
1806
-
1807
- function getCancelRaf() {
1808
- return typeof window !== 'undefined' && window.cancelAnimationFrame ? window.cancelAnimationFrame.bind(window) : clearTimeout;
1809
- }
1810
-
1811
- /**
1812
- * @typedef {import('./index').ServiceInterface} ServiceInterface
1813
- */
1814
-
1815
- /**
1816
- * @typedef {Object} RafServiceProps
1817
- * @property {DOMHighResTimeStamp} time
1818
- */
1819
-
1820
- /**
1821
- * @typedef {Object} RafService
1822
- * @property {(key:String, callback:(props:RafServiceProps) => void) => void} add
1823
- * Add a function to the resize service. The key must be uniq.
1824
- * @property {() => RafServiceProps} props
1825
- * Get the current values of the resize service props.
1826
- */
1827
-
1828
- /**
1829
- * Tick service
1830
- */
1831
-
1832
- class Raf extends Service {
1833
- /** @type {Boolean} Whether the loop is running or not. */
1834
-
1835
- /** @type {number} */
1836
-
1837
- /**
1838
- * Bind loop to the instance.
1839
- */
1840
- constructor() {
1841
- super();
1842
- this.isTicking = false;
1843
- this.id = 0;
1844
- this.raf = getRaf();
1845
- this.cancelRaf = getCancelRaf();
1846
- this.loop = this.loop.bind(this);
1847
- }
1848
- /**
1849
- * Start the requestAnimationFrame loop.
1850
- *
1851
- * @return {Raf}
1852
- */
1853
-
1854
-
1855
- init() {
1856
- this.isTicking = true;
1857
- this.loop();
1858
- return this;
1859
- }
1860
- /**
1861
- * Loop method.
1862
- */
1863
-
1864
-
1865
- loop() {
1866
- this.trigger(this.props);
1867
-
1868
- if (!this.isTicking) {
1869
- return;
1870
- }
1871
-
1872
- this.id = this.raf(this.loop);
1873
- }
1874
- /**
1875
- * Stop the requestAnimationFrame loop.
1876
- *
1877
- * @return {Raf}
1878
- */
1879
-
1880
-
1881
- kill() {
1882
- this.cancelRaf(this.id);
1883
- this.isTicking = false;
1884
- return this;
1885
- }
1886
- /**
1887
- * Get raf props.
1888
- *
1889
- * @todo Return elapsed time / index?
1890
- * @type {Object}
1891
- */
1892
-
1893
-
1894
- get props() {
1895
- return {
1896
- time: window.performance.now()
1897
- };
1898
- }
1899
-
1900
- }
1901
-
1902
- let instance$1 = null;
1903
- /**
1904
- * Use the RequestAnimationFrame (raf) service.
1905
- *
1906
- * ```js
1907
- * import { useRaf } from '@studiometa/js/services';
1908
- * const { add, remove, props } = useRag();
1909
- * add(id, (props) => {});
1910
- * remove(id);
1911
- * props();
1912
- * ```
1913
- *
1914
- * @return {ServiceInterface & RafService}
1915
- */
1916
-
1917
- function useRaf$1() {
1918
- if (!instance$1) {
1919
- instance$1 = new Raf();
1920
- }
1921
-
1922
- const add = instance$1.add.bind(instance$1);
1923
- const remove = instance$1.remove.bind(instance$1);
1924
- const has = instance$1.has.bind(instance$1); // eslint-disable-next-line require-jsdoc
1925
-
1926
- function props() {
1927
- return instance$1.props;
1928
- }
1929
-
1930
- return {
1931
- add,
1932
- remove,
1933
- has,
1934
- props
1935
- };
1936
- }
1937
-
1938
- /**
1939
- * Returns a function, that, as long as it continues to be invoked,
1940
- * will not be triggered. The function will be called after it stops
1941
- * being called for N milliseconds.
1942
- *
1943
- * @param {(...args:any[]) => void} fn The function to call.
1944
- * @param {Number=} [delay=300] The delay in ms to wait before calling the function.
1945
- * @return {(...args:any[]) => void} The debounced function.
1946
- */
1947
- function debounce(fn, delay = 300) {
1948
- let timeout;
1949
- return function debounced(...args) {
1950
- clearTimeout(timeout);
1951
- timeout = setTimeout(() => {
1952
- fn(...args);
1953
- }, delay);
1954
- };
1955
- }
1956
-
1957
- /**
1958
- * @typedef {import('./index').ServiceInterface} ServiceInterface
1959
- */
1960
-
1961
- /**
1962
- * @typedef {Object} ResizeServiceProps
1963
- * @property {Number} width
1964
- * @property {Number} height
1965
- * @property {Number} ratio
1966
- * @property {'square'|'landscape'|'portrait'} orientation
1967
- * @property {String} [breakpoint]
1968
- * @property {String[]} [breakpoints]
1969
- */
1970
-
1971
- /**
1972
- * @typedef {Object} ResizeService
1973
- * @property {(key:String, callback:(props:ResizeServiceProps) => void) => void} add
1974
- * Add a function to the resize service. The key must be uniq.
1975
- * @property {() => ResizeServiceProps} props
1976
- * Get the current values of the resize service props.
1977
- */
1978
-
1979
- /**
1980
- * Resize service
1981
- *
1982
- * ```
1983
- * import { useResize } from '@studiometa/js/services';
1984
- * const { add, remove, props } = useResize();
1985
- * add(key, (props) => {});
1986
- * remove(key);
1987
- * props();
1988
- * ```
1989
- */
1990
-
1991
- class Resize extends Service {
1992
- /**
1993
- * Bind the handler to the resize event.
1994
- *
1995
- * @return {this}
1996
- */
1997
- init() {
1998
- this.handler = debounce(() => {
1999
- this.trigger(this.props);
2000
- }).bind(this);
2001
-
2002
- if (this.canUseResizeObserver) {
2003
- this.resizeObserver = new ResizeObserver(this.handler);
2004
- this.resizeObserver.observe(document.documentElement);
2005
- } else {
2006
- window.addEventListener('resize', this.handler);
2007
- }
2008
-
2009
- return this;
2010
- }
2011
- /**
2012
- * Unbind the handler from the resize event.
2013
- *
2014
- * @return {this}
2015
- */
2016
-
2017
-
2018
- kill() {
2019
- if (this.canUseResizeObserver) {
2020
- this.resizeObserver.disconnect();
2021
- } else {
2022
- window.removeEventListener('resize', this.handler);
2023
- }
2024
-
2025
- delete this.resizeObserver;
2026
- return this;
2027
- }
2028
- /**
2029
- * Get resize props.
2030
- *
2031
- * @type {ResizeServiceProps}
2032
- */
2033
-
2034
-
2035
- get props() {
2036
- /** @type {ResizeServiceProps} [description] */
2037
- const props = {
2038
- width: window.innerWidth,
2039
- height: window.innerHeight,
2040
- ratio: window.innerWidth / window.innerHeight,
2041
- orientation: 'square'
2042
- };
2043
-
2044
- if (props.ratio > 1) {
2045
- props.orientation = 'landscape';
2046
- }
2047
-
2048
- if (props.ratio < 1) {
2049
- props.orientation = 'portrait';
2050
- }
2051
-
2052
- if (this.breakpointElement) {
2053
- props.breakpoint = this.breakpoint;
2054
- props.breakpoints = this.breakpoints;
2055
- }
2056
-
2057
- return props;
2058
- }
2059
- /**
2060
- * The element holding the breakpoints data.
2061
- * @return {HTMLElement}
2062
- */
2063
-
2064
-
2065
- get breakpointElement() {
2066
- return document.querySelector('[data-breakpoint]') || null;
2067
- }
2068
- /**
2069
- * Get the current breakpoint.
2070
- * @return {String}
2071
- */
2072
-
2073
-
2074
- get breakpoint() {
2075
- return window.getComputedStyle(this.breakpointElement, '::before').getPropertyValue('content').replace(/"/g, '');
2076
- }
2077
- /**
2078
- * Get all breakpoints.
2079
- * @return {Array}
2080
- */
2081
-
2082
-
2083
- get breakpoints() {
2084
- const breakpoints = window.getComputedStyle(this.breakpointElement, '::after').getPropertyValue('content').replace(/"/g, '');
2085
- return breakpoints.split(',');
2086
- }
2087
- /**
2088
- * Test if we can use the `ResizeObserver` API.
2089
- * @return {Boolean}
2090
- */
2091
-
2092
-
2093
- get canUseResizeObserver() {
2094
- return typeof window.ResizeObserver !== 'undefined';
2095
- }
2096
-
2097
- }
2098
-
2099
- let resize = null;
2100
- /**
2101
- * Use the resize service.
2102
- *
2103
- * ```js
2104
- * import useResize from '@studiometa/js-toolkit/services/resize';
2105
- * const { add, remove, props } = useResize();
2106
- * add(key, (props) => {});
2107
- * remove(key);
2108
- * props();
2109
- * ```
2110
- * @return {ServiceInterface & ResizeService}
2111
- */
2112
-
2113
- function useResize() {
2114
- if (!resize) {
2115
- resize = new Resize();
2116
- }
2117
-
2118
- const add = resize.add.bind(resize);
2119
- const remove = resize.remove.bind(resize);
2120
- const has = resize.has.bind(resize);
2121
-
2122
- const props = () => resize.props;
2123
-
2124
- return {
2125
- add,
2126
- remove,
2127
- has,
2128
- props
2129
- };
2130
- }
2131
-
2132
- /**
2133
- * @typedef {import('./index').ServiceInterface} ServiceInterface
2134
- */
2135
-
2136
- /**
2137
- * @typedef {Object} ScrollServiceProps
2138
- * @property {Number} x
2139
- * @property {Number} y
2140
- * @property {{ x: Boolean, y: Boolean }} changed
2141
- * @property {{ x: Number, y: Number }} last
2142
- * @property {{ x: Number, y: Number }} delta
2143
- * @property {{ x: Number, y: Number }} progress
2144
- * @property {{ x: Number, y: Number }} max
2145
- * @property {{ x: 'LEFT'|'RIGHT'|'NONE', y: 'UP'|'DOWN'|'NONE' }} direction
2146
- */
2147
-
2148
- /**
2149
- * @typedef {Object} ScrollService
2150
- * @property {(key:String, callback:(props:ScrollServiceProps) => void) => void} add
2151
- * Add a function to the resize service. The key must be uniq.
2152
- * @property {() => ScrollServiceProps} props
2153
- * Get the current values of the resize service props.
2154
- */
2155
-
2156
- /**
2157
- * Scroll service
2158
- */
2159
-
2160
- class Scroll extends Service {
2161
- constructor(...args) {
2162
- super(...args);
2163
- this.y = window.pageYOffset;
2164
- this.yLast = window.pageYOffset;
2165
- this.x = window.pageXOffset;
2166
- this.xLast = window.pageXOffset;
2167
- }
2168
-
2169
- /**
2170
- * Bind the handler to the scroll event.
2171
- *
2172
- * @return {Scroll}
2173
- */
2174
- init() {
2175
- document.addEventListener('scroll', this, {
2176
- passive: true,
2177
- capture: true
2178
- });
2179
- return this;
2180
- }
2181
- /**
2182
- * Debounced handler.
2183
- *
2184
- * @return {() => void}
2185
- */
2186
-
2187
-
2188
- get debouncedHandler() {
2189
- const debounced = debounce(() => {
2190
- this.trigger(this.props);
2191
- }, 0); // Define property to avoid multiple call to the getter
2192
-
2193
- Object.defineProperty(this, 'debouncedHandler', {
2194
- value: debounced
2195
- });
2196
- return debounced;
2197
- }
2198
- /**
2199
- * Scroll event handler.
2200
- *
2201
- * @return {void}
2202
- */
2203
-
2204
-
2205
- handleEvent() {
2206
- this.trigger(this.props);
2207
- this.debouncedHandler();
2208
- }
2209
- /**
2210
- * Unbind the handler from the scroll event.
2211
- *
2212
- * @return {Scroll}
2213
- */
2214
-
2215
-
2216
- kill() {
2217
- document.removeEventListener('scroll', this);
2218
- return this;
2219
- }
2220
- /**
2221
- * Get scroll props.
2222
- *
2223
- * @type {Object}
2224
- */
2225
-
2226
-
2227
- get props() {
2228
- this.yLast = this.y;
2229
- this.xLast = this.x; // Check scroll Y
2230
-
2231
- if (window.pageYOffset !== this.y) {
2232
- this.y = window.pageYOffset;
2233
- } // Check scroll x
2234
-
2235
-
2236
- if (window.pageXOffset !== this.x) {
2237
- this.x = window.pageXOffset;
2238
- }
2239
-
2240
- return {
2241
- x: this.x,
2242
- y: this.y,
2243
- changed: {
2244
- x: this.x !== this.xLast,
2245
- y: this.y !== this.yLast
2246
- },
2247
- last: {
2248
- x: this.xLast,
2249
- y: this.yLast
2250
- },
2251
- delta: {
2252
- x: this.x - this.xLast,
2253
- y: this.y - this.yLast
2254
- },
2255
- progress: {
2256
- x: this.max.x === 0 ? 1 : this.x / this.max.x,
2257
- y: this.max.y === 0 ? 1 : this.y / this.max.y
2258
- },
2259
- direction: {
2260
- /* eslint-disable no-nested-ternary */
2261
- x: this.x > this.xLast ? 'RIGHT' : this.x < this.xLast ? 'LEFT' : 'NONE',
2262
- y: this.y > this.yLast ? 'DOWN' : this.y < this.yLast ? 'UP' : 'NONE'
2263
- /* eslint-enable no-nested-ternary */
2264
-
2265
- },
2266
- max: this.max
2267
- };
2268
- }
2269
- /**
2270
- * Get scroll max values.
2271
- *
2272
- * @type {Object}
2273
- */
2274
-
2275
-
2276
- get max() {
2277
- return {
2278
- x: (document.scrollingElement || document.body).scrollWidth - window.innerWidth,
2279
- y: (document.scrollingElement || document.body).scrollHeight - window.innerHeight
2280
- };
2281
- }
2282
-
2283
- }
2284
-
2285
- let scroll = null;
2286
- /**
2287
- * Use the scroll service.
2288
- *
2289
- * ```js
2290
- * import { useScroll } from '@studiometa/js-toolkit/services';
2291
- * const { add, remove, props } = useScroll();
2292
- * add(key, (props) => {});
2293
- * remove(key);
2294
- * props();
2295
- * ```
2296
- *
2297
- * @return {ServiceInterface & ScrollService}
2298
- */
2299
-
2300
- function useScroll() {
2301
- if (!scroll) {
2302
- scroll = new Scroll();
2303
- }
2304
-
2305
- const add = scroll.add.bind(scroll);
2306
- const remove = scroll.remove.bind(scroll);
2307
- const has = scroll.has.bind(scroll);
2308
-
2309
- const props = () => scroll.props;
2310
-
2311
- return {
2312
- add,
2313
- remove,
2314
- has,
2315
- props
2316
- };
2317
- }
2318
-
2319
- var keyCodes = {
2320
- ENTER: 13,
2321
- SPACE: 32,
2322
- TAB: 9,
2323
- ESC: 27,
2324
- LEFT: 37,
2325
- UP: 38,
2326
- RIGHT: 39,
2327
- DOWN: 40
2328
- };
2329
-
2330
- /**
2331
- * @typedef {import('./index').ServiceInterface} ServiceInterface
2332
- */
2333
-
2334
- /**
2335
- * @typedef {Object} KeyServiceProps
2336
- * @property {KeyboardEvent} event
2337
- * @property {Number} triggered
2338
- * @property {Boolean} isUp
2339
- * @property {Boolean} isDown
2340
- * @property {Boolean} ENTER
2341
- * @property {Boolean} SPACE
2342
- * @property {Boolean} TAB
2343
- * @property {Boolean} ESC
2344
- * @property {Boolean} LEFT
2345
- * @property {Boolean} UP
2346
- * @property {Boolean} RIGHT
2347
- * @property {Boolean} DOWN
2348
- */
2349
-
2350
- /**
2351
- * @typedef {Object} KeyService
2352
- * @property {(key:String, callback:(props:KeyServiceProps) => void) => void} add
2353
- * Add a function to the resize service. The key must be uniq.
2354
- * @property {() => KeyServiceProps} props
2355
- * Get the current values of the resize service props.
2356
- */
2357
-
2358
- /**
2359
- * Scroll service
2360
- */
2361
-
2362
- class Key extends Service {
2363
- constructor(...args) {
2364
- super(...args);
2365
- this.event = {};
2366
- this.triggered = 0;
2367
- this.previousEvent = {};
2368
- }
2369
-
2370
- /**
2371
- * Bind the handler to the keyboard event.
2372
- *
2373
- * @return {Key}
2374
- */
2375
- init() {
2376
- this.handler = event => {
2377
- this.event = event;
2378
- this.trigger(this.props);
2379
- };
2380
-
2381
- document.addEventListener('keydown', this.handler, {
2382
- passive: false
2383
- });
2384
- document.addEventListener('keyup', this.handler, {
2385
- passive: false
2386
- });
2387
- return this;
2388
- }
2389
- /**
2390
- * Unbind the handler from the keyboard event.
2391
- *
2392
- * @return {Key}
2393
- */
2394
-
2395
-
2396
- kill() {
2397
- document.removeEventListener('keydown', this.handler);
2398
- document.removeEventListener('keyup', this.handler);
2399
- return this;
2400
- }
2401
- /**
2402
- * Get keyboard props.
2403
- *
2404
- * @type {Object}
2405
- */
2406
-
2407
-
2408
- get props() {
2409
- const keys = Object.entries(keyCodes).reduce((acc, [name, code]) => {
2410
- acc[name] = code === this.event.keyCode;
2411
- return acc;
2412
- }, {});
2413
-
2414
- if (!this.previousEvent.type) {
2415
- this.triggered = 0;
2416
- }
2417
-
2418
- if (this.event.type === 'keydown' && this.previousEvent.type === 'keydown') {
2419
- this.triggered += 1;
2420
- } else {
2421
- this.triggered = 1;
2422
- }
2423
-
2424
- this.previousEvent = this.event;
2425
- return _extends({
2426
- event: this.event,
2427
- triggered: this.triggered,
2428
- direction: this.event.type === 'keydown' ? 'down' : 'up',
2429
- isUp: this.event.type === 'keyup',
2430
- isDown: this.event.type === 'keydown'
2431
- }, keys);
2432
- }
2433
-
2434
- }
2435
-
2436
- let key = null;
2437
- /**
2438
- * Use the keyboard service.
2439
- *
2440
- * ```js
2441
- * import { useKey } from '@studiometa/js-toolkit/services';
2442
- * const { add, remove, props } = useKey();
2443
- * add(key, (props) => {});
2444
- * remove(key);
2445
- * props();
2446
- * ```
2447
- *
2448
- * @return {ServiceInterface & KeyService}
2449
- */
2450
-
2451
- function useKey() {
2452
- if (!key) {
2453
- key = new Key();
2454
- }
2455
-
2456
- const add = key.add.bind(key);
2457
- const remove = key.remove.bind(key);
2458
- const has = key.has.bind(key);
2459
-
2460
- const props = () => key.props;
2461
-
2462
- return {
2463
- add,
2464
- remove,
2465
- has,
2466
- props
2467
- };
2468
- }
2469
-
2470
- /**
2471
- * @typedef {import('./index').ServiceInterface} ServiceInterface
2472
- */
2473
-
2474
- /**
2475
- * @typedef {Object} LoadServiceProps
2476
- * @property {DOMHighResTimeStamp} time
2477
- */
2478
-
2479
- /**
2480
- * @typedef {Object} LoadService
2481
- * @property {(key:String, callback:(props:LoadServiceProps) => void) => void} add
2482
- * Add a function to the resize service. The key must be uniq.
2483
- * @property {() => LoadServiceProps} props
2484
- * Get the current values of the resize service props.
2485
- */
2486
-
2487
- /**
2488
- * Load service
2489
- */
2490
-
2491
- class Load extends Service {
2492
- /**
2493
- * Start the requestAnimationFrame loop.
2494
- *
2495
- * @return {Load}
2496
- */
2497
- init() {
2498
- this.handler = () => {
2499
- this.trigger(this.props);
2500
- };
2501
-
2502
- window.addEventListener('load', this.handler);
2503
- return this;
2504
- }
2505
- /**
2506
- * Stop the requestAnimationFrame loop.
2507
- *
2508
- * @return {Load}
2509
- */
2510
-
2511
-
2512
- kill() {
2513
- window.removeEventListener('load', this.handler);
2514
- return this;
2515
- }
2516
- /**
2517
- * Get raf props.
2518
- *
2519
- * @todo Return elapsed time / index?
2520
- * @type {Object}
2521
- */
2522
-
2523
-
2524
- get props() {
2525
- return {};
2526
- }
2527
-
2528
- }
2529
-
2530
- let instance = null;
2531
- /**
2532
- * Use the load service.
2533
- *
2534
- * ```js
2535
- * import { useLoad } from '@studiometa/js/services';
2536
- * const { add, remove, props } = useRag();
2537
- * add(id, (props) => {});
2538
- * remove(id);
2539
- * props();
2540
- * ```
2541
- *
2542
- * @return {ServiceInterface & LoadService}
2543
- */
2544
-
2545
- function useRaf() {
2546
- if (!instance) {
2547
- instance = new Load();
2548
- }
2549
-
2550
- const add = instance.add.bind(instance);
2551
- const remove = instance.remove.bind(instance);
2552
- const has = instance.has.bind(instance); // eslint-disable-next-line require-jsdoc
2553
-
2554
- function props() {
2555
- return instance.props;
2556
- }
2557
-
2558
- return {
2559
- add,
2560
- remove,
2561
- has,
2562
- props
2563
- };
2564
- }
2565
-
2566
- /**
2567
- * @typedef {import('../index').default} Base
2568
- * @typedef {import('../../../services').ServiceInterface} ServiceInterface
2569
- */
2570
-
2571
- /**
2572
- * @type {Record<string, () => ServiceInterface>}
2573
- */
2574
-
2575
- const SERVICES_MAP = {
2576
- scrolled: useScroll,
2577
- resized: useResize,
2578
- ticked: useRaf$1,
2579
- moved: usePointer,
2580
- keyed: useKey,
2581
- loaded: useRaf
2582
- };
2583
- /**
2584
- * @typedef {keyof SERVICES_MAP} ServiceName
2585
- */
2586
-
2587
- /**
2588
- * Services management for the Base class.
2589
- */
2590
-
2591
- var _base = /*#__PURE__*/_classPrivateFieldLooseKey("base");
2592
-
2593
- class Services {
2594
- /** @type {Base} */
2595
-
2596
- /**
2597
- * Class constructor.
2598
- * @param {Base} instance The Base instance.
2599
- */
2600
- constructor(instance) {
2601
- Object.defineProperty(this, _base, {
2602
- writable: true,
2603
- value: void 0
2604
- });
2605
- _classPrivateFieldLooseBase(this, _base)[_base] = instance;
2606
- }
2607
- /**
2608
- * Test if the given service is registered.
2609
- *
2610
- * @param {ServiceName} service The name of the service.
2611
- * @return {Boolean}
2612
- */
2613
-
2614
-
2615
- has(service) {
2616
- if (!hasMethod(_classPrivateFieldLooseBase(this, _base)[_base], service) && !SERVICES_MAP[service]) {
2617
- return false;
2618
- }
2619
-
2620
- const {
2621
- has
2622
- } = SERVICES_MAP[service]();
2623
- return has(_classPrivateFieldLooseBase(this, _base)[_base].$id);
2624
- }
2625
- /**
2626
- * Init the given service and bind it to the given instance.
2627
- *
2628
- * @param {ServiceName} service The name of the service.
2629
- * @return {() => void} A function to unbind the service.
2630
- */
2631
-
2632
-
2633
- enable(service) {
2634
- if (this.has(service)) {
2635
- return this.disable.bind(this, service);
2636
- }
2637
-
2638
- if (!hasMethod(_classPrivateFieldLooseBase(this, _base)[_base], service) || !SERVICES_MAP[service]) {
2639
- return function noop() {};
2640
- }
2641
-
2642
- const {
2643
- add
2644
- } = SERVICES_MAP[service]();
2645
- const self = this;
2646
- /**
2647
- * @param {any[]} args
2648
- */
2649
-
2650
- function serviceHandler(...args) {
2651
- callMethod(_classPrivateFieldLooseBase(self, _base)[_base], service, ...args);
2652
- }
2653
-
2654
- add(_classPrivateFieldLooseBase(this, _base)[_base].$id, serviceHandler);
2655
- return this.disable.bind(this, service);
2656
- }
2657
- /**
2658
- * Enable all services and return methods to disable them.
2659
- *
2660
- * @return {Function[]}
2661
- */
2662
-
2663
-
2664
- enableAll() {
2665
- return Object.keys(SERVICES_MAP).map(
2666
- /** @param {ServiceName} serviceName */
2667
- serviceName => this.enable(serviceName));
2668
- }
2669
- /**
2670
- * Disable all services.
2671
- *
2672
- * @return {void}
2673
- */
2674
-
2675
-
2676
- disableAll() {
2677
- Object.keys(SERVICES_MAP).forEach(
2678
- /** @param {ServiceName} serviceName */
2679
- serviceName => {
2680
- this.disable(serviceName);
2681
- });
2682
- }
2683
- /**
2684
- * Disable a service.
2685
- *
2686
- * @param {String} service The name of the service.
2687
- * @return {void}
2688
- */
2689
-
2690
-
2691
- disable(service) {
2692
- if (!SERVICES_MAP[service]) {
2693
- return;
2694
- }
2695
-
2696
- const {
2697
- remove
2698
- } = SERVICES_MAP[service]();
2699
- remove(_classPrivateFieldLooseBase(this, _base)[_base].$id);
2700
- }
2701
- /**
2702
- * Register a new service to be enabled/disabled.
2703
- *
2704
- * @param {string} name The name of the service hook.
2705
- * @param {() => ServiceInterface} useFunction The `use...` function for the service.
2706
- */
2707
-
2708
-
2709
- register(name, useFunction) {
2710
- SERVICES_MAP[name] = useFunction;
2711
- }
2712
- /**
2713
- * Unregister a new service to be enabled disabled.
2714
- *
2715
- * @param {string} name The name of the service hooK
2716
- */
2717
-
2718
-
2719
- unregister(name) {
2720
- delete SERVICES_MAP[name];
2721
- }
2722
-
2723
- }
2724
-
2725
- /**
2726
- * @typedef {import('./index.js').default} Base
2727
- */
2728
-
2729
- /**
2730
- * Bind event handler methods to the root HTML element.
2731
- *
2732
- * @param {Base} instance A Base instance.
2733
- * @param {Array} eventMethods A list of methods to bind.
2734
- * @return {Array} A list of unbind functions.
2735
- */
2736
-
2737
- function bindRootEvents(instance, eventMethods) {
2738
- return eventMethods.map(eventMethod => {
2739
- const eventName = eventMethod.replace(/^on/, '').toLowerCase();
2740
-
2741
- const handler = (...args) => {
2742
- if (__DEV__) {
2743
- debug(instance, eventMethod, instance.$el, ...args);
2744
- }
2745
-
2746
- instance[eventMethod](...args);
2747
- };
2748
-
2749
- instance.$el.addEventListener(eventName, handler);
2750
- return () => {
2751
- instance.$el.removeEventListener(eventName, handler);
2752
- };
2753
- });
2754
- }
2755
- /**
2756
- * Bind event handler methods to refs HTML element.
2757
- *
2758
- * @param {Base} instance A Base instance.
2759
- * @param {Array} eventMethods A list of methods to bind.
2760
- * @return {Array} A list of unbind functions.
2761
- */
2762
-
2763
-
2764
- function bindRefsEvents(instance, eventMethods) {
2765
- const unbindMethods = [];
2766
- Object.entries(instance.$refs).forEach(([refName, $refOrRefs]) => {
2767
- const $refs = Array.isArray($refOrRefs) ? $refOrRefs : [$refOrRefs];
2768
- const refEventMethod = `on${refName.replace(/^\w/, c => c.toUpperCase())}`;
2769
- eventMethods.filter(eventMethod => eventMethod.startsWith(refEventMethod)).forEach(eventMethod => {
2770
- $refs.forEach(($ref, index) => {
2771
- const eventName = eventMethod.replace(refEventMethod, '').toLowerCase();
2772
-
2773
- const handler = (...args) => {
2774
- if (__DEV__) {
2775
- debug(instance, eventMethod, $ref, ...args, index);
2776
- }
2777
-
2778
- instance[eventMethod](...args, index);
2779
- };
2780
-
2781
- if (__DEV__) {
2782
- debug(instance, 'binding ref event', refName, eventName);
2783
- }
2784
-
2785
- if ($ref instanceof instance.constructor) {
2786
- // @ts-ignore
2787
- $ref = $ref.$el; // eslint-disable-line no-param-reassign
2788
- }
2789
- /** @type {HTMLElement} */
2790
-
2791
-
2792
- $ref.addEventListener(eventName, handler);
2793
-
2794
- const unbindMethod = () => {
2795
- if (__DEV__) {
2796
- debug(instance, 'unbinding ref event', refName, eventMethod);
2797
- }
2798
- /** @type {HTMLElement} */
2799
-
2800
-
2801
- $ref.removeEventListener(eventName, handler);
2802
- };
2803
-
2804
- unbindMethods.push(unbindMethod);
2805
- });
2806
- });
2807
- });
2808
- return unbindMethods;
2809
- }
2810
- /**
2811
- * Bind event handler methods to children Base instance.
2812
- * @param {Base} instance A Base instance.
2813
- * @param {Array} eventMethods A list of methods to bind.
2814
- * @return {Array} A list of unbind functions.
2815
- */
2816
-
2817
-
2818
- function bindChildrenEvents(instance, eventMethods) {
2819
- const unbindMethods = [];
2820
- Object.entries(instance.$children).forEach(([childName, $children]) => {
2821
- const childEventMethod = `on${childName.replace(/^\w/, c => c.toUpperCase())}`;
2822
- eventMethods.filter(eventMethod => eventMethod.startsWith(childEventMethod)).forEach(eventMethod => {
2823
- $children.forEach(
2824
- /**
2825
- * @param {Base|Promise<Base>} $child
2826
- * @param {Number} index
2827
- */
2828
- async ($child, index) => {
2829
- const eventName = eventMethod.replace(childEventMethod, '').toLowerCase();
2830
-
2831
- const handler = (...args) => {
2832
- if (__DEV__) {
2833
- debug(instance, eventMethod, $child, ...args, index);
2834
- }
2835
-
2836
- instance[eventMethod](...args, index);
2837
- };
2838
-
2839
- if (__DEV__) {
2840
- debug(instance, 'binding child event', childName, eventName);
2841
- }
2842
-
2843
- if ($child instanceof Promise) {
2844
- // eslint-disable-next-line no-param-reassign
2845
- $child = await $child;
2846
- }
2847
-
2848
- const unbindMethod = $child.$on(eventName, handler);
2849
- unbindMethods.push(() => {
2850
- if (__DEV__) {
2851
- debug(instance, 'unbinding child event', childName, eventName);
2852
- }
2853
-
2854
- unbindMethod();
2855
- });
2856
- });
2857
- });
2858
- });
2859
- return unbindMethods;
2860
- }
2861
- /**
2862
- * Bind ref and children component's events to their corresponding method.
2863
- *
2864
- * @param {Base} instance A Base instance.
2865
- * @return {Array} A list of methods to unbind the events.
2866
- */
2867
-
2868
-
2869
- function bindEvents(instance) {
2870
- const ROOT_EVENT_REGEX = /^on[A-Z][a-z]+$/;
2871
- const REFS_CHILDREN_EVENT_REGEX = /^on([A-Z]([a-z]+)?)([A-Z][a-z]+)+$/; // Get all event methods
2872
-
2873
- const eventMethods = getAllProperties(instance).reduce((acc, [name]) => {
2874
- // Testing camelCase with one word: onEvent.
2875
- if (ROOT_EVENT_REGEX.test(name) && !acc.root.includes(name)) {
2876
- acc.root.push(name);
2877
- return acc;
2878
- } // Testing camelCase with more than two words: onRefEvent.
2879
-
2880
-
2881
- if (REFS_CHILDREN_EVENT_REGEX.test(name) && !acc.refsOrChildren.includes(name)) {
2882
- acc.refsOrChildren.push(name);
2883
- }
2884
-
2885
- return acc;
2886
- }, {
2887
- root: [],
2888
- refsOrChildren: []
2889
- });
2890
- const unbindMethods = [...bindRootEvents(instance, eventMethods.root), ...bindRefsEvents(instance, eventMethods.refsOrChildren), ...bindChildrenEvents(instance, eventMethods.refsOrChildren)];
2891
- return unbindMethods;
2892
- }
2893
-
2894
- if (typeof __DEV__ === 'undefined') {
2895
- if (typeof globalThis !== 'undefined') {
2896
- globalThis.__DEV__ = false;
2897
- } else if (typeof window !== 'undefined') {
2898
- window.__DEV__ = false;
2899
- }
2900
- }
2901
-
2902
- let id = 0;
2903
- /**
2904
- * @typedef {typeof Base} BaseComponent
2905
- * @typedef {(Base) => Promise<BaseComponent | { default: BaseComponent }>} BaseAsyncComponent
2906
- * @typedef {{ name: string, debug: boolean, log: boolean, [name:string]: any }} BaseOptions
2907
- * @typedef {{ [name:string]: HTMLElement | HTMLElement[] | Base | Base[] | Promise<Base> | Promise<Base>[] }} BaseRefs
2908
- * @typedef {{ [nameOrSelector:string]: Base[] | Promise<Base>[] }} BaseChildren
2909
- * @typedef {{ [nameOrSelector:string]: BaseComponent | BaseAsyncComponent }} BaseConfigComponents
2910
- * @typedef {import('./classes/Options').OptionsSchema} BaseConfigOptions
2911
- */
2912
-
2913
- /**
2914
- * @typedef {Object} BaseConfig
2915
- * @property {String} name
2916
- * @property {Boolean} [debug]
2917
- * @property {Boolean} [log]
2918
- * @property {String[]} [refs]
2919
- * @property {BaseConfigComponents} [components]
2920
- * @property {BaseConfigOptions} [options]
2921
- */
2922
-
2923
- /**
2924
- * @typedef {import('./classes/Services.js').ServiceName} ServiceName
2925
- */
2926
-
2927
- /**
2928
- * Base class to easily create components.
2929
- *
2930
- * @example
2931
- * ```js
2932
- * class Component extends Base {
2933
- * static config = {
2934
- * name: 'Component',
2935
- * log: true,
2936
- * };
2937
- *
2938
- * mounted() {
2939
- * this.$log('Component is mounted!');
2940
- * }
2941
- * }
2942
- *
2943
- * class App extends Base {
2944
- * static config = {
2945
- * name: 'App',
2946
- * components: {
2947
- * Component,
2948
- * },
2949
- * };
2950
- * }
2951
- *
2952
- * new App(document.body).$mount();
2953
- * ```
2954
- */
2955
-
2956
- class Base extends EventManager {
2957
- /**
2958
- * The instance parent.
2959
- * @type {Base}
2960
- */
2961
-
2962
- /**
2963
- * The state of the component.
2964
- * @type {Boolean}
2965
- */
2966
-
2967
- /**
2968
- * This is a Base instance.
2969
- * @type {Boolean}
2970
- */
2971
-
2972
- /**
2973
- * Get properties to exclude from the autobind call.
2974
- * @return {Array<String|RegExp>}
2975
- */
2976
- get _excludeFromAutoBind() {
2977
- return ['$mount', '$update', '$destroy', '$terminate', '$log', '$on', '$once', '$off', '$emit', 'mounted', 'loaded', 'ticked', 'resized', 'moved', 'keyed', 'scrolled', 'destroyed', 'terminated'];
2978
- }
2979
- /**
2980
- * @deprecated Use the static `config` property instead.
2981
- * @return {BaseConfig}
2982
- */
2983
-
2984
-
2985
- get config() {
2986
- return null;
2987
- }
2988
- /** @type {BaseConfig} */
2989
-
2990
-
2991
- /**
2992
- * Get the component's refs.
2993
- * @return {BaseRefs}
2994
- */
2995
- get $refs() {
2996
- return getRefs(this, this.$el);
2997
- }
2998
- /**
2999
- * Class constructor where all the magic takes place.
3000
- *
3001
- * @param {HTMLElement} element The component's root element dd.
3002
- */
3003
-
3004
-
3005
- constructor(element) {
3006
- super();
3007
- this.$parent = null;
3008
- this.$isMounted = false;
3009
-
3010
- if (!element) {
3011
- throw new Error('The root element must be defined.');
3012
- }
3013
-
3014
- const {
3015
- name
3016
- } = getConfig(this);
3017
- /** @type {String} */
3018
-
3019
- this.$id = `${name}-${id}`;
3020
- id += 1;
3021
- /** @type {HTMLElement} */
3022
-
3023
- this.$el = element;
3024
- this.$options = getOptions(this, element, getConfig(this));
3025
- this.$children = getChildren(this, this.$el, getConfig(this).components || {});
3026
- this.$services = new Services(this);
3027
-
3028
- if (!('__base__' in this.$el)) {
3029
- Object.defineProperty(this.$el, '__base__', {
3030
- get: () => this,
3031
- configurable: true
3032
- });
3033
- } // Autobind all methods to the instance
3034
-
3035
-
3036
- autoBind(this, {
3037
- exclude: [...this._excludeFromAutoBind]
3038
- });
3039
- let unbindMethods = [];
3040
- this.$on('mounted', () => {
3041
- this.$services.enableAll();
3042
- unbindMethods = [...bindEvents(this)];
3043
- mountComponents(this);
3044
- this.$isMounted = true;
3045
- });
3046
- this.$on('updated', () => {
3047
- this.$services.disableAll();
3048
- unbindMethods.forEach(method => method());
3049
- unbindMethods = [...bindEvents(this)];
3050
- this.$services.enableAll();
3051
- mountOrUpdateComponents(this);
3052
- });
3053
- this.$on('destroyed', () => {
3054
- this.$isMounted = false;
3055
- this.$services.disableAll();
3056
- unbindMethods.forEach(method => method());
3057
- destroyComponents(this);
3058
- });
3059
-
3060
- if (__DEV__) {
3061
- debug(this, 'constructor', this);
3062
- }
3063
-
3064
- return this;
3065
- }
3066
- /**
3067
- * Small helper to log stuff.
3068
- *
3069
- * @return {(...args: any) => void} A log function if the log options is active.
3070
- */
3071
-
3072
-
3073
- get $log() {
3074
- return this.$options.log ? window.console.log.bind(window, `[${this.$options.name}]`) : function noop() {};
3075
- }
3076
- /**
3077
- * Trigger the `mounted` callback.
3078
- */
3079
-
3080
-
3081
- $mount() {
3082
- if (__DEV__) {
3083
- debug(this, '$mount');
3084
- }
3085
-
3086
- callMethod(this, 'mounted');
3087
- return this;
3088
- }
3089
- /**
3090
- * Update the instance children.
3091
- */
3092
-
3093
-
3094
- $update() {
3095
- if (__DEV__) {
3096
- debug(this, '$update');
3097
- }
3098
-
3099
- callMethod(this, 'updated');
3100
- return this;
3101
- }
3102
- /**
3103
- * Trigger the `destroyed` callback.
3104
- */
3105
-
3106
-
3107
- $destroy() {
3108
- if (__DEV__) {
3109
- debug(this, '$destroy');
3110
- }
3111
-
3112
- callMethod(this, 'destroyed');
3113
- return this;
3114
- }
3115
- /**
3116
- * Terminate a child instance when it is not needed anymore.
3117
- * @return {void}
3118
- */
3119
-
3120
-
3121
- $terminate() {
3122
- if (__DEV__) {
3123
- debug(this, '$terminate');
3124
- } // First, destroy the component.
3125
-
3126
-
3127
- this.$destroy(); // Execute the `terminated` hook if it exists
3128
-
3129
- callMethod(this, 'terminated'); // Delete the reference to the instance
3130
- // delete this.$el.__base__;
3131
- // And update its status to prevent re-instantiation when accessing the
3132
- // parent's `$children` property
3133
-
3134
- Object.defineProperty(this.$el, '__base__', {
3135
- value: 'terminated',
3136
- configurable: false,
3137
- writable: false
3138
- });
3139
- }
3140
- /**
3141
- * Factory method to generate multiple instance of the class.
3142
- *
3143
- * @param {String} nameOrSelector The selector on which to mount each instance.
3144
- * @return {Array<Base>} A list of the created instance.
3145
- */
3146
-
3147
-
3148
- static $factory(nameOrSelector) {
3149
- if (!nameOrSelector) {
3150
- throw new Error('The $factory method requires a component’s name or selector to be specified.');
3151
- }
3152
-
3153
- return getComponentElements(nameOrSelector).map(el => new this(el).$mount());
3154
- }
3155
-
3156
- }
3157
- Base.$isBase = true;
3158
-
3159
- const _excluded = ["config", "methods"];
3160
- /**
3161
- * @typedef {import('../abstracts/Base').BaseComponent} BaseComponent
3162
- */
3163
-
3164
- /**
3165
- * Define a component without a class.
3166
- *
3167
- * @param {Object} options The component's object
3168
- * @return {BaseComponent} A component's class.
3169
- */
3170
-
3171
- function defineComponent(options) {
3172
- const {
3173
- config,
3174
- methods
3175
- } = options,
3176
- hooks = _objectWithoutPropertiesLoose(options, _excluded);
3177
-
3178
- if (!config) {
3179
- throw new Error('The `config` property is required.');
3180
- }
3181
-
3182
- if (!config.name) {
3183
- throw new Error('The `config.name` property is required.');
3184
- }
3185
- /**
3186
- * Component class.
3187
- */
3188
-
3189
-
3190
- class Component extends Base {}
3191
-
3192
- Component.config = config;
3193
- const allowedHooks = ['mounted', 'loaded', 'ticked', 'resized', 'moved', 'keyed', 'scrolled', 'destroyed', 'terminated'];
3194
- const filteredHooks = Object.entries(hooks).reduce((acc, [name, fn]) => {
3195
- if (allowedHooks.includes(name)) {
3196
- acc[name] = fn;
3197
- } else {
3198
- throw new Error(`
3199
- The "${name}" method is not a Base lifecycle hook,
3200
- it should be placed in the "method" property.
3201
- The following hooks are available: ${allowedHooks.join(', ')}
3202
- `);
3203
- }
3204
-
3205
- return acc;
3206
- }, {});
3207
- [...Object.entries(methods || {}), ...Object.entries(filteredHooks)].forEach(([name, fn]) => {
3208
- Component.prototype[name] = fn;
3209
- });
3210
- return Component;
3211
- }
3212
-
3213
- /**
3214
- * Create a Base instance with the given object configuration.
3215
- *
3216
- * @param {HTMLElement|String} elementOrSelector The instance root HTML element.
3217
- * @param {Object} options The Base class configuration.
3218
- */
3219
-
3220
- function createBase(elementOrSelector, options) {
3221
- const Component = defineComponent(options);
3222
- /** @type {HTMLElement} */
3223
-
3224
- const element = typeof elementOrSelector === 'string' ? document.querySelector(elementOrSelector) : elementOrSelector;
3225
- return new Component(element);
3226
- }
3227
-
3228
- export default Base;
3229
- export { Base, createBase, defineComponent };
3230
- //# sourceMappingURL=index.modern.js.map
1
+ function e(){return(e=Object.assign||function(e){for(var t=1;t<arguments.length;t++){var i=arguments[t];for(var s in i)Object.prototype.hasOwnProperty.call(i,s)&&(e[s]=i[s])}return e}).apply(this,arguments)}var t=0;function i(e){return"__private_"+t+++"_"+e}function s(e,t){if(!Object.prototype.hasOwnProperty.call(e,t))throw new TypeError("attempted to use private field on non-instance");return e}function n(e,t){return"function"==typeof e[t]}function r(e,t,...i){return e.__debug("callMethod",t,...i),"destroyed"===t&&!e.$isMounted||"mounted"===t&&e.$isMounted?(e.__debug("not",t,"because the method has already been triggered once."),e):(e.$emit(t,...i),n(e,t)?(e[t].call(e,...i),e.__debug(t,e,...i),e):e)}function o(e,t=document){const i=`[data-component="${e}"]`;let s=[];try{s=Array.from(t.querySelectorAll(i))}catch(e){}return 0===s.length&&(s=Array.from(t.querySelectorAll(e))),s}class a{get registeredNames(){return Object.keys(this).filter(e=>!e.startsWith("__"))}constructor(e,t,i,s){Object.defineProperties(this,{__base:{enumerable:!1,writable:!1,value:e},__element:{enumerable:!1,writable:!1,value:t},__components:{enumerable:!1,writable:!1,value:i},__eventsManager:{enumerable:!1,writable:!1,value:s}})}registerAll(){Object.entries(this.__components).forEach(([e,t])=>this.__register(e,t))}__register(e,t){Object.defineProperty(this,e,{enumerable:!0,configurable:!0,get:()=>{const i=o(e,this.__element);return 0===i.length?[]:i.map(i=>this.__getChild(i,t,e)).filter(e=>"terminated"!==e)}})}__getChild(e,t,i){if(e.__base__)return e.__base__;if("$isBase"in t){const i=new t(e);return Object.defineProperty(i,"$parent",{get:()=>this.__base}),i}return t(this.__base).then(t=>{var s;return this.__getChild(e,null!=(s=t.default)?s:t,i)})}mountAll(){this.__triggerHookForAll("$mount")}updateAll(){this.__triggerHookForAll("$update")}destroyAll(){this.__triggerHookForAll("$destroy")}__triggerHookForAll(e){this.registeredNames.forEach(t=>{this[t].forEach(i=>{i instanceof Promise?i.then(i=>this.__triggerHook(e,i,t)):this.__triggerHook(e,i,t)})})}__triggerHook(e,t,i){"$update"!==e||t.$isMounted||(e="$mount"),"$update"!==e&&"$destroy"!==e||this.__eventsManager.unbindChild(i,t),"$update"!==e&&"$mount"!==e||this.__eventsManager.bindChild(i,t),t[e]()}}class h{constructor(e,t,i,s){Object.defineProperties(this,{__element:{enumerable:!1,writable:!1,value:t},__refs:{enumerable:!1,writable:!1,value:i},__base:{enumerable:!1,writable:!1,value:e},__eventsManager:{enumerable:!1,writable:!1,value:s}})}registerAll(){this.__refs.forEach(e=>this.__register(e))}unregisterAll(){this.__refs.forEach(e=>this.__unregister(e))}__register(e){const t=e.endsWith("[]"),i=h.normalizeRefName(e),s=Array.from(this.__element.querySelectorAll(`[data-ref="${e}"]`)).filter(e=>this.__filterRefsBelongingToInstance(e));!t&&s.length>1&&console.warn(`[${this.__base.$options.name}]`,`The "${e}" ref has been found multiple times.`,"Did you forgot to add the `[]` suffix to its name?"),this.__eventsManager.bindRef(e,s),Object.defineProperty(this,i,{value:t||s.length>1?s:s[0],enumerable:!0,configurable:!0})}__unregister(e){const t=h.normalizeRefName(e),i=Array.isArray(this[t])?this[t]:[this[t]];this.__eventsManager.unbindRef(e,i)}static normalizeRefName(e){return e.endsWith("[]")?e.replace(/\[\]$/,""):e}__filterRefsBelongingToInstance(e){let t=e.parentElement;for(;t&&void 0===t.dataset.component;)t=t.parentElement;return null===t||t===this.__element}}class l{constructor(){this.callbacks=new Map,this.isInit=!1}get props(){throw new Error("The `props` getter must be implemented.")}init(){throw new Error("The `init` method must be implemented.")}kill(){throw new Error("The `kill` method must be implemented.")}add(e,t){if(this.has(e))throw new Error(`A callback with the key \`${e}\` has already been registered.`);return 0!==this.callbacks.size||this.isInit||(this.init(),this.isInit=!0),this.callbacks.set(e,t),this}has(e){return this.callbacks.has(e)}get(e){return this.callbacks.get(e)}remove(e){return this.callbacks.delete(e),0===this.callbacks.size&&this.isInit&&(this.kill(),this.isInit=!1),this}trigger(...e){return this.callbacks.forEach(function(t){t(...e)}),this}}function d(e){return"undefined"!=typeof TouchEvent&&e instanceof TouchEvent}class c extends l{constructor(...e){super(...e),this.isDown=!1,this.y=window.innerHeight/2,this.yLast=window.innerHeight/2,this.x=window.innerWidth/2,this.xLast=window.innerWidth/2,this.hasRaf=!1}init(){document.documentElement.addEventListener("mouseenter",this,{once:!0,capture:!0});const e={passive:!0,capture:!0};return document.addEventListener("mousemove",this,e),document.addEventListener("touchmove",this,e),document.addEventListener("mousedown",this,e),document.addEventListener("touchstart",this,e),document.addEventListener("mouseup",this,e),document.addEventListener("touchend",this,e),this}handleEvent(e){switch(e.type){case"mouseenter":case"mousemove":case"touchmove":this.handler(e);break;case"mousedown":case"touchstart":this.downHandler();break;case"mouseup":case"touchend":this.upHandler()}}kill(){return document.removeEventListener("mousemove",this),document.removeEventListener("touchmove",this),document.removeEventListener("mousedown",this),document.removeEventListener("touchstart",this),document.removeEventListener("mouseup",this),document.removeEventListener("touchend",this),this}handler(e){this.updateValues(e),this.trigger(this.props)}downHandler(){this.isDown=!0,this.trigger(this.props)}upHandler(){this.isDown=!1,this.trigger(this.props)}updateValues(e){var t,i;this.event=e,this.yLast=this.y,this.xLast=this.x;const s=d(e)?null==(t=e.touches[0])?void 0:t.clientY:e.clientY;s!==this.y&&(this.y=s);const n=d(e)?null==(i=e.touches[0])?void 0:i.clientX:e.clientX;n!==this.x&&(this.x=n)}get props(){return{event:this.event,isDown:this.isDown,x:this.x,y:this.y,changed:{x:this.x!==this.xLast,y:this.y!==this.yLast},last:{x:this.xLast,y:this.yLast},delta:{x:this.x-this.xLast,y:this.y-this.yLast},progress:{x:this.x/window.innerWidth,y:this.y/window.innerHeight},max:{x:window.innerWidth,y:window.innerHeight}}}}let u=null;function m(){return u||(u=new c),{add:u.add.bind(u),remove:u.remove.bind(u),has:u.has.bind(u),props:()=>u.props}}class p extends l{constructor(){super(),this.isTicking=!1,this.id=0,this.raf="undefined"!=typeof window&&window.requestAnimationFrame?window.requestAnimationFrame.bind(window):setTimeout,this.cancelRaf="undefined"!=typeof window&&window.cancelAnimationFrame?window.cancelAnimationFrame.bind(window):clearTimeout,this.loop=this.loop.bind(this)}init(){return this.isTicking=!0,this.loop(),this}loop(){this.trigger(this.props),this.isTicking&&(this.id=this.raf(this.loop))}kill(){return this.cancelRaf(this.id),this.isTicking=!1,this}get props(){return{time:window.performance.now()}}}let _=null;function g(){return _||(_=new p),{add:_.add.bind(_),remove:_.remove.bind(_),has:_.has.bind(_),props:function(){return _.props}}}function f(e,t=300){let i;return function(...s){clearTimeout(i),i=setTimeout(()=>{e(...s)},t)}}class b extends l{init(){return this.handler=f(()=>{this.trigger(this.props)}).bind(this),window.addEventListener("resize",this.handler),this}kill(){return window.removeEventListener("resize",this.handler),this}get props(){const e={width:window.innerWidth,height:window.innerHeight,ratio:window.innerWidth/window.innerHeight,orientation:"square"};return e.ratio>1&&(e.orientation="landscape"),e.ratio<1&&(e.orientation="portrait"),this.breakpointElement&&(e.breakpoint=this.breakpoint,e.breakpoints=this.breakpoints),e}get breakpointElement(){return document.querySelector("[data-breakpoint]")||null}get breakpoint(){return window.getComputedStyle(this.breakpointElement,"::before").getPropertyValue("content").replace(/"/g,"")}get breakpoints(){return window.getComputedStyle(this.breakpointElement,"::after").getPropertyValue("content").replace(/"/g,"").split(",")}}let v=null;function y(){return v||(v=new b),{add:v.add.bind(v),remove:v.remove.bind(v),has:v.has.bind(v),props:()=>v.props}}class w extends l{constructor(...e){super(...e),this.y=window.pageYOffset,this.yLast=window.pageYOffset,this.x=window.pageXOffset,this.xLast=window.pageXOffset}init(){return document.addEventListener("scroll",this,{passive:!0,capture:!0}),this}get debouncedHandler(){const e=f(()=>{this.trigger(this.props)},0);return Object.defineProperty(this,"debouncedHandler",{value:e}),e}handleEvent(){this.trigger(this.props),this.debouncedHandler()}kill(){return document.removeEventListener("scroll",this),this}get props(){return this.yLast=this.y,this.xLast=this.x,window.pageYOffset!==this.y&&(this.y=window.pageYOffset),window.pageXOffset!==this.x&&(this.x=window.pageXOffset),{x:this.x,y:this.y,changed:{x:this.x!==this.xLast,y:this.y!==this.yLast},last:{x:this.xLast,y:this.yLast},delta:{x:this.x-this.xLast,y:this.y-this.yLast},progress:{x:0===this.max.x?1:this.x/this.max.x,y:0===this.max.y?1:this.y/this.max.y},direction:{x:this.x>this.xLast?"RIGHT":this.x<this.xLast?"LEFT":"NONE",y:this.y>this.yLast?"DOWN":this.y<this.yLast?"UP":"NONE"},max:this.max}}get max(){return{x:(document.scrollingElement||document.body).scrollWidth-window.innerWidth,y:(document.scrollingElement||document.body).scrollHeight-window.innerHeight}}}let $=null;function E(){return $||($=new w),{add:$.add.bind($),remove:$.remove.bind($),has:$.has.bind($),props:()=>$.props}}var x={ENTER:13,SPACE:32,TAB:9,ESC:27,LEFT:37,UP:38,RIGHT:39,DOWN:40};class k extends l{constructor(...e){super(...e),this.event={},this.triggered=0,this.previousEvent={}}init(){return this.handler=e=>{this.event=e,this.trigger(this.props)},document.addEventListener("keydown",this.handler,{passive:!1}),document.addEventListener("keyup",this.handler,{passive:!1}),this}kill(){return document.removeEventListener("keydown",this.handler),document.removeEventListener("keyup",this.handler),this}get props(){const t=Object.entries(x).reduce((e,[t,i])=>(e[t]=i===this.event.keyCode,e),{});return this.previousEvent.type||(this.triggered=0),"keydown"===this.event.type&&"keydown"===this.previousEvent.type?this.triggered+=1:this.triggered=1,this.previousEvent=this.event,e({event:this.event,triggered:this.triggered,direction:"keydown"===this.event.type?"down":"up",isUp:"keyup"===this.event.type,isDown:"keydown"===this.event.type},t)}}let O=null;function A(){return O||(O=new k),{add:O.add.bind(O),remove:O.remove.bind(O),has:O.has.bind(O),props:()=>O.props}}class L extends l{init(){return this.handler=()=>{this.trigger(this.props)},window.addEventListener("load",this.handler),this}kill(){return window.removeEventListener("load",this.handler),this}get props(){return{}}}let j=null;function N(){return j||(j=new L),{add:j.add.bind(j),remove:j.remove.bind(j),has:j.has.bind(j),props:function(){return j.props}}}const M={scrolled:E,resized:y,ticked:g,moved:m,keyed:A,loaded:N},T=Object.keys(M);class H{get __services(){return e({},this.__customServices,M)}constructor(e){this.__customServices={},Object.defineProperties(this,{__base:{enumerable:!1,writable:!1,value:e}})}has(e){if(!n(this.__base,e)&&!this.__services[e])return!1;const{has:t}=this.__services[e]();return t(this.__base.$id)}enable(e){if(this.has(e))return this.disable.bind(this,e);if(!n(this.__base,e)||!this.__services[e])return function(){};const{add:t}=this.__services[e](),i=this;return t(this.__base.$id,function(...t){r(i.__base,e,...t)}),this.disable.bind(this,e)}enableAll(){return Object.keys(this.__services).map(e=>this.enable(e))}disableAll(){Object.keys(this.__services).forEach(e=>{this.disable(e)})}disable(e){if(!this.__services[e])return;const{remove:t}=this.__services[e]();t(this.__base.$id)}register(e,t){this.__customServices[e]=t}unregister(e){if(T.includes(e))throw new Error(`[ServicesManager] The \`${e}\` core service can not be unregistered.`);delete this.__customServices[e]}}function P(e,t=[],i=null){const s=Object.getPrototypeOf(e);if(s===Object.prototype)return t;let n=Object.getOwnPropertyNames(s);return"function"==typeof i&&(n=n.filter(e=>i(e,s))),n=n.map(e=>[e,s]).reduce((e,t)=>[...e,t],t),P(s,n,i)}class B{constructor(e,t){this.__methodsCache=new Map,this.__rootElementHandler={handleEvent:e=>{const t=B.normalizeName(e.type);this.__base[`on${t}`](e)}},this.__refsHandler={handleEvent:e=>{const t=e.currentTarget,i=h.normalizeRefName(t.dataset.ref),s=`on${B.normalizeName(i)}${B.normalizeName(e.type)}`;let n=0;Array.isArray(this.__base.$refs[i])&&(n=this.__base.$refs[i].indexOf(t)),this.__base[s](e,n)}},this.__childrenHandler={handleEvent:e=>{const t=e.currentTarget.__base__;let i,s=0;const n=this.__base.$children;n.registeredNames.find(e=>!!n[e].includes(t)&&(i=e,s=n[e].indexOf(t),!0));const r=`on${B.normalizeName(i)}${B.normalizeName(e.type)}`,o=Array.isArray(e.detail)?e.detail:[];this.__base[r](...o,s,e)}},Object.defineProperties(this,{__rootElement:{enumerable:!1,writable:!1,value:e},__base:{enumerable:!1,writable:!1,value:t},__methodsCache:{enumerable:!1,writable:!1,value:this.__methodsCache},__rootElementHandler:{enumerable:!1,writable:!1,value:this.__rootElementHandler},__refsHandler:{enumerable:!1,writable:!1,value:this.__refsHandler},__childrenHandler:{enumerable:!1,writable:!1,value:this.__childrenHandler}})}__manageRef(e,t,i="add"){const s=`${i}EventListener`;this.__getEventMethodsByName(e).forEach(i=>{const n=this.__getEventNameByMethod(i,e);t.forEach(e=>e[s](n,this.__refsHandler))})}bindRef(e,t){this.__manageRef(e,t)}unbindRef(e,t){this.__manageRef(e,t,"remove")}__manageChild(e,t,i="add"){const s="add"===i?"$on":"$off";this.__getEventMethodsByName(e).forEach(i=>{const n=this.__getEventNameByMethod(i,e);t[s](n,this.__childrenHandler)})}bindChild(e,t){this.__manageChild(e,t)}unbindChild(e,t){this.__manageChild(e,t,"remove")}__manageRootElement(e="add"){const t=`${e}EventListener`;this.__getEventMethodsByName().forEach(e=>{const i=this.__getEventNameByMethod(e);this.__rootElement[t](i,this.__rootElementHandler)})}bindRootElement(){this.__manageRootElement()}unbindRootElement(){this.__manageRootElement("remove")}__getEventNameByMethod(e,t=""){const i=B.normalizeName(t),s=new RegExp(`^on${i}([A-Z].*)$`),[,n]=e.match(s);return B.normalizeEventName(n)}__getEventMethodsByName(e=""){const t=B.normalizeName(e),i=new RegExp(`^on${t}[A-Z].*$`),s=i.toString();let n=this.__methodsCache.get(s);return n||(n=Array.from(P(this.__base,[],e=>i.test(e)).reduce((e,[t])=>e.add(t),new Set)),this.__methodsCache.set(s,n)),n}static normalizeName(e){return e.replace(/[A-Z]([A-Z].*)/g,e=>e.toLowerCase()).replace(/[^a-zA-Z\d\s:]/g," ").replace(/(^\w|\s+\w)/g,e=>e.trim().toUpperCase()).trim()}static normalizeEventName(e){return e.replace(/[A-Z]/g,e=>`-${e.toLowerCase()}`).replace(/^-/,"")}}var S=function(e){return function(e){return!!e&&"object"==typeof e}(e)&&!function(e){var t=Object.prototype.toString.call(e);return"[object RegExp]"===t||"[object Date]"===t||function(e){return e.$$typeof===C}(e)}(e)},C="function"==typeof Symbol&&Symbol.for?Symbol.for("react.element"):60103;function R(e,t){return!1!==t.clone&&t.isMergeableObject(e)?q(Array.isArray(e)?[]:{},e,t):e}function I(e,t,i){return e.concat(t).map(function(e){return R(e,i)})}function W(e){return Object.keys(e).concat(function(e){return Object.getOwnPropertySymbols?Object.getOwnPropertySymbols(e).filter(function(t){return e.propertyIsEnumerable(t)}):[]}(e))}function z(e,t){try{return t in e}catch(e){return!1}}function q(e,t,i){(i=i||{}).arrayMerge=i.arrayMerge||I,i.isMergeableObject=i.isMergeableObject||S,i.cloneUnlessOtherwiseSpecified=R;var s=Array.isArray(t);return s===Array.isArray(e)?s?i.arrayMerge(e,t,i):function(e,t,i){var s={};return i.isMergeableObject(e)&&W(e).forEach(function(t){s[t]=R(e[t],i)}),W(t).forEach(function(n){(function(e,t){return z(e,t)&&!(Object.hasOwnProperty.call(e,t)&&Object.propertyIsEnumerable.call(e,t))})(e,n)||(s[n]=z(e,n)&&i.isMergeableObject(t[n])?function(e,t){if(!t.customMerge)return q;var i=t.customMerge(e);return"function"==typeof i?i:q}(n,i)(e[n],t[n],i):R(t[n],i))}),s}(e,t,i):R(t,i)}q.all=function(e,t){if(!Array.isArray(e))throw new Error("first argument should be an array");return e.reduce(function(e,i){return q(e,i,t)},{})};var D=q;class V{constructor(e,t,i){var s,n;return this.__values={},this.__defaultValues={String:"",Number:0,Boolean:!1,Array:()=>[],Object:()=>({})},this.name="Base",this.debug=!1,this.log=!1,Object.defineProperties(this,{__element:{enumerable:!1,writable:!1,value:e},__values:{enumerable:!1,writable:!1,value:this.__values},__defaultValues:{enumerable:!1,writable:!1,value:this.__defaultValues}}),this.name=i.name,t.debug={type:Boolean,default:null!=(s=i.debug)&&s},t.log={type:Boolean,default:null!=(n=i.log)&&n},Object.entries(t).forEach(([e,t])=>{this.__register(e,t)}),this}__register(e,t){const i=!V.types.includes(t),s=i?t.type:t;if(!V.types.includes(s))throw new Error(`The "${e}" option has an invalid type. The allowed types are: String, Number, Boolean, Array and Object.`);const n=i?t.default:this.__defaultValues[s.name];if((s===Array||s===Object)&&"function"!=typeof n)throw new Error(`The default value for options of type "${s.name}" must be returned by a function.`);Object.defineProperty(this,e,{get:()=>this.get(e,s,n),set:t=>{this.set(e,s,t,n)},enumerable:!0})}get(e,t,i){const s=V.__getPropertyName(e),n=this.__hasProperty(s);if(t===Boolean){if(i){const t=V.__getPropertyName(e,"No");return!this.__hasProperty(t)}return n||i}const r=this.__element.dataset[s];if(t===Number)return n?Number(r):i;if(t===Array||t===Object){const s=D(i(),n?JSON.parse(r):this.__defaultValues[t.name]());return this.__values[e]||(this.__values[e]=s),this.__values[e]}return n?r:i}set(e,t,i,s){const n=V.__getPropertyName(e);if(i.constructor.name!==t.name){const s=Array.isArray(i)||function(e){return"object"==typeof e&&!!e&&"[object Object]"===e.toString()}(i)?JSON.stringify(i):i;throw new TypeError(`The "${s}" value for the "${e}" option must be of type "${t.name}"`)}switch(t){case Boolean:if(s){const t=V.__getPropertyName(e,"No");i?delete this.__element.dataset[t]:this.__element.dataset[t]=""}else i?this.__element.dataset[n]="":delete this.__element.dataset[n];break;case Array:case Object:this.__values[e]=i;break;default:this.__element.dataset[n]=i}}__hasProperty(e){return void 0!==this.__element.dataset[e]}static __getPropertyName(e,t=""){const i=e+t;if(V.__propertyNameCache.has(i))return V.__propertyNameCache.get(i);const s=`option${t}${e.replace(/^\w/,e=>e.toUpperCase())}`;return V.__propertyNameCache.set(i,s),s}}V.types=[String,Number,Boolean,Array,Object],V.__propertyNameCache=new Map;let F=0;function G(){}class Y{get $root(){if(!this.$parent)return this;let e=this.$parent,t=this.$parent;for(;e;)e.$parent||(t=e),e=e.$parent;return t}get __config(){let t=Object.getPrototypeOf(this),{config:i}=t.constructor;for(;t.constructor.config&&t.constructor.$isBase;)i=e({},t.constructor.config,i),t.constructor.config.options&&(i.options=e({},t.constructor.config.options,i.options)),t=Object.getPrototypeOf(t);return i}get $services(){const e=this.__services;return this.$emit("get:services",e),e}get $refs(){const e=this.__refs;return this.$emit("get:refs",e),e}get $options(){const e=this.__options;return this.$emit("get:options",e),e}get $children(){const e=this.__children;return this.$emit("get:children",e),e}get $log(){return this.__options.log?window.console.log.bind(window,`[${this.__config.name}]`):G}get __debug(){return this.__options.debug&&void 0!==window.__DEV__&&window.__DEV__?window.console.log.bind(window,`[debug] [${this.$id}]`):G}constructor(e){if(this.$parent=null,this.$isMounted=!1,!e)throw new Error("The root element must be defined.");const{__config:t}=this;if(!t)throw new Error("The `config` static property must be defined.");if(!t.name)throw new Error("The `config.name` property is required.");return this.$id=`${t.name}-${F}`,F+=1,this.$el=e,"__base__"in this.$el||Object.defineProperty(this.$el,"__base__",{get:()=>this,configurable:!0}),this.__options=new V(e,t.options||{},t),this.__services=new H(this),this.__events=new B(e,this),this.__children=new a(this,e,t.components||{},this.__events),this.__refs=new h(this,e,t.refs||[],this.__events),this.__debug("constructor",this),this}$mount(){return this.__debug("$mount"),this.$children.registerAll(),this.$refs.registerAll(),this.__events.bindRootElement(),this.$services.enableAll(),this.$children.mountAll(),r(this,"mounted"),this.$isMounted=!0,this}$update(){return this.__debug("$update"),this.$refs.unregisterAll(),this.$services.disableAll(),this.$children.registerAll(),this.$refs.registerAll(),this.$services.enableAll(),this.$children.updateAll(),r(this,"updated"),this}$destroy(){return this.__debug("$destroy"),this.__events.unbindRootElement(),this.$refs.unregisterAll(),this.$services.disableAll(),this.$children.destroyAll(),r(this,"destroyed"),this.$isMounted=!1,this}$terminate(){this.__debug("$terminate"),this.$destroy(),r(this,"terminated"),Object.defineProperty(this.$el,"__base__",{value:"terminated",configurable:!1,writable:!1})}static $factory(e){if(!e)throw new Error("The $factory method requires a component’s name or selector to be specified.");return o(e).map(e=>new this(e).$mount())}$on(e,t,i){return this.__debug("$on",e,t,i),this.$el.addEventListener(e,t,i),()=>{this.$off(e,t,i)}}$off(e,t,i){this.__debug("$off",e,t),this.$el.removeEventListener(e,t,i)}$emit(e,...t){this.__debug("$emit",e,t),this.$el.dispatchEvent(new CustomEvent(e,{detail:t}))}}function X(e){const{breakpoint:t}=y().props();e.forEach(([e,i])=>{e.includes(t)&&!i.$isMounted?setTimeout(()=>i.$mount(),0):!e.includes(t)&&i.$isMounted&&i.$destroy()})}Y.$isBase=!0;const U=new WeakMap;function Z(e,t){if(!Array.isArray(t))throw new Error("[withBreakpointManager] The `breakpoints` parameter must be an array.");if(t.length<2)throw new Error("[withBreakpointManager] You must define at least 2 breakpoints.");const{add:i,props:s}=y();if(!s().breakpoint)throw new Error("The `BreakpointManager` class requires breakpoints to be defined.");return class extends e{constructor(e){return super(e),U.has(this)||U.set(this,function(e,t){return t.map(([t,i])=>{const s=new i(e.$el);return Object.defineProperty(s,"$parent",{get:()=>e.$parent}),[t,s]})}(this,t)),i(`BreakpointManager-${this.$id}`,()=>{X(U.get(this))}),this.instances=U.get(this),this}$mount(){return super.$mount(),X(U.get(this)),this}$destroy(){return Array.isArray(U.get(this))&&U.get(this).forEach(([,e])=>{e.$destroy()}),super.$destroy()}}}function J(e,t=y().props().breakpoint){const{activeBreakpoints:i,inactiveBreakpoints:s}=e.$options,n=i&&i.split(" ").includes(t),r=s&&s.split(" ").includes(t);return i&&n||s&&!r?"$mount":"$destroy"}function K(e){const{activeBreakpoints:t,inactiveBreakpoints:i}=e.$options;return Boolean(t||i)}function Q(e,t){!function(e){const{activeBreakpoints:t,inactiveBreakpoints:i,name:s}=e.$options;if(t&&i)throw new Error(`[${s}] Incorrect configuration: the \`activeBreakpoints\` and \`inactiveBreakpoints\` are not compatible.`)}(t);const{add:i,has:s}=y();s(e)||i(e,function({breakpoint:e}){const i=J(t,e);"$destroy"===i&&t.$isMounted?t[i]():"$mount"!==i||t.$isMounted||setTimeout(()=>t[i](),0)})}function ee(t){var i,s,n,r,o;return s=i=class extends t{constructor(e){super(e);const{remove:t,props:i}=y(),{name:s}=this.$options;if(!i().breakpoint)throw new Error(`[${s}] The \`BreakpointObserver\` class requires breakpoints to be defined.`);const n=`BreakpointObserver-${this.$id}`;return new MutationObserver(([e])=>{if("attributes"===e.type&&("data-options"===e.attributeName||e.attributeName.startsWith("data-option-"))){if(!K(this))return this.$mount(),void t(n);Q(n,this)}}).observe(this.$el,{attributes:!0}),K(this)?(Q(n,this),this):this}$mount(){return K(this)?"$mount"===J(this)?super.$mount():this:super.$mount()}},i.config=e({},t.config||{},{name:`${null!=(n=null==t||null==(r=t.config)?void 0:r.name)?n:""}WithBreakpointObserver`,options:e({},(null==t||null==(o=t.config)?void 0:o.options)||{},{activeBreakpoints:String,inactiveBreakpoints:String})}),s}function te(e,t,i=.85){if(i>=1||i<=0)throw new Error(`The \`factor\` parameter must be a number greater than 0 and smaller than 1, \`${i}\` given.`);let s=t,n=e;for(;Math.abs(s)>.1;)n+=s,s*=i;return n}let ie=0;class se extends l{constructor(t,i={}){return super(),this.isGrabbing=!1,this.hasInertia=!1,this.x=0,this.y=0,this.delta={x:0,y:0},this.origin={x:0,y:0},this.distance={x:0,y:0},this.final={x:0,y:0},this.options={factor:.85},ie+=1,this.id=`drag-${ie}`,this.target=t,this.options=e({},this.options,i),this.pointerHandler=this.pointerHandler.bind(this),this.rafHandler=this.rafHandler.bind(this),this}init(){const e={passive:!0};return this.target.addEventListener("mousedown",this,e),this.target.addEventListener("touchstart",this,e),m().add(this.id,this.pointerHandler),this}kill(){return this.target.removeEventListener("mousemove",this),this.target.removeEventListener("touchmove",this),m().remove(this.id),this}handleEvent(e){const t=e instanceof MouseEvent?e.clientX:e.touches[0].clientX,i=e instanceof MouseEvent?e.clientY:e.touches[0].clientY;this.start(t,i)}start(e,t){this.x=e,this.y=t,this.origin.x=e,this.origin.y=t,this.delta.x=0,this.delta.y=0,this.distance.x=0,this.distance.y=0,this.final.x=e,this.final.y=t,this.mode="start",this.isGrabbing=!0,this.trigger(this.props)}drop(){this.isGrabbing=!1,this.mode="drop",this.hasInertia=!0,this.final.x=te(this.x,this.delta.x,this.options.factor),this.final.y=te(this.y,this.delta.y,this.options.factor),this.trigger(this.props),setTimeout(()=>{const e=g();e.remove(this.id),e.add(this.id,this.rafHandler)},0)}stop(){g().remove(this.id),this.hasInertia=!1,this.mode="stop",this.trigger(this.props)}rafHandler(){this.isGrabbing||(this.x+=this.delta.x,this.y+=this.delta.y,this.distance.x=this.x-this.origin.x,this.distance.y=this.y-this.origin.y,this.delta.x*=this.options.factor,this.delta.y*=this.options.factor,"inertia"!==this.mode&&(this.mode="inertia"),this.trigger(this.props),Math.abs(this.delta.x)<.1&&Math.abs(this.delta.y)<.1&&this.stop())}pointerHandler(e){this.isGrabbing&&(this.x=e.x,this.y=e.y,this.delta.x=e.delta.x,this.delta.y=e.delta.y,this.final.x=e.x,this.final.y=e.y,this.distance.x=this.x-this.origin.x,this.distance.y=this.y-this.origin.y,"drag"!==this.mode&&(this.mode="drag"),this.trigger(this.props),e.isDown||this.drop())}get props(){return{target:this.target,mode:this.mode,isGrabbing:this.isGrabbing,hasInertia:this.hasInertia,x:this.x,y:this.y,delta:this.delta,origin:this.origin,distance:this.distance,final:this.final}}}const ne=new WeakMap;function re(e,t){let i=ne.get(e);return i||(i=new se(e,t),ne.set(e,i)),{add:i.add.bind(i),remove:i.remove.bind(i),has:i.has.bind(i),props:()=>i.props}}const oe=["target"];function ae(e,t={target(){return this.$el}}){return class extends e{constructor(e){super(e),this.$on("mounted",()=>{const{target:e}=t,i=function(e,t){if(null==e)return{};var i,s,n={},r=Object.keys(e);for(s=0;s<r.length;s++)t.indexOf(i=r[s])>=0||(n[i]=e[i]);return n}(t,oe),s=re.bind(void 0,e.call(this),i);this.$services.register("dragged",s),this.$services.enable("dragged")}),this.$on("destroyed",()=>{this.$services.disable("dragged"),this.$services.unregister("dragged")})}}}function he(e,t,i={}){var s,n;const r=D(e.config,t,i);return r.name===e.config.name&&(r.name=`${e.config.name}WithExtraConfig`),n=s=class extends e{},s.config=r,n}function le(e){return[...new Array(e+1)].map((t,i)=>i/e)}function de(t,i={threshold:le(100)}){var s,n,r,o,a;return n=s=class extends t{constructor(t){if(super(t),!this.intersected||"function"!=typeof this.intersected)throw new Error("[withIntersectionObserver] The `intersected` method must be defined.");return this.$observer=new IntersectionObserver(e=>{this.__debug("intersected",e),this.$emit("intersected",e),this.intersected(e)},e({},i,this.$options.intersectionObserver||{})),this.$on("mounted",()=>{this.$observer.observe(this.$el)}),this.$on("destroyed",()=>{this.$observer.unobserve(this.$el)}),this}},s.config=e({},t.config||{},{name:`${null!=(r=null==t||null==(o=t.config)?void 0:o.name)?r:""}WithIntersectionObserver`,options:e({},(null==t||null==(a=t.config)?void 0:a.options)||{},{intersectionObserver:Object})}),n}function ce(t,n={threshold:[0,1]}){var r,o,a,h,l,d,c;return o=i("isVisible"),a=i("observer"),h=r=class extends t{constructor(t){return super(t),Object.defineProperty(this,o,{writable:!0,value:!1}),Object.defineProperty(this,a,{writable:!0,value:void 0}),s(this,a)[a]=new IntersectionObserver(e=>{const t=e.reduce((e,t)=>e||t.isIntersecting,!1);s(this,o)[o]!==t&&(s(this,o)[o]=t,this[t?"$mount":"$destroy"]())},e({},n,this.$options.intersectionObserver)),s(this,a)[a].observe(this.$el),this.$on("terminated",()=>{s(this,a)[a].disconnect()}),this}$mount(){return s(this,o)[o]&&super.$mount(),this}},r.config=e({},t.config||{},{name:`${null!=(l=null==t||null==(d=t.config)?void 0:d.name)?l:""}WithMountWhenInView`,options:e({},(null==t||null==(c=t.config)?void 0:c.options)||{},{intersectionObserver:Object})}),h}function ue(e,t){let i,s="complete"===document.readyState;s?i=new e(t).$mount():document.addEventListener("readystatechange",()=>{"complete"===document.readyState&&(i=new e(t).$mount(),s=!0)});const n=new Promise(e=>{document.addEventListener("readystatechange",()=>{"complete"===document.readyState&&setTimeout(()=>e(i),0)})});return function(){return s?Promise.resolve(i):n}}function me(e,t){return"string"==typeof e?o(e,t):Array.isArray(e)?e:[e]}function pe(e,t,i,s){const n="string"==typeof i?[i]:i;let r;return new Promise(i=>{const o=me(t,null==s?void 0:s.$el),a={capture:!0,passive:!0,once:!0},h=()=>{(t=>{e().then(e=>{r="default"in e?e.default:e,t(r)})})(i)};o.forEach(e=>{n.forEach(t=>{e.addEventListener(t,h,a)})})})}function _e(e,t){let i;const s=t=>{e().then(e=>{i="default"in e?e.default:e,t(i)})};return new Promise(e=>{var i;const n=null!=(i=null==t?void 0:t.timeout)?i:1;"requestIdleCallback"in window?window.requestIdleCallback(()=>{setTimeout(()=>{s(e)},0)},{timeout:null==t?void 0:t.timeout}):setTimeout(()=>{s(e)},n)})}function ge(e,t,i,s={}){let n;return new Promise(r=>{const o=new IntersectionObserver(t=>{t.some(e=>e.isIntersecting)&&setTimeout(()=>{((t,i)=>{e().then(e=>{n="default"in e?e.default:e,t(n),o.disconnect()})})(r)},0)},s);me(t,null==i?void 0:i.$el).forEach(e=>o.observe(e))})}export{Y as Base,ue as createApp,pe as importOnInteraction,_e as importWhenIdle,ge as importWhenVisible,re as useDrag,A as useKey,N as useLoad,m as usePointer,g as useRaf,y as useResize,E as useScroll,Z as withBreakpointManager,ee as withBreakpointObserver,ae as withDrag,he as withExtraConfig,de as withIntersectionObserver,ce as withMountWhenInView};