Finding Elements

Knowing how to traverse the DOM is a great tool to have. It gives you a way to navigate the jungle, but it is only good when you have a map, i.e. you know what the content of the DOM is supposed to be. Trying to locate a particular item in the DOM is very difficult by using the relationship properties alone. Luckily, we have a few methods that we can use to find elements we want.

getElementsByTagName

The most basic one is getElementsByTagName. It accepts a string for the element tag you want to find. It is available in any node objects and will use the node object it is called on as the root of the search. Calling document.getElementsByTagName('p') will return an array like object containing all the p elements in the document. This array like object is called a HTMLCollection, similar to NodeList, you can access individual values using bracket notation, but it doesn't have array properties such as slice.

<!doctype html>
<html>
  <head>
    <title>My title</title>
  </head>
  <body>
    <h1>A heading</h1>
    <a href="www.altcademy.com">Link text</a>
    <p>Hello World!</p>
    <p>Another paragraph</p>
    <div>
      <p>Paragraph inside div</p>
    </div>
  </body>
</html>

There are 3 paragraph elements in the document, 2 of them direct children of body and 1 is nested inside a div element.

var allParagraphs = document.getElementsByTagName('p');
console.log(allParagraphs.length);
// -> 3

var div = document.getElementsByTagName('div')[0];
var divParagraphs = div.getElementsByTagName('p');
console.log(divParagraphs.length);
// -> 1

Try it on Repl.

To get all 3 paragraphs, we use getElementsByTagName on the document object. To only get the paragraph in div, we need to first get the div node from document, then use getElementsByTagName on the div node. Notice when we get the div element from document, we had to add a bracket notation at the end [0]. As we mentioned, getElementsByTagName returns an array like object called HTMLCollection and we want the first div node.

getElementsByClassName

If we want to be a bit more precise as to the elements we want to get, we can target them by their classnames. getElementsByClassName will return a HTMLCollection of child elements which have all of the given class names.

<!doctype html>
<html>
  <head>
    <title>My title</title>
  </head>
  <body>
    <h1>A heading</h1>
    <a href="www.altcademy.com">Link text</a>
    <p>Hello World!</p>
    <p class="note">Note</p>
    <div>
      <p class="note">Note inside div</p>
      <p class="green note">Green Note inside div</p>
    </div>
  </body>
</html>
var allNotes = document.getElementsByClassName('note');
console.log(allNotes.length);
// -> 3

var divNotes = document.getElementsByTagName('div')[0].getElementsByClassName('note');
console.log(divNotes.length);
// -> 2

var greenNote = document.getElementsByClassName('green note');
console.log(greenNote.length);
// -> 1

Try it on Repl.

You can target elements with multiple classnames by separating each classname with a space. It will return matching elements that contain all those classnames only.

getElementById

To find just one particular element in the DOM, you can use the getElementById method. Since one unique ID can only be used once on a HTML page, JavaScript expects there to be either none or just one element that returns from the getElementById method. The return value is an element object or null.

<!doctype html>
<html>
  <head>
    <title>My title</title>
  </head>
  <body>
    <h1>A heading</h1>
    <a href="www.altcademy.com">Link text</a>
    <p>Hello World!</p>
    <p class="note">Note</p>
    <div>
      <p class="note" id="note1">Note 1</p>
      <p class="green note" id="note2">Note 2</p>
    </div>
  </body>
</html>
var note1 = document.getElementById('note1');
console.log(note1.childNodes[0].nodeValue);
// -> Note 1

var note2 = document.getElementById('note2');
console.log(note2.childNodes[0].nodeValue);
// -> Note 2

Try it on Repl.

If two or more elements in your DOM use the same ID, although I hope you are not doing that, only the first matching element will be returned.

One thing to note about HTMLCollection is that it is live, it automatically updates when the DOM is changed. In other words, when you get a bunch of paragraphs from var paragraphs = document.getElementsByTagName('p'), you don't have to do this again if the DOM content has changed. The nodes inside paragraphs will always reflect the current information that is projected on the browser screen.

results matching ""

    No results matching ""