Weitere aktuelle Java-Titel finden Sie bei dpunkt.
 Inhaltsverzeichnis   Auf Ebene Zurück   Seite Zurück   Seite Vor   Auf Ebene Vor   Eine Ebene höher   Index


7.2.3

Lebenszyklus eines Applets



Jedes Applet besitzt vier Methoden, die seinen Lebenszyklus bestimmen. Der Aufruf dieser Methoden erfolgt bei bestimmten Benutzeraktionen automatisch vom Browser. Zu diesen Aktionen zählt z. B. das Laden eines Applets oder das Verlassen einer HTML-Seite, in die ein Applet eingebunden ist. Zu diesen Methoden gehören:
init()Wird immer aufgerufen, wenn das Applet initialisiert wird. Dies geschieht sofort, nachdem es geladen ist.
start()Wird nach der Initialisierung eines Applets ausgeführt. Außerdem findet ein Aufruf dieser Methode immer dann statt, wenn der Browser bzw. der Appletviewer von der Icon-Darstellung wieder auf Normalgröße gebracht wird. Bei Browsern wird start() auch dann aufgerufen, wenn eine Seite, auf der sich ein Applet befindet, zum wiederholten Male geladen wird.
stop()Ist das Gegenstück zu start(). Ein Aufruf erfolgt, wenn der Browser bzw. der Appletviewer zum Icon verkleinert oder eine HTML-Seite mit eingebundenem Applet in einem Browser verlassen wird.
destroy()Wird immer aufgerufen, wenn das Applet zerstört wird. Die Zerstörung tritt z. B. ein, wenn es aus dem Browser entfernt wird. Im Laufe einer WWW-Sitzung werden u. U. viele Applets geladen. Dadurch muss eine große Speichermenge zur Verfügung stehen. Damit der Umfang des belegten Speichers nicht ständig steigt, schafft z. B. der Netscape-Navigator Platz, indem bei übermäßiger Speicherbelastung alte Applets entfernt werden. Wird ein entferntes Applet erneut geladen, durchläuft es den Initialisierungsvorgang von neuem.

Abbildung 7.1: Der Lebenszyklus eines Applets
Abbildung 7.1

Standardmäßig enthalten die obigen Methoden keinen Code. Man kann sie in geeigneter Weise überschreiben, um seinem Applet die gewünschte Funktionalität zu verleihen. init() wird bei Applets meistens implementiert, da diese Prozedur nach dem Laden des Applets zuerst ausgeführt wird und Initialisierungsaufgaben, z. B. das Erzeugen von Objekten, übernimmt. Die anderen Methoden können nach Bedarf überschrieben werden.

Um einen Eindruck davon zu bekommen, wie die Lebenszyklusmethoden aufgerufen werden, kann man folgendes Applet testen:
  import java.applet.Applet;
  
  public class ZyklusDemo extends Applet {
  
    public void init() {
      System.out.println("init");
    }
  
    public void start() {
      System.out.println("start");
    }
  
    public void stop() {
      System.out.println("stop");
    }
  
    public void destroy() {
      System.out.println("destroy");
    }
  
  }
Das Applet gibt jeweils den Namen der Methode, die vom Interpreter aufgerufen wird, auf der Standardausgabe aus, d. h. entweder auf der Konsole, von der der Appletviewer gestartet wurde, beim Netscape Communicator z. B. durch Auswahl des Menüpunktes »Communicator¦Java Console« aufrufen oder beim Java-Plug-in durch Aktivierung der Java-Konsole über das Java-Icon in der Task-Leiste. Abbildung 7.1 zeigt die Abhängigkeit der Aufrufe der Lebenszyklusmethoden von den Aktionen des Benutzers.

Mehr Information zur Ein- und Ausgabe ist im Kapitel 10 zu finden.

init()

In init() sollte das Applet initialisiert werden. Darunter versteht man, dass Aktionen durchgeführt werden, die für die spätere Funktion des Applets wichtig sind. Darunter fällt z. B.: Das Einlesen von Parametern wird im nächsten Abschnitt ausführlich erläutert. init() wird während der Lebenszeit eines Applets genau einmal ausgeführt, nämlich direkt, nachdem das Applet geladen wurde. Deshalb sollte in init() Code enthalten sein, der einmalige Initialisierungsaufgaben ausführt. Da Applets wohl in den allermeisten Fällen eine grafische Oberfläche besitzen, fällt darunter z. B. die Erzeugung der Benutzerschnittstelle.

Das Einbinden von Medien wie z. B. Sound oder Bilder wird ebenfalls häufig in der init()-Methode vorgenommen. Sie besitzen ebenfalls die Eigenschaft, dass sie während der Ausführung eines Applets einmal geladen werden müssen. Da init() genau einmal ausgeführt wird, ist dies ein geeigneter Ort, solche Medien einzubinden.

start() und stop()

Applets sollten keine Ressourcen verbrauchen, wenn die Seite, auf der sie sich befinden, nicht zu sehen ist. Wenn in einem Applet kein Thread angelegt wird, ist dies auch immer der Fall (Threads werden ausführlich im Kapitel 11 behandelt).

Ganz ohne einen Thread auszukommen ist für ein Applet nicht möglich, da das Applet selbst in einem Thread ausgeführt wird.

Immer, wenn eine Seite, in der ein Applet eingebunden ist, verlassen wird oder der Browser bzw. Appletviewer zum Icon verkleinert wird, ruft der Interpreter stop() auf und hält die Ausführung des Applet-Threads an. Doch was passiert, wenn innerhalb des Applets vom Programmierer ein zusätzlicher Thread erzeugt wird?

Wenn man z. B. eine Animation mit Hilfe eines eigenen Threads realisiert (z. B. mit dem Interface Runnable), wird sie nebenläufig ausgeführt. Das Applet selbst wird ebenfalls in einem Thread ausgeführt. Durch diesen Thread wird z. B. die Eingabe entgegengenommen.

Verlässt man nun die HTML-Seite des Applets, wird nur der Applet-Thread angehalten, nicht jedoch der Animations-Thread. Wird dessen Ausführung nicht vom Programmierer durch geeigneten Code abgebrochen, läuft er weiter, auch wenn die Seite des Applets nicht mehr sichtbar ist.

Um die Animation nur dann ablaufen zu lassen, wenn die Seite sichtbar ist, muss man start() und stop() überschreiben. In start() sollte der Thread, der für die Animation zuständig ist, erzeugt und gestartet werden. In stop() sollte er wieder beendet werden:
  public void start() {
    if (t == null) {
      t = new Thread(this); // Anlegen eines Threads
      t.start();            // Starten des Threads
    }
  }

  public void run() {
    // Ergibt false, nachdem stop() aufgerufen wurde
    while (t == Thread.currentThread()) {
      ...  // Aktionen des Threads
    }
  }

  public void stop() {
      t = null;         // Dereferenzieren des Threads
    }
  }

t ist ein Exemplar der Klasse Thread, die in dem Applet deklariert ist, dem obiger Programmauszug entstammt. Dieser Thread wird angelegt und gestartet, wenn start() aufgerufen wird. Und er wird wieder beendet, nachdem stop() aufgerufen wurde. Im Abschnitt 11.3.2 wird die Vorgehensweise in diesem Auszug im Detail beschrieben.

Will man längere Berechnungen von einem Applet vornehmen lassen, ohne die ganze Zeit auf einer Seite verweilen zu müssen, nimmt man die Berechnung in einem eigenen Thread vor, ohne start() und stop() in obiger Weise zu implementieren. Man sollte diese Möglichkeit aber mit Vorsicht genießen. Wenn mehrere Applets im Hintergrund ablaufen, macht sich dies in einem nicht unbeträchtlichen Performance-Verlust bemerkbar.

Es ist zu beachten, dass der wechselseitige Aufruf von start() stop() im Browser bei der Ikonifizierung bzw. beim temporären Wechsel der Seite heute nicht mehr die ganz so relevant ist, da diese Funktion nicht in allen Browsern unterstützt wird (z. B. im Internet Explorer oder im Java-Plug-in). So kann es sein, dass bei der Ikonifizierung ein Aufruf von stop() unterbleibt und beim Verlassen einer HTML-Seite mit Applet sofort beim Verlassen stop() und destroy() nacheinander aufgerufen werden. In diesem Fall ist bei der Rückkehr erneut ein Aufruf von init() und start() erforderlich.

destroy()

destroy() wird aufgerufen, wenn das Applet zerstört wird. In destroy() sollte man deshalb vom Applet belegte Ressourcen freigeben. Wird dies nicht getan, kann die Performance darunter leiden. Unter Ressourcen versteht man sowohl Rechenzeit als auch Speicherplatz.

Aber wie kann man Speicherplatz freigeben, wenn es keine Methoden zur Speicherfreigabe gibt? Java besitzt zwar einen automatischen Garbage Collector, dieser verrichtet seine Arbeit jedoch nur in bestimmten Zeitabständen. Werden in einem Applet viele Bilder gebraucht, ist es besser, den von den Bildern belegten Speicherplatz direkt freizugeben. Hierzu besitzt die Klasse Image die Methode flush():
  myImage.flush();
Ein anderer Sachverhalt, der in destroy() gelöst werden kann, ist das Schließen von Sockets und Dateien, wenn in einem Applet Netzverbindungen aufgebaut oder Dateien geöffnet wurden.

Auf diese Weise können Sockets ordnungsgemäß geschlossen werden, obwohl vom Benutzer der Verbindungsabbau nicht explizit eingeleitet wurde.


 Inhaltsverzeichnis   Auf Ebene Zurück   Seite Zurück   Seite Vor   Auf Ebene Vor   Eine Ebene höher   Index

Copyright © 2002 dpunkt.Verlag, Heidelberg. Alle Rechte vorbehalten.