02 Apr

Esto es una referncia de las funciones principales que podemos usar para manipular el DOM desde JavaScript, sin usar frameworks ni librerías externas.

Para una introducción más completa en forma de tutorial puedes ir a MDN.

¿Qué es el DOM?

El DOM da una representación del documento como un grupo de nodos y objetos estructurados que tienen propiedades y métodos. En resumen, es la representación de la página web en la memoria del navegador, a la que podemos acceder a través de JavaScript. El DOM es un árbol donde cada nodo es un objeto con todas sus propiedades y métodos que nos permiten modificarlo. Estas son algunas funciones que nos permiten acceder y modificar los elmentos del DOM:

Acceso a elementos del DOM

// Obtiene un elemento por id
document.getElementById('someid');

// Obtinee una lista con los elementos que tienen esa clase
document.getElementsByClassName('someclass');

// Obtiene una HTMLCollection con los todos los elementos 'li'
document.getElementsByTagName('LI');

// Devuelve el primer elemento del documento que cumpla la selección (la notación es como en CSS)
document.querySelector('.someclass');

// Devuelve una lista de elementos que cumplen con la selección (notación como en CSS)
document.querySelectorAll('div.note, div.alert');

Acceder a hijos/padres de un elemento

// Obtener los hijos de un elemento
var elem = document.getElementById('someid');
var hijos = elem.childNodes;

// Su nodo padre
var padre = elem.parentNode;

Crear nuevos elementos en el DOM

// Para crear elementos llamamos a createElement con el nombre del elemento
var nuevoH1 = document.createElement('h1');
var nuevoParrafo = document.createElement('p');

// Crear nodos de texto para un elemento
var textoH1 = document.createTextNode('Hola mundo!');
var textoParrafo = document.createTextNode('lorem ipsum...');

// Añadir el texto a los elementos
nuevoH1.appendChild(textoH1);
nuevoParrafo.appendChild(textoParrafo);

// también podemos asignar directamente el valor a la propiedad innerHTML
nuevoH1.innerHTML = textoH1
nuevoParrafo.innerHTML = textoParrafo

// los elementos estarían listos para añadirlos al DOM, ahora mismo solo existen en memoria, pero no serán visibles hasta que no los añadamos a un elemento del DOM

Añadir elementos al DOM

// seleccionamos un elemento
var cabecera = document.getElementById('cabecera');

// Añadir elementos hijos a un elemento
cabecera.appendChild(nuevoH1);
cabecera.appendChild(nuevoParrafo);

// También podemos añadir elementos ANTES del elemento seleccionado

// Tomamos el padre
var padre = cabecera.parentNode;

// Insertamos el h1 antes de la cabecera
padre.insertBefore(nuevoH1, cabecera);

También podemos añadir directamente un trozo de HTML antes o después de un elemento del DOM, supongamos que tenemos estos elementos en la página:

<div id='box1'>  <p>aquí algo de texto</p>
</div>
<div id='box2'>  <p>otro parrafo bla bla bla</p>
</div>

Podemos hacer:

var box2 = document.getElementById('box2');
box2.insertAdjacentHTML('beforebegin', '<div><p>un parrafo nuevo.</p></div>');

// beforebegin - El nuevo HTML es insertado justo antes del elemento, a la misma altura (hermano).
// afterbegin - El nuevo HTML se inserta dentro del elemento, antes del primer hijo.
// beforeend - El nuevo HTML se inserta dentro del elemento, después del último hijo.
// afterend - El nuevo HTML es insertado justo después del elemento, a la misma altura (hermano).

Añadir/eliminar/modificar Clases

// Tomamos un elemento
var cabecera = document.getElementById('cabecera');

// elimina una clase del elemento
cabecera.classList.remove('foo');

// Añade una clase si no existe
cabecera.classList.add('otra');

// añade o elimina varias clases a la vez
cabecera.classList.add('foo', 'bar');
cabecera.classList.remove('foo', 'bar');

// Si la clase existe la elimina, si no existe, la crea
cabecera.classList.toggle('visible');

// Devuelve true si el elemento contiene esa clase
cabecera.classList.contains('foo');

Manipulando los estilos de los elementos

Como se ha visto, los atributos que le son asignados a las etiquetas HTML están disponibles como propiedades de sus correspondientes nodos en el DOM. Las propiedades de estilo pueden ser aplicadas a través del DOM.

Cada atributo CSS posee una propiedad del DOM equivalente, formándose con el mismo nombre del atributo CSS pero sin los guiones y llevando la primera letra de las palabras a mayúsculas. Véase el siguiente ejemplo para mayor entendimiento donde se utiliza un atributo CSS modelo:

algun-atributo-css 

Tendrá como equivalente la siguiente propiedad o método en Javascript:

algunAtributoCss

Por tanto, para cambiar el atributo CSS font-family de un elemento, podría realizarse de lo siguiente:

ancla.style.fontFamily = 'sans-serif'; 

Los valores CSS en Javascript serán en su mayoría del tipo cadena; por ejemplo: font-size, pues posee dimensiones tales como “px”, “%”. Sólo los atributos completamente numéricos, tales como z-index serán del tipo entero.

En muchos casos es necesario aparecer y desaparecer un determinado elemento, para ellos se utiliza el atributo CSS display, por ejemplo, para desaparecer:

ancla.style.display = 'none'; 

Luego para volverlo a mostrar se le asigna otro valor:

ancla.style.display = 'inline'; 

Ejemplo: Adjuntar múltiples ficheros a la vez

Este es el primer ejemplo completo donde se propone utilizar la manipulación del DOM mediante javascript con el objetivo de adicionar tantos elementos input del tipo file como tantos ficheros se deseen subir al servidor.

Se muestra una versión simplificada del problema limitada tan sólo al lado del cliente. Para ello es necesario imaginarse un sistema en línea donde se suben ficheros al servidor, ejemplo de ello podría ser una aplicación de correo electrónico.

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd"> <html> <head> <title>Ejemplo para adjuntar múltiples ficheros</title> <script language="javascript" type="text/javascript"> function nuevoFichero() { var input = document.getElementsByTagName("input")[0]; var nuevoInput = input.cloneNode(true); input.parentNode.appendChild(nuevoInput); }
</script> </head> <body> <form action="upload.php" method="post" enctype="multipart/form-data"> <fieldset><legend>Adjuntar múltiples ficheros</legend> <input name="ficheros[]" type="file" size="60" > </fieldset> <a href="javascript: nuevoFichero();">Adjuntar otro fichero</a>    <input name="Subir" type="submit" value="Adjuntar" > </form> </body> </html>

El enlace para adjuntar otro fichero hace una llamada a la función nuevoFichero() realizándose las siguientes tareas en la misma:

Se accede al primer elemento input encontrado en el documento:

var input = document.getElementsByTagName("input")[0]; 
  • Se crea un nuevo elemento input referenciado por la variable nuevoInput utilizando el método cloneNode resultando un elemento idéntico al primero:
var nuevoInput = input.cloneNode(true); 
  • Aquí se accede al nodo padre del elemento input mediante el método parentNode y la vez se inserta un nuevo elemento hijo copia del primero por medio del método appendChild:
input.parentNode.appendChild(nuevoInput); 

Es de notar que en este ejemplo podría haberse usado el evento clic para la llamada de la función, si embargo se dejó reservado para cuando el tema de la manipulación de eventos del DOM sea abordado.

Ejemplo: Mostrador de diapositivas

Este ejemplo contempla un mostrador de diapositivas (en este caso imágenes). Se tienen dos enlaces, uno mostrar la diapositiva siguiente y otro para mostrar la diapositiva anterior. Una posible aplicación práctica podría ser en una galería de fotos.

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" 
"http://www.w3.org/TR/html4/strict.dtd"> <html> <head> <title>Ejemplo de un mostrador de diapositivas</title> <script type="text/javascript"> var contador = 0; var diapositivas = []; function inicio() { var contenedor = document.getElementById("diapositivas"); while (contenedor.childNodes.length > 0){ if (contenedor.getElementsByTagName("img")[0]==contenedor.firstChild){ diapositivas[diapositivas.length] = contenedor.removeChild(contenedor .firstChild); }
else contenedor.removeChild(contenedor.firstChild); }
} function adelante() { contador++; if (contador >= diapositivas.length) contador = 0; ponerImagen() }
function atras() { contador--; if (contador < 0 ) contador = diapositivas.length - 1; ponerImagen(); } function ponerImagen() { var contenedor = document.getElementById("diapositivas"); if (contenedor.childNodes.length==0) contenedor.appendChild(diapositivas[contador]); else contenedor.replaceChild(diapositivas[contador], contenedor.childNodes[0]); }
</script> </head> <body> <a href="javascript: atras();">Atrás</a> <span id="diapositivas"> <img src="diapositiva1.jpg" alt="Diapositiva 1" height="100" width="200"> <img src="diapositiva2.jpg" alt="Diapositiva 2" height="100" width="200"> <img src="diapositiva3.jpg" alt="Diapositiva 3" height="100" width="200"> </span> <a href="javascript: adelante();">Adelante</a> </body> </html> <script type="text/javascript"> inicio(); ponerImagen(); </script> 

Este ejemplo se analizará de manera abreviada dejando un análisis detallado por parte del lector. Se tiene dos variables globales, contador y diapositivas, la primera para indicar la diapositiva que se está mostrando actualmente y la última para almacenar en un arreglo el conjunto de diapositivas a mostrar.

La función inicio() remueve todos elementos img y los almacena. Es de notar que todo nodo hijo del nodo con id diapositivas parásito (ejemplo: salto de línea) es eliminado para evitar un mal funcionamiento posterior.

Por otro lado la función ponerImagen() se encarga de colocar la imagen apuntada por el contador en el contenedor de diapositivas. Mientras que las funciones atras() y adelante() se encargan de decrementar e incrementar el contador respectivamente.

Publicado por:  Luján Mora Sergio.

Fecha de Publicación: 18/09/2013

Bibliografía

Luján S. (2013). Lenguajes y Sistemas Informáticos .Universidad de Alicante. 

Recuperado de: https://rua.ua.es/dspace/bitstream/10045/31303/1/idesweb-prac6-dom.pdf 


Comentarios
* No se publicará la dirección de correo electrónico en el sitio web.
ESTE SITIO FUE CONSTRUIDO USANDO