Last active
December 2, 2021 00:02
-
-
Save shgysk8zer0/ea40deafd59d7e9f451457f0d0319580 to your computer and use it in GitHub Desktop.
A demo of <github-gist> usage (See https://codepen.io/shgysk8zer0/full/jOGEJRj)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const protectedData = new WeakMap(); | |
function render(target) { | |
const { user, gist, file, height, width } = target; | |
const { shadow } = protectedData.get(target); | |
const iframe = document.createElement('iframe'); | |
const script = document.createElement('script'); | |
const link = document.createElement('link'); | |
const src = new URL(`/${user}/${gist}.js`, 'https://gist.github.com'); | |
const controller = new AbortController(); | |
link.rel = 'preconnect'; | |
link.href = 'https://github.githubassets.com'; | |
iframe.addEventListener('load', () => { | |
target.dispatchEvent(new Event('load')); | |
controller.abort(); | |
}, { | |
signal: controller.signal, | |
once: true, | |
}); | |
iframe.addEventListener('error', () => { | |
target.dispatchEvent(new Event('error')); | |
controller.abort(); | |
}, { | |
signal: controller.signal, | |
once: true, | |
}); | |
if (typeof file === 'string' && file.length !== 0) { | |
src.searchParams.set('file', file); | |
} | |
script.src = src.href; | |
iframe.referrerPolicy = 'no-referrer'; | |
iframe.sandbox.add('allow-scripts'); | |
iframe.frameBorder = 0; | |
if (! Number.isNaN(width)) { | |
iframe.width = width; | |
} | |
if (! Number.isNaN(height)) { | |
iframe.height = height; | |
} | |
if ('part' in iframe) { | |
iframe.part.add('embed'); | |
} | |
iframe.srcdoc = `<!DOCTYPE html><head>${link.outerHTML}</head><html><body>${script.outerHTML}</body></html>`; | |
shadow.append(iframe); | |
} | |
const observer = new IntersectionObserver((entries, observer) => { | |
entries.forEach(({ target, isIntersecting }) => { | |
if (isIntersecting && protectedData.has(target)) { | |
observer.unobserve(target); | |
render(target); | |
protectedData.delete(target); | |
} | |
}); | |
}, { | |
rootMargin: `${Math.round(0.5 * screen.height)}px`, | |
root: document.body, | |
}); | |
customElements.define('github-gist', class HTMLGitHubGistElement extends HTMLElement { | |
constructor() { | |
super(); | |
const shadow = this.attachShadow({ mode: 'open' }); | |
protectedData.set(this, { shadow }); | |
} | |
connectedCallback() { | |
switch(this.loading) { | |
case 'lazy': | |
observer.observe(this); | |
break; | |
default: | |
render(this); | |
} | |
} | |
get file() { | |
return this.getAttribute('file'); | |
} | |
set file(val) { | |
if (typeof val === 'string' && val.length !== 0) { | |
this.setAttribute('file', val); | |
} else { | |
this.removeAtttribute('file'); | |
} | |
} | |
get gist() { | |
return this.getAttribute('gist'); | |
} | |
set gist(val) { | |
if (typeof val === 'string' && val.length !== 0) { | |
this.setAttribute('gist', val); | |
} else { | |
this.removeAtttribute('gist'); | |
} | |
} | |
get height() { | |
return parseInt(this.getAttribute('height')); | |
} | |
set height(val) { | |
if (Number.isSafeInteger(val) && val > 0) { | |
this.setAttribute('height', val); | |
} else { | |
this.removeAttribute('height'); | |
} | |
} | |
get loading() { | |
return this.getAttribute('loading') || 'eager'; | |
} | |
set loading(val) { | |
if (typeof val === 'string' && val.length !== 0) { | |
this.setAttribute('loading', val); | |
} else { | |
this.removeAttribute('val'); | |
} | |
} | |
get user() { | |
return this.getAttribute('user'); | |
} | |
set user(val) { | |
if (typeof val === 'string' && val.length !== 0) { | |
this.setAttribute('user', val); | |
} else { | |
this.removeAtttribute('user'); | |
} | |
} | |
get width() { | |
return parseInt(this.getAttribute('width')); | |
} | |
set width(val) { | |
if (Number.isSafeInteger(val) && val > 0) { | |
this.setAttribute('width', val); | |
} else { | |
this.removeAttribute('width'); | |
} | |
} | |
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<script src="https://cdn.kernvalley.us/components/github/gist.js" crossorigin="anonymous" referrerpolicy="no-referrer" defer=""></script> | |
<script type="module" src="https://cdn.kernvalley.us/components/github/user.js" crossorigin="anonymous" referrerpolicy="no-referrer"></script> | |
<style> | |
github-gist::part(embed) { | |
max-width: 900px; | |
margin-left: max(10px, calc(50% - 450px)); | |
margin-top: 20px; | |
width: calc(100% - 20px); | |
height: 400px; | |
} | |
</style> | |
<header> | |
<h1><code><github-gist></code> demo</h1> | |
</header> | |
<main> | |
<noscript>This demo requires JavaScript</noscript> | |
<blockquote>A demo of <code><github-gist></code> usage</blockquote> | |
<p>Here is a <a href="https://gist.github.com/shgysk8zer0/ea40deafd59d7e9f451457f0d0319580" rel="noopener noreferrer external">Gist</a> of all the code used to create this <a href="https://codepen.io/shgysk8zer0/full/jOGEJRj" rel="noopener noreferrer external">Pen.</a></p> | |
<h2>The HTML</h2> | |
<github-gist class="embed-html" user="shgysk8zer0" gist="ea40deafd59d7e9f451457f0d0319580" file="index.html" loading="lazy" width="900" height="400"> | |
<p>Your browser does not support <code>customElements.define()</code>, which is required for this demo.</p> | |
</github-gist> | |
<h2>The JavaScript</h2> | |
<github-gist class="embed-js" user="shgysk8zer0" gist="ea40deafd59d7e9f451457f0d0319580" file="gist.js" loading="lazy" width="900" height="400"> | |
</main> | |
<footer> | |
<hr /> | |
<b>By:</b><br /> | |
<github-user user="shgysk8zer0" loading="lazy"></github-user> | |
<github-user user="kernvalley" loading="lazy"></github-user> | |
</footer> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment