@dooboostore/simple-web-component 1.0.19 → 1.0.22

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 (174) hide show
  1. package/README.md +2759 -201
  2. package/dist/cjs/decorators/addEventListener.js +8 -4
  3. package/dist/cjs/decorators/addEventListener.js.map +2 -2
  4. package/dist/cjs/decorators/{appendChild.js → applyNode.js} +26 -18
  5. package/dist/cjs/decorators/applyNode.js.map +7 -0
  6. package/dist/cjs/decorators/attribute.js +162 -0
  7. package/dist/cjs/decorators/attribute.js.map +7 -0
  8. package/dist/cjs/decorators/{changedAttribute.js → changedAttributeHost.js} +11 -11
  9. package/dist/cjs/decorators/changedAttributeHost.js.map +7 -0
  10. package/dist/cjs/decorators/classList.js +15 -5
  11. package/dist/cjs/decorators/classList.js.map +2 -2
  12. package/dist/cjs/decorators/elementDefine.js +124 -46
  13. package/dist/cjs/decorators/elementDefine.js.map +3 -3
  14. package/dist/cjs/decorators/emitCustomEvent.js +8 -7
  15. package/dist/cjs/decorators/emitCustomEvent.js.map +2 -2
  16. package/dist/cjs/decorators/index.js +3 -3
  17. package/dist/cjs/decorators/index.js.map +2 -2
  18. package/dist/cjs/decorators/lifecycles.js +8 -4
  19. package/dist/cjs/decorators/lifecycles.js.map +2 -2
  20. package/dist/cjs/decorators/onConnectedInnerHtml.js +4 -4
  21. package/dist/cjs/decorators/onConnectedInnerHtml.js.map +2 -2
  22. package/dist/cjs/decorators/query.js +9 -5
  23. package/dist/cjs/decorators/query.js.map +2 -2
  24. package/dist/cjs/decorators/queryAll.js +9 -5
  25. package/dist/cjs/decorators/queryAll.js.map +2 -2
  26. package/dist/cjs/decorators/setAttribute.js +51 -21
  27. package/dist/cjs/decorators/setAttribute.js.map +2 -2
  28. package/dist/cjs/decorators/style.js +4 -4
  29. package/dist/cjs/decorators/style.js.map +2 -2
  30. package/dist/cjs/elements/SwcAppEngine.js +8 -8
  31. package/dist/cjs/elements/SwcAppEngine.js.map +3 -3
  32. package/dist/cjs/elements/SwcAppMixin.js +28 -1
  33. package/dist/cjs/elements/SwcAppMixin.js.map +2 -2
  34. package/dist/cjs/elements/SwcAsync.js +6 -6
  35. package/dist/cjs/elements/SwcAsync.js.map +2 -2
  36. package/dist/cjs/elements/SwcChoose.js +6 -6
  37. package/dist/cjs/elements/SwcChoose.js.map +2 -2
  38. package/dist/cjs/elements/SwcIf.js +6 -6
  39. package/dist/cjs/elements/SwcIf.js.map +2 -2
  40. package/dist/cjs/elements/SwcLoop.js +6 -6
  41. package/dist/cjs/elements/SwcLoop.js.map +2 -2
  42. package/dist/cjs/elements/register.js +19 -18
  43. package/dist/cjs/elements/register.js.map +2 -2
  44. package/dist/cjs/index.js +6 -17
  45. package/dist/cjs/index.js.map +2 -2
  46. package/dist/cjs/router/ElementRouter.js +7 -7
  47. package/dist/cjs/router/ElementRouter.js.map +2 -2
  48. package/dist/cjs/types.js.map +2 -2
  49. package/dist/esm/decorators/addEventListener.js +5 -1
  50. package/dist/esm/decorators/addEventListener.js.map +2 -2
  51. package/dist/esm/decorators/{appendChild.js → applyNode.js} +23 -15
  52. package/dist/esm/decorators/applyNode.js.map +7 -0
  53. package/dist/esm/decorators/attribute.js +143 -0
  54. package/dist/esm/decorators/attribute.js.map +7 -0
  55. package/dist/esm/decorators/{changedAttribute.js → changedAttributeHost.js} +4 -4
  56. package/dist/esm/decorators/changedAttributeHost.js.map +7 -0
  57. package/dist/esm/decorators/classList.js +12 -2
  58. package/dist/esm/decorators/classList.js.map +2 -2
  59. package/dist/esm/decorators/elementDefine.js +119 -41
  60. package/dist/esm/decorators/elementDefine.js.map +2 -2
  61. package/dist/esm/decorators/emitCustomEvent.js +5 -4
  62. package/dist/esm/decorators/emitCustomEvent.js.map +2 -2
  63. package/dist/esm/decorators/index.js +3 -3
  64. package/dist/esm/decorators/index.js.map +1 -1
  65. package/dist/esm/decorators/lifecycles.js +5 -1
  66. package/dist/esm/decorators/lifecycles.js.map +2 -2
  67. package/dist/esm/decorators/onConnectedInnerHtml.js +1 -1
  68. package/dist/esm/decorators/onConnectedInnerHtml.js.map +1 -1
  69. package/dist/esm/decorators/query.js +6 -2
  70. package/dist/esm/decorators/query.js.map +2 -2
  71. package/dist/esm/decorators/queryAll.js +6 -2
  72. package/dist/esm/decorators/queryAll.js.map +2 -2
  73. package/dist/esm/decorators/setAttribute.js +47 -17
  74. package/dist/esm/decorators/setAttribute.js.map +2 -2
  75. package/dist/esm/decorators/style.js +1 -1
  76. package/dist/esm/decorators/style.js.map +1 -1
  77. package/dist/esm/elements/SwcAppEngine.js +4 -4
  78. package/dist/esm/elements/SwcAppEngine.js.map +2 -2
  79. package/dist/esm/elements/SwcAppMixin.js +28 -1
  80. package/dist/esm/elements/SwcAppMixin.js.map +2 -2
  81. package/dist/esm/elements/SwcAsync.js +3 -3
  82. package/dist/esm/elements/SwcAsync.js.map +2 -2
  83. package/dist/esm/elements/SwcChoose.js +3 -3
  84. package/dist/esm/elements/SwcChoose.js.map +2 -2
  85. package/dist/esm/elements/SwcIf.js +3 -3
  86. package/dist/esm/elements/SwcIf.js.map +2 -2
  87. package/dist/esm/elements/SwcLoop.js +3 -3
  88. package/dist/esm/elements/SwcLoop.js.map +2 -2
  89. package/dist/esm/elements/register.js +7 -6
  90. package/dist/esm/elements/register.js.map +2 -2
  91. package/dist/esm/index.js +6 -17
  92. package/dist/esm/index.js.map +2 -2
  93. package/dist/esm/router/ElementRouter.js +2 -2
  94. package/dist/esm/router/ElementRouter.js.map +1 -1
  95. package/dist/esm/types.js.map +2 -2
  96. package/dist/esm-bundle/dooboostore-simple-web-component.esm.js +5444 -3317
  97. package/dist/esm-bundle/dooboostore-simple-web-component.esm.js.map +4 -4
  98. package/dist/types/decorators/addEventListener.d.ts +6 -0
  99. package/dist/types/decorators/addEventListener.d.ts.map +1 -1
  100. package/dist/types/decorators/applyNode.d.ts +38 -0
  101. package/dist/types/decorators/applyNode.d.ts.map +1 -0
  102. package/dist/types/decorators/attribute.d.ts +29 -0
  103. package/dist/types/decorators/attribute.d.ts.map +1 -0
  104. package/dist/types/decorators/{changedAttribute.d.ts → changedAttributeHost.d.ts} +6 -2
  105. package/dist/types/decorators/changedAttributeHost.d.ts.map +1 -0
  106. package/dist/types/decorators/classList.d.ts +25 -0
  107. package/dist/types/decorators/classList.d.ts.map +1 -1
  108. package/dist/types/decorators/elementDefine.d.ts.map +1 -1
  109. package/dist/types/decorators/emitCustomEvent.d.ts +14 -2
  110. package/dist/types/decorators/emitCustomEvent.d.ts.map +1 -1
  111. package/dist/types/decorators/index.d.ts +3 -3
  112. package/dist/types/decorators/index.d.ts.map +1 -1
  113. package/dist/types/decorators/lifecycles.d.ts +2 -0
  114. package/dist/types/decorators/lifecycles.d.ts.map +1 -1
  115. package/dist/types/decorators/query.d.ts +6 -0
  116. package/dist/types/decorators/query.d.ts.map +1 -1
  117. package/dist/types/decorators/queryAll.d.ts +6 -0
  118. package/dist/types/decorators/queryAll.d.ts.map +1 -1
  119. package/dist/types/decorators/setAttribute.d.ts +8 -0
  120. package/dist/types/decorators/setAttribute.d.ts.map +1 -1
  121. package/dist/types/elements/SwcAppEngine.d.ts +5 -4
  122. package/dist/types/elements/SwcAppEngine.d.ts.map +1 -1
  123. package/dist/types/elements/SwcAppMixin.d.ts +1 -1
  124. package/dist/types/elements/SwcAppMixin.d.ts.map +1 -1
  125. package/dist/types/elements/register.d.ts +1 -1
  126. package/dist/types/elements/register.d.ts.map +1 -1
  127. package/dist/types/index.d.ts +3 -14
  128. package/dist/types/index.d.ts.map +1 -1
  129. package/dist/types/router/ElementRouter.d.ts +1 -1
  130. package/dist/types/router/ElementRouter.d.ts.map +1 -1
  131. package/dist/types/types.d.ts +3 -1
  132. package/dist/types/types.d.ts.map +1 -1
  133. package/dist/umd-bundle/dooboostore-simple-web-component.umd.js +5444 -3317
  134. package/dist/umd-bundle/dooboostore-simple-web-component.umd.js.map +4 -4
  135. package/package.json +10 -5
  136. package/src/decorators/addEventListener.ts +10 -1
  137. package/src/decorators/applyNode.ts +127 -0
  138. package/src/decorators/attribute.ts +192 -0
  139. package/src/decorators/{changedAttribute.ts → changedAttributeHost.ts} +6 -2
  140. package/src/decorators/classList.ts +33 -1
  141. package/src/decorators/elementDefine.ts +148 -47
  142. package/src/decorators/emitCustomEvent.ts +14 -6
  143. package/src/decorators/index.ts +3 -3
  144. package/src/decorators/lifecycles.ts +4 -2
  145. package/src/decorators/onConnectedInnerHtml.ts +1 -1
  146. package/src/decorators/query.ts +10 -1
  147. package/src/decorators/queryAll.ts +10 -1
  148. package/src/decorators/setAttribute.ts +57 -17
  149. package/src/decorators/style.ts +1 -1
  150. package/src/elements/SwcAppEngine.ts +10 -8
  151. package/src/elements/SwcAppMixin.ts +34 -2
  152. package/src/elements/SwcAsync.ts +3 -3
  153. package/src/elements/SwcChoose.ts +3 -3
  154. package/src/elements/SwcIf.ts +3 -3
  155. package/src/elements/SwcLoop.ts +3 -3
  156. package/src/elements/register.ts +8 -6
  157. package/src/index.ts +8 -16
  158. package/src/router/ElementRouter.ts +2 -2
  159. package/src/types.ts +3 -1
  160. package/dist/cjs/decorators/appendChild.js.map +0 -7
  161. package/dist/cjs/decorators/changedAttribute.js.map +0 -7
  162. package/dist/cjs/decorators/replaceChildren.js +0 -79
  163. package/dist/cjs/decorators/replaceChildren.js.map +0 -7
  164. package/dist/esm/decorators/appendChild.js.map +0 -7
  165. package/dist/esm/decorators/changedAttribute.js.map +0 -7
  166. package/dist/esm/decorators/replaceChildren.js +0 -60
  167. package/dist/esm/decorators/replaceChildren.js.map +0 -7
  168. package/dist/types/decorators/appendChild.d.ts +0 -17
  169. package/dist/types/decorators/appendChild.d.ts.map +0 -1
  170. package/dist/types/decorators/changedAttribute.d.ts.map +0 -1
  171. package/dist/types/decorators/replaceChildren.d.ts +0 -9
  172. package/dist/types/decorators/replaceChildren.d.ts.map +0 -1
  173. package/src/decorators/appendChild.ts +0 -86
  174. package/src/decorators/replaceChildren.ts +0 -64
@@ -1,21 +1,18 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
2
- import { FunctionUtils } from '@dooboostore/core/function/FunctionUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
+ import { FunctionUtils } from '@dooboostore/core';
3
3
  import { getOnConnectedInnerHtmlMetadata } from './onConnectedInnerHtml';
4
4
  import { getAddEventListenerMetadata } from './addEventListener';
5
- import { ON_BEFORE_CONNECTED_METADATA_KEY, ON_AFTER_CONNECTED_METADATA_KEY, ON_BEFORE_DISCONNECTED_METADATA_KEY, ON_AFTER_DISCONNECTED_METADATA_KEY, ON_BEFORE_ADOPTED_METADATA_KEY, ON_AFTER_ADOPTED_METADATA_KEY, findAllLifecycleMetadata } from './lifecycles';
5
+ import { ON_CONSTRUCTOR_METADATA_KEY, ON_BEFORE_CONNECTED_METADATA_KEY, ON_AFTER_CONNECTED_METADATA_KEY, ON_BEFORE_DISCONNECTED_METADATA_KEY, ON_AFTER_DISCONNECTED_METADATA_KEY, ON_BEFORE_ADOPTED_METADATA_KEY, ON_AFTER_ADOPTED_METADATA_KEY, findAllLifecycleMetadata } from './lifecycles';
6
6
  import { getEmitCustomEventMetadataList } from './emitCustomEvent';
7
- import { findAllAttributeChangedMetadata } from './changedAttribute';
7
+ import { findAllAttributeChangedMetadata } from './changedAttributeHost';
8
8
  import { findAllSetAttributeMetadata } from './setAttribute';
9
- import { findAllReplaceChildrenMetadata } from './replaceChildren';
10
- import { findAllAppendChildMetadata } from './appendChild';
11
- import { findAllClassListMetadata } from './classList';
12
- import { findAllStyleMetadata } from './style';
9
+ import { findAllAttributeMetadata } from './attribute';
13
10
  import { SwcUtils } from '../utils/Utils';
14
11
  import { HTML_TAG_ENTRIES, DOM_EVENT_NAMES } from '../config/config';
15
12
  import { SituationTypeContainer, SituationTypeContainers } from '@dooboostore/simple-boot/decorators/inject/Inject';
16
13
  import { InjectSituationType, HostSet } from '../types';
17
14
 
18
- // --- Core Interfaces & Types (Moved back from base.ts) ---
15
+ // --- Core Interfaces & Types ---
19
16
 
20
17
  export const ELEMENT_CONFIG_KEY = Symbol('simple-web-component:element-config');
21
18
 
@@ -46,6 +43,12 @@ export const ensureInit = (inst: any) => {
46
43
  // Call constructor script if present
47
44
  const hostSet = SwcUtils.getHostSet(inst);
48
45
  inst._executeSwcScript?.('swc-on-constructor', hostSet);
46
+
47
+ // Call @onConstructor lifecycle methods
48
+ const cMethods = findAllLifecycleMetadata(inst, ON_CONSTRUCTOR_METADATA_KEY);
49
+ if (cMethods) {
50
+ for (const m of cMethods) (inst)._invokeLifecycleMethod(m, hostSet);
51
+ }
49
52
  }
50
53
  };
51
54
 
@@ -159,7 +162,9 @@ const setupPrototype = (proto: any) => {
159
162
  if (oldHandler) el.removeEventListener(eventName, oldHandler);
160
163
 
161
164
  const handler = async (event: any) => {
162
- const hostSet = SwcUtils.getHostSet(el);
165
+ console.log('execute handler', event);
166
+ const parent = SwcUtils.findNearestSwcHost(el);
167
+ const hostSet = SwcUtils.getHostSet(parent || el);
163
168
  const conf = getElementConfig(this);
164
169
  const currentWin = (this as any)._resolveWindow(conf);
165
170
  const helpers = SwcUtils.getHelperSet(currentWin);
@@ -180,13 +185,19 @@ const setupPrototype = (proto: any) => {
180
185
 
181
186
  proto.__swc_executeAttributeEvent = async function (el: HTMLElement, attrName: string, script: string, event: Event) {
182
187
  ensureInit(this);
183
- const hostSet = SwcUtils.getHostSet(el);
188
+
189
+ console.log('execute handler2', event);
190
+ const parent = SwcUtils.findNearestSwcHost(el);
191
+ const hostSet = SwcUtils.getHostSet(parent || el);
184
192
  const conf = getElementConfig(this);
185
193
  const currentWin = (this as any)._resolveWindow(conf);
186
194
  const currentHelpers = SwcUtils.getHelperSet(currentWin);
195
+ const detail = (event as CustomEvent).detail;
187
196
  const args = {
188
197
  event,
189
- $data: (event as CustomEvent).detail,
198
+ $event: event,
199
+ $data: detail,
200
+ $detail: detail,
190
201
  ...hostSet,
191
202
  ...currentHelpers,
192
203
  $el: el,
@@ -219,14 +230,17 @@ export const elementDefine =
219
230
  }
220
231
 
221
232
  const emitCustomEventList = getEmitCustomEventMetadataList(constructor) || [];
233
+ const emitHostCustomEventList = emitCustomEventList.filter(meta => meta.selector === ':host' || meta.selector === '');
222
234
  const addEventListenerList = getAddEventListenerMetadata(constructor) || [];
235
+ const addHostEventListenerList = addEventListenerList.filter(meta => meta.selector === ':host' || meta.selector === '');
223
236
  const attrChangeMap = findAllAttributeChangedMetadata(constructor);
237
+ const attributeList = findAllAttributeMetadata(constructor);
224
238
 
225
239
  const swcLifecycleAttributes = ['swc-on-constructor', 'swc-on-connected', 'swc-on-disconnected', 'swc-on-before-connected', 'swc-on-after-connected', 'swc-on-before-disconnected', 'swc-on-after-disconnected', 'swc-on-before-adopted', 'swc-on-after-adopted', 'swc-on-attribute-changed'];
226
240
  const swcOnEvents = DOM_EVENT_NAMES.map(e => `swc-on-${e}`);
227
241
 
228
242
  // Collect all observed attributes from all decorators
229
- const mergedObservedAttributes = [...new Set([...(metadata.observedAttributes ?? []), ...attrChangeMap.keys(), ...Array.from(findAllSetAttributeMetadata(constructor).values()).map(it => it.name), ...emitCustomEventList.map(it => it.options.attributeName!), ...swcLifecycleAttributes, ...swcOnEvents])];
243
+ const mergedObservedAttributes = [...new Set([...(metadata.observedAttributes ?? []), ...attrChangeMap.keys(), ...Array.from(findAllSetAttributeMetadata(constructor).values()).map(it => it.name), ...attributeList.map(it => it.options.name || String(it.propertyKey)), ...emitHostCustomEventList.map(it => (it.options as any).attributeName).filter(Boolean), ...swcLifecycleAttributes, ...swcOnEvents])];
230
244
 
231
245
  const connectedInnerHtmlList = getOnConnectedInnerHtmlMetadata(constructor) || [];
232
246
 
@@ -251,7 +265,23 @@ export const elementDefine =
251
265
  for (const m of bMethods) (this as any)._invokeLifecycleMethod(m, hostSet);
252
266
  }
253
267
 
254
- if (typeof (this as any).initCore === 'function') (this as any).initCore();
268
+ // Initialize @attribute fields (DOM <-> JS Sync)
269
+ attributeList.forEach(meta => {
270
+ const attrName = meta.options.name || String(meta.propertyKey);
271
+ if (meta.options.connectedInitialize === true) {
272
+ // JS -> DOM (FORCE OVERWRITE with JS value)
273
+ (this as any).__swc_syncing_init = true;
274
+ try {
275
+ const memoryVal = (this as any)[meta.privateKey];
276
+ if (memoryVal !== undefined) {
277
+ (this as any)[meta.propertyKey] = memoryVal; // Trigger setter to update DOM
278
+ }
279
+ } finally {
280
+ (this as any).__swc_syncing_init = false;
281
+ }
282
+ }
283
+ // else: Do NOT sync - Keep the default value from class initialization
284
+ });
255
285
 
256
286
  if (connectedInnerHtmlList.length > 0) {
257
287
  let sContent = '',
@@ -275,7 +305,76 @@ export const elementDefine =
275
305
  globalDelegatedRoots.add(root);
276
306
  }
277
307
 
308
+ // Separate delegate and non-delegate listeners
309
+ const delegateListeners: typeof addEventListenerList = [];
310
+ const nonDelegateListeners: typeof addEventListenerList = [];
311
+
278
312
  addEventListenerList.forEach(meta => {
313
+ if (meta.options.delegate && meta.selector !== ':window' && meta.selector !== ':document' && meta.selector !== ':parentHost' && meta.selector !== ':appHost' && meta.selector !== ':firstHost' && meta.selector !== ':lastHost' && meta.selector !== ':firstAppHost' && meta.selector !== ':lastAppHost' && meta.selector !== ':hosts' && meta.selector !== ':appHosts' && meta.selector !== ':host' && meta.selector !== '') {
314
+ delegateListeners.push(meta);
315
+ } else {
316
+ nonDelegateListeners.push(meta);
317
+ }
318
+ });
319
+
320
+ // Group delegate listeners by (type, root) combination
321
+ const delegatesByTypeAndRoot = new Map<string, any[]>();
322
+ delegateListeners.forEach(meta => {
323
+ const r = meta.options.root || 'auto';
324
+ const rootKey = `${meta.type}:${r}`;
325
+ if (!delegatesByTypeAndRoot.has(rootKey)) {
326
+ delegatesByTypeAndRoot.set(rootKey, []);
327
+ }
328
+ delegatesByTypeAndRoot.get(rootKey)!.push(meta);
329
+ });
330
+
331
+ // Register unified handlers for delegate listeners
332
+ delegatesByTypeAndRoot.forEach((metaList, typeRootKey) => {
333
+ const [type, rStr] = typeRootKey.split(':');
334
+ const r = rStr === 'auto' ? 'auto' : rStr;
335
+ const opts = { capture: metaList[0].options.capture, once: metaList[0].options.once, passive: metaList[0].options.passive };
336
+
337
+ const bindRoots: (HTMLElement | ShadowRoot)[] = [];
338
+ if (r === 'auto') bindRoots.push(this.shadowRoot || (this as any));
339
+ else if (r === 'light') bindRoots.push(this as any);
340
+ else if (r === 'shadow' && this.shadowRoot) bindRoots.push(this.shadowRoot);
341
+ else if (r === 'all') {
342
+ bindRoots.push(this as any);
343
+ if (this.shadowRoot) bindRoots.push(this.shadowRoot);
344
+ }
345
+
346
+ bindRoots.forEach(br => {
347
+ // Sort: stopPropagation handlers first (more specific/terminal actions)
348
+ const sortedMetaList = [...metaList].sort((a, b) => {
349
+ const aStop = a.options.stopPropagation ? 1 : 0;
350
+ const bStop = b.options.stopPropagation ? 1 : 0;
351
+ return bStop - aStop; // stopPropagation: true comes first
352
+ });
353
+
354
+ const unifiedHandler = async (event: Event) => {
355
+ for (const meta of sortedMetaList) {
356
+ const { selector, options } = meta;
357
+ const matchedEl = (event.target as HTMLElement).closest(selector);
358
+ if (matchedEl && (br as any).contains(matchedEl)) {
359
+ if (options.stopPropagation) event.stopPropagation();
360
+ if (options.stopImmediatePropagation) event.stopImmediatePropagation();
361
+ if (options.preventDefault) event.preventDefault();
362
+ const currentHostSet = SwcUtils.getHostSet(this as any);
363
+ const args = { event, ...currentHostSet, $el: matchedEl, $root: br };
364
+ await (this as any)[meta.propertyKey](event, currentHostSet, matchedEl, args);
365
+
366
+ // Stop processing if event propagation was stopped
367
+ if ((event as any).cancelBubble) break;
368
+ }
369
+ }
370
+ };
371
+ br.addEventListener(type, unifiedHandler, opts);
372
+ (this as any)._boundListeners.push({ target: br, type, handler: unifiedHandler, options: opts });
373
+ });
374
+ });
375
+
376
+ // Process non-delegate listeners
377
+ nonDelegateListeners.forEach(meta => {
279
378
  const { selector, type, options } = meta;
280
379
  const opts = { capture: options.capture, once: options.once, passive: options.passive };
281
380
  const bindTargets: EventTarget[] = [];
@@ -301,34 +400,7 @@ export const elementDefine =
301
400
  else if (selector === ':hosts') hostSet.$hosts.forEach(applyRootOption);
302
401
  else if (selector === ':appHosts') hostSet.$appHosts.forEach(applyRootOption);
303
402
  else if (selector === ':host' || !selector) applyRootOption(this);
304
- else if (options.delegate) {
305
- const bindRoots: (HTMLElement | ShadowRoot)[] = [];
306
- if (r === 'auto') bindRoots.push(this.shadowRoot || (this as any));
307
- else if (r === 'light') bindRoots.push(this as any);
308
- else if (r === 'shadow' && this.shadowRoot) bindRoots.push(this.shadowRoot);
309
- else if (r === 'all') {
310
- bindRoots.push(this as any);
311
- if (this.shadowRoot) bindRoots.push(this.shadowRoot);
312
- }
313
-
314
- bindRoots.forEach(br => {
315
- const handler = async (event: Event) => {
316
- const matchedEl = (event.target as HTMLElement).closest(selector);
317
- if (matchedEl && (br as any).contains(matchedEl)) {
318
- if (options.stopPropagation) event.stopPropagation();
319
- if (options.stopImmediatePropagation) event.stopImmediatePropagation();
320
- if (options.preventDefault) event.preventDefault();
321
- const currentHostSet = SwcUtils.getHostSet(this as any);
322
- const args = { event, ...currentHostSet, $el: matchedEl, $root: br };
323
- await (this as any)._invokeLifecycleMethod(meta.propertyKey, currentHostSet, [event, currentHostSet, matchedEl, args]);
324
- }
325
- };
326
- br.addEventListener(type, handler, opts);
327
- if (options.removeOnDisconnected === true || (br !== this && br !== this.shadowRoot)) {
328
- (this as any)._boundListeners.push({ target: br, type, handler, options: opts });
329
- }
330
- });
331
- } else {
403
+ else {
332
404
  const searchRoots: (HTMLElement | ShadowRoot)[] = [];
333
405
  if (r === 'auto') searchRoots.push(this.shadowRoot || (this as any));
334
406
  else if (r === 'light') searchRoots.push(this as any);
@@ -350,7 +422,7 @@ export const elementDefine =
350
422
  if (options.preventDefault) event.preventDefault();
351
423
  const currentHostSet = SwcUtils.getHostSet(this as any);
352
424
  const args = { event, ...currentHostSet, $el: t, $root: t };
353
- await (this as any)._invokeLifecycleMethod(meta.propertyKey, currentHostSet, [event, currentHostSet, args]);
425
+ await (this as any)[meta.propertyKey](event, currentHostSet, args);
354
426
  };
355
427
  t.addEventListener(type, handler, opts);
356
428
  if (options.removeOnDisconnected === true || t === currentWin || t === currentWin.document) {
@@ -359,13 +431,33 @@ export const elementDefine =
359
431
  });
360
432
  });
361
433
 
434
+ addHostEventListenerList.forEach(meta => {
435
+ const { type, options } = meta;
436
+ const opts = { capture: options.capture, once: options.once, passive: options.passive };
437
+
438
+ const handler = async (event: Event) => {
439
+ if (options.stopPropagation) event.stopPropagation();
440
+ if (options.stopImmediatePropagation) event.stopImmediatePropagation();
441
+ if (options.preventDefault) event.preventDefault();
442
+ const currentHostSet = SwcUtils.getHostSet(this as any);
443
+ const args = { event, ...currentHostSet, $el: this, $root: this.getRootNode() };
444
+ await (this as any)[meta.propertyKey](event, currentHostSet, args);
445
+ };
446
+ this.addEventListener(type, handler, opts);
447
+ if (options.removeOnDisconnected === true) {
448
+ (this as any)._boundListeners.push({ target: this, type, handler, options: opts });
449
+ }
450
+ });
451
+
362
452
  if (originalConnected) originalConnected.apply(this);
453
+
363
454
  const aMethods = findAllLifecycleMetadata(this, ON_AFTER_CONNECTED_METADATA_KEY);
364
455
  if (aMethods) {
365
456
  for (const m of aMethods) (this as any)._invokeLifecycleMethod(m, hostSet);
366
457
  }
367
458
  (this as any)._executeSwcScript('swc-on-connected', hostSet);
368
459
  (this as any)._executeSwcScript('swc-on-after-connected', hostSet);
460
+ (this as any).__swc_connected = true;
369
461
  };
370
462
 
371
463
  const originalDisconnected = proto.disconnectedCallback;
@@ -390,6 +482,7 @@ export const elementDefine =
390
482
  }
391
483
  (this as any)._executeSwcScript('swc-on-disconnected', hostSet);
392
484
  (this as any)._executeSwcScript('swc-on-after-disconnected', hostSet);
485
+ (this as any).__swc_connected = false;
393
486
  };
394
487
 
395
488
  const originalAdopted = proto.adoptedCallback;
@@ -415,18 +508,26 @@ export const elementDefine =
415
508
  proto.attributeChangedCallback = function (name: string, old: string | null, newVal: string | null) {
416
509
  if (originalAttributeChanged) originalAttributeChanged.apply(this, [name, old, newVal]);
417
510
 
511
+ const hSet = SwcUtils.getHostSet(this as any);
512
+
513
+ // Handle swc-on-* events
418
514
  if (name.startsWith('swc-on-') && !swcLifecycleAttributes.includes(name)) {
419
515
  if (newVal !== null) {
420
- const customEventMeta = emitCustomEventList.find(it => it.options.attributeName === name);
421
- const eventName = customEventMeta ? customEventMeta.type : name.substring(7);
516
+ const eventName = name.substring(7);
422
517
  (this as any)._bindAttributeEvent(this as any, name, newVal, eventName);
423
518
  }
424
519
  }
425
520
 
521
+ // Handle @emitHostCustomEvent attribute changes
522
+ const hostCustomEventMeta = emitHostCustomEventList.find(it => (it.options as any).attributeName === name);
523
+ if (hostCustomEventMeta && newVal !== null) {
524
+ (this as any)._bindAttributeEvent(this as any, name, newVal, hostCustomEventMeta.type);
525
+ }
526
+
527
+ // Handle @changedAttribute callbacks
426
528
  const mKeys = attrChangeMap.get(name);
427
529
  if (mKeys && Array.isArray(mKeys)) {
428
- const hSet = SwcUtils.getHostSet(this as any);
429
- for (const key of mKeys) (this as any)._invokeLifecycleMethod(key, hSet, [newVal, old, name]);
530
+ for (const key of mKeys) (this as any)[key](newVal, old, name, hSet);
430
531
  }
431
532
  };
432
533
 
@@ -1,10 +1,9 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
2
  import { SpecialSelector, SwcQueryOptions } from '../types';
3
3
  import { ensureInit, getElementConfig } from './elementDefine';
4
4
  import { SwcUtils } from '../utils/Utils';
5
5
 
6
6
  export interface EmitCustomEventBaseOptions {
7
- attributeName?: string;
8
7
  bubbles?: boolean;
9
8
  composed?: boolean;
10
9
  cancelable?: boolean;
@@ -14,7 +13,7 @@ export interface EmitCustomEventMetadata {
14
13
  propertyKey: string | symbol;
15
14
  selector: string;
16
15
  type: string;
17
- options: EmitCustomEventBaseOptions & SwcQueryOptions;
16
+ options: (EmitCustomEventBaseOptions & SwcQueryOptions) | (EmitCustomEventBaseOptions & SwcQueryOptions & { attributeName?: string });
18
17
  }
19
18
 
20
19
  export const EMIT_CUSTOM_EVENT_METADATA_KEY = Symbol('simple-web-component:emit-custom-event');
@@ -29,9 +28,6 @@ export function emitCustomEvent(selectorOrTarget: string, type: string, options:
29
28
 
30
29
  const fullOptions: any = { ...options, type };
31
30
 
32
- if (!fullOptions.attributeName) {
33
- fullOptions.attributeName = `swc-on-${type}`;
34
- }
35
31
  if (fullOptions.bubbles === undefined) fullOptions.bubbles = true;
36
32
  if (fullOptions.composed === undefined) fullOptions.composed = true;
37
33
 
@@ -103,3 +99,15 @@ export const getEmitCustomEventMetadataList = (target: any): EmitCustomEventMeta
103
99
  const constructor = target instanceof Function ? target : target.constructor;
104
100
  return ReflectUtils.getMetadata(EMIT_CUSTOM_EVENT_METADATA_KEY, constructor);
105
101
  };
102
+
103
+ /**
104
+ * @emitCustomEventHost decorator - simplified version of @emitCustomEvent for :host selector
105
+ * Usage: @emitCustomEventHost('navigate')
106
+ * Usage: @emitCustomEventHost('navigate', { attributeName: 'on-navigate' })
107
+ *
108
+ * The attributeName option is used to automatically observe attributes for this event.
109
+ * For example, { attributeName: 'on-navigate' } will add 'on-navigate' to observedAttributes.
110
+ */
111
+ export function emitCustomEventHost(type: string, options?: EmitCustomEventBaseOptions & SwcQueryOptions & { attributeName?: string }): MethodDecorator {
112
+ return emitCustomEvent(':host', type, options);
113
+ }
@@ -1,10 +1,10 @@
1
1
  export * from './addEventListener';
2
+ export * from './attribute';
2
3
  export * from './elementDefine';
3
- export * from './changedAttribute';
4
+ export * from './changedAttributeHost';
4
5
  export * from './setAttribute';
5
6
  export * from './emitCustomEvent';
6
- export * from './replaceChildren';
7
- export * from './appendChild';
7
+ export * from './applyNode';
8
8
  export * from './lifecycles';
9
9
  export * from './query';
10
10
  export * from './queryAll';
@@ -1,7 +1,8 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
2
- import { ON_ATTRIBUTE_CHANGED_METADATA_KEY } from './changedAttribute';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
+ import { ON_ATTRIBUTE_CHANGED_METADATA_KEY } from './changedAttributeHost';
3
3
  import { SET_ATTRIBUTE_METADATA_KEY } from './setAttribute';
4
4
 
5
+ export const ON_CONSTRUCTOR_METADATA_KEY = Symbol('simple-web-component:on-constructor');
5
6
  export const ON_BEFORE_CONNECTED_METADATA_KEY = Symbol('simple-web-component:on-before-connected');
6
7
  export const ON_AFTER_CONNECTED_METADATA_KEY = Symbol('simple-web-component:on-after-connected');
7
8
  export const ON_BEFORE_DISCONNECTED_METADATA_KEY = Symbol('simple-web-component:on-before-disconnected');
@@ -24,6 +25,7 @@ function createLifecycleDecorator(metadataKey: symbol): MethodDecorator {
24
25
  };
25
26
  }
26
27
 
28
+ export const onConstructor = createLifecycleDecorator(ON_CONSTRUCTOR_METADATA_KEY);
27
29
  export const onBeforeConnected = createLifecycleDecorator(ON_BEFORE_CONNECTED_METADATA_KEY);
28
30
  export const onAfterConnected = createLifecycleDecorator(ON_AFTER_CONNECTED_METADATA_KEY);
29
31
  export const onConnected = onAfterConnected;
@@ -1,4 +1,4 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
2
 
3
3
  export interface InnerHtmlOptions {
4
4
  useShadow?: boolean;
@@ -1,4 +1,4 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
2
  import { getElementConfig, ensureInit } from './elementDefine';
3
3
  import { SwcUtils } from '../utils/Utils';
4
4
  import { SpecialSelector, SwcQueryOptions } from '../types';
@@ -108,3 +108,12 @@ export const getQueryMetadata = (target: any): QueryMetadata[] | undefined => {
108
108
  const constructor = target instanceof Function ? target : target.constructor;
109
109
  return ReflectUtils.getMetadata(QUERY_METADATA_KEY, constructor);
110
110
  };
111
+
112
+ /**
113
+ * @hostQuery decorator - simplified version of @query for :host selector
114
+ * Usage: @hostQuery()
115
+ * Usage: @hostQuery({ root: 'shadow' })
116
+ */
117
+ export function queryHost(options?: SwcQueryOptions): PropertyDecorator {
118
+ return query(':host', options);
119
+ }
@@ -1,4 +1,4 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
2
  import { getElementConfig, ensureInit } from './elementDefine';
3
3
  import { SwcUtils } from '../utils/Utils';
4
4
  import { SpecialSelector, SwcQueryOptions } from '../types';
@@ -107,3 +107,12 @@ export const getQueryAllMetadata = (target: any): QueryAllMetadata[] | undefined
107
107
  const constructor = target instanceof Function ? target : target.constructor;
108
108
  return ReflectUtils.getMetadata(QUERY_ALL_METADATA_KEY, constructor);
109
109
  };
110
+
111
+ /**
112
+ * @hostQueryAll decorator - simplified version of @queryAll for :host selector
113
+ * Usage: @hostQueryAll()
114
+ * Usage: @hostQueryAll({ root: 'shadow' })
115
+ */
116
+ export function queryAllHost(options?: SwcQueryOptions): PropertyDecorator {
117
+ return queryAll(':host', options);
118
+ }
@@ -1,11 +1,13 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
2
  import { ensureInit, getElementConfig } from './elementDefine';
3
3
  import { SwcUtils } from '../utils/Utils';
4
+ import { SwcQueryOptions } from '../types';
4
5
 
5
6
  export interface SetAttributeMetadata {
6
7
  propertyKey: string | symbol;
7
8
  selector: string;
8
9
  name: string;
10
+ options: SwcQueryOptions;
9
11
  }
10
12
 
11
13
  export const SET_ATTRIBUTE_METADATA_KEY = Symbol('simple-web-component:set-attribute');
@@ -15,7 +17,9 @@ export const SET_ATTRIBUTE_METADATA_KEY = Symbol('simple-web-component:set-attri
15
17
  * Usage: @setAttribute(':host', 'count')
16
18
  * Usage: @setAttribute('#child', 'disabled')
17
19
  */
18
- export function setAttribute(selector: string, name: string): MethodDecorator {
20
+ export function setAttribute(selector: string, name: string): MethodDecorator;
21
+ export function setAttribute(selector: string, name: string, options?: SwcQueryOptions): MethodDecorator;
22
+ export function setAttribute(selector: string, name: string, options: SwcQueryOptions = {}): MethodDecorator {
19
23
  return (target: Object, propertyKey: string | symbol, descriptor: PropertyDescriptor) => {
20
24
  const constructor = target.constructor;
21
25
  let metaList = ReflectUtils.getOwnMetadata(SET_ATTRIBUTE_METADATA_KEY, constructor) as Map<string | symbol, SetAttributeMetadata>;
@@ -23,7 +27,7 @@ export function setAttribute(selector: string, name: string): MethodDecorator {
23
27
  metaList = new Map<string | symbol, SetAttributeMetadata>();
24
28
  ReflectUtils.defineMetadata(SET_ATTRIBUTE_METADATA_KEY, metaList, constructor);
25
29
  }
26
- metaList.set(propertyKey, { propertyKey, selector, name });
30
+ metaList.set(propertyKey, { propertyKey, selector, name, options });
27
31
 
28
32
  const original = descriptor.value;
29
33
  descriptor.value = async function (...args: any[]) {
@@ -34,22 +38,50 @@ export function setAttribute(selector: string, name: string): MethodDecorator {
34
38
  const conf = getElementConfig(this);
35
39
  const currentWin = (this as any)._resolveWindow?.(conf) || ((typeof window !== 'undefined' ? window : undefined) as Window);
36
40
 
37
- let targetEl: HTMLElement | null = null;
38
- if (selector === ':host' || !selector) targetEl = this as any;
39
- else if (selector === ':window') targetEl = currentWin as any;
40
- else if (selector === ':document') targetEl = currentWin.document as any;
41
- else if (selector === ':parentHost') targetEl = hostSet.$parentHost;
42
- else if (selector === ':appHost') targetEl = hostSet.$appHost;
43
- else if (selector === ':firstHost') targetEl = hostSet.$firstHost;
44
- else if (selector === ':lastHost') targetEl = hostSet.$lastHost;
45
- else if (selector === ':firstAppHost') targetEl = hostSet.$firstAppHost;
46
- else if (selector === ':lastAppHost') targetEl = hostSet.$lastAppHost;
47
- else targetEl = (this.shadowRoot || (this as any)).querySelector(selector);
41
+ const targetEls: any[] = [];
42
+ const r = options.root || 'auto';
48
43
 
49
- if (targetEl) {
50
- if (res === null) targetEl.removeAttribute(name);
51
- else targetEl.setAttribute(name, String(res));
44
+ const applyRoot = (t: any) => {
45
+ if (!t) return;
46
+ if (r === 'auto') {
47
+ targetEls.push((t as any).shadowRoot || t);
48
+ return;
49
+ }
50
+ if (r === 'light' || r === 'all') targetEls.push(t);
51
+ if ((r === 'shadow' || r === 'all') && (t as any).shadowRoot) targetEls.push((t as any).shadowRoot);
52
+ };
53
+
54
+ if (selector === ':window') targetEls.push(currentWin);
55
+ else if (selector === ':document') targetEls.push(currentWin.document as any);
56
+ else if (selector === ':parentHost') applyRoot(hostSet.$parentHost);
57
+ else if (selector === ':appHost') applyRoot(hostSet.$appHost);
58
+ else if (selector === ':firstHost') applyRoot(hostSet.$firstHost);
59
+ else if (selector === ':lastHost') applyRoot(hostSet.$lastHost);
60
+ else if (selector === ':firstAppHost') applyRoot(hostSet.$firstAppHost);
61
+ else if (selector === ':lastAppHost') applyRoot(hostSet.$lastAppHost);
62
+ else if (selector === ':hosts') hostSet.$hosts.forEach(applyRoot);
63
+ else if (selector === ':appHosts') hostSet.$appHosts.forEach(applyRoot);
64
+ else if (selector === ':host' || !selector) applyRoot(this);
65
+ else {
66
+ const roots: any[] = [];
67
+ if (r === 'shadow') {
68
+ if ((this as any).shadowRoot) roots.push((this as any).shadowRoot);
69
+ } else if (r === 'light') {
70
+ roots.push(this as any);
71
+ } else if (r === 'all') {
72
+ roots.push(this as any);
73
+ if ((this as any).shadowRoot) roots.push((this as any).shadowRoot);
74
+ } else {
75
+ roots.push((this as any).shadowRoot || (this as any));
76
+ }
77
+ roots.forEach(root => targetEls.push(...root.querySelectorAll(selector)));
52
78
  }
79
+
80
+ targetEls.forEach(targetEl => {
81
+ if (!targetEl || typeof (targetEl as any).setAttribute !== 'function') return;
82
+ if (res === null) (targetEl as any).removeAttribute(name);
83
+ else (targetEl as any).setAttribute(name, String(res));
84
+ })
53
85
  }
54
86
  return res;
55
87
  };
@@ -71,3 +103,11 @@ export const findAllSetAttributeMetadata = (target: any): Map<string | symbol, S
71
103
  });
72
104
  return result;
73
105
  };
106
+
107
+ /**
108
+ * @setAttributeHost decorator - simplified version of @setAttribute for :host selector
109
+ * Usage: @setAttributeHost('aria-disabled')
110
+ */
111
+ export function setAttributeHost(name: string, options?: SwcQueryOptions): MethodDecorator {
112
+ return setAttribute(':host', name, options);
113
+ }
@@ -1,4 +1,4 @@
1
- import { ReflectUtils } from '@dooboostore/core/reflect/ReflectUtils';
1
+ import { ReflectUtils } from '@dooboostore/core';
2
2
  import { ensureInit } from './elementDefine';
3
3
  import { SwcUtils } from '../utils/Utils';
4
4
 
@@ -1,22 +1,23 @@
1
1
  import { SimpleApplication } from '@dooboostore/simple-boot/SimpleApplication';
2
- import { PathRouter } from '@dooboostore/core-web/routers/PathRouter';
3
- import { HashRouter } from '@dooboostore/core-web/routers/HashRouter';
2
+ import { PathRouter } from '@dooboostore/core-web';
3
+ import { HashRouter } from '@dooboostore/core-web';
4
4
  import { ElementRouter } from '../router/ElementRouter';
5
5
  import { SimOption } from '@dooboostore/simple-boot/SimOption';
6
- import { Router, RouterEventType } from '@dooboostore/core-web/routers/Router';
7
- import { Subscription } from '@dooboostore/core/message/Subscription';
8
- import { ConstructorType, Optional } from '@dooboostore/core/types';
9
- import { FunctionUtils } from '@dooboostore/core/function/FunctionUtils';
6
+ import { Router, RouterEventType } from '@dooboostore/core-web';
7
+ import { Subscription } from '@dooboostore/core';
8
+ import { ConstructorType, OptionalType } from '@dooboostore/core';
9
+ import { FunctionUtils } from '@dooboostore/core';
10
10
  import { SwcUtils } from '../utils/Utils';
11
11
 
12
12
  export type SwcConfigType = {
13
- rootRouter: ConstructorType<any> | Symbol;
13
+ rootRouter: ConstructorType<any> | symbol;
14
14
  routeType: 'path' | 'hash' | 'element';
15
+ connectMode?: 'direct' | 'swap';
15
16
  path?: string;
16
17
  window: Window;
17
18
  };
18
19
 
19
- export type SwcAttributeConfigType = Optional<SwcConfigType, 'routeType' | 'window'>;
20
+ export type SwcAttributeConfigType = OptionalType<SwcConfigType, 'routeType' | 'window'>;
20
21
 
21
22
  export class SwcAppEngine {
22
23
  public simpleApplication?: SimpleApplication;
@@ -87,6 +88,7 @@ export class SwcAppEngine {
87
88
  // Rendering
88
89
  const data = this.simpleApplication.sim(_config.rootRouter);
89
90
  if (data instanceof Node) {
91
+ // console.warn('[SWC-APP-ENGINE] Rendering failed: Root element is not a DocumentFragment.', data);
90
92
  if (this.host.shadowRoot) this.host.shadowRoot.replaceChildren(data);
91
93
  else this.host.replaceChildren(data);
92
94
  }
@@ -1,7 +1,8 @@
1
1
  import { SwcAppEngine, SwcAttributeConfigType } from './SwcAppEngine';
2
+ import {SwcAppInterface} from "../types";
2
3
 
3
4
  export function SwcAppMixin<T extends { new (...args: any[]): HTMLElement }>(Base: T) {
4
- return class extends Base {
5
+ return class extends Base implements SwcAppInterface{
5
6
  __swc_engine = new SwcAppEngine(this as any);
6
7
 
7
8
  get simpleApplication() {
@@ -12,7 +13,38 @@ export function SwcAppMixin<T extends { new (...args: any[]): HTMLElement }>(Bas
12
13
  }
13
14
 
14
15
  async connect(config?: SwcAttributeConfigType) {
15
- await this.__swc_engine.connect(config);
16
+ const mode = config?.connectMode || 'direct';
17
+
18
+ if (mode !== 'swap') {
19
+ await this.__swc_engine.connect(config);
20
+ this.setAttribute('swc-connect-mode', 'direct');
21
+ return;
22
+ }
23
+
24
+ const parent = this.parentNode;
25
+ if (!parent) {
26
+ await this.__swc_engine.connect(config);
27
+ this.setAttribute('swc-connect-mode', 'direct');
28
+ return;
29
+ }
30
+
31
+ const clonedApp = this.cloneNode(true) as any;
32
+ clonedApp.style.display = 'none';
33
+ parent.insertBefore(clonedApp, this.nextSibling);
34
+
35
+ try {
36
+ await clonedApp.connect({ ...(config || {}), connectMode: 'direct' });
37
+ if (this.parentNode) {
38
+ this.parentNode.removeChild(this);
39
+ }
40
+ clonedApp.setAttribute('swc-connect-mode', 'swap');
41
+ clonedApp.style.display = '';
42
+ } catch (e) {
43
+ if (clonedApp.parentNode) {
44
+ clonedApp.parentNode.removeChild(clonedApp);
45
+ }
46
+ throw e;
47
+ }
16
48
  }
17
49
 
18
50
  connectedCallback() {