Ever wondered how custom HTML elements function in modern frameworks such as React, Angular, Vue, and more? In this series, I'll explain how they work and even demonstrate how to replicate their behavior without using any frameworks. All you need is HTML and vanilla JavaScript. And don't worry, we'll cover styling in the next episode. Stay tuned!
A custom HTML element, also known as a Web Component, is a self-defined tag in HTML that extends the browser's built-in elements. It lets developers create custom functionality and behavior encapsulated within a single tag. These elements can be reused across projects, making code more maintainable and scalable without being tied to specific frameworks or libraries. Web Components aim to enhance web development by providing a standardized way to create and share reusable components.
How Custom HTML Elements Work:
Custom HTML elements, or Web Components, leverage the Shadow DOM and the Custom Elements API to function effectively.
Shadow DOM: The Shadow DOM allows encapsulation by creating a hidden DOM subtree within a custom element. This isolation prevents styles and scripts from leaking in or out, ensuring that the component's internal structure and styling do not interfere with the rest of the page.
Custom Elements API: This API enables developers to define new custom elements and their behavior. By using the
customElements.define()
method, developers can register a new tag name along with its corresponding class constructor. This association allows the browser to recognize and instantiate the custom element whenever it appears in the HTML code.
Once registered, developers can define the custom element's lifecycle callbacks, such as connectedCallback()
and disconnectedCallback()
, to handle element insertion and removal events. Additionally, custom elements can have their own properties, attributes, and methods to manage their behavior.
By combining the Shadow DOM and the Custom Elements API, developers can create reusable and encapsulated components with custom functionality, unleashing the potential of Web Components in modern web development. We'll talk about Shadow DOM later, so let's get started!
Creating a New Project Folder and Opening Your Preferred Code Editor:
To begin, initiate a fresh folder for our project. Next, navigate to the folder using your file explorer and open your preferred code editor. This will serve as the starting point for our development journey.
After setting up the project folder and launching your favorite code editor, proceed to create two files named index.html
and app.js
. These files will serve as the foundation for our project, enabling us to build and structure the web application effectively.
Here's our index.html
file should look like:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Custom HTML Elements</title>
<script src="app.js" type="module"></script>
</head>
<body>
</body>
</html>
If you notice I declare the type of the script as module
because I want to import all of the Custom HTML Elements there.
And here's how our app.js
file should look like for a starter:
const app = () => {
console.log('DOM Content Loaded')
}
document.addEventListener('DOMContentLoaded', app)
In this file, we will import all of our custom HTML elements and load them only when the DOMContentLoaded
event occurs.
Let's get started with creating the new folder and organizing our custom HTML elements.
Step 1: Create a new folder in the project root directory. We'll call it components
or anything that suits you.
Step 2: Inside the components
folder, create another folder called hello-world
.
Step 3: Within the hello-world
folder, create the necessary JS files.
Once you've completed these steps, your project structure should look like this:
- project-root
- components
- hello-world
- hello-world.js
Let's take a look at hello-world.js
, it's empty, right? Now let's write some code.
class HelloWorld extends HTMLElement {
constructor() {
super();
}
connectedCallback() {
this.innerHTML = "<p>hello world</p>";
}
}
customElements.define("hello-world", HelloWorld);
With this code, we've defined a class HelloWorld
that extends HTMLElement
. Inside the constructor, we call super()
to ensure proper inheritance. Then, in the connectedCallback
method, we set the inner HTML of the custom element to <p>hello world</p>
.
Now, when you include the hello-world.js
script in your HTML file and use the custom element <hello-world>
, it will render the "hello world" message as specified in the connectedCallback
method.
Your index.html
file should look like this:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Custom HTML Elements</title>
<script src="app.js" type="module"></script>
</head>
<body>
<hello-world></hello-world>
<script src="components/hello-world/hello-world.js"></script>
</body>
</html>
And that's it! We've had a blast exploring the basics of web components and how to create our very own custom element from scratch, all without any frameworks!
But guess what? We're just getting started! In my next blog series, I'm thrilled to take you on a journey to the land of dynamic components. π We'll learn how to make our web components interactive and data-driven, giving them superpowers to create even cooler and more flexible web applications.
So, grab your coding gear and get ready for some serious fun! Stay tuned for the upcoming blog series, where we'll dive into the exciting world of dynamic web components. Until then, happy coding, and I'll catch you in the next installment! π
Top comments (4)
JSFiddles (jsfiddle.net) can be embed in Dev.To pages, live code really enhances these explanations
Thanks for the input! I already did it in my GitHub, but I'll try with JSFiddles and might update the post later. β€οΈ
Great article!
Is
app.js
only being used to show the order of elements loading?Thanks, but in the current approach I intend to show the basic way of using it. In the next series I will demonstrate the usage of
app.js
so stay tuned!