@epa-wg/custom-element-dist 0.0.1
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.
- package/.editorconfig +11 -0
- package/.gitignore +26 -0
- package/.idea/codeStyles/codeStyleConfig.xml +5 -0
- package/.idea/compiler.xml +6 -0
- package/.idea/custom-element-dist.iml +13 -0
- package/.idea/inspectionProfiles/Project_Default.xml +6 -0
- package/.idea/misc.xml +6 -0
- package/.idea/modules.xml +8 -0
- package/.idea/vcs.xml +6 -0
- package/.storybook/main.ts +21 -0
- package/.storybook/preview.ts +17 -0
- package/.vscode/settings.json +24 -0
- package/LICENSE +201 -0
- package/README.md +32 -0
- package/bin/build.sh +8 -0
- package/bin/clean.sh +5 -0
- package/bin/postinstall.sh +17 -0
- package/bin/start.sh +2 -0
- package/coverage/base.css +224 -0
- package/coverage/block-navigation.js +87 -0
- package/coverage/coverage-final.json +16 -0
- package/coverage/favicon.png +0 -0
- package/coverage/index.html +161 -0
- package/coverage/prettify.css +1 -0
- package/coverage/prettify.js +2 -0
- package/coverage/sort-arrow-sprite.png +0 -0
- package/coverage/sorter.js +196 -0
- package/coverage/src/coverage.svg +10 -0
- package/coverage/src/custom-element/coverage.svg +10 -0
- package/coverage/src/custom-element/custom-element.js/coverage.svg +10 -0
- package/coverage/src/custom-element/custom-element.js.html +2149 -0
- package/coverage/src/custom-element/http-request.js/coverage.svg +10 -0
- package/coverage/src/custom-element/http-request.js.html +352 -0
- package/coverage/src/custom-element/index.html +161 -0
- package/coverage/src/custom-element/local-storage.js/coverage.svg +10 -0
- package/coverage/src/custom-element/local-storage.js.html +346 -0
- package/coverage/src/custom-element/location-element.js/coverage.svg +10 -0
- package/coverage/src/custom-element/location-element.js.html +343 -0
- package/coverage/src/index.html +116 -0
- package/coverage/src/mocks/coverage.svg +10 -0
- package/coverage/src/mocks/handlers.ts/coverage.svg +10 -0
- package/coverage/src/mocks/handlers.ts.html +172 -0
- package/coverage/src/mocks/index.html +116 -0
- package/coverage/src/stories/attributes.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/attributes.stories.ts.html +481 -0
- package/coverage/src/stories/coverage.svg +10 -0
- package/coverage/src/stories/css.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/css.stories.ts.html +397 -0
- package/coverage/src/stories/dom-merge.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/dom-merge.stories.ts.html +424 -0
- package/coverage/src/stories/external-template.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/external-template.stories.ts.html +820 -0
- package/coverage/src/stories/http-request.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/http-request.stories.ts.html +817 -0
- package/coverage/src/stories/index.html +236 -0
- package/coverage/src/stories/local-storage.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/local-storage.stories.ts.html +1249 -0
- package/coverage/src/stories/location-element.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/location-element.stories.ts.html +484 -0
- package/coverage/src/stories/renderPlay.ts/coverage.svg +10 -0
- package/coverage/src/stories/renderPlay.ts.html +151 -0
- package/coverage/src/stories/slice-events.stories.ts/coverage.svg +10 -0
- package/coverage/src/stories/slice-events.stories.ts.html +436 -0
- package/coverage/src/sum.ts/coverage.svg +10 -0
- package/coverage/src/sum.ts.html +94 -0
- package/dist/confused.svg +37 -0
- package/dist/custom-element-B4v-KaIh.cjs +53 -0
- package/dist/custom-element-_g0GTup2.js +436 -0
- package/dist/custom-element-bundle.cjs +1 -0
- package/dist/custom-element-bundle.js +31 -0
- package/dist/embed-1.html +3 -0
- package/dist/html-template.html +126 -0
- package/dist/html-template.xhtml +45 -0
- package/dist/html-template.xml +45 -0
- package/dist/http-request-BOvP4KTl.js +56 -0
- package/dist/http-request-DPrY7mGh.cjs +1 -0
- package/dist/local-storage-Boafngui.cjs +1 -0
- package/dist/local-storage-BqDEu2kF.js +59 -0
- package/dist/location-element-2m0gWq_d.cjs +1 -0
- package/dist/location-element-nA_wsqBt.js +49 -0
- package/dist/mockServiceWorker.js +284 -0
- package/dist/tree.xsl +33 -0
- package/dist/vite.svg +1 -0
- package/index.html +17 -0
- package/package.json +97 -0
- package/public/confused.svg +37 -0
- package/public/embed-1.html +3 -0
- package/public/html-template.html +126 -0
- package/public/html-template.xhtml +45 -0
- package/public/html-template.xml +45 -0
- package/public/mockServiceWorker.js +284 -0
- package/public/tree.xsl +33 -0
- package/public/vite.svg +1 -0
- package/src/assets/lit.svg +1 -0
- package/src/custom-element/custom-element.d.ts +36 -0
- package/src/custom-element/custom-element.js +688 -0
- package/src/custom-element/demo/a.html +63 -0
- package/src/custom-element/demo/confused.svg +37 -0
- package/src/custom-element/demo/data-slices.html +184 -0
- package/src/custom-element/demo/dce-social-preview.png +0 -0
- package/src/custom-element/demo/demo.css +22 -0
- package/src/custom-element/demo/dom-merge.html +123 -0
- package/src/custom-element/demo/embed-1.html +3 -0
- package/src/custom-element/demo/external-template.html +179 -0
- package/src/custom-element/demo/hex-grid-dce.html +183 -0
- package/src/custom-element/demo/hex-grid-transform.png +0 -0
- package/src/custom-element/demo/hex-grid.html +66 -0
- package/src/custom-element/demo/html-template.html +126 -0
- package/src/custom-element/demo/html-template.xhtml +45 -0
- package/src/custom-element/demo/html-template.xml +45 -0
- package/src/custom-element/demo/http-request.html +143 -0
- package/src/custom-element/demo/local-storage.html +218 -0
- package/src/custom-element/demo/location-element.html +155 -0
- package/src/custom-element/demo/logo.png +0 -0
- package/src/custom-element/demo/parameters.html +70 -0
- package/src/custom-element/demo/s.xml +14 -0
- package/src/custom-element/demo/s.xslt +76 -0
- package/src/custom-element/demo/scoped-css.html +169 -0
- package/src/custom-element/demo/ss.html +57 -0
- package/src/custom-element/demo/table.xml +25 -0
- package/src/custom-element/demo/table.xsl +293 -0
- package/src/custom-element/demo/template.xsl +46 -0
- package/src/custom-element/demo/tree.xml +25 -0
- package/src/custom-element/demo/tree.xsl +33 -0
- package/src/custom-element/demo/wc-square.svg +1 -0
- package/src/custom-element/demo/xhtml-template.xhtml +45 -0
- package/src/custom-element/demo/z.html +62 -0
- package/src/custom-element/demo/z.xml +60 -0
- package/src/custom-element/http-request.js +89 -0
- package/src/custom-element/ide/IDE.md +31 -0
- package/src/custom-element/ide/customData-dce.json +112 -0
- package/src/custom-element/ide/customData-xsl.json +1018 -0
- package/src/custom-element/ide/web-types-dce.json +111 -0
- package/src/custom-element/ide/web-types-xsl.json +867 -0
- package/src/custom-element/index.html +168 -0
- package/src/custom-element/index.js +7 -0
- package/src/custom-element/local-storage.js +87 -0
- package/src/custom-element/location-element.js +87 -0
- package/src/custom-element.test.ts +10 -0
- package/src/index.css +38 -0
- package/src/mocks/handlers.ts +29 -0
- package/src/mocks/pokemons.mock.ts +13 -0
- package/src/stories/Configure.mdx +364 -0
- package/src/stories/assets/accessibility.png +0 -0
- package/src/stories/assets/accessibility.svg +5 -0
- package/src/stories/assets/addon-library.png +0 -0
- package/src/stories/assets/assets.png +0 -0
- package/src/stories/assets/avif-test-image.avif +0 -0
- package/src/stories/assets/context.png +0 -0
- package/src/stories/assets/discord.svg +15 -0
- package/src/stories/assets/docs.png +0 -0
- package/src/stories/assets/figma-plugin.png +0 -0
- package/src/stories/assets/github.svg +3 -0
- package/src/stories/assets/share.png +0 -0
- package/src/stories/assets/styling.png +0 -0
- package/src/stories/assets/testing.png +0 -0
- package/src/stories/assets/theming.png +0 -0
- package/src/stories/assets/tutorials.svg +12 -0
- package/src/stories/assets/youtube.svg +4 -0
- package/src/stories/attributes.stories.ts +132 -0
- package/src/stories/attributes.test.ts +14 -0
- package/src/stories/css.stories.ts +104 -0
- package/src/stories/css.test.ts +12 -0
- package/src/stories/dom-merge.stories.ts +113 -0
- package/src/stories/dom-merge.test.ts +12 -0
- package/src/stories/external-template.stories.ts +245 -0
- package/src/stories/external-template.test.ts +12 -0
- package/src/stories/http-request.stories.ts +244 -0
- package/src/stories/http-request.test.ts +29 -0
- package/src/stories/local-storage.stories.ts +388 -0
- package/src/stories/local-storage.test.ts +12 -0
- package/src/stories/location-element.stories.ts +133 -0
- package/src/stories/location-element.test.ts +14 -0
- package/src/stories/renderPlay.ts +22 -0
- package/src/stories/slice-events.stories.ts +117 -0
- package/src/stories/slice-events.test.ts +12 -0
- package/src/sum.test.ts +6 -0
- package/src/sum.ts +4 -0
- package/src/vite-env.d.ts +1 -0
- package/storybook-static/assets/Color-RQJUDNI5-C4yZhNbM.js +1 -0
- package/storybook-static/assets/Configure-C7d36rng.js +173 -0
- package/storybook-static/assets/DocsRenderer-K4EAMTCU-BLMupvSb.js +2 -0
- package/storybook-static/assets/WithTooltip-Y7J54OF7-BAQSPSFk.js +1 -0
- package/storybook-static/assets/accessibility-W_h2acOZ.png +0 -0
- package/storybook-static/assets/addon-library-BWUCAmyN.png +0 -0
- package/storybook-static/assets/attributes.stories-ZB0RTY1d.js +151 -0
- package/storybook-static/assets/context-C0qIqeS4.png +0 -0
- package/storybook-static/assets/css.stories-CLSX-Xxd.js +86 -0
- package/storybook-static/assets/custom-element-BLZZ00dz.js +53 -0
- package/storybook-static/assets/docs---vsFbMi.png +0 -0
- package/storybook-static/assets/dom-merge.stories-CgHZUABU.js +138 -0
- package/storybook-static/assets/entry-preview-CQqNFx4W.js +8 -0
- package/storybook-static/assets/entry-preview-docs-CWgqLfd3.js +2 -0
- package/storybook-static/assets/external-template.stories-DtSLMxvg.js +316 -0
- package/storybook-static/assets/figma-plugin-CH2hELiO.png +0 -0
- package/storybook-static/assets/formatter-B5HCVTEV-tKeEfJA9.js +58 -0
- package/storybook-static/assets/http-request.stories-CUzlXO89.js +300 -0
- package/storybook-static/assets/iframe-gCvlWuoC.js +2 -0
- package/storybook-static/assets/index-CBQwM6ST.js +508 -0
- package/storybook-static/assets/index-CDavW7r9.js +193 -0
- package/storybook-static/assets/index-CQA5dlr6.js +13 -0
- package/storybook-static/assets/index-Cc7K62zD.js +3 -0
- package/storybook-static/assets/index-DgaNIR0t.js +1 -0
- package/storybook-static/assets/index-Dkj0J1ds.js +1 -0
- package/storybook-static/assets/index-DnEJ_bKa.js +1 -0
- package/storybook-static/assets/index-DrFu-skq.js +6 -0
- package/storybook-static/assets/lit-element-B4_0akdT.js +19 -0
- package/storybook-static/assets/local-storage.stories-BkO6djDz.js +415 -0
- package/storybook-static/assets/location-element.stories-DCIOUd0D.js +108 -0
- package/storybook-static/assets/preview-B4GcaC1c.js +1 -0
- package/storybook-static/assets/preview-B63p-W8V.js +20 -0
- package/storybook-static/assets/preview-BAz7FMXc.js +396 -0
- package/storybook-static/assets/preview-BDY5ThwJ.js +1 -0
- package/storybook-static/assets/preview-C6t8KBFr.js +1 -0
- package/storybook-static/assets/preview-CYD85dwb.js +7 -0
- package/storybook-static/assets/preview-CkgAD_DE.js +2 -0
- package/storybook-static/assets/preview-D8LadFCz.js +48 -0
- package/storybook-static/assets/preview-DNpCpRPf.js +1 -0
- package/storybook-static/assets/preview-PxUn-cIn.js +1 -0
- package/storybook-static/assets/share-DGA-UcQf.png +0 -0
- package/storybook-static/assets/slice-events.stories-DXKjXI37.js +115 -0
- package/storybook-static/assets/styling-Bk6zjRzU.png +0 -0
- package/storybook-static/assets/syntaxhighlighter-JOJW2KGS-C04pIVD3.js +1 -0
- package/storybook-static/assets/testing-cbzR9l9r.png +0 -0
- package/storybook-static/assets/theming-D6WJLNoW.png +0 -0
- package/storybook-static/assets/tiny-invariant-BxWVcicq.js +1 -0
- package/storybook-static/confused.svg +37 -0
- package/storybook-static/embed-1.html +3 -0
- package/storybook-static/favicon.svg +7 -0
- package/storybook-static/html-template.html +126 -0
- package/storybook-static/html-template.xhtml +45 -0
- package/storybook-static/html-template.xml +45 -0
- package/storybook-static/iframe.html +492 -0
- package/storybook-static/index.html +163 -0
- package/storybook-static/index.json +1 -0
- package/storybook-static/mockServiceWorker.js +284 -0
- package/storybook-static/project.json +1 -0
- package/storybook-static/sb-addons/chromatic-com-storybook-9/manager-bundle.js +327 -0
- package/storybook-static/sb-addons/chromatic-com-storybook-9/manager-bundle.js.LEGAL.txt +40 -0
- package/storybook-static/sb-addons/essentials-actions-3/manager-bundle.js +3 -0
- package/storybook-static/sb-addons/essentials-actions-3/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/essentials-backgrounds-4/manager-bundle.js +12 -0
- package/storybook-static/sb-addons/essentials-backgrounds-4/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/essentials-controls-2/manager-bundle.js +60 -0
- package/storybook-static/sb-addons/essentials-controls-2/manager-bundle.js.LEGAL.txt +18 -0
- package/storybook-static/sb-addons/essentials-measure-7/manager-bundle.js +3 -0
- package/storybook-static/sb-addons/essentials-measure-7/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/essentials-outline-8/manager-bundle.js +3 -0
- package/storybook-static/sb-addons/essentials-outline-8/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/essentials-toolbars-6/manager-bundle.js +3 -0
- package/storybook-static/sb-addons/essentials-toolbars-6/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/essentials-viewport-5/manager-bundle.js +3 -0
- package/storybook-static/sb-addons/essentials-viewport-5/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/interactions-10/manager-bundle.js +33 -0
- package/storybook-static/sb-addons/interactions-10/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/links-1/manager-bundle.js +3 -0
- package/storybook-static/sb-addons/links-1/manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-addons/storybook-core-server-presets-0/common-manager-bundle.js +3 -0
- package/storybook-static/sb-addons/storybook-core-server-presets-0/common-manager-bundle.js.LEGAL.txt +0 -0
- package/storybook-static/sb-common-assets/fonts.css +31 -0
- package/storybook-static/sb-common-assets/nunito-sans-bold-italic.woff2 +0 -0
- package/storybook-static/sb-common-assets/nunito-sans-bold.woff2 +0 -0
- package/storybook-static/sb-common-assets/nunito-sans-italic.woff2 +0 -0
- package/storybook-static/sb-common-assets/nunito-sans-regular.woff2 +0 -0
- package/storybook-static/sb-manager/WithTooltip-Y7J54OF7-CEHQ77YF.js +1 -0
- package/storybook-static/sb-manager/chunk-E3WK6ZOZ.js +234 -0
- package/storybook-static/sb-manager/chunk-E6ABNH5R.js +183 -0
- package/storybook-static/sb-manager/chunk-FEE35O7J.js +9 -0
- package/storybook-static/sb-manager/chunk-S4VOIVUE.js +347 -0
- package/storybook-static/sb-manager/chunk-XCO5HRLK.js +6 -0
- package/storybook-static/sb-manager/chunk-XP3HGWTR.js +1 -0
- package/storybook-static/sb-manager/formatter-B5HCVTEV-7DCBOGO6.js +58 -0
- package/storybook-static/sb-manager/globals-module-info.js +1 -0
- package/storybook-static/sb-manager/globals-runtime.js +1 -0
- package/storybook-static/sb-manager/globals.js +1 -0
- package/storybook-static/sb-manager/index.js +1 -0
- package/storybook-static/sb-manager/runtime.js +1 -0
- package/storybook-static/sb-manager/syntaxhighlighter-JOJW2KGS-VF6EEVPI.js +1 -0
- package/storybook-static/sb-preview/globals.js +1 -0
- package/storybook-static/sb-preview/runtime.js +139 -0
- package/storybook-static/tree.xsl +33 -0
- package/storybook-static/vite.svg +1 -0
- package/tsconfig.json +25 -0
- package/vite.config.js +55 -0
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
|
|
3
|
+
<head>
|
|
4
|
+
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
|
|
5
|
+
<title>custom-element Declarative Custom Element implementation demo</title>
|
|
6
|
+
<link rel="icon" href="demo/wc-square.svg" />
|
|
7
|
+
<script type="module" src="custom-element.js"></script>
|
|
8
|
+
<style>
|
|
9
|
+
@import "demo/demo.css";
|
|
10
|
+
</style>
|
|
11
|
+
</head>
|
|
12
|
+
<body xmlns:xhtml="http://www.w3.org/1999/xhtml">
|
|
13
|
+
<nav>
|
|
14
|
+
<h3><code>custom-element</code> demo</h3>
|
|
15
|
+
<div><a href="https://github.com/EPA-WG/custom-element"
|
|
16
|
+
><img src="https://cdnjs.cloudflare.com/ajax/libs/octicons/8.5.0/svg/mark-github.svg" alt="icon">GIT</a>
|
|
17
|
+
| <a href="https://github.com/EPA-WG/custom-element/blob/main/README.md">README</a>
|
|
18
|
+
| <a href="https://stackblitz.com/github/EPA-WG/custom-element?file=index.html">Sandbox</a>
|
|
19
|
+
| <a href="https://chrome.google.com/webstore/detail/epa-wgcustom-element/hiofgpmmkdembdogjpagmbbbmefefhbl"
|
|
20
|
+
>Chrome devtools plugin</a>
|
|
21
|
+
</div>
|
|
22
|
+
<p>
|
|
23
|
+
This <em>Declarative Custom Element</em> allows to define<br/>
|
|
24
|
+
custom HTML tag with template filled from slots, attributes, dataset. </p>
|
|
25
|
+
<p>The template is fully loaded with variables, conditions, loops, etc. <br/>
|
|
26
|
+
The data query is powered by XPath. </p>
|
|
27
|
+
<p>Try in <a href="https://stackblitz.com/github/EPA-WG/custom-element?file=index.html" >Sandbox</a> </p>
|
|
28
|
+
<section>
|
|
29
|
+
<h4>Features demo</h4>
|
|
30
|
+
<a href="./demo/local-storage.html" >local-storage </a> |
|
|
31
|
+
<a href="./demo/http-request.html" >http-request </a> |
|
|
32
|
+
<a href="./demo/location-element.html" >location-element </a> |
|
|
33
|
+
<a href="./demo/external-template.html" >external template </a> <br/>
|
|
34
|
+
<a href="./demo/hex-grid.html" >hex grid lib </a> |
|
|
35
|
+
<a href="./demo/scoped-css.html" >scoped CSS </a> |
|
|
36
|
+
<a href="./demo/parameters.html" >attributes </a> |
|
|
37
|
+
<a href="./demo/data-slices.html" >data slices/events </a> |
|
|
38
|
+
<a href="./demo/dom-merge.html" >DOM merge on dynamic update </a>
|
|
39
|
+
</section>
|
|
40
|
+
</nav>
|
|
41
|
+
<html-demo-element legend="1. simple payload"
|
|
42
|
+
description="payload is ignored as in DCE definition there is no default slot">
|
|
43
|
+
<template>
|
|
44
|
+
<custom-element tag="dce-link" hidden>
|
|
45
|
+
<a href="#">link 😃</a>
|
|
46
|
+
</custom-element>
|
|
47
|
+
<dce-link><i>🍋</i></dce-link>
|
|
48
|
+
</template>
|
|
49
|
+
</html-demo-element>
|
|
50
|
+
|
|
51
|
+
<html-demo-element legend="2. payload with slot definition and slot value"
|
|
52
|
+
description="slots are filled as in template+shadow root">
|
|
53
|
+
<template>
|
|
54
|
+
<custom-element tag="dce-1-slot" hidden>
|
|
55
|
+
🐇❤️<slot name="slot1"> 🥦</slot>
|
|
56
|
+
</custom-element>
|
|
57
|
+
<dce-1-slot><i slot="slot1">🥕</i></dce-1-slot>
|
|
58
|
+
</template>
|
|
59
|
+
</html-demo-element>
|
|
60
|
+
|
|
61
|
+
<html-demo-element legend="2a. payload with slot definition and slot value"
|
|
62
|
+
description="unlike in TEMPLATE, same slot can be used multiple times and within attribute ">
|
|
63
|
+
<template>
|
|
64
|
+
<custom-element tag="dce-2-slots" hidden>
|
|
65
|
+
<slot name="slot2"> 😃</slot> and again:
|
|
66
|
+
<slot name="slot2"> 😃</slot>
|
|
67
|
+
<xhtml:input placeholder="🐇❤️{//*[@slot='slot2']}"/>
|
|
68
|
+
</custom-element>
|
|
69
|
+
<dce-2-slots><i slot="slot2">🥕</i></dce-2-slots>
|
|
70
|
+
<dce-2-slots></dce-2-slots>
|
|
71
|
+
</template>
|
|
72
|
+
</html-demo-element>
|
|
73
|
+
|
|
74
|
+
<html-demo-element legend="2b. named default slot"
|
|
75
|
+
description="slot without `name` attribute or with blank value `name=''` use whole payload">
|
|
76
|
+
<template>
|
|
77
|
+
<custom-element tag="dce-3-slot" hidden>
|
|
78
|
+
#1
|
|
79
|
+
<slot name=""> 😃</slot>
|
|
80
|
+
and
|
|
81
|
+
<slot> 😃</slot>
|
|
82
|
+
</custom-element>
|
|
83
|
+
<dce-3-slot><i slot="">🥕</i></dce-3-slot>
|
|
84
|
+
</template>
|
|
85
|
+
</html-demo-element>
|
|
86
|
+
|
|
87
|
+
<html-demo-element legend="2c. named default slot"
|
|
88
|
+
description="slot without `name` attribute or with blank value `name=''` use whole payload">
|
|
89
|
+
<template>
|
|
90
|
+
<custom-element tag="dce-4-slot" hidden>
|
|
91
|
+
#2
|
|
92
|
+
<slot name=""> 😃</slot>
|
|
93
|
+
and
|
|
94
|
+
<slot> 😃</slot>
|
|
95
|
+
</custom-element>
|
|
96
|
+
<dce-4-slot>🥕</dce-4-slot>
|
|
97
|
+
</template>
|
|
98
|
+
</html-demo-element>
|
|
99
|
+
|
|
100
|
+
<html-demo-element legend="2d. default slot"
|
|
101
|
+
description="slot without `name` attribute use whole payload">
|
|
102
|
+
<template>
|
|
103
|
+
|
|
104
|
+
<custom-element tag="greet-element" hidden>
|
|
105
|
+
<slot> Hello </slot> World!
|
|
106
|
+
</custom-element>
|
|
107
|
+
<greet-element></greet-element>
|
|
108
|
+
<greet-element>👋</greet-element>
|
|
109
|
+
</template>
|
|
110
|
+
</html-demo-element>
|
|
111
|
+
|
|
112
|
+
<html-demo-element legend="3. 💪 DCE template "
|
|
113
|
+
description="Complex case with slots, attributes, dataset, conditional render">
|
|
114
|
+
<template>
|
|
115
|
+
|
|
116
|
+
<custom-element tag="pokemon-tile" hidden id="shared-template">
|
|
117
|
+
<template>
|
|
118
|
+
<h3> {title} </h3> <!-- title is an attribute in instance
|
|
119
|
+
mapped into /*/attributes/title -->
|
|
120
|
+
<if test="//smile"> <!-- data-smile DCE instance attribute,
|
|
121
|
+
mapped into /*/dataset/smile
|
|
122
|
+
used in condition -->
|
|
123
|
+
<!-- data-smile DCE instance attribute, used as HTML -->
|
|
124
|
+
<div>Smile as: {//smile}</div> <!-- /datadom/dataset/smile -->
|
|
125
|
+
</if>
|
|
126
|
+
<!-- image would not be visible in sandbox, see live demo -->
|
|
127
|
+
<img src="https://unpkg.com/pokeapi-sprites@2.0.2/sprites/pokemon/other/dream-world/{pokemon-id}.svg"
|
|
128
|
+
alt="{title} image"/>
|
|
129
|
+
<!-- image-src and title are DCE instance attributes,
|
|
130
|
+
mapped into /*/attributes/
|
|
131
|
+
used within output attribute via curly brackets -->
|
|
132
|
+
|
|
133
|
+
<!-- `slot name=xxx` replaced with elements with `slot=xxx` attribute -->
|
|
134
|
+
<p><slot name="description"><i>description is not available</i></slot></p>
|
|
135
|
+
<for-each select="//*[@pokemon-id]">
|
|
136
|
+
<!-- loop over payload elements with `pokemon-id` attribute,
|
|
137
|
+
i.e LI elements -->
|
|
138
|
+
<button>
|
|
139
|
+
<img height="32"
|
|
140
|
+
src="https://unpkg.com/pokeapi-sprites@2.0.2/sprites/pokemon/other/dream-world/{@pokemon-id}.svg"
|
|
141
|
+
alt="{text()}"/>
|
|
142
|
+
<br/>
|
|
143
|
+
{text()} <!-- text from LI element in loop -->
|
|
144
|
+
</button>
|
|
145
|
+
|
|
146
|
+
</for-each>
|
|
147
|
+
</template>
|
|
148
|
+
</custom-element>
|
|
149
|
+
|
|
150
|
+
<pokemon-tile title="bulbasaur" data-smile="👼" pokemon-id="1" >
|
|
151
|
+
<p slot="description">Bulbasaur is a cute Pokémon born with a large seed firmly affixed to its back;
|
|
152
|
+
the seed grows in size as the Pokémon does.</p>
|
|
153
|
+
<ul>
|
|
154
|
+
<li pokemon-id="2">ivysaur</li>
|
|
155
|
+
<li pokemon-id="3">venusaur</li>
|
|
156
|
+
</ul>
|
|
157
|
+
</pokemon-tile>
|
|
158
|
+
|
|
159
|
+
<pokemon-tile title="ninetales" pokemon-id="38" >
|
|
160
|
+
<li pokemon-id="37">vulpix</li>
|
|
161
|
+
</pokemon-tile>
|
|
162
|
+
</template>
|
|
163
|
+
</html-demo-element>
|
|
164
|
+
|
|
165
|
+
<script type="module" src="https://unpkg.com/html-demo-element@1.0/html-demo-element.js"></script>
|
|
166
|
+
|
|
167
|
+
</body>
|
|
168
|
+
</html>
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
const string2value = (type, v) =>
|
|
2
|
+
{ if( type === 'text')
|
|
3
|
+
return v;
|
|
4
|
+
if( type === 'json')
|
|
5
|
+
try{ return JSON.parse( v );}
|
|
6
|
+
catch(err){ return null }
|
|
7
|
+
const el = document.createElement('input');
|
|
8
|
+
el.setAttribute('type',type);
|
|
9
|
+
if( 'number' === type )
|
|
10
|
+
{ el.value = v;
|
|
11
|
+
return el.valueAsNumber;
|
|
12
|
+
}
|
|
13
|
+
if( 'date' === type )
|
|
14
|
+
{ if(!v) return null;
|
|
15
|
+
el.valueAsDate = new Date( v );
|
|
16
|
+
return el.value;
|
|
17
|
+
}
|
|
18
|
+
el.value = v;
|
|
19
|
+
return el.value;
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
let originalSetItem,originalRemoveItem,originalClear;
|
|
23
|
+
|
|
24
|
+
function ensureTrackLocalStorage()
|
|
25
|
+
{ if( originalSetItem )
|
|
26
|
+
return;
|
|
27
|
+
originalSetItem = localStorage.setItem;
|
|
28
|
+
localStorage.setItem = function( key, value, ...rest )
|
|
29
|
+
{ originalSetItem.apply(this, [ key, value, ...rest ]);
|
|
30
|
+
window.dispatchEvent( new CustomEvent('local-storage',{detail:{key,value}}) );
|
|
31
|
+
};
|
|
32
|
+
originalRemoveItem = localStorage.removeItem;
|
|
33
|
+
localStorage.removeItem = function( key, ...rest )
|
|
34
|
+
{ originalRemoveItem.apply(this, [ key, ...rest ]);
|
|
35
|
+
window.dispatchEvent( new CustomEvent('local-storage',{detail:{key}}) );
|
|
36
|
+
};
|
|
37
|
+
originalClear = localStorage.clear;
|
|
38
|
+
localStorage.clear = function( ...rest )
|
|
39
|
+
{ originalClear.apply(this, [ ...rest ]);
|
|
40
|
+
window.dispatchEvent( new CustomEvent('local-storage',{detail:{}}) );
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
export function localStorageSetItem(key, value)
|
|
45
|
+
{ localStorage.setItem(key, value);
|
|
46
|
+
window.dispatchEvent( new CustomEvent('local-storage',{detail:{key,value}}) );
|
|
47
|
+
}
|
|
48
|
+
export class LocalStorageElement extends HTMLElement
|
|
49
|
+
{
|
|
50
|
+
static observedAttributes=
|
|
51
|
+
[ 'value' // populated from localStorage, if defined initially, sets the value in storage
|
|
52
|
+
, 'slice'
|
|
53
|
+
, 'key'
|
|
54
|
+
, 'type' // `text|json`, defaults to text, other types are compatible with INPUT field
|
|
55
|
+
, 'live' // monitors localStorage change
|
|
56
|
+
];
|
|
57
|
+
|
|
58
|
+
#value;
|
|
59
|
+
get value(){ return this.#value ===null ? undefined: this.#value }
|
|
60
|
+
set value(o){ return this.#value = o; }
|
|
61
|
+
|
|
62
|
+
async connectedCallback()
|
|
63
|
+
{
|
|
64
|
+
const attr = attr => this.getAttribute(attr)
|
|
65
|
+
, fromStorage = ()=>
|
|
66
|
+
{ this.#value = string2value( attr('type'), localStorage.getItem( attr( 'key' ) ) );
|
|
67
|
+
this.dispatchEvent( new Event('change') )
|
|
68
|
+
}
|
|
69
|
+
this.#value = string2value( attr('type'), localStorage.getItem( attr( 'key' ) ) );
|
|
70
|
+
|
|
71
|
+
if( this.hasAttribute('value'))
|
|
72
|
+
localStorageSetItem( attr( 'key' ), this.#value = attr( 'value' ) )
|
|
73
|
+
else
|
|
74
|
+
fromStorage()
|
|
75
|
+
|
|
76
|
+
if( this.hasAttribute('live') )
|
|
77
|
+
{ const listener = (e => (e.detail.key === attr( 'key' ) || !e.detail.key ) && fromStorage());
|
|
78
|
+
window.addEventListener( 'local-storage', listener );
|
|
79
|
+
ensureTrackLocalStorage();
|
|
80
|
+
this._destroy = ()=> window.removeEventListener('local-storage', listener );
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
disconnectedCallback(){ this._destroy?.(); }
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
window.customElements.define( 'local-storage', LocalStorageElement );
|
|
87
|
+
export default LocalStorageElement;
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
const attr = ( el, attr )=> el.getAttribute( attr );
|
|
2
|
+
|
|
3
|
+
let originalHistory;
|
|
4
|
+
|
|
5
|
+
function ensureTrackLocationChange()
|
|
6
|
+
{ if( originalHistory )
|
|
7
|
+
return;
|
|
8
|
+
originalHistory = {};
|
|
9
|
+
'back,forward,go,pushState,replaceState'.split(',').forEach( k =>
|
|
10
|
+
{
|
|
11
|
+
originalHistory[ k ] = history[ k ];
|
|
12
|
+
history[ k ] = function(...rest )
|
|
13
|
+
{
|
|
14
|
+
originalHistory[k].apply( history, rest );
|
|
15
|
+
window.dispatchEvent( new CustomEvent('dce-location',{detail:{ k }}) );
|
|
16
|
+
}
|
|
17
|
+
});
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export class LocationElement extends HTMLElement
|
|
21
|
+
{
|
|
22
|
+
static observedAttributes=
|
|
23
|
+
[ 'value' // populated from url
|
|
24
|
+
, 'slice'
|
|
25
|
+
, 'href' // url to be parsed. When omitted window.location is used.
|
|
26
|
+
, 'type' // `text|json`, defaults to text, other types are compatible with INPUT field
|
|
27
|
+
, 'live' // monitors history change, applicable only when href is omitted.
|
|
28
|
+
];
|
|
29
|
+
|
|
30
|
+
constructor()
|
|
31
|
+
{
|
|
32
|
+
super();
|
|
33
|
+
const state = {}
|
|
34
|
+
, listener = () => setTimeout( propagateSlice,1 )
|
|
35
|
+
, propagateSlice = ()=>
|
|
36
|
+
{ const urlStr = attr(this,'href')
|
|
37
|
+
if(!urlStr)
|
|
38
|
+
ensureTrackLocationChange();
|
|
39
|
+
const url = urlStr? new URL(urlStr, window.location) : window.location;
|
|
40
|
+
|
|
41
|
+
const params= {}
|
|
42
|
+
const search = new URLSearchParams(url.search);
|
|
43
|
+
for (const key of search.keys())
|
|
44
|
+
params[key] = search.getAll(key)
|
|
45
|
+
|
|
46
|
+
const detail = {params}
|
|
47
|
+
for( const k in url )
|
|
48
|
+
{ if ('string' === typeof url[k])
|
|
49
|
+
detail[k] = url[k]
|
|
50
|
+
}
|
|
51
|
+
this.value = detail;
|
|
52
|
+
this.dispatchEvent( new Event('change') );
|
|
53
|
+
};
|
|
54
|
+
this.sliceInit = s =>
|
|
55
|
+
{
|
|
56
|
+
if( !state.listener && this.hasAttribute('live') )
|
|
57
|
+
{ state.listener = 1;
|
|
58
|
+
window.navigation?.addEventListener("navigate", listener );
|
|
59
|
+
window.addEventListener( 'popstate' , listener );
|
|
60
|
+
window.addEventListener( 'hashchange' , listener );
|
|
61
|
+
window.addEventListener( 'dce-location' , listener );
|
|
62
|
+
}
|
|
63
|
+
propagateSlice();
|
|
64
|
+
return s || {}
|
|
65
|
+
}
|
|
66
|
+
this._destroy = ()=>
|
|
67
|
+
{
|
|
68
|
+
window.removeEventListener('popstate' , listener);
|
|
69
|
+
window.removeEventListener('hashchange' , listener);
|
|
70
|
+
window.removeEventListener('dce-location', listener);
|
|
71
|
+
delete state.listener;
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
}
|
|
75
|
+
attributeChangedCallback(name, oldValue, newValue)
|
|
76
|
+
{
|
|
77
|
+
if('href'!== name)
|
|
78
|
+
return;
|
|
79
|
+
this.sliceInit && this.sliceInit();
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
connectedCallback(){ this.sliceInit() }
|
|
83
|
+
disconnectedCallback(){ this._destroy() }
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
window.customElements.define( 'location-element', LocationElement );
|
|
87
|
+
export default LocationElement;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { expect, test } from 'vitest'
|
|
2
|
+
import { deepEqual} from './custom-element/custom-element.js'
|
|
3
|
+
|
|
4
|
+
test('deepEqual', () => {
|
|
5
|
+
expect(deepEqual(1, 1) ).toBe(true);
|
|
6
|
+
expect(deepEqual({}, null) ).toBe(false);
|
|
7
|
+
expect(deepEqual({a:1},{a:1,b:2}) ).toBe(false);
|
|
8
|
+
expect(deepEqual({a:1},{a:2}) ).toBe(false);
|
|
9
|
+
expect(deepEqual({a:1},{a:1}) ).toBe(true);
|
|
10
|
+
})
|
package/src/index.css
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
:root {
|
|
2
|
+
font-family: Inter, system-ui, Avenir, Helvetica, Arial, sans-serif;
|
|
3
|
+
line-height: 1.5;
|
|
4
|
+
font-weight: 400;
|
|
5
|
+
|
|
6
|
+
color-scheme: light dark;
|
|
7
|
+
color: rgba(255, 255, 255, 0.87);
|
|
8
|
+
background-color: #242424;
|
|
9
|
+
|
|
10
|
+
font-synthesis: none;
|
|
11
|
+
text-rendering: optimizeLegibility;
|
|
12
|
+
-webkit-font-smoothing: antialiased;
|
|
13
|
+
-moz-osx-font-smoothing: grayscale;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
a {
|
|
17
|
+
font-weight: 500;
|
|
18
|
+
color: #646cff;
|
|
19
|
+
text-decoration: inherit;
|
|
20
|
+
}
|
|
21
|
+
a:hover {
|
|
22
|
+
color: #535bf2;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
body {
|
|
26
|
+
margin: 0;
|
|
27
|
+
display: flex;
|
|
28
|
+
place-items: center;
|
|
29
|
+
min-width: 320px;
|
|
30
|
+
min-height: 100vh;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
@media (prefers-color-scheme: light) {
|
|
34
|
+
:root {
|
|
35
|
+
color: #213547;
|
|
36
|
+
background-color: #ffffff;
|
|
37
|
+
}
|
|
38
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import {delay, http, HttpResponse} from 'msw'
|
|
2
|
+
|
|
3
|
+
import pokemonsMock from './pokemons.mock.ts';
|
|
4
|
+
|
|
5
|
+
export const handlers =
|
|
6
|
+
[ http.get('/pokemon', ({ request }) =>
|
|
7
|
+
{
|
|
8
|
+
const url = new URL(request.url);
|
|
9
|
+
const limit = url.searchParams.get('limit');
|
|
10
|
+
const data = structuredClone(pokemonsMock);
|
|
11
|
+
if( limit )
|
|
12
|
+
data.results = data.results.slice(0,Number(limit))
|
|
13
|
+
return HttpResponse.json(data); })
|
|
14
|
+
, http.get('/noreturn', async () =>
|
|
15
|
+
{
|
|
16
|
+
await delay(500);
|
|
17
|
+
// half second to be able to catch the initial state before the full data returned;
|
|
18
|
+
return HttpResponse.json(pokemonsMock);
|
|
19
|
+
})
|
|
20
|
+
, http.get('/reflect', ({request}) =>
|
|
21
|
+
{ const headers: Record<string, string> = {};
|
|
22
|
+
[...request.headers.entries()].map(([key, val]) => headers[key] = 'reflected-'+val);
|
|
23
|
+
headers['x-added'] = 'abc';
|
|
24
|
+
return HttpResponse.json(pokemonsMock, {headers});
|
|
25
|
+
})
|
|
26
|
+
, http.get('/404', () =>
|
|
27
|
+
{
|
|
28
|
+
return new HttpResponse(null, {status: 404, statusText: 'not found'}) })
|
|
29
|
+
];
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export default {
|
|
2
|
+
"count": 1279,
|
|
3
|
+
"next": "https://pokeapi.co/api/v2/pokemon?offset=6&limit=6",
|
|
4
|
+
"previous": null,
|
|
5
|
+
"results":
|
|
6
|
+
[ {"name": "bulbasaur" ,"url": "https://pokeapi.co/api/v2/pokemon/1/" }
|
|
7
|
+
, {"name": "ivysaur" ,"url": "https://pokeapi.co/api/v2/pokemon/2/" }
|
|
8
|
+
, {"name": "venusaur" ,"url": "https://pokeapi.co/api/v2/pokemon/3/" }
|
|
9
|
+
, {"name": "charmander" ,"url": "https://pokeapi.co/api/v2/pokemon/4/" }
|
|
10
|
+
, {"name": "charmeleon" ,"url": "https://pokeapi.co/api/v2/pokemon/5/" }
|
|
11
|
+
, {"name": "charizard" ,"url": "https://pokeapi.co/api/v2/pokemon/6/" }
|
|
12
|
+
]
|
|
13
|
+
}
|