Shadow DOM: eventos, target y bubbling.
Tags: javascript, customelements, shadowdom
Published: 2019-07-01 19:51:33

👉 Para mejor entendimiento del presente artículo, es necesario entender lo que significa [bubbling](https://stackoverflow.com/questions/4616694/what-is-event-bubbling-and-capturing) en JavaScript.

---

La idea detrás del Shadow DOM es el encapsulamiento. No es tan distinto, en lo que a objetivos se refiere, a algunos patrones de diseño y/o técnicas de abstracción.

Cuando hablamos de encapsulamiento generalmente nos referimos a datos e información que deseamos se mantenga en un ambiente protegido, sin poder ser accedida fuera de este. Shadow DOM encapsula datos: _DOM Tree_, estilos y código JavaScript, pero también encapsula otra cosa: **eventos**.

## Eventos en el Shadow DOM

Los eventos que ocurren dentro del Shadow DOM tienen su ciclo de vida solo dentro de este. Es decir, si un botón dentro de un Shadow DOM dispara un evento 'click', el efecto _bubbling_ taladrará por el árbol DOM hasta llegar al `host`, el cual es el _custom element_ en sí. Una vez que llega allí, no podrá avanzar hacia fuera (light DOM). Es decir: el `host` **es el techo** de un evento. Sin embargo, se nos da una "versión" del evento original, versión que omite partes importantes, como el **origen del evento**.

Veamos cómo funciona con un ejemplo. En el siguiente ejemplo tenemos un elemento `fancy-button`, el cual es un _custom element_ que contiene un botón con algunos estilos. Si añadimos un listener para el evento `click` sobre este elemento y obtenemos el _target_, obtendremos el elemento mismo.

Pruébalo y abran la consola de CodeSandbox para ver el resultado:

{% codesandbox shadow-dom-events-vz4gh %}

Aquí podemos observar claramente que el _bubbling_ del evento tiene como "techo" al host mismo; por ende, **el light DOM** está completamente inconsciente de los eventos que se originan allí.

Pero, ¿qué pasa cuando necesitamos acceder al _target_ real?

## 🚀 Bubbling, `composed` y `composedPath`:

Algunos eventos (que implementan la interfaz [Event](https://developer.mozilla.org/en-US/docs/Web/API/Event)) tienen una propiedad _booleana_ llamada [`composed`](https://developer.mozilla.org/en-US/docs/Web/API/Event/composed), la cual indica si en el payload del evento se podrá acceder a toda la cadena bubbling del evento incluso fuera del Shadow DOM.

> Todos los eventos que son disparados por elementos UI (click, paste, change, etc.) tienen esta propiedad en `true` por defecto.

Cuando esta propiedad está en `true`, se armará un array con todos los elementos por los cuales ha burbujeado el evento. Para acceder a dicho array lo hacemos mediante el método [`composedPath`](https://developer.mozilla.org/en-US/docs/Web/API/Event/composedPath).

Veamos el mismo ejemplo anterior, pero esta vez, accediendo al primer elemento del array que viene a ser el primer elemento en donde se originó el evento. Lo desactivaremos durante 1.5 segundos y luego lo activaremos nuevamente.

{% codesandbox shadow-dom-events-composed-pnpvo %}

---

Espero hayan encontrado entretenido este tutorial y, sobre todo, que hayan aprendiendo algo nuevo. Si les gustó, no olviden compartir  😉

¡Nos vemos en la próxima!