Signatur
Beschreibung
splitText() teilt einen Textknoten an der Stelle offset (gezählt in UTF-16-Codeeinheiten). Der ursprüngliche Knoten behält den Text vor der Trennstelle. Der Rest landet in einem neu erzeugten Text-Knoten, der direkt hinter dem Original als nächster Geschwisterknoten in den Baum eingefügt wird.
Gebraucht wird die Methode vor allem dann, wenn man einen Teil eines Textes mit einem Element umschließen will, ohne innerHTML neu zu schreiben, z. B. beim Hervorheben von Suchtreffern, beim Einfügen von Links oder Markierungen oder beim Aufbau eigener Rich-Text-Editoren. Weil die vorhandenen Knoten erhalten bleiben, gehen Ereignis-Listener, Referenzen und der Zustand benachbarter Elemente nicht verloren.
Ist der Knoten nicht im Dokument eingehängt (hat also kein Elternelement), wird der neue Knoten zwar erzeugt und zurückgegeben, aber nirgendwo eingefügt. Aktive Range-Objekte, die in den geteilten Knoten zeigen, passt der Browser automatisch an.
Parameter
| Name | Typ | Default | Beschreibung |
|---|---|---|---|
| $offset Pflicht | number | Position, an der geteilt wird, als Index in UTF-16-Codeeinheiten (0 bis length). Der Text ab dieser Position wandert in den neuen Knoten. |
Rückgabewert
Text-Knoten mit dem Text ab offset. Der ursprüngliche Knoten enthält danach nur noch den Teil davor.Beispiele
Einfaches Teilen eines Textknotens
const p = document.createElement('p');
p.textContent = 'Hallo Welt';
const original = p.firstChild;
const rest = original.splitText(5);
console.log(JSON.stringify(original.data)); // Teil vor der Trennstelle
console.log(JSON.stringify(rest.data)); // neuer Knoten
console.log(p.childNodes.length);
console.log(original.nextSibling === rest);
Suchbegriff mit <mark> hervorheben
const highlight = (textNode, term) => {
const index = textNode.data.toLowerCase().indexOf(term.toLowerCase());
if (index === -1) return null;
// Treffer vom Anfang abtrennen, danach den Rest hinter dem Treffer
const match = textNode.splitText(index);
match.splitText(term.length);
const mark = document.createElement('mark');
match.replaceWith(mark);
mark.append(match);
return mark;
};
const p = document.createElement('p');
p.textContent = 'JavaScript macht Spaß';
highlight(p.firstChild, 'macht');
console.log(p.innerHTML);
Freistehender Knoten ohne Elternelement
const text = new Text('abcdef');
const tail = text.splitText(3);
console.log(text.data, tail.data);
console.log(tail.parentNode); // nicht eingefügt
Fehler bei ungültigem Offset abfangen
const text = new Text('kurz');
try {
text.splitText(10);
} catch (err) {
console.log(err.name);
}
// Wichtig · Fallstricke
- Ist
offsetgrößer als die Länge des Textes, wirft die Methode eineDOMExceptionvom TypIndexSizeError. Negative Werte werden nach WebIDL inunsigned longumgewandelt, ergeben also sehr große Zahlen und lösen ebenfalls diesen Fehler aus. - Der Offset zählt UTF-16-Codeeinheiten, keine Zeichen. Bei Emojis oder anderen Surrogatpaaren kann ein falscher Offset ein Zeichen in zwei ungültige Hälften zerlegen.
offsetgleich0oder gleichlengthist erlaubt und erzeugt einen leeren Textknoten. Solche leeren Knoten bereinigt man bei Bedarf mitNode.normalize().- Wenn man beim Durchlaufen mit
TreeWalkeroderchildNodesteilt, ändert sich die Knotenliste während der Schleife. Deshalb vorher die Knoten sammeln und erst danach bearbeiten. - Die Methode funktioniert auch für
CDATASection, weil diese vonTexterbt. Sie wird in allen Browsern unterstützt.