Start · Sprachen · JavaScript · Referenz · Selection.containsNode()

Selection.containsNode()

Methode

Prüft, ob ein bestimmter Knoten ganz oder (optional) teilweise in der aktuellen Textauswahl des Benutzers liegt.

seit JavaScript Baseline: alle modernen Browser (seit 2020 weitgeh Kategorie: webapi

Signatur

Selection.prototype.containsNode(node, allowPartialContainment)

Beschreibung

Die Methode containsNode() des Selection-Objekts prüft, ob ein bestimmter DOM-Knoten Teil der aktuellen Auswahl ist. Das Selection-Objekt bekommst du über window.getSelection() oder document.getSelection(). Nützlich ist die Methode etwa für Rich-Text-Editoren, Kommentar- und Markierungsfunktionen oder Werkzeugleisten, die nur erscheinen sollen, wenn bestimmte Elemente markiert sind.

Standardmäßig (allowPartialContainment = false) liefert die Methode nur dann true, wenn der Knoten vollständig in der Auswahl liegt. Übergibst du true als zweites Argument, reicht es, wenn die Auswahl den Knoten teilweise berührt, zum Beispiel wenn nur ein paar Wörter eines Absatzes markiert sind.

Die Prüfung bezieht sich auf alle Bereiche (Range) der Auswahl. In der Praxis unterstützen die meisten Browser nur einen einzigen Bereich. Ist die Auswahl leer (rangeCount === 0), gibt die Methode immer false zurück.

Parameter

Name Typ Default Beschreibung
$node Pflicht Node Der Knoten, der geprüft werden soll, z. B. ein Element oder ein Textknoten.
$allowPartialContainment boolean false Bei true ergibt die Prüfung auch dann true, wenn der Knoten nur teilweise ausgewählt ist. Bei false muss er vollständig in der Auswahl liegen.

Beispiele

Vollständige und teilweise Auswahl vergleichen

// HTML: <p id="absatz">Hallo <strong id="wort">Welt</strong>, schön hier.</p>
const absatz = document.getElementById('absatz');
const wort = document.getElementById('wort');

// Nur „Welt“ auswählen (per Programm)
const range = document.createRange();
range.selectNodeContents(wort);
const selection = window.getSelection();
selection.removeAllRanges();
selection.addRange(range);

console.log(selection.containsNode(absatz));        // Absatz vollständig?
console.log(selection.containsNode(absatz, true));  // Absatz teilweise?
false true

Hinweis anzeigen, wenn ein geschützter Bereich markiert wird

const geheim = document.querySelector('.vertraulich');
const hinweis = document.querySelector('#hinweis');

document.addEventListener('selectionchange', () => {
  const selection = document.getSelection();
  const betroffen = selection.rangeCount > 0 && selection.containsNode(geheim, true);
  hinweis.hidden = !betroffen;
});

Alle markierten Listeneinträge ermitteln

// Liste mit <li>-Einträgen, der Benutzer markiert mehrere davon mit der Maus
const holeMarkierteEintraege = () => {
  const selection = window.getSelection();
  return [...document.querySelectorAll('#aufgaben li')]
    .filter((li) => selection.containsNode(li, true))
    .map((li) => li.textContent.trim());
};

document.querySelector('#kopieren').addEventListener('click', () => {
  console.log(holeMarkierteEintraege());
});
["Einkaufen", "Wäsche waschen"]

// Wichtig · Fallstricke

  • Ohne zweites Argument gilt vollständige Enthaltenheit. Ein häufiger Fehler ist, true für teilweise markierte Elemente zu erwarten.
  • Mit selectNodeContents() ausgewählte Inhalte schließen den Elternknoten selbst nicht vollständig ein. containsNode(element) kann dann false liefern, obwohl der gesamte Text markiert ist. Verwende in diesem Fall allowPartialContainment = true oder prüfe die Kindknoten.
  • Auswahlen in <input> und <textarea> lassen sich damit nicht erkennen. Nutze dafür selectionStart und selectionEnd.
  • Inhalte im Shadow DOM werden je nach Browser unterschiedlich behandelt. Die Unterstützung von getComposedRanges() ist noch uneinheitlich.
  • Ältere Safari-Versionen haben den Parameter allowPartialContainment verlangt. Gib ihn deshalb am besten immer ausdrücklich an.
  • Das Ereignis selectionchange kann sehr oft ausgelöst werden. Teure Prüfungen über viele Knoten solltest du drosseln (Throttling oder Debouncing).