Zum Inhalt springen

Shadow DOM und Events

Willkommen zu unserem Leitfaden zum Meistern der Ereignisbehandlung im Shadow DOM. Dieses Tutorial behandelt wesentliche Konzepte wie Event-Bubbling, event.composedPath(), event.composed und benutzerdefinierte Events. Am Ende werden Sie verstehen, wie Sie Events effektiv innerhalb von Shadow DOM-Komponenten verwalten können.

Event-Bubbling im Shadow DOM

Event-Bubbling ist ein grundlegender Mechanismus in JavaScript, der beschreibt, wie Events durch die DOM-Hierarchie propagieren. Wenn ein Event auf einem DOM-Element ausgelöst wird, werden zunächst die an diesem Element angehängten Event-Handler aufgerufen. Anschließend breitet es sich zu den übergeordneten Elementen aus und löst deren Handler nacheinander aus.

Im Kontext des Shadow DOM verhält sich Event-Bubbling jedoch etwas anders. Standardmäßig sind die meisten nativen Events (wie click oder mouseover) composed und breiten sich über die Shadow-Grenze hinweg aus. Einige Events (wie focus oder scroll) sind jedoch nicht composed und bleiben im Shadow DOM enthalten. Benutzerdefinierte Events erfordern eine explizite Konfiguration, um die Grenze zu überschreiten. Um die Propagation an jeder Stelle vollständig zu stoppen, können Sie event.stopPropagation() verwenden.

Verwendung von event.composedPath()

Die Methode event.composedPath() bietet eine Möglichkeit, die Reihenfolge der DOM-Elemente abzurufen, die ein Event während seiner Propagation durchläuft, einschließlich Elemente innerhalb des Shadow DOM. Diese Methode gibt ein Array von DOM-Knoten zurück, das den Pfad des Events darstellt, sodass Entwickler den Propagationsfluss untersuchen und manipulieren können.

Veranschaulichen wir, wie event.composedPath() zur Verfolgung der Event-Propagation innerhalb des Shadow DOM verwendet werden kann:


html
<div id="outer"></div>
<script>
  const outer = document.getElementById('outer');
  const shadow = outer.attachShadow({ mode: 'open' });
  const inner = document.createElement('div');
  inner.textContent = 'Click me';

  inner.addEventListener('click', event => {
    const composedInfo = document.createElement('p');
    composedInfo.textContent = 'The event composedPath contains the following elements:';
    shadow.appendChild(composedInfo);
    const path = event.composedPath();
    path.forEach((e) => {
      const pathItem = document.createElement('p');
      pathItem.textContent = e.tagName;
      shadow.appendChild(pathItem);
    });
  });

  shadow.appendChild(inner);
</script>

In diesem Beispiel löst ein Klick auf das innere <div> den daran angehängten Click-Event-Handler aus. Wir erstellen dynamisch einige <p>-Elemente, um die Antwort von event.composedPath() innerhalb des Shadow DOM anzuzeigen.

Verständnis von event.composed

Die Eigenschaft event.composed zeigt an, ob ein Event composed ist oder nicht. Composed-Events können Shadow-Grenzen überschreiten, während nicht-composed-Events innerhalb der Shadow-Grenze verbleiben. Beachten Sie, dass event.composed eine schreibgeschützte Eigenschaft ist. Dies ist insbesondere bei der Arbeit mit benutzerdefinierten Events nützlich, die in ihren Optionen composed: true benötigen, um Shadow-Grenzen zu überschreiten, im Gegensatz zu nativen Events wie click, die standardmäßig composed sind.

Untersuchen wir, wie event.composed in der Praxis genutzt werden kann:


html
<div id="outer"></div>

<script>
  const outer = document.getElementById('outer');
  const shadow = outer.attachShadow({ mode: 'open' });
  const button = document.createElement('button');
  button.textContent = 'Click me';

  button.addEventListener('click', event => {
    const composedInfo = document.createElement('p');
    composedInfo.textContent = `Composed: ${event.composed}`;
    shadow.appendChild(composedInfo);
  });

  shadow.appendChild(button);
</script>

In diesem Beispiel löst ein Klick auf die Schaltfläche innerhalb des Shadow DOM ein Click-Event aus. Wir erstellen dynamisch ein <p>-Element, um die Eigenschaft event.composed innerhalb des Shadow DOM anzuzeigen.

Benutzerdefinierte Events im Shadow DOM

Benutzerdefinierte Events ermöglichen es Entwicklern, eigene Event-Typen zu definieren und auszulösen, was einen flexiblen Mechanismus für die Kommunikation zwischen Komponenten bietet. Bei der Arbeit mit Shadow DOM können benutzerdefinierte Events genutzt werden, um die Kommunikation zwischen Shadow- und Light-DOM-Elementen zu erleichtern und so eine nahtlose Interaktion innerhalb der Webanwendung zu ermöglichen.

Erstellen und lösen wir ein benutzerdefiniertes Event innerhalb eines Shadow DOM aus:


html
<div id="container"></div>

<script>
  const container = document.getElementById('container');
  const shadow = container.attachShadow({ mode: 'open' });
  const button = document.createElement('button');
  button.textContent = 'Click me';

  button.addEventListener('click', () => {
    const event = new CustomEvent('customEvent', { bubbles: true, composed: true });
    button.dispatchEvent(event);
  });

  shadow.appendChild(button);

  container.addEventListener('customEvent', () => {
    const composedInfo = document.createElement('p');
    composedInfo.textContent = `Custom Event Triggered!`;
    container.appendChild(composedInfo);
  });
</script>

In diesem Beispiel löst ein Klick auf die Schaltfläche innerhalb des Shadow DOM ein benutzerdefiniertes Event namens customEvent mit den Optionen bubbles: true und composed: true aus, wodurch es sich über Shadow-Grenzen hinweg ausbreiten kann. Der Event-Listener ist an das Host-Element (container) im Light DOM angehängt, was zeigt, wie das Event die Shadow-Grenze überschreitet und den Handler auslöst.

Fazit

Das Beherrschen der Ereignisbehandlung im Shadow DOM ist entscheidend für den Aufbau robuster Webanwendungen. Durch das Verständnis von Event-Bubbling, event.composedPath(), event.composed und benutzerdefinierten Events können Sie die Event-Propagation effektiv verwalten und eine nahtlose Kommunikation zwischen Komponenten ermöglichen. Experimentieren Sie weiter mit diesen Beispielen, um sich in der ereignisgesteuerten Programmierung innerhalb des Shadow DOM zu vervollkommnen.

Practice

Welche Methode bietet eine Möglichkeit, die Reihenfolge der DOM-Elemente abzurufen, die ein Event während seiner Propagation durchläuft?

Finden Sie das nützlich?

Dual-run-Vorschau — vergleichen Sie mit den Symfony-Routen live.