Bearbeitungszeit: bis Dienstag, 8. Juni 2004, 17:30 Uhr
Bewertungsschema
Mit einigen Einschränkungen erlaubt DHTML auch die Programmierung von Animationen. Die Einschränkungen ergeben sich daraus, dass DHTML (und damit JavaScript) zumindest derzeit keine Befehle zum Zeichnen von Linien und nicht-rechteckigen Flächen kennt. Um mit solchen Objekte zu arbeiten, ist man auf entsprechende GIF- oder PNG-Grafiken mit transparentem Hintergrund angewiesen, was trotz der Möglichkeit, deren Höhe und Breite dynamisch zu ändern, nicht immer ganz befriedigend ist.
Animationen bestehen aus einer Reihe von Schritten mit einem gewissen zeitlichen Abstand.
Damit dieser Zeitabstand eingehalten wird, muss ein Wartebefehl eingebaut werden. In praktisch
allen Programmiersprachen gibt es einen solchen Befehl, der meistens sleep() heisst und
als Argument die Wartezeit (z.B. in Millisekunden) erwartet. Eine Animation wird dann etwa
so programmiert:
for(i = 0; i < AnzahlSchritte; i++) {
AnimationsSchritt(i); // Eine selbst programmierte Funktion
sleep(50); // nach 50 ms = 1/20 s der naechste Schritt
}
In JavaScript fehlt eine solche Funktion. Statt dessen gibt es die Befehle
setInterval() und
setTimeout(). Diese
Funktionen erwarten als erstes Argument einen beliebigen Programmierbefehl inkl. abschliessenden
Strichpunkt, eingeschlossen in einfache oder doppelte Gänsefüsschen (ein absoluter
Schandfleck für eine Programmiersprache). Als zweites Argument erwarten sie eine Zeitangabe
in Millisekunden. Im Fall von setInterval() wird dieser Befehl von da an
immer wieder ausgeführt, im Abstand von so vielen Millisekunden, wie im zweiten Argument
angegeben wird. Bei setTimeout() wird der Befehl nur einmal, nach entsprechend vielen
Millisekunden, ausgeführt. Will man setTimeout() für eine Animation verwenden,
muss man es nach jedem Schritt erneut aufrufen, hat dann aber gegenüber setInverval()
den Vorteil, dass man die Zeit zwischen zwei Schritten variieren kann.
Mit setTimeout() sieht das obige Beispiel, nach JavaScript übertragen, so aus:
var i = 0; // ausserhalb von allen Funktionen definieren function naechsterSchritt() { Animationsschritt(i); // Eine selbst programmierte Funktion if(++i < AnzahlSchritte) setTimeout('naechsterSchritt();', 50); } naechsterSchritt(); // Dieser Befehl setzt die Animation in Gang
Um das Beispiel zu konkretisieren und auch gleich zu zeigen, wie dieser allgemeine Rahmen
im konkreten Fall variieren kann, lassen wir eine Überschrift quer über den Bildschirm
laufen. Dazu müssen wir zuerst die Breite des Fensters ermitteln, was einige hässliche Programmzeilen erfordert,
weil Mozilla und Internet Explorer die Fensterbreite in unterschiedlichen Variablen speichern. Wir setzten dann einen
<div>-Bereich ganz rechts an den Bildschirm und schieben ihn Stück für Stück
nach links. Wenn er links verschwunden ist, beginnen wir rechts erneut:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="de">
<head>
<title>Laufschrift</title>
<meta http-equiv="Content-type" content="text/html; charset=iso-8859-1" />
</head>
<body onload="javascript:naechsterSchritt()">
<div style="width:100%; overflow:hidden">
<div id="laufschrift" style="position:relative; visibility:hidden"><h1>Laufschrift</h1></div>
</div>
<script type="text/javascript">
//<![CDATA[
var i, j, rechts; // ausserhalb von allen Funktionen definieren
j = 0;
if(window.innerWidth) // falls die Variable innerWidth existiert
rechts = innerWidth; // (z.B. bei Netscape und Mozilla)
else if(document.body.offsetWidth) // falls document.body.offsetWidth existiert
rechts = document.body.offsetWidth; // (z.B. beim Internet Explorer)
else // falls nicht
rechts = 1024; // raten wir mal.
i = rechts;
marquee = document.getElementById("laufschrift");
marquee.style.left = i+"px";
marquee.style.visibility = "visible";
function naechsterSchritt() {
Animationsschritt(i); // Eine selbst programmierte Funktion
i -= 5; // i zaehlt hier die Pixel von links
if(i < -300) // wenn die Schrift links verschwunden ist
i = rechts; // geht es rechts neu los
setTimeout('naechsterSchritt();', 50);
}
function Animationsschritt() {
marquee.style.left = i + "px"; // Eine eigene Funktion fuer diese Zeile waere
} // nicht wirklich noetig
//]]>
</script>
<p>
<a href="http://validator.w3.org/check/referer"><img style="border:0"
src="valid-xhtml11.png" alt="Valid XHTML 1.1!" /></a>
<a href="http://jigsaw.w3.org/css-validator/check/referer"><img style="border:0"
src="vcss.png" alt="Valid CSS!" /></a>
</p>
</body>
</html>
Um die Laufschrift in Aktion zu sehen, klicken Sie hier.
Will man zwei oder mehr Animationen parallel laufen lassen, so muss die Funktion Animationsschritt()
einfach mehrere Objekte pro Schritt bewegen. So kann man zum Beispiel zwei Lauftexte ineinander laufen
lassen. Der entsprechende Code sieht dann so aus:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="de">
<head>
<title>Laufschrift</title>
<meta http-equiv="Content-type" content="text/html; charset=iso-8859-1" />
<style type="text/css">
.background { position:absolute; width:98%; top:30px; overflow:hidden }
.marquee { position:relative; font-family:Times New Roman; font-size:20pt; font-weight:bold; top:0px; visibility:hidden }
</style>
</head>
<body onload="javascript:naechsterSchritt()">
<div class="background">
<span id="marquee_l" class="marquee">Laufschrift</span>
</div>
<div class="background">
<span id="marquee_r" class="marquee">Laufschrift</span>
</div>
<script type="text/javascript">
//<![CDATA[
var schritt = 10;
var links, rechts, r, l; // ausserhalb von allen Funktionen definieren
var marquee_l, marquee_r;
marquee_l = document.getElementById("marquee_l");
marquee_r = document.getElementById("marquee_r");
if(window.innerWidth) // falls die Variable innerWidth existiert
rechts = innerWidth; // (z.B. bei Netscape und Mozilla)
else if(document.body.offsetWidth) // falls document.body.offsetWidth existiert
rechts = document.body.offsetWidth; // (z.B. beim Internet Explorer)
else // falls nicht
rechts = 1024; // raten wir mal.
links = -170;
r = rechts;
l = links;
marquee_l.style.left = links+"px";
marquee_r.style.left = rechts+"px";
marquee_l.style.visibility = "visible";
marquee_r.style.visibility = "visible";
function naechsterSchritt() {
Animationsschritt(); // Eine selbst programmierte Funktion
r -= schritt;
l += schritt;
if(r > l)
setTimeout('naechsterSchritt();', 50);
else {
r = l;
Animationsschritt(); // letzter Schritt: beide am gleichen Ort
}
}
function Animationsschritt() {
marquee_l.style.left = l+"px";
marquee_r.style.left = r+"px";
}
//]]>
</script>
<p style="padding-top:50px">
<a href="http://validator.w3.org/check/referer"><img style="border:0"
src="valid-xhtml11.png" alt="Valid XHTML 1.1!" /></a>
<a href="http://jigsaw.w3.org/css-validator/check/referer"><img style="border:0"
src="vcss.png" alt="Valid CSS!" /></a>
</p>
</body>
</html>
In dem Beispiel ist zu beachten, dass beide Texte je relativ zu einem <div>-Bereich positioniert werden,
der aber in beiden Fällen absolut und identisch positioniert ist. Nur so lässt sich, zusammen mit der Angabe
overflow:hidden, verhindern, dass die anfangs über den Bilschirmrand hinauslappenden Bereiche einen
vertikalen Scrollbalken erzeugen, der die Animation stört.
Beim Internet Explorer 5 für Macintosh (Classic oder OS X) führt allerdings gerade diese Massnahme dazu,
dass die Laufschrift überhaupt nicht angezeigt wird.
Will man mehrere Animationen hintereinander laufen lassen, braucht man in der Funktion
naechsterSchritt() eine zusätzliche Variable, um zu zählen, welche Animation gerade am laufen ist.
Um dies zu zeigen, wurde das obige Beispiel noch um eine Sequenz erweitert, in der sich die zusammengelaufenen Schriften
rot färben. Der Quelltext ist im folgenden aufgelistet, für das lauffähige Beispiel (wieder nicht auf IE 5
für Mac) klicken Sie hier.
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="de">
<head>
<title>Laufschrift</title>
<meta http-equiv="Content-type" content="text/html; charset=iso-8859-1" />
<style type="text/css">
.background { position:absolute; width:98%; top:30px; overflow:hidden }
.marquee { position:relative; font-family:Times New Roman;
font-size:20pt; font-weight:bold; top:0px;
color:rgb(0,0,0); visibility:hidden }
</style>
</head>
<body onload="javascript:naechsterSchritt()">
<div class="background">
<span id="marquee_l" class="marquee">Laufschrift</span>
</div>
<div class="background">
<span id="marquee_r" class="marquee">Laufschrift</span>
</div>
<script type="text/javascript">
//<![CDATA[
var schritt = 10, farbschritt = 5, anim_no = 1;
var links, rechts, r, l, f; // ausserhalb von allen Funktionen definieren
var marquee_l, marquee_r;
marquee_l = document.getElementById("marquee_l");
marquee_r = document.getElementById("marquee_r");
if(window.innerWidth) // falls die Variable innerWidth existiert
rechts = innerWidth; // (z.B. bei Netscape und Mozilla)
else if(document.body.offsetWidth) // falls document.body.offsetWidth existiert
rechts = document.body.offsetWidth; // (z.B. beim Internet Explorer)
else // falls nicht
rechts = 1024; // raten wir mal.
links = -170;
r = rechts;
l = links;
marquee_l.style.left = links+"px";
marquee_r.style.left = rechts+"px";
marquee_l.style.visibility = "visible";
marquee_r.style.visibility = "visible";
function naechsterSchritt() {
if(anim_no == 1) {
Animationsschritt1(); // Eine selbst programmierte Funktion
r -= schritt;
l += schritt;
if(r < l) {
r = l;
Animationsschritt1(); // letzter Schritt: beide am gleichen Ort
anim_no = 2;
f = 0;
}
setTimeout('naechsterSchritt();', 50);
} else if(anim_no == 2) {
Animationsschritt2();
f += farbschritt;
if(f < 255)
setTimeout('naechsterSchritt();', 50);
else {
f = 255;
Animationsschritt2(); // letzter Schritt: knallrot
anim_no = 3; // fertig
}
}
}
function Animationsschritt1() {
marquee_l.style.left = l+"px";
marquee_r.style.left = r+"px";
}
function Animationsschritt2() {
marquee_l.style.color = 'rgb(' + f + ',0,0)';
marquee_r.style.color = 'rgb(' + f + ',0,0)';
}
//]]>
</script>
<p style="padding-top:50px">
<a href="http://validator.w3.org/check/referer"><img style="border:0"
src="valid-xhtml11.png" alt="Valid XHTML 1.1!" /></a>
<a href="http://jigsaw.w3.org/css-validator/check/referer"><img style="border:0"
src="vcss.png" alt="Valid CSS!" /></a>
</p>
</body>
</html>
Schreiben Sie selbst eine kleine Animation, mit der Sie z.B. Ihre Willkommensseite schmücken können. Versuchen Sie, etwas möglichst eigenes herzustellen, also nicht einfach einen Lauftext von links nach rechts, der grün wird und auch keinen Lauftext von oben nach unten, der später auf zwei Seiten auseinander wandert.