DOM Tutorial
Tags: javascript, html, css, dom
Published: 2020-06-01 02:50:49

## What is DOM?

Document Object Model or DOM is an API to manipulate HTML and XML documents. DOM represents a document or HTML page as a tree of nodes. DOM allows to add, remove, and modify each nodes of trees effectively. 

According to DOM, a HTML page is a document which consist of multiple HTML tags where each tag is an object. Nested tags creates a tree like structure of nodes. These object can accessible using javascript and can be use to modify the document or HTML page.  

To understand the hierarchy of nodes, consider this HTML document below: 

```html
<html>
    <head>
        <title>JavaScript DOM</title>
    </head>
    <body>
        <p>Hello DOM!</p>
    </body>
</html>
```

The following tree represents the above HTML document: 

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/4rfp2kpurukzq6nvzl4l.png)

As you see that `Document` is a root node and everything else is a child node. DOM is all about child-parent relationship between nodes. In the HTML page, <HTML> is a root node and then <head> and <body> are its children nodes.

The text inside these element forms <i>text nodes</i> and are labelled as #text. Here is the example of text nodes:

```html
<HTML>
<head>
<title>About elk</title>
</head>
<body>The truth about elk.
</body>
</html>
```
Here is the structure
```
HTML
   HEAD
      TITLE
         #text About elk
   BODY
      #text The truth about elk.
```
To summarize, the Document Object Model (DOM) is a cross-platform and language independent interface that treats an XML or HTML document as a tree structure wherein each node is an object representing a part of the document. The DOM represents a document with a logical tree. 

## Selecting elements

In this section, I will show you how you can select different types elements on the document or HTML page. 

### getElementById()

The getElementById() is a method of a document object. It lets you select the HTML tag based on specific id on the document. A document or HTML page can only one id with a same name which means id element is unique. Id is also case-sensitive, which means 'hello' and 'Hello' are two different ids. Therefore, it is easy to retrieve element using getElementById() method. 

Syntax of getElementById():

```js
const element = document.getElementById(id);
```

Example of getElementById():

HTML document:

```html
<html>
    <head>
        <title>getElementById()</title>
    </head>
    <body>
        <div class="container">
           <p id="hello">Hello from Sukhbir</p>
        </div>
    </body>
</html>
```
Let's retrieve paragraph element with id of `hello`.

```js
const helloMessage = document.getElementById(`hello`);
console.log(helloMessage);
```

Output:
```html
<p id="hello">Hello from Sukhbir</p>
```

Let's check out the real world example. 

Scenario: Extract text `Sukhbir Sekhon` from the document below:

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/zq5mn3gzxbscksob72te.png)

First thing first, right-click on desired text and look for id upn that element. 

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/koinlzcf3f9g4u0apx4a.png)

So id=`nameHeading`. Move onto the console and extract the h2 element from the document with id=`nameHeading`. Then we can use special method called innerHTML() to extract the #text from the element node. 

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/2n6vup1e3chjlpnck627.png)

innerHTML allows you to pull out the #text inside the element. 

### getElementsByName()

Elements on an HTML document can have a `name` attribute. Unline the id attribute, multiple element can share the same value of the name attribute.

Syntax for getElementByName():

```js
const elements = document.getElementsByName(name);
```

`elements` would return a node list with multiple elements with a same name attribute. 

Let's check out a real work example.

Scenario: Obtain project names from each of project cards which has name attribute to be `projectName`

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/migoft0rwvtvsc11r6wm.png)

There is total of 7 project cards. Let's move to the console panel and retrieve project name of each project cards.

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/lj0hlx1lt00jw1hb4cp5.png)

I created a variable to store the node list of 7 node elements.

Now let's see how we can retrieve text from specific node element. 

![Alt Text](https://dev-to-uploads.s3.amazonaws.com/i/n63vnedcbv3ptn3txvlb.png)

Since `projects` contains list, therefore, we can easily access each element just like in array list and then call innerHTML method on it to extract #text. 

### getElementsByTagName()

The getElementsByTagName() method accepts a tag name and returns a live HTMLCollection of elements with the matching tag name in the order which they appear in the document.

Syntax of getElementsByTagName():

```js
const elements = document.getElementsByTagName(tagName);
```

How to use it?

Let's say if we want to extract all the elements with a tag of `h1`. You can do that like this:

```js
const h1 = document.getElementsByTagName(`h1`);
```
The return collection of the getElementsByTagName() is live, meaning that it is automatically updated when elements with the matching tag name are added and/or removed from the document.

### getElementsByClassName()

The getElementsByClassName() method is available on the document object and any HTML element. The getElementsByClassName() method accepts a single argument, which is a string that contains one or more class names:

```js
const elements = document.getElementsByClassName(classNames);
```

In this syntax, the classNames parameter is a string that represents a class name or a list of comma-separated class names to match.

The getElementsByClassName() method returns a live HTMLCollection of elements.

If you call the getElementsByClassName() method on the document object, the method searches for elements with the specified class names in the whole document.

However, when you call the getElementsByClassName() method on a specific element, it returns only matching elements in the subtree of the element.

### querySelector

The querySelector() is a method of the Element interface. The querySelector() allows you to find the first element, which is a descendant of the parent element on which it is invoked, that matches a CSS selector or a group of CSS selectors.

Besides the querySelector(), you can use the querySelectorAll() method to find all elements that match a CSS selector or a group of CSS selector.

Examples of querySelector() and querySelectorAll()

- Finds first h1 element in the document:

```js
const firstHeading = document.querySelector(`h1`);
```

- Finds all h1 elements in the document:

```js
const heading1 = document.querySelectorAll(`h1`);
```

- Finds first element with a hello-world class name:

```js
const hello = document.querySelector(`.hello-world`);
```

- Finds all the elements with a hello-world class name:

```js
const hellos = document.querySelectorAll(`.hello-world`);
```

- Finds first element with a id of menu:

```js
const menu = document.querySelector(`#menu`);
```

- Finds all the element with a id of menu:

```js
const menus = document.querySelectorAll(`#menu`);
```

- Finds the first element with a attribute `autoplay` with any value:

```js
const autoplay = document.querySelector(`[autoplay]`);
```

- Find the first `<a>` element inside p element:

```js
const a = document.querySelector(`p a`);
```

- Find the first `li` element that are directly inside a <ul> element:

```js
const list = document.querySelector(`ul > li`);
```

- Find all the `li` element that are directly inside a <ul> element:

```js
const lists = document.querySelectorAll(`ul >li`);
```

- Select all list items that are directly inside <ul> element with class nav:

```js
const lists = document.querySelectorAll(`ul.nav > li`);
```

- Find all the links or `<a>` elements that have been visited:

```js
const visitedLogs = document.querySelectorAll(`a:visited`);
```


## Conclusion

The Document Object Model (DOM) is a way to manipulate HTML document or pages. There are a lot of implications for this API. For example, you can perform web scrapping using third party APIs such as cheerio. Cheerio allows you to call HTML page and parse HTML document and manipulate it. You can create a alert system for your favorite product that is currently unavailable on amazon. You can create an app that will always run on the background and monitor the particular URL for the product that is currently unavailable on amazon and as soon as the div element of availability changes, the app will send an email or text message to you and will alert you that your favorite item is now available on amazon. Its just one of countless examples how you can use DOM in your application. 

Tell me your experiences with DOM in a comment section! Looking forward to hear your stories. :)