Skip to content

Commit

Permalink
Support new shadowrootmode attribute for Declarative Shadow DOM
Browse files Browse the repository at this point in the history
  • Loading branch information
zachleat committed Mar 1, 2023
1 parent a303778 commit a338a55
Show file tree
Hide file tree
Showing 2 changed files with 28 additions and 17 deletions.
25 changes: 19 additions & 6 deletions demo-declarative-shadow-dom.html
Original file line number Diff line number Diff line change
Expand Up @@ -6,22 +6,35 @@ <h1><a href="/">is-land</a></h1>

<p>For <a href="https://github.com/11ty/is-land/issues/13">GitHub issue #13</a>.</p>

<p>As of time of writing, Firefox and Safari do not support Declarative Shadow DOM. This component does include a small (4 LoC) polyfill but it is *not* applied to elements outside of <code>&lt;is-land&gt;</code>.</p>
<p>As of time of writing, Firefox and Safari do not support Declarative Shadow DOM. This component does include a small (4 LoC) polyfill but it is scoped <strong>exclusively</strong> to elements inside of <code>&lt;is-land&gt;</code>.</p>

<p>Note that if <code>chocolate-web-component.js</code> is not available on page load, any <code>&lt;chocolate-web-component&gt;</code> elements outside of <code>&lt;is-land&gt;</code> will be initialized when the file is loaded. This is better solved by implementing <a href="/demo-defer-hydration/"><code>defer-hydration</code> in your component code</a>.</p>

<script src="/lib/chocolate-web-component.js" type="module"></script>

<chocolate-web-component class="demo-component">
<p>Declarative shadow DOM polyfill is not applied to elements outside of an <code>&lt;is-land&gt;</code></p>

<!-- <chocolate-web-component class="demo-component">
<template shadowroot="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component>
<chocolate-web-component class="demo-component">
<template shadowroot="open" shadowrootmode="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component> -->

<chocolate-web-component class="demo-component">
<template shadowroot="open" shadowrootmode="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component>


<is-land on:interaction>
<button type="button" onclick="console.log('Click test')">Click test (log to console)</button>

<chocolate-web-component class="demo-component">
<template shadowroot="open">Chocolate shadow root</template>
<template shadowroot="open" shadowrootmode="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component>
</is-land>
Expand All @@ -32,7 +45,7 @@ <h1><a href="/">is-land</a></h1>
<button type="button" onclick="console.log('Click test')">Click test (log to console)</button>

<chocolate-web-component class="demo-component">
<template shadowroot="open">Chocolate shadow root</template>
<template shadowroot="open" shadowrootmode="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component>
</is-land>
Expand All @@ -41,7 +54,7 @@ <h1><a href="/">is-land</a></h1>
<button type="button" onclick="console.log('Click test')">Click test (log to console)</button>

<chocolate-web-component class="demo-component">
<template shadowroot="open">Chocolate shadow root</template>
<template shadowroot="open" shadowrootmode="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component>
</is-land>
Expand All @@ -50,7 +63,7 @@ <h1><a href="/">is-land</a></h1>
<button type="button" onclick="console.log('Click test')">Click test (log to console)</button>

<chocolate-web-component class="demo-component">
<template shadowroot="open">Chocolate shadow root</template>
<template shadowroot="open" shadowrootmode="open">Chocolate shadow root</template>
Chocolate web component
</chocolate-web-component>
</is-land>
Expand Down
20 changes: 9 additions & 11 deletions is-land.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
const islandOnceCache = new Map();

class Island extends HTMLElement {
static tagName = "is-land";
static prefix = "is-land--";
Expand All @@ -11,6 +9,8 @@ class Island extends HTMLElement {
defer: "defer-hydration",
};

static onceCache = new Map();

static fallback = {
":not(:defined):not([defer-hydration])": (readyPromise, node, prefix) => {
// remove from document to prevent web component init
Expand All @@ -23,7 +23,7 @@ class Island extends HTMLElement {
let shadowroot = node.shadowRoot;
if(!shadowroot) {
// polyfill
let tmpl = node.querySelector(":scope > template[shadowroot]");
let tmpl = node.querySelector(":scope > template:is([shadowrootmode], [shadowroot])");
if(tmpl) {
shadowroot = node.attachShadow({ mode: "open" });
shadowroot.appendChild(tmpl.content.cloneNode(true));
Expand Down Expand Up @@ -168,12 +168,12 @@ class Island extends HTMLElement {
} else {
let html = node.innerHTML;
if(value === "once" && html) {
if(islandOnceCache.has(html)) {
if(Island.onceCache.has(html)) {
node.remove();
return;
}

islandOnceCache.set(html, true);
Island.onceCache.set(html, true);
}

node.replaceWith(node.content);
Expand Down Expand Up @@ -217,9 +217,7 @@ class Island extends HTMLElement {
}
}

this.readyResolve({
// import: mod
});
this.readyResolve();

this.setAttribute(Island.attr.ready, "");

Expand Down Expand Up @@ -271,9 +269,9 @@ class Conditions {
});
}

// TODO make sure this runs after all of the conditions have finished, otherwise it will
// finish way before the other lazy loaded promises and will be the same as a noop when
// on:interaction or on:visible finishes much later
// This isn’t very useful with other conditions as periods of idle may
// happen before other conditions are satisfied. Would be more useful if waited
// for all other conditions to finish.
static idle() {
let onload = new Promise(resolve => {
if(document.readyState !== "complete") {
Expand Down

0 comments on commit a338a55

Please sign in to comment.