@epa-wg/custom-element-dist 0.0.21 → 0.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 (171) hide show
  1. package/README.md +4 -4
  2. package/coverage/coverage-final.json +15 -11
  3. package/coverage/index.html +25 -25
  4. package/coverage/src/custom-element/coverage.svg +1 -1
  5. package/coverage/src/custom-element/custom-element.js/coverage.svg +1 -1
  6. package/coverage/src/custom-element/custom-element.js.html +604 -421
  7. package/coverage/src/custom-element/custom-element1-1.js/coverage.svg +10 -0
  8. package/coverage/src/custom-element/custom-element1-1.js.html +2374 -0
  9. package/coverage/src/custom-element/custom-element1.js/coverage.svg +10 -0
  10. package/coverage/src/custom-element/custom-element1.js.html +2374 -0
  11. package/coverage/src/custom-element/http-request.js.html +10 -10
  12. package/coverage/src/custom-element/index.html +49 -19
  13. package/coverage/src/custom-element/local-storage.js.html +6 -6
  14. package/coverage/src/custom-element/location-element.js.html +1 -1
  15. package/coverage/src/index.html +1 -1
  16. package/coverage/src/mocks/handlers.ts.html +1 -1
  17. package/coverage/src/mocks/index.html +1 -1
  18. package/coverage/src/stories/{attributes.stories.ts.html → attributes.test.stories.ts.html} +51 -15
  19. package/coverage/src/stories/{css.stories.ts.html → css.test.stories.ts.html} +77 -17
  20. package/coverage/src/stories/{dom-merge.stories.ts.html → dom-merge.test.stories.ts.html} +60 -12
  21. package/coverage/src/stories/{external-template.stories.ts.html → external-template.test.stories.ts.html} +42 -12
  22. package/coverage/src/stories/form.test.stories.ts.html +658 -0
  23. package/coverage/src/stories/http-request.stories.ts.html +7 -7
  24. package/coverage/src/stories/index.html +71 -41
  25. package/coverage/src/stories/{local-storage.stories.ts.html → local-storage.test.stories.ts.html} +56 -20
  26. package/coverage/src/stories/{location-element.stories.ts.html → location-element.test.stories.ts.html} +53 -17
  27. package/coverage/src/stories/renderPlay.ts.html +12 -15
  28. package/coverage/src/stories/slice-events.test.stories.ts/coverage.svg +10 -0
  29. package/coverage/src/stories/{slice-events.stories.ts.html → slice-events.test.stories.ts.html} +264 -15
  30. package/coverage/src/stories/slots.test.stories.ts/coverage.svg +10 -0
  31. package/coverage/src/stories/slots.test.stories.ts.html +739 -0
  32. package/coverage/src/sum.ts.html +1 -1
  33. package/dist/custom-element-BISbI4SU.js +463 -0
  34. package/dist/custom-element-N-sWiqGK.cjs +53 -0
  35. package/dist/custom-element-bundle.cjs +1 -1
  36. package/dist/custom-element-bundle.js +2 -2
  37. package/dist/mockServiceWorker.js +1 -1
  38. package/package.json +4 -4
  39. package/public/mockServiceWorker.js +1 -1
  40. package/src/custom-element/custom-element.d.ts +4 -0
  41. package/src/custom-element/custom-element.js +103 -42
  42. package/src/custom-element/custom-element1-1.js +763 -0
  43. package/src/custom-element/custom-element1.js +763 -0
  44. package/src/custom-element/custom-element1.js0 +750 -0
  45. package/src/custom-element/custom-element2.js0 +759 -0
  46. package/src/custom-element/custom-element3.js0 +763 -0
  47. package/src/custom-element/demo/a.html +38 -41
  48. package/src/custom-element/demo/b.html +13 -0
  49. package/src/custom-element/demo/data-slices.html +32 -0
  50. package/src/custom-element/demo/form.html +193 -0
  51. package/src/custom-element/demo/s.xml +19 -14
  52. package/src/custom-element/demo/s.xslt +22 -38
  53. package/src/custom-element/demo/s1.xslt +60 -0
  54. package/src/custom-element/ide/customData-dce.json +14 -1
  55. package/src/custom-element/ide/web-types-dce.json +6 -1
  56. package/src/custom-element/ide/web-types-xsl.json +1 -1
  57. package/src/custom-element/index.html +1 -0
  58. package/src/custom-element.test.ts +24 -8
  59. package/src/stories/{attributes.stories.ts → attributes.test.stories.ts} +19 -7
  60. package/src/stories/{css.stories.ts → css.test.stories.ts} +29 -9
  61. package/src/stories/{dom-merge.stories.ts → dom-merge.test.stories.ts} +19 -3
  62. package/src/stories/{external-template.stories.ts → external-template.test.stories.ts} +13 -3
  63. package/src/stories/form.test.stories.ts +191 -0
  64. package/src/stories/http-request.stories.ts +6 -6
  65. package/src/stories/http-request.test.ts +0 -9
  66. package/src/stories/{local-storage.stories.ts → local-storage.test.stories.ts} +24 -12
  67. package/src/stories/{location-element.stories.ts → location-element.test.stories.ts} +21 -9
  68. package/src/stories/renderPlay.ts +1 -2
  69. package/src/stories/{slice-events.stories.ts → slice-events.test.stories.ts} +88 -5
  70. package/src/stories/slots.test.stories.ts +218 -0
  71. package/storybook-static/assets/{Color-RQJUDNI5-C4yZhNbM.js → Color-PRSJMWNM-e4s261EJ.js} +1 -1
  72. package/storybook-static/assets/{Configure-C7d36rng.js → Configure-DWut7txe.js} +1 -1
  73. package/storybook-static/assets/DocsRenderer-K4EAMTCU-CaXVGjCl.js +2 -0
  74. package/storybook-static/assets/WithTooltip-KJL26V4Q--B8vdnMi.js +1 -0
  75. package/storybook-static/assets/{attributes.stories-ZB0RTY1d.js → attributes.test.stories-IuwazrdL.js} +21 -21
  76. package/storybook-static/assets/css.test.stories-D9WaxrEv.js +96 -0
  77. package/storybook-static/assets/custom-element-BV8-hRQS.js +219 -0
  78. package/storybook-static/assets/{dom-merge.stories-CgHZUABU.js → dom-merge.test.stories-BhbNeum_.js} +5 -6
  79. package/storybook-static/assets/{entry-preview-CQqNFx4W.js → entry-preview-DrgzXgwT.js} +1 -1
  80. package/storybook-static/assets/{entry-preview-docs-CWgqLfd3.js → entry-preview-docs-Bxv0qQWs.js} +1 -1
  81. package/storybook-static/assets/{external-template.stories-DtSLMxvg.js → external-template.test.stories-Bpr_wxBo.js} +23 -24
  82. package/storybook-static/assets/form.test.stories-3tURbEdv.js +250 -0
  83. package/storybook-static/assets/{formatter-B5HCVTEV-tKeEfJA9.js → formatter-2WMMO6ZP-SJtgH3vM.js} +5 -5
  84. package/storybook-static/assets/http-request.stories-8K_qSs8C.js +300 -0
  85. package/storybook-static/assets/iframe-CM82WlGY.js +2 -0
  86. package/storybook-static/assets/index-CEZitmnt.js +548 -0
  87. package/storybook-static/assets/index-CVRyq5ci.js +27 -0
  88. package/storybook-static/assets/{index-DnEJ_bKa.js → index-D1MP-Zis.js} +1 -1
  89. package/storybook-static/assets/index-DNL-IEpS.js +1 -0
  90. package/storybook-static/assets/index-DXimoRZY.js +1 -0
  91. package/storybook-static/assets/index-DuIEV_9C.js +13 -0
  92. package/storybook-static/assets/{lit-element-B4_0akdT.js → lit-element-CenEXOuS.js} +2 -2
  93. package/storybook-static/assets/{local-storage.stories-BkO6djDz.js → local-storage.test.stories-CtisAQBB.js} +28 -24
  94. package/storybook-static/assets/{location-element.stories-DCIOUd0D.js → location-element.test.stories-5O_t_m4Y.js} +11 -11
  95. package/storybook-static/assets/preview-4Up_z4Em.js +7 -0
  96. package/storybook-static/assets/{preview-CkgAD_DE.js → preview-5Y0XiZgz.js} +2 -2
  97. package/storybook-static/assets/preview-BKCN0mOr.js +1 -0
  98. package/storybook-static/assets/preview-DRnyIGXK.js +48 -0
  99. package/storybook-static/assets/preview-FpHGYA1q.js +1 -0
  100. package/storybook-static/assets/{preview-PxUn-cIn.js → preview-TCN6m6T-.js} +1 -1
  101. package/storybook-static/assets/slice-events.test.stories-BSXCLIA5.js +231 -0
  102. package/storybook-static/assets/slots.test.stories-B1vqfHmN.js +214 -0
  103. package/storybook-static/assets/syntaxhighlighter-BP7B2CQK-BWFH_0wQ.js +1 -0
  104. package/storybook-static/iframe.html +153 -10
  105. package/storybook-static/index.html +1 -1
  106. package/storybook-static/index.json +1 -1
  107. package/storybook-static/mockServiceWorker.js +1 -1
  108. package/storybook-static/project.json +1 -1
  109. package/storybook-static/sb-addons/chromatic-com-storybook-9/manager-bundle.js +35 -29
  110. package/storybook-static/sb-addons/chromatic-com-storybook-9/manager-bundle.js.LEGAL.txt +1 -1
  111. package/storybook-static/sb-addons/essentials-actions-3/manager-bundle.js +1 -1
  112. package/storybook-static/sb-addons/essentials-backgrounds-4/manager-bundle.js +5 -5
  113. package/storybook-static/sb-addons/essentials-controls-2/manager-bundle.js +35 -35
  114. package/storybook-static/sb-addons/essentials-measure-7/manager-bundle.js +1 -1
  115. package/storybook-static/sb-addons/essentials-outline-8/manager-bundle.js +1 -1
  116. package/storybook-static/sb-addons/essentials-toolbars-6/manager-bundle.js +1 -1
  117. package/storybook-static/sb-addons/essentials-viewport-5/manager-bundle.js +1 -1
  118. package/storybook-static/sb-addons/interactions-10/manager-bundle.js +18 -16
  119. package/storybook-static/sb-addons/links-1/manager-bundle.js +1 -1
  120. package/storybook-static/sb-addons/storybook-core-server-presets-0/common-manager-bundle.js +1 -1
  121. package/storybook-static/sb-manager/WithTooltip-KJL26V4Q-5LS5AN27.js +1 -0
  122. package/storybook-static/sb-manager/{chunk-S4VOIVUE.js → chunk-B3YDJJJH.js} +9 -9
  123. package/storybook-static/sb-manager/{chunk-FEE35O7J.js → chunk-BLWCBWKL.js} +3 -3
  124. package/storybook-static/sb-manager/{chunk-XCO5HRLK.js → chunk-GUVK2GTO.js} +3 -3
  125. package/storybook-static/sb-manager/chunk-LFRML3ZV.js +186 -0
  126. package/storybook-static/sb-manager/chunk-MC7RAF2B.js +274 -0
  127. package/storybook-static/sb-manager/{chunk-XP3HGWTR.js → chunk-ZR5JZWHI.js} +1 -1
  128. package/storybook-static/sb-manager/{formatter-B5HCVTEV-7DCBOGO6.js → formatter-2WMMO6ZP-JI7RHVTW.js} +1 -1
  129. package/storybook-static/sb-manager/globals-module-info.js +1 -1
  130. package/storybook-static/sb-manager/globals-runtime.js +1 -1
  131. package/storybook-static/sb-manager/index.js +1 -1
  132. package/storybook-static/sb-manager/runtime.js +1 -1
  133. package/storybook-static/sb-manager/{syntaxhighlighter-JOJW2KGS-VF6EEVPI.js → syntaxhighlighter-BP7B2CQK-WOJYHKQR.js} +1 -1
  134. package/storybook-static/sb-preview/runtime.js +28 -11
  135. package/vite.config.js +5 -5
  136. package/dist/custom-element-B4v-KaIh.cjs +0 -53
  137. package/dist/custom-element-_g0GTup2.js +0 -436
  138. package/src/stories/attributes.test.ts +0 -14
  139. package/src/stories/css.test.ts +0 -12
  140. package/src/stories/dom-merge.test.ts +0 -12
  141. package/src/stories/external-template.test.ts +0 -12
  142. package/src/stories/local-storage.test.ts +0 -12
  143. package/src/stories/location-element.test.ts +0 -14
  144. package/src/stories/slice-events.test.ts +0 -12
  145. package/storybook-static/assets/DocsRenderer-K4EAMTCU-BLMupvSb.js +0 -2
  146. package/storybook-static/assets/WithTooltip-Y7J54OF7-BAQSPSFk.js +0 -1
  147. package/storybook-static/assets/css.stories-CLSX-Xxd.js +0 -86
  148. package/storybook-static/assets/custom-element-BLZZ00dz.js +0 -53
  149. package/storybook-static/assets/http-request.stories-CUzlXO89.js +0 -300
  150. package/storybook-static/assets/iframe-gCvlWuoC.js +0 -2
  151. package/storybook-static/assets/index-CBQwM6ST.js +0 -508
  152. package/storybook-static/assets/index-CDavW7r9.js +0 -193
  153. package/storybook-static/assets/index-CQA5dlr6.js +0 -13
  154. package/storybook-static/assets/index-DgaNIR0t.js +0 -1
  155. package/storybook-static/assets/index-Dkj0J1ds.js +0 -1
  156. package/storybook-static/assets/preview-C6t8KBFr.js +0 -1
  157. package/storybook-static/assets/preview-CYD85dwb.js +0 -7
  158. package/storybook-static/assets/preview-D8LadFCz.js +0 -48
  159. package/storybook-static/assets/preview-DNpCpRPf.js +0 -1
  160. package/storybook-static/assets/slice-events.stories-DXKjXI37.js +0 -115
  161. package/storybook-static/assets/syntaxhighlighter-JOJW2KGS-C04pIVD3.js +0 -1
  162. package/storybook-static/sb-manager/WithTooltip-Y7J54OF7-CEHQ77YF.js +0 -1
  163. package/storybook-static/sb-manager/chunk-E3WK6ZOZ.js +0 -234
  164. package/storybook-static/sb-manager/chunk-E6ABNH5R.js +0 -183
  165. /package/coverage/src/stories/{attributes.stories.ts → attributes.test.stories.ts}/coverage.svg +0 -0
  166. /package/coverage/src/stories/{css.stories.ts → css.test.stories.ts}/coverage.svg +0 -0
  167. /package/coverage/src/stories/{dom-merge.stories.ts → dom-merge.test.stories.ts}/coverage.svg +0 -0
  168. /package/coverage/src/stories/{external-template.stories.ts → external-template.test.stories.ts}/coverage.svg +0 -0
  169. /package/coverage/src/stories/{local-storage.stories.ts → form.test.stories.ts}/coverage.svg +0 -0
  170. /package/coverage/src/stories/{location-element.stories.ts → local-storage.test.stories.ts}/coverage.svg +0 -0
  171. /package/coverage/src/stories/{slice-events.stories.ts → location-element.test.stories.ts}/coverage.svg +0 -0
@@ -13,7 +13,6 @@ const attr = (el, attr)=> el.getAttribute?.(attr)
13
13
  , createText = ( d, t) => (d.ownerDocument || d ).createTextNode( t )
14
14
  , removeChildren = n => { while(n.firstChild) n.firstChild.remove(); return n; }
15
15
  , emptyNode = n => { n.getAttributeNames().map( a => n.removeAttribute(a) ); return removeChildren(n); }
16
- , createNS = ( ns, tag, t = '' ) => ( e => ((e.innerText = t||''),e) )(document.createElementNS( ns, tag ))
17
16
  , xslNs = x => ( x?.setAttribute('xmlns:xsl', XSL_NS_URL ), x )
18
17
  , xslHtmlNs = x => ( x?.setAttribute('xmlns:xhtml', HTML_NS_URL ), xslNs(x) )
19
18
  , cloneAs = (p,tag) =>
@@ -23,7 +22,7 @@ const attr = (el, attr)=> el.getAttribute?.(attr)
23
22
  while( p.firstChild )
24
23
  px.append(p.firstChild);
25
24
  return px;
26
- }
25
+ };
27
26
 
28
27
  function
29
28
  ASSERT(x)
@@ -66,17 +65,22 @@ assureSlot( e )
66
65
  export function
67
66
  obj2node( o, tag, doc )
68
67
  { const t = typeof o;
69
- if( t === 'function'){debugger}
70
68
  if( t === 'string' )
71
69
  return create(tag,o,doc);
72
70
  if( t === 'number' )
73
71
  return create(tag,''+o,doc);
74
72
 
75
73
  if( o instanceof Array )
76
- { const ret = create('array');
74
+ { const ret = create('array','',doc);
77
75
  o.map( ae => ret.append( obj2node(ae,tag,doc)) );
78
76
  return ret
79
77
  }
78
+ if( o instanceof FormData )
79
+ { const ret = create('form-data','',doc);
80
+ for( const p of o )
81
+ ret.append( obj2node(p[1],p[0],doc) );
82
+ return ret
83
+ }
80
84
  const ret = create(tag,'',doc);
81
85
  for( let k in o )
82
86
  if( isNode(o[k]) || typeof o[k] ==='function' || o[k] instanceof Window )
@@ -91,13 +95,14 @@ obj2node( o, tag, doc )
91
95
  export function
92
96
  tagUid( node )
93
97
  { // {} to xsl:value-of
94
- forEach$(node,'*',d => [...d.childNodes].filter( e=>e.nodeType === 3 ).forEach( e=>
95
- { if( e.parentNode.localName === 'style' )
96
- return;
97
- const m = e.data.matchAll( /{([^}]*)}/g );
98
+ forEach$(node,'*',d => [...d.childNodes]
99
+ .filter( e => e.nodeType === 3 && e.parentNode.localName !== 'style' && e.data )
100
+ .forEach( e=>
101
+ { const s = e.data,
102
+ m = s.matchAll( /{([^}]*)}/g );
98
103
  if(m)
99
104
  { let l = 0
100
- , txt = t => createText(e,t||'')
105
+ , txt = t => createText(e,t)
101
106
  , tt = [];
102
107
  [...m].forEach(t=>
103
108
  { if( t.index > l )
@@ -107,8 +112,8 @@ tagUid( node )
107
112
  tt.push(v);
108
113
  l = t.index+t[0].length;
109
114
  })
110
- if( l < e.data.length)
111
- tt.push( txt( e.data.substring(l,e.data.length) ));
115
+ if( l < s.length)
116
+ tt.push( txt( s.substring(l,s.length) ));
112
117
  if( tt.length )
113
118
  { for( let t of tt )
114
119
  d.insertBefore(t,e);
@@ -250,7 +255,7 @@ createXsltFromDom( templateNode, S = 'xsl:stylesheet' )
250
255
  const slotCall = $(xslDom,'call-template[name="slot"]')
251
256
  , slot2xsl = s =>
252
257
  { const v = slotCall.cloneNode(true)
253
- , name = attr(s,'name') || '';
258
+ , name = attr(s,'name');
254
259
  name && v.firstElementChild.setAttribute('select',`'${ name }'`)
255
260
  for( let c of s.childNodes)
256
261
  v.lastElementChild.append(c)
@@ -297,16 +302,20 @@ deepEqual(a, b, O=false)
297
302
  return O
298
303
  return true;
299
304
  }
305
+ const splitSliceNames = v => v.split('|').map( s=>s.trim() ).filter(s=>s);
306
+
300
307
  export const
301
308
  assureSlices = ( root, names) =>
302
- names.split('|').map(n=>n.trim()).map( xp =>
303
- { if(xp.includes('/'))
304
- { const ret = [], r = root.ownerDocument.evaluate( xp, root );
309
+ splitSliceNames(names).map( xp =>
310
+ { let d = root.ownerDocument
311
+ , append = n=> (root.append(n),n);
312
+ if(xp.includes('/'))
313
+ { const ret = [], r = d.evaluate( xp, root );
305
314
  for( let n; n = r.iterateNext(); )
306
315
  ret.push( n )
307
316
  return ret
308
317
  }
309
- return [...root.childNodes].find(n=>n.localName === xp) || create(xp);
318
+ return [...root.childNodes].find(n=>n.localName === xp) || append( create(xp,'',d) );
310
319
  }).flat();
311
320
 
312
321
  /**
@@ -319,19 +328,24 @@ assureSlices = ( root, names) =>
319
328
  export function
320
329
  event2slice( x, sliceNames, ev, dce )
321
330
  {
331
+ if( ev.sliceProcessed )
332
+ return
333
+ ev.sliceProcessed = 1;
322
334
  // evaluate slices[]
323
335
  // inject @attributes
324
336
  // inject event
325
337
  // evaluate slice-value
326
338
  // slice[i] = slice-value
327
- assureSlices(x,sliceNames).map( s =>
339
+ return assureSlices( x, sliceNames ?? '' ).map( s =>
328
340
  {
329
341
  const d = x.ownerDocument
330
342
  , el = ev.sliceEventSource
331
343
  , sel = ev.sliceElement
332
- , cleanSliceValue = ()=>[...s.childNodes].filter(n=>n.nodeType===3 || n.localName==='value').map(n=>n.remove());
344
+ , cleanSliceValue = ()=>[...s.childNodes].filter(n=>n.nodeType===3 || n.localName==='value' || n.localName==='form-data').map(n=>n.remove());
333
345
  el.getAttributeNames().map( a => s.setAttribute( a, attr(el,a) ) );
334
346
  [...s.childNodes].filter(n=>n.localName==='event').map(n=>n.remove());
347
+ if( 'validationMessage' in el )
348
+ s.setAttribute('validation-message', el.validationMessage);
335
349
  ev.type==='init' && cleanSliceValue();
336
350
  s.append( obj2node( ev, 'event', d ) );
337
351
  if( sel.hasAttribute('slice-value') )
@@ -343,7 +357,12 @@ event2slice( x, sliceNames, ev, dce )
343
357
  cleanSliceValue();
344
358
  s.append( createText( d, v ) );
345
359
  }else
346
- { const v = el.value ?? attr( sel, 'value' ) ;
360
+ { if( 'elements' in el )
361
+ { cleanSliceValue();
362
+ s.append( obj2node(new FormData(el),'value', s.ownerDocument) )
363
+ return s
364
+ }
365
+ const v = el.value ?? attr( sel, 'value' ) ;
347
366
  cleanSliceValue();
348
367
  if( v === null || v === undefined )
349
368
  [...s.childNodes].filter(n=>n.localName!=='event').map(n=>n.remove());
@@ -353,6 +372,7 @@ event2slice( x, sliceNames, ev, dce )
353
372
  else
354
373
  s.append( obj2node(v,'value',s.ownerDocument) )
355
374
  }
375
+ return s
356
376
  })
357
377
  }
358
378
 
@@ -360,7 +380,6 @@ function forEach$( el, css, cb){
360
380
  if( el.querySelectorAll )
361
381
  [...el.querySelectorAll(css)].forEach(cb)
362
382
  }
363
- const getByHashId = ( n, id )=> ( p => n===p? null: (p && ( p.querySelector(id) || getByHashId(p,id) ) ))( n.getRootNode() )
364
383
  const loadTemplateRoots = async ( src, dce )=>
365
384
  {
366
385
  if( !src || !src.trim() )
@@ -388,12 +407,7 @@ const loadTemplateRoots = async ( src, dce )=>
388
407
  }catch (error){ return [dce]}
389
408
  }
390
409
  export function mergeAttr( from, to )
391
- { if( isText(from) )
392
- {
393
- if( !isText(to) ){ debugger }
394
- return
395
- }
396
- for( let a of from.attributes)
410
+ { for( let a of from.attributes)
397
411
  { a.namespaceURI? to.setAttributeNS( a.namespaceURI, a.name, a.value ) : to.setAttribute( a.name, a.value )
398
412
  if( a.name === 'value')
399
413
  to.value = a.value
@@ -472,12 +486,18 @@ export const xPathDefaults = x=>
472
486
  // return xx.length ? `${a}|(${xPathDefaults(xx.join('??'))})[not(${a})]`: a
473
487
  }
474
488
  export const xPath = (x,root)=>
475
- { x = xPathDefaults(x);
489
+ {
490
+ const xx = x.split('??');
491
+ if( xx.length > 1 )
492
+ return xPath(xx[0], root) || xPath(xx[1], root);
493
+
494
+ x = xPathDefaults(x);
476
495
 
477
496
  const it = root.ownerDocument.evaluate(x, root);
478
497
  switch( it.resultType )
479
498
  { case XPathResult.NUMBER_TYPE: return it.numberValue;
480
499
  case XPathResult.STRING_TYPE: return it.stringValue;
500
+ case XPathResult.BOOLEAN_TYPE: return it.booleanValue;
481
501
  }
482
502
 
483
503
  let ret = '';
@@ -529,7 +549,10 @@ CustomElement extends HTMLElement
529
549
 
530
550
  const dce = this
531
551
  , sliceNodes = [...this.templateNode.querySelectorAll('[slice]')]
532
- , sliceNames = sliceNodes.map(e=>attr(e,'slice')).filter(n=>!n.includes('/')).filter((v, i, a)=>a.indexOf(v) === i)
552
+ , sliceNames = sliceNodes.map(e=>attr(e,'slice'))
553
+ .filter(n=>!n.includes('/'))
554
+ .filter((v, i, a)=>a.indexOf(v) === i)
555
+ .map(splitSliceNames).flat()
533
556
  , declaredAttributes = templateDocs.reduce( (ret,t) => { if( t.params ) ret.push( ...t.params ); return ret; }, [] );
534
557
 
535
558
  class DceElement extends HTMLElement
@@ -540,6 +563,8 @@ CustomElement extends HTMLElement
540
563
  { let payload = this.childNodes;
541
564
  if( this.firstElementChild?.tagName === 'TEMPLATE' )
542
565
  {
566
+ if( this.firstElementChild !== this.lastElementChild )
567
+ { console.error('payload should have TEMPLATE as only child', this.outerHTML ) }
543
568
  const t = this.firstElementChild;
544
569
  t.remove();
545
570
  payload = t.content.childNodes;
@@ -563,7 +588,7 @@ CustomElement extends HTMLElement
563
588
  })(x.ownerDocument.createElement( tag ))
564
589
  injectData( x, 'payload' , payload , assureSlot );
565
590
  this.innerHTML='';
566
- injectData( x, 'attributes' , this.attributes, e => createXmlNode( e.nodeName, e.value ) );
591
+ const attrsRoot = injectData( x, 'attributes' , this.attributes, e => createXmlNode( e.nodeName, e.value ) );
567
592
  injectData( x, 'dataset', Object.keys( this.dataset ), k => createXmlNode( k, this.dataset[ k ] ) );
568
593
  const sliceRoot = injectData( x, 'slice', sliceNames, k => createXmlNode( k, '' ) )
569
594
  , sliceXPath = x => xPath(x, sliceRoot);
@@ -585,14 +610,12 @@ CustomElement extends HTMLElement
585
610
  let timeoutID;
586
611
 
587
612
  this.onSlice = ev=>
588
- { ev.stopPropagation?.();
589
- ev.sliceEventSource = ev.currentTarget || ev.target;
590
- sliceEvents.push(ev);
613
+ { sliceEvents.push(ev);
591
614
  if( !timeoutID )
592
615
  timeoutID = setTimeout(()=>
593
616
  { applySlices();
594
617
  timeoutID =0;
595
- },10);
618
+ },1);
596
619
  };
597
620
  const transform = this.transform = ()=>
598
621
  { if(this.#inTransform){ debugger }
@@ -619,20 +642,58 @@ CustomElement extends HTMLElement
619
642
  }
620
643
  })
621
644
 
622
- forEach$( this,'[slice]', el =>
645
+ forEach$( this,'[slice],[slice-event]', el =>
623
646
  { if( !el.dceInitialized )
624
647
  { el.dceInitialized = 1;
625
- const evs = attr(el,'slice-event');
626
- (evs || 'change')
627
- .split(' ')
648
+ let evs = attr(el,'slice-event');
649
+ if( attr(el,'custom-validity') )
650
+ evs += ' change submit';
651
+
652
+ [...new Set((evs || 'change') .split(' '))]
628
653
  .forEach( t=> (el.localName==='slice'? el.parentElement : el)
629
- .addEventListener( t, ev=>
630
- { ev.sliceElement = el;
631
- this.onSlice(ev)
632
- } ));
654
+ .addEventListener( t, ev=>
655
+ { ev.sliceElement = el;
656
+ ev.sliceEventSource = ev.currentTarget || ev.target;
657
+ const slices = event2slice( sliceRoot, attr( ev.sliceElement, 'slice'), ev, this );
658
+
659
+ forEach$(this,'[custom-validity]',el =>
660
+ { if( !el.setCustomValidity )
661
+ return;
662
+ const x = attr( el, 'custom-validity' );
663
+ try
664
+ { const v = x && xPath( x, attrsRoot );
665
+ el.setCustomValidity( v === true? '': v === false ? 'invalid' : v );
666
+ }catch(err)
667
+ { console.error(err, 'xPath', x) }
668
+ })
669
+ const x = attr(el,'custom-validity')
670
+ , v = x && xPath( x, attrsRoot )
671
+ , msg = v === true? '' : v;
672
+
673
+ if( x )
674
+ { el.setCustomValidity ? el.setCustomValidity( msg ) : ( el.validationMessage = msg );
675
+ slices.map( s => s.setAttribute('validation-message', msg ) );
676
+ if( ev.type === 'submit' )
677
+ { if( v === true )
678
+ return;
679
+ setTimeout(transform,1)
680
+ if( !!v === v )
681
+ { v || ev.preventDefault();
682
+ return v;
683
+ }
684
+ if( v )
685
+ { ev.preventDefault();
686
+ return !1
687
+ }
688
+ return ;
689
+ }else
690
+ setTimeout(transform,1)
691
+ }
692
+ this.onSlice(ev);
693
+ } ));
633
694
  if( !evs || evs.includes('init') )
634
695
  { if( el.hasAttribute('slice-value') || el.hasAttribute('value') || el.value )
635
- this.onSlice({type:'init', target: el, sliceElement:el })
696
+ this.onSlice({type:'init', target: el, sliceElement:el, sliceEventSource:el })
636
697
  else
637
698
  el.value = sliceXPath( attr(el,'slice') )
638
699
  }