Explorer un tableau HTML avec des interfaces DOM et JavaScript

par 3 contributeurs :

Introduction

Cet article propose une vue d'ensemble de certaines méthodes DOM Level 1 fondamentales et la façon de les utiliser depuis JavaScript. Vous y apprendrez à créer, accéder, contrôler, et supprimer dynamiquement des éléments HTML. Les méthodes DOM décrites ne sont pas spécifiques au HTML et s'appliquent également au XML. Les exemples fonctionneront dans tous les navigateurs offrant le support complet du DOM niveau 1, ce qui est le cas de tous les navigateurs basés sur Mozilla comme Firefox ou Netscape. Les morceaux de code de ce document fonctionneront également dans Internet Explorer 5.

Les méthodes décrites ici font partie de la spécification Document Object Model level 1 (Core). DOM level 1 comprend des méthodes destinées à l'accès et à la manipulation des documents (DOM 1 core) ainsi que des méthodes spécifiques aux documents HTML (DOM 1 HTML).

Vue d'ensemble de Exemple1.html

Cet article est une introduction au DOM à travers des exemples de code. Pour vous lancer, testez le code HTML suivant. Il emploie des méthodes DOM level 1 depuis JavaScript pour créer dynamiquement un tableau HTML à quatre cellules, chacune contenant le texte « la cellule est ligne x colonne y », indiquant ainsi sa position dans le tableau.

<html>
<head>
<title>Code de démonstration - Explorer un tableau HTML avec des interfaces DOM et JavaScript</title>
<script>
    function start() {
        // récupère une référence vers l'élément body
        var body = document.getElementsByTagName("body")[0];

        // crée un élément <table> et un élément <tbody>
        table     = document.createElement("table");
        tablebody = document.createElement("tbody");

        // création des cellules
        for(var j = 0; j < 2; j++) {
            // crée une ligne de tableau
            var row = document.createElement("tr");
            
            for(var i = 0; i < 2; i++) {
                // Crée un élément <td> et un nœud texte, place le nœud texte
                // comme contenu texte de l'élément <td> et le place à la fin
                // de la ligne du tableau
                cell = document.createElement("td");
                texte = document.createTextNode("la cellule est ligne "+j+", colonne "+i);
                cell.appendChild(texte);
                row.appendChild(cell);
            }
            // ajoute la ligne à la fin du corps du tableau
            tablebody.appendChild(row);
        }
        // place <tbody> dans l'élément <table>
        table.appendChild(tablebody);
        // ajoute <table> à l'élément <body>
        body.appendChild(table);
        // définit l'attribut border du tableau à 2
        table.setAttribute("border", "2");
    }
</script></head>
<body onload="start()">
</body>
</html>

Remarquez l'ordre dans lequel les éléments et le nœud texte sont créés :

  1. On crée d'abord l'élément <table>.
  2. Ensuite, l'élément <tbody> qui est un enfant de l'élément <table>.
  3. Puis, grâce à une boucle, on crée les éléments <tr>, qui sont des enfants de l'élément <tbody>.
  4. Pour chaque élément <tr>, on emploie une boucle pour créer les éléments enfants <td>.
  5. Enfin pour chaque élément <td>, on crée le nœud texte contenant le texte de la cellule du tableau.

Après avoir créé les éléments <table>, <tbody>, <tr>, <td> et le nœud texte, on ajoute chaque objet à son parent dans l'ordre inverse :

  1. On attache d'abord chaque nœud texte à son élément parent <td> en utilisant
    cell.appendChild(texte);
  2. Ensuite, on lie chaque élément <td> à son élément <tr> parent avec
    row.appendChild(cell);
  3. Puis chaque <tr> à son parent <tbody> avec
    tablebody.appendChild(row);
  4. Puis l'élément <tbody> est attaché à son élément parent <table> grace à
    table.appendChild(tablebody);
  5. Enfin, <table> est rattaché à <body> avec
    body.appendChild(table);

Souvenez-vous de cette technique, vous l'utiliserez souvent en programmant pour le DOM W3C. On crée d'abord les éléments du haut vers le bas, puis on attache les enfants aux parents dans l'ordre inverse.

Voici l'HTML généré par ce code JavaScript :

...
<table border="2">
<tr><td>la cellule est ligne 0 colonne 0</td><td>la cellule est ligne 0 colonne 1</td></tr>
<tr><td>la cellule est ligne 1 colonne 0</td><td>la cellule est ligne 1 colonne 1</td></tr>
</table>
...

Voici l'arborescence objet DOM créée par le code, pour l'élément TABLE et ses enfants :

Image:sample1-tabledom.jpg

Vous pouvez construire ce tableau ainsi que ses éléments enfants internes en utilisant juste quelques méthodes DOM. Conservez à l'esprit le modèle en arbre des structures que vous comptez créer, cela rendra plus facile l'écriture du code nécessaire. Dans l'arbre <table> de la figure 1, l'élément <table> a un enfant, l'élément <tbody>, qui lui-même a deux enfants <tr>, qui à leur tour ont chacun un enfant <td>. Enfin, chacun de ces éléments <td> a un enfant, un nœud texte.

Méthodes DOM fondamentales - Exemple2.html

getElementsByTagName est à la fois une méthode de l'interface Document et de l'interface Element. Par conséquent, tant l'objet document racine que l'ensemble des objets Element possèdent la méthode getElementByTagName. Pour obtenir la liste des enfants d'un élément en les sélectionnant par les noms de leurs balises, vous pouvez employer element.getElementsByTagName(tagname).

getElementsByTagName renvoie une liste des éléments enfants qui ont le nom de balise spécifié. Dans cette liste d'éléments enfants, vous pouvez atteindre un élément en particulier en appelant la méthode item avec un indice indiquant le numéro de l'élément que vous désirez récupérer. La numérotation commence à zéro pour le premier élément. C'est simple, mais cela demande un peu d'attention lorsque vous travaillez sur de grosses structures. Au prochain paragraphe nous continuerons à travailler avec l'exemple du tableau, mais dans l'immédiat nous utilisons un exemple plus simple, pour illustrer quelques méthodes de base :

<html>
<head>
<title>Code de démonstration - Explorer un tableau HTML avec des interfaces DOM et JavaScript</title>
<script>
    function start() {
        // récupère une liste de tous les éléments body (il n'y en aura qu'un),
        // et sélectionne le premier (indice 0) de ces éléments
        body = document.getElementsByTagName("body")[0];

        // à présent, trouve tous les éléments p enfants de cet élément body
        bodyElements = body.getElementsByTagName("p");

        // récupère le second élément de cette liste d'éléments p
        myP = bodyElements[1];
    }
</script>
</head>
<body onload="start()">
<p>hi</p>
<p>hello</p>
</body>
</html>

Dans cet exemple, on assigne à la variable myP l'objet DOM du second élément p du corps (body).

  1. On récupère d'abord une liste de tous les éléments body avec
    body = document.getElementsByTagName("body")[0]
    Puisqu'il n'existe qu'un seul élément body dans un document HTML valide, cette liste ne comporte qu'un élément, que l'on récupère en sélectionnant le premier élément de la liste grace à [0].
  2. Ensuite, on récupère tous les éléments p qui sont des enfants de body en utilisant
    bodyElements = body.getElementsByTagName("p");
  3. Pour finir on prend le deuxième élément de la liste des éléments p avec
    myP = bodyElements[1];

Image:sample2a2.jpg

Une fois que vous avez l'objet DOM pour un élément HTML, vous pouvez modifier ses propriétés. Si par exemple vous voulez définir la propriété couleur d'arrière-plan du style, ajoutez simplement :

myP.style.background = "rgb(255,0,0)";
// ajoute une propriété de style inline

Création de nœuds texte avec document.createTextNode("..")

Employez l'objet document pour appeler la méthode createTextNode et créer un nœud texte. Il suffit de lui communiquer le contenu texte, et la valeur renvoyée est un objet représentant le nœud texte.

noeudTexte = document.createTextNode("world");

Ce morceau de code crée un nœud de type TEXT_NODE qui contient la donnée texte "world", et monNoeudTexte est la référence de l'objet nœud créé. Pour afficher ce texte sur votre page HTML, vous devez ensuite définir ce nœud texte comme l'enfant d'un autre élément nœud.

Insertion d'éléments avec appendChild(...)

En invoquant myP.appendChild([element_nœud)], vous définissez element_nœud comme un nouvel enfant du second élément p (myP a été défini plus haut comme étant le second élément p).

myP.appendChild(noeudTexte);

En exécutant cet exemple, vous pouvez remarquer que les mots « hello » et « world » ne sont pas séparés : helloworld. Quand vous parcourez la page HTML les deux nœuds semblent donc n'en former qu'un seul, rappelez-vous cependant qu'ils sont bien distincts dans le modèle de document. Le second nœud est de type TEXT_NODE, et est le second enfant de la seconde balise <p>. Le schéma suivant situe ce nouvel objet dans l'arborescence du document :

Image:sample2b2.jpg

L'utilisation de createTextNode et de appendChild permet aisément d'ajouter un espace entre ces deux mots. Notez cependant que la méthode appendChild ajoute le nouvel enfant à la suite de ceux déjà présents, à la manière de « world » placé après « hello ». Pour ajouter un nœud texte entre « hello » et « world » (par exemple un espace), utilisez insertBefore à la place de appendChild.

Création de nouveaux éléments avec l'objet document et la méthode createElement(...)

Vous pouvez créer de nouveaux éléments, dont des éléments HTML, avec createElement. Pour créer un élément <p> enfant de l'élément <body>, vous pouvez vous servir de body défini dans l'exemple précédent et lui greffer un nouvel élément nœud. Pour ce faire, invoquez document.createElement("nombalise"). Voici un exemple :

nouveauNoeudBALISEP = document.createElement("p");
body.appendChild(nouveauNoeudBALISEP);

Image:sample2c.jpg

Suppression de nœuds avec la méthode removeChild(...)

Tous les nœuds peuvent être supprimés. La ligne ci-dessous supprime de myP (deuxième élément <p>) le nœud texte contenant le mot « world » :

myP.removeChild(noeudTexte);

Vous pouvez ensuite ajouter monNoeudTexte (contenant "world") dans l'élément <p> récemment créé :

nouveauNoeudBALISEP.appendChild(noeudTexte);

L'arborescence des objets se présente désormais comme ceci :

Image:sample2d.jpg

Création dynamique d'un tableau (Exemple1.html)

Jusqu'à la fin de cet article, nous travaillons de nouveau sur Exemple1.html. Le schéma qui suit vous rappelle la structure de l'arbre des objets pour le tableau créé dans l'exemple.

Rappel de la structure arborescente d'un tableau HTML

Image:sample1-tabledom.jpg

Création et insertion des éléments dans l'arborescence

On peut décomposer la création du tableau de Exemple1.html en trois étapes :

  • Récupérer l'objet body (c'est le premier élément de l'objet document).
  • Créer tous les éléments.
  • Greffer chaque enfant sur son parent en respectant la structure du tableau (cf. le schéma ci-dessus).

Le code source qui suit est un exemple commenté qui crée le tableau de Exemple1.

Il y a une ligne de code supplémentaire à la fin de la fonction start(), qui définit la propriété bordure du tableau en employant la méthode setAttribute. setAttribute utilise deux arguments : le nom de l'attribut et sa valeur, et permet de définir n'importe quelle propriété de n'importe quel élément.
<head>
<title>Code de démonstration - Explorer un tableau HTML avec des interfaces DOM et JavaScript</title>
<script>
    function start() {
        // récupère une référence vers l'élément body
        var body = document.getElementsByTagName("body")[0];

        // création des éléments <table> et <tbody>
        table     = document.createElement("table");
        tablebody = document.createElement("tbody");

        // création des cellules
        for(var j = 0; j < 2; j++) {
            // création d'un élément <tr>
            row = document.createElement("tr");

            for(var i = 0; i < 2; i++) {
                // création d'un élément <td>
                cell = document.createElement("td");
                // création d'un nœud texte
                texte = document.createTextNode("la cellule est ligne " + j + ", colonne " + i);
                // ajoute le nœud texte créé à la cellule <td>
                cell.appendChild(texte);
                // ajoute la cellule <td> à la ligne <tr>
                row.appendChild(cell);
            }
            // ajoute la ligne <tr> à l'élément <tbody>
            tablebody.appendChild(row);
        }

        // ajoute <tbody> à l'élément <table>
        table.appendChild(tablebody);
        // ajoute <table> à l'élément <body>
        body.appendChild(table);
        // définit l'attribut border de table à 2;
        table.setAttribute("border", "2");
    }
</script>
</head>
<body onload="start()">
</body>
</html>

Manipulation du tableau avec DOM et CSS

Récupérer un nœud texte dans le tableau

Cet exemple présente deux nouveaux attributs DOM. D'abord, l'attribut childNodes qui est utilisé pour récupérer la liste des nœuds enfants de cel. A la différence de getElementsByTagName, la liste renvoyée par childNodes comporte tous les enfants sans considération de type. Une fois la liste obtenue, la méthode [x] est employée pour sélectionner l'élément enfant désiré. Dans cet exemple, le nœud texte de la seconde cellule de la seconde ligne du tableau est enregistré dans celtext. Ensuite, un nouveau nœud texte contenant les données de celtext est greffé en tant qu'enfant sur l'élément <body>.

Si l'objet est un nœud texte, vous pouvez récupérer le texte qu'il contient en employant l'attribut data.
body      = document.getElementsByTagName("body")[0];
table     = body.getElementsByTagName("table")[0];
tablebody = table.getElementsByTagName("tbody")[0];
row       = tablebody.getElementsByTagName("tr")[1];
cel       = row.getElementsByTagName("td")[1];

// premier élément de la liste childNodes de cel
celtext = cel.childNodes[0];

// le contenu de text est le contenu des données de celtext
text = document.createTextNode(celtext.data);
body.appendChild(currenttext);

Récupérer la valeur d'un attribut

A la fin d'Exemple1, l'appel à setAttribute sur l'objet table définit la propriété border du tableau. Si vous désirez simplement récupérez la valeur de cet attribut, vous pouvez employer la méthode getAttribute :

table.getAttribute("border");

Cacher une colonne en changeant les propriétés de style

Une fois que vous avez l'objet dans une variable JavaScript, vous pouvez définir les propriétés directement. Le code qui suit est une version modifiée de Exemple1.html où les cellules de la seconde colonne sont cachées, et le fond de celles de la première colonne est rouge. Remarquez que la propriété de style y est définie directement.


<html>
<body onload="start()">
</body>
<script>
    function start() {
       var body  = document.getElementsByTagName("body")[0];
       table     = document.createElement("table");
       tablebody = document.createElement("tbody");

       for(var j = 0; j < 2; j++) {
           row = document.createElement("tr");
           for(var i = 0; i < 2; i++) {
               cell = document.createElement("td");
               text = document.createTextNode("la cellule est :" + i + j);
               cell.appendChild(text);
               row.appendChild(cell);
               // change la couleur de fond de la cellule
               // si la colonne est 0. Si la colonne est 1, cache la cellule
               if (i == 0) {
                   cell.style.background = "rgb(255,0,0)";
               } else {
                   cell.style.display = "none";
               }
           }
           tablebody.appendChild(row);
       }
       table.appendChild(tablebody);
       body.appendChild(table);
    }
</script>
</html>


Interwiki

Étiquettes et contributeurs liés au document

Étiquettes : 
Contributeurs à cette page : BenoitL, Mgjbot, Planche
Dernière mise à jour par : BenoitL,