Comment manipuler le DOM en javascript ?

Si vous désirez plus de contenu francophone comme celui-ci, cliquer Follow ou suivez-moi sur Twitter

Qu'est ce que le DOM ?

DOM est l'acronyme pour "Document Object Model". C'est une représentation structurée d'un document html. Il permet à vore code javascript d'accéder aux éléments et styles html pour les manipuler.

Avec javascript, nous pouvons entre autre ajouter, retirer des éléments et également modifier le texte, les attributs HTML et même le style CSS.

Exemple de manipulation duDOM

<html>
  <body>
    <div class="message">
      Hello World
    </div>
    <input type="text" id="search" placeholder="search" />
  </body>
</html>

Dans ce document HTML, nous avons de nombreux éléments comme body, div, input, etc.

Ce document HTML et tous ses éléments peuvent être accessibles et manipulés par JS.

// Lire un élément du DOM 
const searchInput = document.querySelector('#search')
console.log(searchInput.placeHolder) // Search

Dans l'exemple précédent, JS utilise document.querySelector pour accéder à un élément DOM. L'élément DOM peut être sélectionné en fonction de nombreux critères.

Pour cette requête, la clé '#search' a été utilisée. Le symbole '#' indique à JS de rechercher dans les attributs id une clé correspondante.

document.querySelector('#search') n'a qu'un seul élément correspondant aux attributs d'identifiant :

<input type="text" id="search" placeholder="search" />

Une référence à cet élément est placée dans la variable searchInput.

const searchInput = document.querySelector('#search')

Une fois la référence définie, nous pouvons récupérer ou modifier tous les attributs d'élément.

searchInput.value = 'Hello World' // Will change input value to 'Hello World'

Un autre exemple sera de sélectionner un élément avec un nom de classe 'message'

<html>
  <body>
    <div class="message">
      Hello World
    </div>
    <input type="text" id="search" placeholder="search" />
  </body>
</html>

Dans ce document, un seul élément a une classe de message et c'est la première div.

L'élément peut être référencé à l'aide du document.querySelector. Mais cette fois, nous n'utiliserons pas le symbole # mais un point "." Le point indique à JS de rechercher une correspondance de nom de classe

const divMessage = document.querySelector('.message')
console.log(divMessage.textContent)) // Hello World
divMessage.textContent = 'Hi World' // Change le text pour Hi World

Que faire si je veux accéder tag "body" de mon document ?
Dans ce cas je peux utiliser :

const body = document.querySelector('body')

Nous commençons donc à voir un modèle. Lorsque nous voulons sélectionner un élément, nous utilisons document.querySelector. Cette méthode prend un argument et c'est le texte que nous recherchons. Ce texte peut avoir un préfixe qui spécifie JS où chercher.

// Pas de prefix = cherche pour un nom de tag 
document.querySelector('body')

// # prefix = chercher pour un attribut "id"
document.querySelector('#search')

// point (.) = cherche pour un nom de classe 
document.querySelector('.message')

Event Listener:
Que se passe-t-il si nous voulons que JS réagisse à un événement de clic ? Par exemple, comment changer un message à chaque clic sur un bouton ?

<html>
  <body>
    <div class="message">
      This is a message
    </div>
    <input type="text" id="inputMessage" placeholder="Enter a message" />
    <button id="btnChange">Change message</button>
    <script src="main.js"></script>
  </body>
</html>

Chaque fois qu'un bouton est cliqué dans le DOM, un événement est déclenché. Nous pouvons dire à JS d'écouter cet événement et de faire quelque chose lorsque le DOM déclenchera cet événement particulier.

// La première étape est de sélectionner l'élément "button"
const btnChange = document.querySelector('#btnChange')

// Deuxièmement nous créons un event listener pour chaque clic
btnChange.addEventListener('click', function() {
  // Cette fonction s'exécutera à chaque clic sur le bouton
  const inputMessage = document.querySelector('#inputMessage')
  const message = document.querySelector('.message')
  message.textContent = inputMessage.value
})

Que faire si nous voulons changer le message à chaque fois que l'input change. Ainsi, chaque frappe dans l'input mettra automatiquement à jour le message. Pas besoin d'utiliser le bouton.

Dans ce cas, nous écouterons un autre événement. L'input a un appel d'événement « entrée » qui est déclenché à chaque changement d'entrée. Nous pouvons même écouter cela et exécuter du code pour mettre à jour le message.

// Première étape, obtenir une référence au champ de saisie
const inputMessage = document.querySelector('#inputMessage')

// Créez ensuite un event listener pour l'événement de changement
inputMessage.addEventListener('input', function(e) {
  // Cette fonction s'exécutera à chaque fois que l'entrée changera
  const message = document.querySelector('.message')
  // e reference l'événement actuel
  // Target référence la source de l'élément événement (dans ce cas, le champ de saisie
  message.textContent = e.target.value
})

Événement global. Que diriez-vous d'un événement qui s'ajoute partout sur toute la page. Vous aimez faire un listening sur pression d'une touche ?
Vous pouvez utiliser document.addEventListener:

document.addEventListener('keydown', function(e) {
  if (e.key === 'Escape') {
    console.log('Escape key press')
  }
})

Changer le style d'élément DOM (CCS)
Par exemple, nous pouvons changer la couleur d'arrière-plan du document body

// Passer au fond vert clair
document.querySelector('body').style.backgroundColor = '#60b250' 
// Cacher un élément
document.querySelector('.message').style.display = 'none'
// Afficher un élément
document.querySelector('.message').style.display = 'block'

Selection multiple:
Que faire lorsque plusieurs éléments contiennent par exemple un nom de classe ".message" ?

<html>
  <body>
    <div class="message">
      This is a message
    </div>
    <div class="message">
      This is another message
    </div>
    <div class="message">
      This is last message
    </div>

  </body>
</html>

Si nous sélectionnons en utilisant:

devMessage = document.querySelector(.message)

Le querySelector ne retournera que la première occurrence.

Que dois-je faire si je veux sélectionner les 3 ?
Utiliser querySelectorAll:

divMessages = document.querySelectorAll('.message)

Pour accéder à chaque élément, nous pouvons boucler :

for (const element of divMessages) {
  console.log(element.textContent);
}
// or
divMessages.forEach((element) => console.log(element.textContent))

Modifier la liste des classes d'éléments :
Il est possible d'ajouter ou de supprimer une classe à un élément. Voici un exemple de div avec 2 classes.

<html>
  <body>
    <div class="message hidden">
      This is a message
    </div>
  </body>
</html>

On peut par exemple supprimer la classe cachée dans JS :

const divMessage = document.querySelector('.message')
divMessage.classList.remove('hidden')
// ou vous pouvez également ajouter une classe
divMessage.classList.add('hidden')

// Nous pouvons vérifier si un élément contient une classe spécifique
if (divMessage.classList.contains('hidden')) {
  // do something
}

29