forked from molily/javascript-einfuehrung
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathevent-handling-onload.html
More file actions
74 lines (64 loc) · 8 KB
/
event-handling-onload.html
File metadata and controls
74 lines (64 loc) · 8 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
<!DOCTYPE html>
<html lang="de">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>JavaScript: Onload-Techniken: Scripte ausführen, sobald das Dokument verfügbar ist</title>
<link rel="stylesheet" href="js-doku.css">
<script type="text/javascript" src="js-doku.js"></script>
</head>
<body>
<div id="nav">
<p>Hier entsteht eine <strong>JavaScript-Dokumentation</strong> von <a href="http://molily.de/">molily</a>. Derzeit ist sie noch lückenhaft, wächst aber nach und nach. Kommentare und Feedback werden gerne per <a href="mailto:zapperlott@gmail.com">E-Mail</a> entgegen genommen.</p>
<p class="contents-link"><a href="./">Zum Inhaltsverzeichnis</a></p>
</div>
<h1>JavaScript: Onload-Techniken</h1>
<p></p>
<div class="section" id="onload-nachteile">
<h2>Nachteile des <code>load</code>-Ereignisses</h2>
<p>Wir haben bereits die <a href="event-handling-grundlagen.html#ereignisbasierung#ereignisbasierung">drei Phasen von ereignisbasierten Scripten</a> kennengelernt. Die zweite Phase tritt ein, wenn das Dokument fertig geladen ist und der DOM-Elementenbaum des Dokuments vollständig aufgebaut ist. Sinnvolle Scripte schalten sich automatisch hinzu, ohne dass JavaScript-Code direkt ins HTML eingebettet ist (Unobtrusive JavaScript). Dazu ist es von zentraler Wichtigkeit, das Script zu initialisieren, sobald der Zugriff auf den gesamten DOM-Baum möglich ist, vor allem um Event-Handler bei gewissen Elementen registriert.</p>
<p>Mit dem dokumentweiten <code>load</code>-Ereignis (<code>window.onload</code>) haben wir eine Funktion nach dem vollständigen Laden des Dokuments ausgeführt. Das <code>load</code>-Ereignis tritt jedoch erst dann ein, wenn das gesamte Dokument <em>mitsamt aller externen Ressourcen</em> vom Webserver heruntergeladen wurde. Dazu gehören eingebettete Grafiken, Multimedia-Plugins und gegebenenfalls Iframes mit weiteren HTML-Dokumenten. Je nachdem, welche externen Ressourcen eingebunden werden, kann das Dokument zum Zeitpunkt des <code>load</code>-Ereignisses schon längst im Browser aufgebaut sein und der Anwender kann es schon größtenteils lesen und bedienen.</p>
<p>Für das Event-Handling interessiert uns nicht, wann alle eingebetteten Ressourcen fertig geladen sind, sondern lediglich, wann der JavaScript-Zugriff auf den DOM-Baum möglich ist. Dieser Zeitpunkt, genannt <em>DOM ready</em>, tritt meistens weit vor dem <code>load</code>-Ereignis ein. Ein Script sollte dem Dokument so zeitnah wie möglich Interaktivität hinzufügen und notwendige Änderungen vornehmen, damit das Dokument einschließlich der JavaScript-Funktionalität bereits während des Ladens für den Anwender bedienbar ist.</p>
</div>
<div class="section" id="domcontentloaded">
<h2>DOMContentLoaded</h2>
<p>Der <code>load</code>-Event ist aus heutiger Sicht für Unobtrusive JavaScript nicht geeignet. Glücklicherweise gibt es ein Ereignis, das eintritt, sobald der Parser den gesamten HTML-Code eingelesen hat und der komplette DOM-Baum für JavaScripte zugänglich ist: <code>DOMContentLoaded</code>.</p>
<p>Die Überwachung dieses Ereignises ist allerdings nur im Zusammenhang mit <a href="#addEventListener">addEventListener</a>, also dem W3C-Modell möglich. Alle großen Browser, die den DOM-Standard umsetzen, kennen mittlerweile auch <code>DOMContentLoaded</code>. Eine Ausnahme bilden der Internet Explorer vor Version 9: Diese älteren Versionen unterstützen weder den DOM-Events-Standard, noch kennen sie das Ereignis <code>DOMContentLoaded</code>.</p>
<p>Das folgende Beispiel demonstriert die Überwachung der beiden Ereignisse <code>load</code> und <code>DOMContentLoaded</code>:</p>
<pre>function dokumentGeladen (e) {
alert("Das Ereignis " + e.type + " ist passiert.")
}
document.addEventListener("load", dokumentGeladen, false);
document.addEventListener("DOMContentLoaded", dokumentGeladen, false);</pre>
<p>Internet Explorer vor Version 9 können dieses Beispiel nicht ausführen, sie kennen die Methode <code>addEventListener</code> nicht.</p>
<p>Wenn Sie das Beispiel in ein HTML-Dokument einfügen, so demonstriert es, dass der <code>DOMContentLoaded</code>-Event vor dem <code>load</code>-Event passiert. Wenn große und zahlreiche externen Ressourcen in das Dokument eingebunden sind, dann kann zwischen beiden Ereignissen viel Zeit vergehen – wertvolle Zeit, die ein Script nicht untätig verstreichen lassen sollte.</p>
</div>
<div class="section" id="domcontentloaded-crossbrowser">
<h2>Browserübergreifendes <code>DOMContentLoaded</code></h2>
<p>Leider gibt es ältere Browser, die das äußerst nützliche <code>DOMContentLoaded</code>-Ereignis nicht unterstützen. Ältere Internet Explorer kennen auch kein gleichwertiges Ereignis. Daher nutzt die verbreitete Sonderlösung verschiedene Microsoft-eigene Techniken, um Rückschlüsse darauf zu ziehen, ob der Elementenbaum bereits vollständig eingelesen wurde. Die genaue Funktionsweise sei hier nicht näher erklärt. Stattdessen sei auf eine browserübergreifende Fertiglösung hingewiesen, die sowohl <code>DOMContentLoaded</code> unterstützt als auch einen erprobten Workaround für ältere Internet Explorer enthält: <a href="http://javascript.nwbox.com/ContentLoaded/contentloaded.js">ContentLoaded.js von Diego Perini</a>. Das Script ist abwärtskompatibel, das heißt, wenn alle Stricke reißen, wird auf das robuste <code>load</code>-Ereignis zurückgefallen.</p>
<p>Wenn Sie dieses Script einbinden, können Sie eine Funktion folgendermaßen ausführen, sobald der DOM-Baum zur Verfügung steht:</p>
<pre>function init () {
// Diese Funktion kann auf den gesamten DOM-Baum zugreifen.
}
// Nutzung von Diego Perinis Helferfunktion
ContentLoaded(window, init);</pre>
<p>Ein solche DOM-Ready-Technik ist in den verbreiteten <a href="bibliotheken.html">JavaScript-Frameworks</a> bereits eingebaut. Diese bringen eigene Event-Handling-Systeme mit sich, die das Ausführen von Funktionen erlauben, sobald die DOM-Schnittstelle vollständig nutzbar ist.</p>
</div>
<div class="section" id="domcontentloaded-fallstricke">
<h2>Fallstricke bei <code>DOMContentLoaded</code></h2>
<p>Das <code>DOMContentLoaded</code>-Ereignis wurde ursprünglich vom Browserhersteller Mozilla erfunden. Andere Browserhersteller haben es übernommen, weil sie sie nützlich fanden. Mittlerweile wird die genaue Funktionsweise in HTML5 standardisiert.</p>
<p>Trotz dieser Standardisierung verhalten sich die Browser im Detail noch unterschiedlich. Eine Unstimmigkeit ist die Frage, ob das Ereignis durch den Ladevorgang externer Stylesheets verzögert werden soll.</p>
<p>Beide Varianten ergeben Sinn: Es reicht zwar aus, dass der DOM-Baum komplett eingelesen ist, wenn man Event-Handler registrieren will. Allerdings gibt es auch Scripte, die in der Initialisierungsphase bereits auf die Darstellung gewisser Elemente reagieren sollen – und diese wird üblicherweise durch externe Stylesheets geregelt. Wenn das Script beispielsweise die Größe eines Elements in Erfahrung bringen will, muss der Browser bereits die Stylesheets verarbeitet und die Darstellung berechnet haben.</p>
<p>In HTML5 ist geregelt, dass das Laden von Stylesheets das <code>DOMContentLoaded</code>-Ereignis verzögert. ...</p>
<!-- <p>Wenn Ihre Scripte <a href="werte-auslesen">Informationen über die Darstellung der Elemente abfragen</a>, ...</p> -->
</div>
<div class="sequence-navigation">
<p class="next"><a href="event-handling-effizient.html" rel="next">Effiziente Ereignisverarbeitung</a></p>
<p class="prev"><a href="event-handling-fortgeschritten.html" rel="prev">Fortgeschrittene Ereignisverarbeitung</a></p>
</div>
<div id="footer">
<p><strong>JavaScript-Dokumentation</strong> · <a href="./">Zum Inhaltsverzeichnis</a></p>
<p>Autor: <a href="http://molily.de/">molily</a> · Kontakt: <a href="mailto:zapperlott@gmail.com">zapperlott@gmail.com</a></p>
<p>Lizenz: <a rel="license" href="http://creativecommons.org/licenses/by-sa/3.0/de/">Creative Commons Namensnennung - Weitergabe unter gleichen Bedingungen</a>.</p>
</div>
</body>
</html>