#text-Knoten & Javascript

Zugriff auf den "Text-Inhalt" von Webseiten

#text-Knoten enthalten den "Text-Inhalt" von Webseiten.
Sie sind einerseits DOM-Elemente (Knoten) wie andere auch, haben aber einige spezielle Eigenschaften (rechts).

Für den Zugriff auf Textknoten gibt es eigene Methoden, einige davon werden auf dieser Webseite vorgestellt.
#text-Knoten sind eine spezielle Unterart von DOM-Knoten:
Sie haben keine Attribute. Daher werden sie über ihren parentNode adressiert.
Sie haben keine childNodes
Die Type ist immer nodeType=3
Der Name ist immer nodeName="#text"
Der Inhalt nodeValue besteht aus einem Text-String
DOM & Javascript Zugriff auf alle Elemente einer Webseite
#text-Knoten Der Text-Inhalt von Webseiten
Adressieren #text-Knoten werden über ihr parent-Element adressiert
Lesen Lesen des Inhalts von #text-Knoten
Schreiben Schreiben / Ändern des Inhalts von #text-Knoten
Neue Textknoten Erstellen neuer #text-Knoten, Einhängen in den DOM-Baum
Löschen Löschen der Knoten oder nur des Inhalts

Textknoten - Der eigentliche Text-"Inhalt" von Webseiten

Das DOM-Modell konzentriert die Aufmerksamkeit ganz auf die Struktur eines Dokuments, den 'hierarchischen Baum'. Der gesamte Text-Inhalt befindet sich dabei in speziellen Elementen, den #text-Knoten. Die #text-Knoten sind Endpunkte, sozusagen die 'Blätter' des hierarchischen Baums. Von ihnen gehen keine weiteren Verzweigungen (childNodes, Attribute) aus.
Beispiel id="t1" enthält einen Textknoten mit dem Inhalt "Das ist Text 11": Der Text kann beliebig lang sein, auch über mehrere Zeilen, allerdings nicht unterbrochen.

Beispiel id="t2":   Das <div>-Element enthält 3 childnodes: Zwei #text-Knoten und ein <b>-Element, welches selbst wiederum einen #text-Knoten ('Fettgedruckt') enthält.

Beispiel id="t3":   Entspricht weitgehend dem vorigen Beispiel, hier ist der Text allerdings durch ein <br>-Zeilenumbruch-Element unterbrochen:
Das <div>-Element enthält daher 5 childNodes, davon 3 #text-Knoten sowie je ein <br> und <span>-Element. Das <span>-Element enthält selbst wieder einen #text-Knoten.
HTML-Beispiele für #text-Knoten:
<div id="t1">Das ist Text 11</div>

<div id="t2">
Text 21
<b>Fettgedruckt</b>
Text 22
</div>

<div id="t3">
Text 31<br>
Text 32
<span style="font-weight:bold;">Fett</span>
Text 33
</div>
Javascript-Funktion get_node_info zeigt Live die DOM-Daten der Test-Elemente an. Dabei werden alle childNodes des adressierten DOM-Knotens durchlaufen und ebenfalls angezeigt. Live--Javascript (Klicken sie die Zeilen):
Das ist Text 11
Text 21 Fettgedruckt Text 22
Text 31
Text 32 Fett Text 33

Textknoten adressieren

#text-Knoten werden nicht direkt adressiert, da sie keine Attribute haben können. Meist wird das direkt übergeordnete parent-Element adressiert, und danach dessen childNode aufgesucht.

id-Attribute

In allen Beispielen dieser Seite werden id-Attribute zur Adressierung der jeweiligen parent-Elemente (DOM-Knoten) verwendet.
Alternativ sind auch andere Methoden möglich.
Adressierung von DOM-Elementen).

id-Attribute müssen eindeutig sein, d.h. jedes auf einer Webseite verwendete id-Attribut muss einen anderen Wert haben.

Das <div>-Element im Beispiel rechts kann mit Hilfe seines id-Attributs eindeutig adressiert werden. Das Element (DOM-Knoten) hat nur einen einzigen childNode mit nodeName="#text" und nodeValue="Text"
HTML-Beispiel:
<div id="t0">Text</div>

Adressierung mit Javascript:
var n = document.getElementById("t0");
var tn = n.firstChild;

Variable n vom Typ object bezeichnet das DOM-Objekt mit dem angeführten id-Attribut - In diesem Fall das <div>-Element dieses Beispiels.

Variable tn vom Typ object bezeichnet den gesuchten #text-Knoten.

Mehrere childNodes

Häufig haben DOM-Elemente mehrere childNodes
In diesem Fall ist
n.childNodes.length>1
und die einzelnen childNodes werden mit ihrem Index adressiert, z.B.
childNodes[0], childNodes[1], ...
Alternative Möglichkeiten zur Adressierung eines einzigen childNode
tn = n.firstChild;
tn = n.childNodes[0];
tn = n.lastChild;
Adressierung im Fall mehrerer childNodes
tn = n.childNodes[2];
adressiert den dritten childNode von Objekt n

Error-handler

Bei der Adressierung von #text-Knoten kann es leicht zu Fehlern kommen (z.B. wenn der gesuchte childNode ↓ gelöscht wurde).
Verwenden sie am besten immer die try-Anweisung.
Im Beispiel rechts wird ein Alarmfenster geöffnet, wenn der Knoten n keine childNodes enthält.
Abfangen eines möglichen Fehlers:
try{
var tn = n.firstChild;
}
catch(e) {
// Wenn kein firstChild existiert:
alert("Fehler = "+e);
}

Funktions-Argumente

In allen Beispielen dieser Seite wird das id-Attribut als String-Argument an die jeweilige Funktion übergeben, so wie an die Funktion test1 (rechts).

Alternativ könnte man das adressierte Element (DOM-Knoten) auch im aufrufenden Programm definieren und als Objekt-Variable an die Funktion test2 (rechts) übergeben.
Diese Technik kann auf alle Funktionen angewendet werden, mit denen DOM-Elemente manipuliert werden.

Die beiden Muster-Funktionen führen mit dem Objekt tn keine Arbeit aus - Das ist lediglich durch einen Kommentar (...) angedeutet.
Javascript-Beispiel: id-Attribut als String-Argument
function test1(nid) {
var n = document.getElementById(nid);
var tn = n.firstChild;
// ...
}
// Anwendung:
test1("t0");

Javascript-Beispiel: DOM-Objekt als Argument:
function test2(nobj) {
var tn = nobj.firstChild;
// ...
}
// Anwendung:
var n = document.getElementById("t0");
test2(n);

Lesen von Textknoten

Zum Lesen wird ein #text-Knoten adressiert und danach seine Eigenschaft nodeValue gelesen.
Prüfen sie vorher evtl. die Standard-Eigenschaften jedes #text-Knotens:
nodeName="#text", nodeType=3

Das nebenstehende Live-Live-Javascript-Beispiel für child_text_read("t4") zeigt, wie sie den Inhalt eines #text-Knotens lesen können.
Anfangs ist es irritierend, nicht den Wert des <div>-Knotens (id="t4"), sondern seines childNodes, eben des #text-Knotens zu lesen.

Mit DOM-Methoden werden immer die jeweils aktuellen Daten gelesen. Wenn ein Text mit DOM-Methoden geändert wurde, dann ist der Original-Quelltext dieses Knotens für Javascript nicht mehr zugänglich.
HTML Beispiel
<div id="t4">Beispiel 41</div>

Javascript-Funktion zum Lesen des #text-Knotens
function child_text_read(nid) {
var n=document.getElementById(nid);
var tn = n.firstChild;
var t = nid+".firstChild";
if(tn.nodeType==3) {
var txt = tn.nodeValue;
t+=" enthält den Text '"+txt+"'";
}
else { t+="ist kein #text"; }
alert(t);
}
// Anwendung:
child_text_read("t4");

Schreiben / Ändern von Textknoten

Zum Ändern / Schreiben wird ein #text-Knoten adressiert und danach seine Eigenschaft nodeValue geschrieben.
Live--Beispiel für child_text_write("t5","abc")
(Etwas erweitert - Sie können einen beliebigen Text eingeben).

Man kann auch einen 'leeren Text' (ohne Zeichen) schreiben. In diesem Fall ist derr #text-Knoten noch vorhanden, kann adressiert und geändert werden.
Wenn der #text-Knoten ↓ gelöscht wurde, kann er nicht mehr adressiert werden (Fehler).

DOM-Methoden lesen jeweils den aktuellen Text. Der Original-Quelltext ist nach einer Änderung nicht mehr zugänglich !
Live--Beispiel für child_text_read("t5")
HTML-Beispiel:
<div id="t5">Text 5</div>

Javascript-Beispiel zum Schreiben / Ändern eines #text-Knotens:
function child_text_write(nid,txt) {
var n = document.getElementById(nid);
var tn = n.firstChild; // #text
if(tn.nodeType==3) {
tn.nodeValue=txt;
}
}
// Anwendung:
child_text_write("t5","abc");
In der Praxis ist es sicherer, zuerst alle childNodes zu ↓ löschen, und dann einen neuen #text-Knoten mit dem gewünschten Text anzulegen.
Mit dieser Methode werden auch komplexe Texte sicher gelöscht (z.B. wenn sie <br> Umbruch-Zeichen oder <span>-Elemente zur CSS-Formatierung enthalten).
function child_text_replace(nid,txt) {
var n=document.getElementById(nid);
while(n.childNodes.length>0) {
n.removeChild(node.firstChild);
}
var tn=document.createTextNode(txt);
n.appendChild(tn);
}
// Anwendung:
child_text_replace("t5","xyz");

Textknoten neu erstellen und einhängen

Dazu muss bekannt sein, wo der neue Text eingefügt werden soll. Am besten planen sie an der gewünschten Stelle ein leeres Element mit einem eindeutigen id-Attribut, ähnlich wie im Beispiel rechts.

Adressieren sie zuerst den (zukünftigen) parentNode des gewünschten #text-Knotens.
Erzeugen sie den Textknoten mit createTextNode
Hängen sie den erzeugten Textknoten an den parentNode

Live--Beispiel für child_text_create("t6","abc")
(Etwas erweitert - Sie können einen beliebigen Text eingeben).
Live--Beispiel für child_text_read("t6")
Live--Beispiel für childnodes_delete("t6")
(↓ nächstes Kapitel).

Man kann mehrfach neue Textknoten anhängen. Der erzeugte Text besteht dann aus den einzelnen Knoten, nicht (wie es aussieht) aus einem längeren Text !
HTML-Beispiel:
<div id="t6"></div>

Javascript-Funktion zum Erzeugen eines neuen #text-Knotens
function child_text_create(nid,txt) {
var n = document.getElementById(nid);
var tn=document.createTextNode(txt);
n.appendChild(tn);
}
// Anwendung:
child_text_create("t6","xyz");

Tabellen-Zellen

Der Inhalt einer Tabellen-Zelle sollte niemals leer sein, da sonst Probleme bei der Darstellung auftreten.
Daher wird bereits im Quelltext ein geschützes Leerzeichen &nbsp; (→ Unicode U+00A0) eingefügt.
Bei jeder Änderung wird die Länge des neuen Strings überprüft. An Stelle eines leeren Textes wird ein geschützes Leerzeichen eingefügt.
Details zu Tabellen und zu Zeichen-Codes
Zelle einer HTML-Tabelle
<td>&nbsp;</td>
Text-Änderung mit Javascript:
if(!txt.length) {txt="\u00A0";}
tn.nodeValue = txt;
oder
tn = document.createTextNode(txt);

Textknoten löschen

Textknoten (Element/e) löschen

Wie bei anderen Knoten müssen sie den parentNode adressieren, um an den #text-Knoten zu kommen.
Wenn sie sicher sind, dass der parentNode nur einen einzigen #text-Knoten als childNode hat, dann lässt sich die Funktion vereinfachen.
Sicherer ist jedoch die rechts vorgestellte Form: Sie löscht alle childNodes eines DOM-Knotens, also nicht nur einfache Texte, sondern auch formatierte - die z.B. Elemente wie <b>, <u> oder <span> enthalten.
Live-Anwendung im Kapitel neuer Textknoten.
Javascript-Funktion zum Löschen aller childNodes eines Elements:
function childnodes_delete(nid) {
var n = document.getElementById(nid);
while(n.childNodes.length>0) {
n.removeChild(node.firstChild);
}
}
// Anwendung:
childnodes_delete("t6");

Text (Inhalt) löschen

Alternativ kann man (Kapitel Text schreiben) einen leeren Text als Wert in einen #text-Knoten schreiben. Das Ergebnis sieht auf der Webseite gleich aus wie nach dem Löschen des #text-Elements. Allerdings ist der #text-Knoten noch vorhanden und kann adressiert werden.
Javascript: Schreiben eines 'leeren Textes':
n = document.getElementById("t6");
tn = n.firstChild;
tn.nodeValue = "";