This is the 29th day of my participation in the August Gwen Challenge.

Web Components

Web Components are a different set of technologies that allow you to create reusable custom elements whose functionality is encapsulated outside of your code and use them in your Web applications.

Concepts and Usage

As developers, we all know it’s a good idea to reuse as much code as possible. This is often not so easy for custom tag structures — think of complex HTML (and associated styles and scripts), sometimes you have to write code to render custom UI controls, and using them multiple times can mess up your pages if you’re not careful.

Web Components aims to solve these problems — it consists of three main techniques that can be used together to create custom elements that encapsulate functionality and can be reused anywhere you like without worrying about code conflicts.

  • Custom Elements: A set of JavaScript apis that allow you to define Custom elements and their behavior, and then use them as needed in your user interface.
  • Shadow DOM: A set of JavaScript apis for attaching a wrapped “Shadow” DOM tree to an element (rendered separately from the main document DOM) and controlling its associated functionality. This way, you can keep the functionality of elements private so that they can be scripted and styled without fear of running afoul of the rest of the document.
  • HTML Templates (HTML templates) : The

The basic approach to implementing a Web Component is usually as follows:

  1. Create a class or function to specify the functionality of a Web component. If you use classes, use ECMAScript 2015’s class syntax (see Classes for more information).
  2. Using CustomElementRegistry. Define () method to register your new custom element, and transfer to define the elements to its name, specify the element function class, as well as its inherited from optional elements.
  3. If necessary, attach a shadow DOM to the custom Element using the element.attachShadow () method. Add child elements, event listeners, and so on to the Shadow DOM using the usual DOM methods.
  4. If necessary, define an HTML template using
  5. Use custom elements wherever you like on the page, just as you would use regular HTML elements.

In actual combat

Now let’s create a Web Components button component that will pop up with a message Hello World! .

The browser provides a customElements.define() method that allows usto define a custom element and its behavior and then use it in the page.

class CustomButton extends HTMLElement {
    constructor() {
        // The super method must be called first
        super(a)// The function code of the element is written here
        const templateContent = document.getElementById('custom-button').content
        const shadowRoot = this.attachShadow({ mode: 'open' })

        shadowRoot.appendChild(templateContent.cloneNode(true))

        shadowRoot.querySelector('button').onclick = () = > {
            alert('Hello World! ')}}connectedCallback() {
        console.log('connected')
    }
}

customElements.define('custom-button', CustomButton)
Copy the code

The above code registers a new element using the customElements.define() method and passes it the element name custom-button, the class CustomButton that specifies the element’s functionality. We can then use this in the page:

<custom-button></custom-button>
Copy the code

This custom element inherits from HTMLElement (the HTMLElement interface represents all HTML elements), indicating that the custom element has the characteristics of an HTML element.

#use<template>Sets the custom element content

<template id="custom-button">
    <button>Custom button</button>
    <style>
        button {
            display: inline-block;
            line-height: 1;
            white-space: nowrap;
            cursor: pointer;
            text-align: center;
            box-sizing: border-box;
            outline: none;
            margin: 0;
            transition:.1s;
            font-weight: 500;
            padding: 12px 20px;
            font-size: 14px;
            border-radius: 4px;
            color: #fff;
            background-color: #409eff;
            border-color: #409eff;
            border: 0;
        }

        button:active {
            background: #3a8ee6;
            border-color: #3a8ee6;
            color: #fff;
        }
      </style>
</template>
Copy the code

As you can see from the code above, we set the content and the style for this custom element, in the

#Shadow DOM

With the name, content, and style of the custom element set, the last step is to mount the content and style onto the custom element.

// The function code of the element is written here
const templateContent = document.getElementById('custom-button').content
const shadowRoot = this.attachShadow({ mode: 'open' })

shadowRoot.appendChild(templateContent.cloneNode(true))

shadowRoot.querySelector('button').onclick = () = > {
    alert('Hello World! ')}Copy the code

The element has a attachShadow() method in the function code, which attaches the shadow DOM to the custom element. DOM, we know what it means, is a page element. So what does “shadow” mean? “Shadow” means that DOM functionality attached to a custom element is private and does not conflict with other elements on the page.

The attachShadow() method also has a mode parameter, which has two values:

  1. openRepresents that the shadow DOM can be accessed externally.
  2. closedThe shadow DOM cannot be accessed externally.
// open, return to shadowRoot
document.querySelector('custom-button').shadowRoot
// closed, returns null
document.querySelector('custom-button').shadowRoot
Copy the code

#The life cycle

Custom elements have four life cycles:

  1. connectedCallback: called when the custom element is first connected to the document DOM.
  2. disconnectedCallback: called when a custom element is disconnected from the document DOM.
  3. adoptedCallback: called when a custom element is moved to a new document.
  4. attributeChangedCallback: called when an attribute of a custom element is added, removed, or changed.

The lifecycle automatically invokes the corresponding callback function when triggered, such as the connectedCallback() hook in this example.

Finally, attach the complete code:

<! DOCTYPEhtml>
<html>
<head>
    <meta charset="utf-8">
    <title>Web Components</title>
</head>
<body>
    <custom-button></custom-button>

    <template id="custom-button">
        <button>Custom button</button>
        <style>
            button {
                display: inline-block;
                line-height: 1;
                white-space: nowrap;
                cursor: pointer;
                text-align: center;
                box-sizing: border-box;
                outline: none;
                margin: 0;
                transition:.1s;
                font-weight: 500;
                padding: 12px 20px;
                font-size: 14px;
                border-radius: 4px;
                color: #fff;
                background-color: #409eff;
                border-color: #409eff;
                border: 0;
            }

            button:active {
                background: #3a8ee6;
                border-color: #3a8ee6;
                color: #fff;
            }
          </style>
    </template>

    <script>
        class CustomButton extends HTMLElement {
            constructor() {
                // The super method must be called first
                super(a)// The function code of the element is written here
                const templateContent = document.getElementById('custom-button').content
                const shadowRoot = this.attachShadow({ mode: 'open' })

                shadowRoot.appendChild(templateContent.cloneNode(true))

                shadowRoot.querySelector('button').onclick = () = > {
                    alert('Hello World! ')}}connectedCallback() {
                console.log('connected')
            }
        }

        customElements.define('custom-button', CustomButton)
    </script>
</body>
</html>
Copy the code

summary

Those of you who have used Vue may notice that the Web Components standard is very similar to Vue

If you want to learn more about Web Components, refer to the MDN documentation (Opens New Window).