0% found this document useful (0 votes)
539 views

Webcomponents Cheatsheet 2021

This document provides a cheat sheet summarizing key concepts and APIs for web components including: 1. Template elements, slots, shadow DOM, custom elements, and component lifecycle hooks for defining web components. 2. Attribute observation, shadow DOM, styling components, and custom events for building out component functionality. 3. Modern DOM APIs like querySelector and closest for searching and manipulating the DOM, and the LitElement/LitHTML libraries for simplifying component templating.

Uploaded by

cesar javier
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
539 views

Webcomponents Cheatsheet 2021

This document provides a cheat sheet summarizing key concepts and APIs for web components including: 1. Template elements, slots, shadow DOM, custom elements, and component lifecycle hooks for defining web components. 2. Attribute observation, shadow DOM, styling components, and custom events for building out component functionality. 3. Modern DOM APIs like querySelector and closest for searching and manipulating the DOM, and the LitElement/LitHTML libraries for simplifying component templating.

Uploaded by

cesar javier
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 2

CHEAT SHEET

WEB COMPONENTS
Created by @Manz ( https://twitter.com/Manz ) https://lenguajejs.com/

T Template Inert document fragment ES S Slots External slots


HTML TAG ES SIMPLE SLOT

<template> inert tag for html content ES <slot> external html to inside component
<template shadowroot="open"> <slot>��slot>
#DOCUMENT-FRAGMENT declarative
shadow dom C Custom Elements HTML Components NAMED SLOT
<div>...��div> <slot name="text"> multiple html to inside
HTML STRUCTURE
��template>
<prefix-component> custom html tag <slot name="title">��slot>
API TEMPLATE HTMLTemplateElement

DF .content ref to document fragment node <base-name attribute="value"> CSS HTMLTemplateElement

SR .shadowRoot shadow dom root node <div>content��div> SHADOW DOM ::slotted(selector) style to slotted tags
<div>content��div> LIGHT DOM EVENTS HTMLTemplateElement

D DOM HTML Access DOM manipulation ��base-name> slotchange detect slot-element changes
API HTML CLASS API JS PROPERTIES & METHODS <base-name>
s .innerHTML get/replace HTML markup o constructor() initial method super() <h2 slot="title">Default��h2>
s .outerHTML idem (includes HTML tag) public() public properties/methods <p slot="description">Text��p>
s .textContent get/replace text content #private() private properties/methods ��base-name>
MULTIPLE SLOT SIMPLE SLOT
element.innerHTML = `<div>text��div>`; class BaseName extends HTMLElement {
CREATE HTML / ADD ELEMENT ... C CSS in WebComponents Styles (CSS)
e document .createElement(tag) create node } CSS WITHOUT SHADOW DOM GLOBAL CSS
customElements.define("base-name",BaseName) connectedCallback() {
document.createElement("div"); COMPONENT LIFECYCLE HOOKS WHEN? this.innerHTML = `
connectedCallback() added to DOM <style>p { color: red; }��style>
o .appendChild(child) add inside element `;
disconnectedCallback() remove from DOM
element.appendChild(node); adoptedCallback() move to new doc. }
CSS WITH SHADOW DOM LOCAL CSS
INSERT HTML / ELEMENT class BaseName extends HTMLElement {
constructor() { connectedCallback() {
.insertAdjacentHTML(pos, html) add super(); this.shadowRoot.innerHTML = `
el.insertAdjacentHTML("afterend", ... don't forget <style>p { color: red; }��style>
} super() on `;
`<div><p>Content��p>��div>`); constructor
connectedCallback() { ... } }
disconnectedCallback() { ... }
.insertAdjacentElement(pos, node) CSS CONTAINER
adoptedCallback() { ... }
el.insertAdjacentElement("afterend", node); } :host style custom element (container)
customElements.define("base-name", BaseName) :host(selector) idem, if match container
beforebegin afterend ATTRIBUTE OBSERVATION :host-context(selector) idem, ancestor
html tag
<div> text ��div> position to a get observedAttributes() notify changes CSS PARTS
insert
attributeChangedCallback(attr, old, now) <span part="name"> define part
afterbegin beforeend
class BaseName extends HTMLElement {
<span part="name">��span>
F Find HTML Elements DOM search static get observedAttributes() {
return ["name1", "name2"]; ::part(selector) style surface parts
TRADITIONAL DOM SEARCH API
}
o document .getElementById(id)find by #id attributeChangedCallback(name, old, now){ S Shadow DOM .shadowRoot (DOM isolate)
a .getElementsByName(name) name attr ... fire this callback when a WEBCOMPONENT WITHOUT SHADOW DOM
} observed attribute changes
a .getElementsByClassName(class) .class } class BaseName extends HTMLElement {
a .getElementsByTagName(tag) html tag customElements.define("base-name", BaseName) constructor() {
document.getElementById("name"); CUSTOM ELEMENTS REGISTRY GLOBAL REGISTRY super();
this.innerHTML = `<div>��div>`;
MODERN DOM SEARCH API customElements .define(name, class) reg
}
o customElements .get(name) register elem
o .querySelector(selector) return first elem }
customElements .upgrade(node) update el.
a .querySelectorAll(selector) ret all elems WEBCOMPONENT WITH SHADOW DOM
p customElements .whenDefined(name) fire.
o .closest(selector) return closest ancestor s .attachShadow(options) add shadow dom
b .matches(selector) matches with elem? C Custom Events Send/Receive events SHADOW DOM OPTIONS
document.querySelector(".menu > p"); CUSTOM EVENTS API
s mode encapsulation mode open closed
HTML ATTRIBUTE API b .dispatchEvent(event) send event b delegatesFocus shadow get focus false
b .hasAttributes() element w/attributes? CUSTOM EVENT OBJECT
class BaseName extends HTMLElement {
s .getAttributeNames() return attrs array o .detail data object with information constructor() {
b .hasAttribute(name) check attribute b .bubbles bubbles up through the DOM super();
s .getAttribute(name) return value attr b .composed send across shadow DOM this.attachShadow({ mode: "open" });
.removeAttribute(name) delete attribute this.shadowRoot.innerHTML = `<p>��p>`;
const event = new CustomEvent("message", {
}
.setAttribute(name, value) modify attr detail: { ... },
}
b .toggleAttribute(name, force) add/del bubbles: true,
composed: true
element.setAttribute("name", "value"); });
CHEAT SHEET

LIT-ELEMENT/LIT-HTML lit-html
Created by @Manz ( https://twitter.com/Manz ) https://lenguajejs.com/

T Templates Next-gen lit-html templates C Component Lit-Element web component P Properties Properties != Attributes
SETUP & CONFIGURATION SETUP & CONFIGURATION PROPERTIES DECLARATION SYNTAX

<script type="module"> <script type="module"> static get properties() {


import { html, render } from "..."; import { LitElement, html } from "..." return {
��script> ��script> prop1: { type: String, ... },
LIT-HTML SIMPLE TEMPLATES DEFINE COMPONENT LIT-ELEMENT
prop2: { type: Boolean, ... }
}
TR html`code` create HTML template class BaseName extends LitElement {
}
render`template, element` update page ...
PROPERTIES OPTIONS
}
const tpl = html`<div>Hello��div>`; customElements.define("base-name", BaseName) o type hint for convert between props/attr
render(tpl, document.body); BASIC LIFECYCLE HOOKS WHEN? o converter custom func or object props/attr
LIT-HTML DYNAMIC TEMPLATES
update(props) reflect prop to attr & render f fromAttribute(value, type) convert to prop
TR html`code, ...values` template with data if override, super.update(props) or no render f toAttribute(value, type) convert to attr
render`template(val), element` update TR render() use lit-html to render template f hasChanged(now, old) true=requestUpdate
b attribute associate prop with a attribute
const p = (t) �� html`<p>${t}��p>`; class BaseName extends LitElement {
render(tpl("Text"), document.body); constructor() { b noAccessor avoid generate def. accesor
super(); b reflect autoset prop value to attribute
HELPERS (BIND) ...
<tag value=${var}> string attribute } don't forget
connectedCallback() { call super on S Styling CSS in Components
<tag ? disabled=${var}> boolean attribute super.connectedCallback();
parent hooks
SETUP & CONFIGURATION
<tag . value=${obj.value}> bind object value }
<script type="module">
<tag @ event=${func}> bind event to func. update() { ... }
render() { import { ..., html, css } from "..."
CONDITIONALS (TERNARY) / NESTED TEMPLATES
html`<div>Component �div>`; ��script>
html`${user.logged } STYLES IN COMPONENTS ALL INSTANCES
? html`Welcome ${user.name}` }
customElements.define("base-name", BaseName) var(--name) set css variable from in/out
: "User not logged in" nothing
}`;
ADVANCED LIFECYCLE HOOKS WHEN? ${var} set javascript variable
LOOPS
p requestUpdate() manually start an update CR unsafeCSS(css) set unsafe css code
MAP LOOP p requestUpdate(propName, old) prop setter static get styles() {
--theme: ...
html`<ul>${ performUpdate() microtask after ev.loop return css`
arr.map(item �� html`<li>${item}��li>`) b shouldUpdate(props) update proceed :host { color: var(--theme) }
}��ul>`; firstUpdate(props) called on first update div { color: red } css`...`
ARRAY LOOP
updated(props) DOM updated & rendered button { color: ${bgColor} }
for (const item of items) { `;
p .updateComplete true=no pending updates
arr.push(html`<li>${item}��li>`); } return [super.styles, css`...`, css`...`]
} shouldUpdate
html`<ul>${arr}��ul>`; el.prop = "..." hasChanged STYLES IN COMPONENTS SPECIFIC INSTANCES
update
D Directives render() {
lit-html/directives/name.js render
performUpdate requestUpdate return html`
DIRECTIVES
firstUpdate <style>
TR asyncAppend(iterable) async add data resolve updateComplete div { color: red }
asyncReplace(iterable) async change data updated
TR ��style>
TR cache(code) cache DOM for a bind/input S Shadow DOM By default, uses ShadowDOM <div>Hello!��div>
o nothing render a empty text node LITELEMENT WITHOUT SHADOW DOM `;
o ifDefined(value) set value, else no-op class BaseName extends LitElement { }
o guard(deps, func) render func on change createRenderRoot() {
return this; D CSS Directives lit-html/directives/name.js
o live(value) update value (outside lit-html) } CLASSMAP
TR repeat(items, keyfn, tpl) repeat template }
import { classMap } from "...";
REPEAT DIRECTIVE
D Decorators Typescript or Babel needed const classes = { selected : true };
import { repeat } from "..."; DECORATORS const result = html`
html`<ul>${repeat(items, <div class=${classMap(classes)}>
(items) �� items.id, import { customElement, property } ...
Content
(item) �� html`<li>${item.name}��li>`)}
��ul>`; @customElement("base-name") ��div>
class BaseName extends LitElement { `;
TR templateContent(tag) render <template>
@property() STYLEMAP
TR unsafeHTML(html) render unsafe code prop1 = "value"; import { styleMap } from "...";
TR unsafeSVG(svg) render unsafe svg code prop2 = "value"; const styles = { color : "red" };
TR until(...values) render w/priority (1=more) ... const result = html`
UNTIL DIRECTIVE render() { <div style=${styleMap(styles)}>
import { until } from "..."; html`<div>Component��div>`; Content
html`${until(fetchPromise, } ��div>
html`<p>Loading...��p>` )}`; } `;

https://unpkg.com/lit-element?module https://cdn.skypack.dev/lit-element
https://unpkg.com/lit-html/directives/class-map.js?module https://cdn.skypack.dev/lit-html/directives/class-map.js

You might also like