18.11.2013 Aufrufe

Grafikprogrammierung in Java

Grafikprogrammierung in Java

Grafikprogrammierung in Java

MEHR ANZEIGEN
WENIGER ANZEIGEN

Erfolgreiche ePaper selbst erstellen

Machen Sie aus Ihren PDF Publikationen ein blätterbares Flipbook mit unserer einzigartigen Google optimierten e-Paper Software.

<strong>Grafikprogrammierung</strong> <strong>in</strong> <strong>Java</strong>:<br />

Grundlagen<br />

11.1 Grundlagen<br />

11.2 Grafische Grundelemente<br />

11.3 Fensterklassen<br />

11.4 Ereignisse und Widgets<br />

11.5 Applets<br />

11.6 Die Sw<strong>in</strong>g-Klassen<br />

11.1 Grundlagen 11-1


Schnittstellen für Anwenderprogramme<br />

• E<strong>in</strong>e Schnittstelle für Anwenderprogramme (application programm<strong>in</strong>g <strong>in</strong>terface,<br />

API) stellt wohldef<strong>in</strong>ierte und standardisierte Klassen und Methoden zur<br />

Verfügung, die von Anwenderprogrammen genutzt werden können.<br />

• APIs ermöglichen es, vorhandene Software um weitere Funktionen zu ergänzen.<br />

• <strong>Java</strong> stellt beispielsweise APIs für die folgenden Zwecke zur Verfügung:<br />

◦ <strong>Grafikprogrammierung</strong><br />

◦ Datenbankmanagement<br />

◦ Netzwerkprogrammierung<br />

◦ Verarbeitung, Auswertung und Transformation von XML-Dokumenten<br />

◦ Verschlüsselung von Daten<br />

11.1 Grundlagen 11-2


<strong>Grafikprogrammierung</strong><br />

<strong>Java</strong> bietet den Programmierern zwei Bibliotheken zur Programmierung von<br />

grafischen Benutzeroberflächen (graphical user <strong>in</strong>terface, GUI) an:<br />

• Abstract W<strong>in</strong>dow Toolkit (AWT)<br />

Das AWT ermöglicht die Ausführung grundlegender grafischer Operationen. Die<br />

Klassen und Methoden des AWTs s<strong>in</strong>d im Standardpaket java.awt enthalten.<br />

• Sw<strong>in</strong>g<br />

Seit der Version 1.1 gibt es e<strong>in</strong>e zweite Grafikbibliothek im <strong>Java</strong> Development Kit.<br />

Sie heißt Sw<strong>in</strong>g und ist Bestandteil des Erweiterungspakets javax.sw<strong>in</strong>g. Diese<br />

Bibliothek beseitigt etliche Schwächen des AWTs und bietet e<strong>in</strong>e weitgehend<br />

plattformunabhängige Schnittstelle. Die Möglichkeiten, die Sw<strong>in</strong>g bietet,<br />

übersteigen die des AWTs.<br />

11.1 Grundlagen 11-3


<strong>Grafikprogrammierung</strong><br />

Neben AWT und Sw<strong>in</strong>g gibt es e<strong>in</strong>e weitere verbreitete Bibliothek zur<br />

Programmierung grafischer Benutzeroberflächen:<br />

• Standard W<strong>in</strong>dow Toolkit (SWT)<br />

SWT ist e<strong>in</strong>e Bibliothek für die Erstellung grafischer Oberflächen mit <strong>Java</strong>. Sie<br />

wurde im Jahr 2001 von IBM für die Entwicklungsumgebung Eclipse entwickelt<br />

und kommt <strong>in</strong> e<strong>in</strong>er ganzen Reihe von Anwendungen zum E<strong>in</strong>satz, beispielsweise<br />

Eclipse selbst. SWT leidet auf e<strong>in</strong>igen Nicht-W<strong>in</strong>dows-Plattformen unter<br />

Effizienzproblemen. SWT gehört nicht zum JDK.<br />

Wir gehen hier (aus Zeitgründen) nicht auf SWT e<strong>in</strong>.<br />

11.1 Grundlagen 11-4


Das Abstract W<strong>in</strong>dow Toolkit<br />

Die Fähigkeiten des AWTs lassen sich <strong>in</strong> vier Gruppen e<strong>in</strong>teilen:<br />

• Grundoperationen zum Zeichnen von L<strong>in</strong>ien und Flächen und zur Ausgabe von Text<br />

• Methoden zur Programmsteuerung durch die Behandlung von Maus-, Tastaturund<br />

Fensterereignissen<br />

• Dialogelemente zur Kommunikation mit dem Anwender<br />

• Fortgeschrittene Operationen zur Ausgabe von Bitmaps und Tönen<br />

11.1 Grundlagen 11-5


E<strong>in</strong> e<strong>in</strong>führendes Beispiel<br />

import java.awt.*;<br />

public class Fenster extends Frame {<br />

}<br />

Fenster() {<br />

setBackground(Color.yellow);<br />

setSize(200,150);<br />

setLocation(500,500);<br />

setVisible(true);<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

new Fenster();<br />

}<br />

11.1 Grundlagen 11-6


Das Abstract W<strong>in</strong>dow Toolkit<br />

• Zum Ableiten e<strong>in</strong>er eigenen Fensterklasse wird <strong>in</strong> der Regel entweder die Klasse<br />

Frame oder die Klasse Dialog verwendet.<br />

• Um e<strong>in</strong> neues Fenster zu erhalten, muss e<strong>in</strong> Objekt der Klasse Frame erzeugt, auf<br />

die gewünschte Größe gebracht und durch Aufruf der Methode setVisible<br />

sichtbar gemacht werden.<br />

• Die Ausgabe <strong>in</strong> e<strong>in</strong> Fenster erfolgt durch Überlagern der Methode pa<strong>in</strong>t. Diese<br />

Methode wird immer dann aufgerufen, wenn das Fenster neu gezeichnet werden<br />

muss, z. B. beim Programmstart oder beim Verändern der Größe.<br />

• Die Methode void pa<strong>in</strong>t(Graphics g) erhält als Parameter e<strong>in</strong>en grafischen<br />

Kontext. Hierunter versteht man allgeme<strong>in</strong>e E<strong>in</strong>stellungen für Schrift und Grafik,<br />

beispielsweise den aktuellen Font und die aktuelle Farbe.<br />

11.1 Grundlagen 11-7


E<strong>in</strong> e<strong>in</strong>führendes Beispiel<br />

import java.awt.*;<br />

class Rechteck extends Canvas {<br />

}<br />

public void pa<strong>in</strong>t(Graphics g) {<br />

g.setColor(Color.red);<br />

g.fillRect(20,20,100,40);<br />

g.setColor(Color.black);<br />

g.drawStr<strong>in</strong>g("E<strong>in</strong> rotes Rechteck",20,80);<br />

}<br />

11.1 Grundlagen 11-8


class E<strong>in</strong>fachesFenster extends Frame {<br />

E<strong>in</strong>fachesFenster() {<br />

add(new Rechteck());<br />

setBackground(Color.yellow);<br />

setSize(200,150);<br />

setVisible(true);<br />

}<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

new E<strong>in</strong>fachesFenster();<br />

}<br />

11.1 Grundlagen 11-9


Ereignisgesteuerte Programmierung<br />

• Die Programme, die wir bisher betrachtet haben, arbeiten nach dem Pr<strong>in</strong>zip der<br />

E<strong>in</strong>-Ausgabe-Programmierung.<br />

• Dieses Modell wird jetzt zur ereignisgesteuerten Programmierung erweitert.<br />

Ereignisse s<strong>in</strong>d beispielsweise das Drücken e<strong>in</strong>er Taste, die Betätigung des<br />

Rollbalkens oder die Bewegung der Maus.<br />

• Es gibt viele Varianten der ereignisgesteuerten Programmierung. In <strong>Java</strong> wird das<br />

sogenannte Delegation Based Event Handl<strong>in</strong>g verwendet. Es bietet die Möglichkeit,<br />

GUI-Ereignisse an beliebige Objekte weiterzuleiten und dort zu behandeln. Auf<br />

diese Weise können die Oberfläche und die eigentliche Anwendung klar<br />

vone<strong>in</strong>ander getrennt werden.<br />

11.1 Grundlagen 11-10


Ereignisgesteuerte Programmierung<br />

• Jedes Ereignis besitzt e<strong>in</strong>e Quelle (Source). E<strong>in</strong> Ereignis kann von Beobachtern<br />

(Listener) wahrgenommen werden. Die Anmeldung von Beobachtern zur<br />

Benachrichtigung vom E<strong>in</strong>treten e<strong>in</strong>es Ereignisses ist frei programmierbar und muss<br />

immer explizit erfolgen.<br />

• Es ist nicht festgelegt, <strong>in</strong> welcher Reihenfolge die Beobachter vom E<strong>in</strong>treten e<strong>in</strong>es<br />

Ereignisses <strong>in</strong>formiert werden. Sichergestellt ist lediglich, dass jeder Beobachter<br />

e<strong>in</strong>e Kopie des ursprünglichen Ereignisses erhält.<br />

• Bei der Verbreitung von Ereignissen ist zwischen den Modi s<strong>in</strong>gle-cast und<br />

multi-cast zu unterscheiden. Für S<strong>in</strong>gle-Cast-Ereignisse wird der Beobachter mit<br />

e<strong>in</strong>er setxxListener-Methode gesetzt, für Multi-Cast-Ereignisse wird e<strong>in</strong><br />

Beobachter mit e<strong>in</strong>er addxxListener-Methode der Menge der Beobachter<br />

h<strong>in</strong>zugefügt.<br />

11.1 Grundlagen 11-11


Beispiel: Schließen e<strong>in</strong>es Fensters<br />

• Um e<strong>in</strong> Fenster zu schließen, muss e<strong>in</strong> W<strong>in</strong>dowListener registriert werden.<br />

• Hierbei handelt es sich um e<strong>in</strong>en Beobachter, dessen Methode w<strong>in</strong>dowClos<strong>in</strong>g<br />

aufgerufen wird, wenn der Anwender das Fenster über e<strong>in</strong> System-Menü oder e<strong>in</strong>en<br />

Button schließen möchte.<br />

• Das Fenster wird durch setVisible(false) unsichtbar gemacht, se<strong>in</strong>e<br />

Ressourcen durch dispose() wieder freigegeben.<br />

11.1 Grundlagen 11-12


Beispiel: Schließen e<strong>in</strong>es Fensters<br />

import java.awt.*;<br />

import java.awt.event.*;<br />

public class W<strong>in</strong>dowClos<strong>in</strong>gAdapter extends W<strong>in</strong>dowAdapter {<br />

public void w<strong>in</strong>dowClos<strong>in</strong>g(W<strong>in</strong>dowEvent event) {<br />

event.getW<strong>in</strong>dow().setVisible(false);<br />

event.getW<strong>in</strong>dow().dispose();<br />

System.out.pr<strong>in</strong>tln("Das Fenster wurde geschlossen!");<br />

}<br />

}<br />

Frame wnd = new Frame();<br />

wnd.addW<strong>in</strong>dowListener(new W<strong>in</strong>dowClos<strong>in</strong>gAdapter());<br />

wnd.setSize(400,300);<br />

wnd.setVisible(true);<br />

11.1 Grundlagen 11-13


Adapter-Klassen<br />

• E<strong>in</strong>e Adapter-Klasse ist e<strong>in</strong>e Klasse, die e<strong>in</strong>e gegebene Schnittstelle implementiert,<br />

<strong>in</strong>dem sie jede abstrakte Methode durch e<strong>in</strong>en leeren Rumpf realisiert.<br />

• Adapter-Klassen werden verwendet, wenn von e<strong>in</strong>er Schnittstelle lediglich e<strong>in</strong> Teil<br />

der Methoden benötigt wird, der Rest aber un<strong>in</strong>teressant ist. In diesem Fall leitet<br />

man e<strong>in</strong>e neue Klasse aus der Adapter-Klasse ab und überlagert nur die<br />

erforderlichen Methoden.<br />

• Beispiel: Die Klasse W<strong>in</strong>dowAdapter implementiert die Schnittstellen<br />

W<strong>in</strong>dowListener, W<strong>in</strong>dowStateListener und W<strong>in</strong>dowFocusListener durch<br />

leere Rümpfe. Hierbei handelt es sich um die folgenden Methoden:<br />

11.1 Grundlagen 11-14


Die Klasse W<strong>in</strong>dowAdapter<br />

void w<strong>in</strong>dowActivated(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowClosed(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowClos<strong>in</strong>g(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowDeactivated(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowDeiconified(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowGa<strong>in</strong>edFocus(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowIconified(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowLostFocus(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowOpened(W<strong>in</strong>dowEvent e)<br />

void w<strong>in</strong>dowStateChanged(W<strong>in</strong>dowEvent e)<br />

11.1 Grundlagen 11-15


E<strong>in</strong> e<strong>in</strong>führendes Beispiel<br />

Wir fassen zusammen:<br />

import java.awt.*;<br />

import java.awt.event.*;<br />

class W<strong>in</strong>dowClos<strong>in</strong>gAdapter extends W<strong>in</strong>dowAdapter {<br />

public void w<strong>in</strong>dowClos<strong>in</strong>g(W<strong>in</strong>dowEvent event) {<br />

event.getW<strong>in</strong>dow().setVisible(false);<br />

event.getW<strong>in</strong>dow().dispose();<br />

System.out.pr<strong>in</strong>tln("Das Fenster wurde geschlossen!");<br />

}<br />

}<br />

11.1 Grundlagen 11-16


class Rechteck extends Canvas {<br />

}<br />

public void pa<strong>in</strong>t(Graphics g) {<br />

g.setColor(Color.red);<br />

g.fillRect(20,20,100,40);<br />

g.setColor(Color.black);<br />

g.drawStr<strong>in</strong>g("E<strong>in</strong> rotes Rechteck",20,80);<br />

}<br />

11.1 Grundlagen 11-17


public class E<strong>in</strong>fachesFenster extends Frame {<br />

}<br />

E<strong>in</strong>fachesFenster(Str<strong>in</strong>g title) {<br />

super(title);<br />

addW<strong>in</strong>dowListener(new W<strong>in</strong>dowClos<strong>in</strong>gAdapter());<br />

setBackground(Color.yellow);<br />

setSize(400,200);<br />

add(new Rechteck());<br />

setVisible(true);<br />

}<br />

11.1 Grundlagen 11-18


E<strong>in</strong>fachesFenster e1 = new E<strong>in</strong>fachesFenster("Erstes Fenster"),<br />

e2 = new E<strong>in</strong>fachesFenster("Zweites Fenster"),<br />

e3 = new E<strong>in</strong>fachesFenster("Drittes Fenster");<br />

e1.setLocation(200,200);<br />

e2.setLocation(400,300);<br />

e3.setLocation(600,400);<br />

11.1 Grundlagen 11-19


<strong>Grafikprogrammierung</strong> <strong>in</strong> <strong>Java</strong>:<br />

Grafische Grundelemente<br />

11.1 Grundlagen<br />

11.2 Grafische Grundelemente<br />

11.3 Fensterklassen<br />

11.4 Ereignisse und Widgets<br />

11.5 Applets<br />

11.6 Die Sw<strong>in</strong>g-Klassen<br />

11.2 Grafische Grundelemente 11-20


Das grafische Koord<strong>in</strong>atensystem<br />

• Die Ausgabe von grafischen Objekten basiert auf e<strong>in</strong>em zweidimensionalen<br />

Koord<strong>in</strong>atensystem, dessen Ursprung (0,0) <strong>in</strong> der l<strong>in</strong>ken oberen Ecke liegt.<br />

✲<br />

x<br />

y<br />

❄<br />

• Positive x-Werte erstrecken sich nach rechts, positive y-Werte nach unten. Die<br />

Maße<strong>in</strong>heit entspricht e<strong>in</strong>em Bildschirmpixel und ist somit geräteabhängig.<br />

11.2 Grafische Grundelemente 11-21


Der Benutzerbereich<br />

• Es steht nicht das gesamte Fenster für Ausgaben zur Verfügung. Oben, unten,<br />

l<strong>in</strong>ks und rechts wird Platz zur Ausgabe von Rahmen und Titelzeile benötigt.<br />

• Mit<br />

◦ getSize().width() und getSize().height()<br />

kann die Gesamtbreite bzw. -höhe e<strong>in</strong>es Fensters ermittelt werden. Durch<br />

◦ getInsets().left(), getInsets().right(), getInsets().top() und<br />

getInsets().bottom()<br />

lässt sich die Abmessung des Rahmens und durch Differenzbildung die des<br />

Benutzerbereichs (client area) bestimmen.<br />

11.2 Grafische Grundelemente 11-22


Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

• void drawStr<strong>in</strong>g(Str<strong>in</strong>g s, <strong>in</strong>t x, <strong>in</strong>t y)<br />

drawStr<strong>in</strong>g schreibt den Str<strong>in</strong>g s an die Position (x,y). Diese Koord<strong>in</strong>aten stellen<br />

das l<strong>in</strong>ke Ende der Basisl<strong>in</strong>ie von s dar.<br />

• void drawChars(char[] c, <strong>in</strong>t offset, <strong>in</strong>t length, <strong>in</strong>t x, <strong>in</strong>t y)<br />

Diese Methode schreibt e<strong>in</strong> Zeichenfeld. Die Parameter offset und length<br />

können zur Angabe des ersten Zeichens und der Anzahl der auszugebenden<br />

Zeichen verwendet werden.<br />

11.2 Grafische Grundelemente 11-23


Beispiel: Die Anweisungen<br />

Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

char[] c = {’a’,’b’,’c’,’d’,’e’,’f’};<br />

g.drawStr<strong>in</strong>g("Zeichenkette",50,50);<br />

g.drawChars(c,1,4,50,150);<br />

schreiben den Str<strong>in</strong>g "Zeichenkette" an die Position (50,50) und darunter die Zeichen<br />

"bcde" an die Position (50,150).<br />

11.2 Grafische Grundelemente 11-24


Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

• void drawL<strong>in</strong>e(<strong>in</strong>t x1, <strong>in</strong>t y1, <strong>in</strong>t x2, <strong>in</strong>t y2)<br />

Diese Methode zieht e<strong>in</strong>e L<strong>in</strong>ie von der Position (x1,y1) zur Position (x2,y2).<br />

• void drawRect(<strong>in</strong>t x, <strong>in</strong>t y, <strong>in</strong>t width, <strong>in</strong>t height)<br />

drawRect zeichnet e<strong>in</strong> Rechteck der Breite width und der Höhe height, dessen<br />

l<strong>in</strong>ke obere Ecke an der Position (x,y) liegt.<br />

• void drawRoundRect(<strong>in</strong>t x, <strong>in</strong>t y, <strong>in</strong>t width, <strong>in</strong>t height, <strong>in</strong>t<br />

arcWidth, <strong>in</strong>t arcHeight)<br />

Es wird e<strong>in</strong> Rechteck mit abgerundeten Ecken gezeichnet. arcWidth und<br />

arcHeight bestimmen die Halbachsen der Ellipse, die zur Darstellung der Ecken<br />

verwendet wird.<br />

11.2 Grafische Grundelemente 11-25


Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

• void drawPolygon(<strong>in</strong>t[] x, <strong>in</strong>t[] y, <strong>in</strong>t anzahl)<br />

Diese Methode zeichnet e<strong>in</strong>en L<strong>in</strong>ienzug. Die x-Koord<strong>in</strong>aten der Punkte werden<br />

dem ersten Parameter, die y-Koord<strong>in</strong>aten dem zweiten Parameter entnommen. Die<br />

Anzahl der Koord<strong>in</strong>atenpaare wird durch den dritten Parameter festgelegt. Der<br />

Polygonzug wird geschlossen. Durch drawPolyl<strong>in</strong>e kann e<strong>in</strong> nichtgeschlossener<br />

L<strong>in</strong>ienzug dargestellt werden.<br />

E<strong>in</strong>e andere Möglichkeit, e<strong>in</strong> Polygon zu erzeugen, besteht dar<strong>in</strong>, e<strong>in</strong>en Konstruktor<br />

der Klasse Polygon aufzurufen:<br />

• Polygon(<strong>in</strong>t[] x, <strong>in</strong>t[] y, <strong>in</strong>t anzahl)<br />

Polygon()<br />

Durch addPo<strong>in</strong>t kann e<strong>in</strong> Polygon erweitert werden.<br />

11.2 Grafische Grundelemente 11-26


Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

• void drawOval(<strong>in</strong>t x, <strong>in</strong>t y, <strong>in</strong>t width, <strong>in</strong>t height)<br />

Mit dieser Methode können Kreise und Ellipsen gezeichnet werden. Die Parameter<br />

spezifizieren e<strong>in</strong> Rechteck wie <strong>in</strong> der Methode drawRect. Es wird die größte<br />

Ellipse gezeichnet, die <strong>in</strong> dieses Rechteck h<strong>in</strong>e<strong>in</strong>passt.<br />

• void drawArc(<strong>in</strong>t x, <strong>in</strong>t y, <strong>in</strong>t width, <strong>in</strong>t height, <strong>in</strong>t<br />

startAngle, <strong>in</strong>t arcAngle)<br />

Mit drawArc kann e<strong>in</strong> Kreisbogen dargestellt werden. Die ersten vier Parameter<br />

geben den Kreis, startAngle den Anfangspunkt und arcAngle den W<strong>in</strong>kel an.<br />

11.2 Grafische Grundelemente 11-27


Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

Die folgenden Funktionen stellen die gleichen geometrischen Objekte dar wie die<br />

obigen, zeichnen aber nicht nur deren Umrisse, sondern füllen auch ihre Fläche aus.<br />

• void fillRect( ... )<br />

• void fillRoundRect( ... )<br />

• void fillPolygon( ... )<br />

• void fillOval( ... )<br />

• void fillArc( ... )<br />

11.2 Grafische Grundelemente 11-28


Elementare Grafikrout<strong>in</strong>en (Auswahl)<br />

• void clearRect(<strong>in</strong>t x, <strong>in</strong>t y, <strong>in</strong>t width, <strong>in</strong>t height)<br />

Die Methode clearRect überschreibt das angegebene Rechteck mit der aktuellen<br />

H<strong>in</strong>tergrundfarbe.<br />

• void copyArea(<strong>in</strong>t x, <strong>in</strong>t y, <strong>in</strong>t width, <strong>in</strong>t height, <strong>in</strong>t dx, <strong>in</strong>t<br />

dy)<br />

copyArea kopiert das ausgewählte Rechteck an die Position (x + dx, y + dy).<br />

• Mit e<strong>in</strong>er Clipp<strong>in</strong>g-Region kann die Ausgabe auf e<strong>in</strong>en bestimmten Bereich<br />

e<strong>in</strong>geschränkt werden.<br />

11.2 Grafische Grundelemente 11-29


Schriftarten<br />

• Ohne zusätzliche Anweisungen wird Text <strong>in</strong> e<strong>in</strong>em systemabhängigen<br />

Standard-Font ausgegeben. Um e<strong>in</strong>en anderen Font zur Textausgabe zu<br />

verwenden, muss zuerst e<strong>in</strong> Font-Objekt erzeugt und dann <strong>in</strong> den Grafik-Kontext<br />

e<strong>in</strong>getragen werden.<br />

• E<strong>in</strong> Font-Objekt kann mit e<strong>in</strong>em Konstruktor der Klasse Font erzeugt werden:<br />

Font(Str<strong>in</strong>g name, <strong>in</strong>t style, <strong>in</strong>t size)<br />

• Mit<br />

void setFont(Font font) und<br />

Font getFont()<br />

kann der Font gesetzt bzw. abgefragt werden.<br />

11.2 Grafische Grundelemente 11-30


Schriftarten<br />

• Der Parameter name gibt den Namen der gewünschten Schrift an. Font-Namen<br />

s<strong>in</strong>d beispielsweise Times New Roman, Helvetica oder Courier.<br />

• Schriften können Serifen besitzen oder auch serifenlos se<strong>in</strong>.<br />

• E<strong>in</strong> weiteres Kennzeichen e<strong>in</strong>er Schrift ist die Zeichenbreite. Diese kann variabel<br />

oder konstant se<strong>in</strong>. Bei konstanter Zeichenbreite bezeichnet man e<strong>in</strong>e Schrift als<br />

monospaced.<br />

• Beispiel: Der Font, <strong>in</strong> dem diese Folien geschrieben wurden, ist die serifenlose<br />

Variante der „Lat<strong>in</strong> Computer Modern“.<br />

• Es können auch die Font-Namen Serif, SansSerif und Monospaced verwendet<br />

werden. Sie werden auf entsprechende Fonts abgebildet.<br />

11.2 Grafische Grundelemente 11-31


Schriftarten<br />

• Der Parameter size gibt die Schriftgröße an. Übliche Schriftgrößen für Text liegen<br />

zwischen 10 pt und 12 pt.<br />

• Die Schriftart wird durch den Parameter style beschrieben:<br />

Name Wert Bedeutung<br />

Font.PLAIN 0 Standard-Font<br />

Font.BOLD 1 Fettdruck<br />

Font.ITALIC 2 Kursivdruck<br />

3 fetter Kursivdruck<br />

11.2 Grafische Grundelemente 11-32


Schriftarten<br />

Beispiel: Die folgenden Anweisungen bewirken, dass der Str<strong>in</strong>g "Zeichenkette" <strong>in</strong> e<strong>in</strong>er<br />

Schrift mit konstanter Zeichenbreite <strong>in</strong> fettem Kursivdruck <strong>in</strong> 12-Punkt-Schrift an die<br />

Position (50,350) geschrieben wird:<br />

Font f = new Font("Monospaced",3,12);<br />

g.setFont(f);<br />

g.drawStr<strong>in</strong>g("Zeichenkette",50,350);<br />

11.2 Grafische Grundelemente 11-33


Schriftarten<br />

Das folgende Beispiel gibt die drei Standardschriften <strong>in</strong> 36 Punkt aus:<br />

public void pa<strong>in</strong>t(Graphics g) {<br />

}<br />

Font font;<br />

Str<strong>in</strong>g[] arfonts = {"Serif","SansSerif","Monospaced"};<br />

for (<strong>in</strong>t i = 0; i < arfonts.length; ++i) {<br />

font = new Font(arfonts[i],Font.PLAIN,36);<br />

g.setFont(font);<br />

g.drawStr<strong>in</strong>g(arfonts[i],10,30 + (i + 1) * (36 + 5));<br />

}<br />

11.2 Grafische Grundelemente 11-34


Schriftarten<br />

• Die Klasse Font besitzt Methoden, um Informationen über den aktuellen Font zu<br />

gew<strong>in</strong>nen:<br />

◦ Str<strong>in</strong>g getFamily()<br />

◦ <strong>in</strong>t getStyle()<br />

◦ <strong>in</strong>t getSize()<br />

• Die Klasse FontMetrics stellt Methoden zur Verfügung, mit denen die<br />

Größenmaßzahlen e<strong>in</strong>zelner Zeichen – wie Oberlänge, Unterlänge oder Breite –,<br />

Größen wie der Zeilenabstand oder die Länge e<strong>in</strong>es Str<strong>in</strong>gs ermittelt werden<br />

können.<br />

◦ <strong>in</strong>t charWidth(char ch)<br />

◦ <strong>in</strong>t str<strong>in</strong>gWidth(Str<strong>in</strong>g str)<br />

11.2 Grafische Grundelemente 11-35


Farbmodell<br />

E<strong>in</strong>e Möglichkeit, <strong>in</strong> <strong>Java</strong> Farben zu<br />

benutzen, basiert auf dem RGB-Farbmodell<br />

(Rot-Grün-Blau-Farbmodell). Jede dieser<br />

drei Grundfarben wird durch 8 Bits<br />

dargestellt. Der Anteil e<strong>in</strong>er Grundfarbe<br />

kann also durch e<strong>in</strong>e Dezimalzahl zwischen<br />

0 und 255 beschrieben werden. Für die<br />

gesamte Farbtiefe ergeben sich somit 24<br />

Bits.<br />

Farbe Rot Grün Blau<br />

Weiß 255 255 255<br />

Grau 127 127 127<br />

Schwarz 0 0 0<br />

Rot 255 0 0<br />

Grün 0 255 0<br />

Blau 0 0 255<br />

Gelb 255 255 0<br />

Magenta 255 0 255<br />

Cyan 0 255 255<br />

<strong>Java</strong> unterstützt weitere Farbmodelle, <strong>in</strong> denen Farben z. B. durch Farbton, Intensität<br />

und Helligkeit dargestellt werden.<br />

11.2 Grafische Grundelemente 11-36


Erzeugung von Farben<br />

• Farben werden durch die Klasse Color dargestellt. Jedes Objekt repräsentiert e<strong>in</strong>e<br />

Farbe, die durch ihren RGB-Wert e<strong>in</strong>deutig gekennzeichnet ist.<br />

• Konstruktoren:<br />

◦ Color(<strong>in</strong>t r, <strong>in</strong>t g, <strong>in</strong>t b)<br />

◦ Color(float r, float g, float b)<br />

Der erste Konstruktor erwartet ganzzahlige Werte im Bereich von 0 bis 255, der<br />

zweite Fließkommazahlen zwischen 0.0 und 1.0. Der Wert 0.0 entspricht der<br />

ganzzahligen 0, der Wert 1.0 der ganzzahligen 255.<br />

11.2 Grafische Grundelemente 11-37


Erzeugung von Farben<br />

• Die Klasse Color stellt etliche Farben als statische Objekte zur Verfügung:<br />

◦ static Color black<br />

◦ static Color red<br />

◦ static Color green<br />

◦ static Color blue<br />

◦ . . .<br />

• Von e<strong>in</strong>em bestehenden Farbobjekt kann der RGB-Wert mit den Methoden<br />

◦ <strong>in</strong>t getRed(),<br />

◦ <strong>in</strong>t getGreen() und<br />

◦ <strong>in</strong>t getBlue()<br />

ermittelt werden.<br />

11.2 Grafische Grundelemente 11-38


Verwendung von Farben<br />

• Um Farben bei der Ausgabe von Schrift oder Grafik zu verwenden, muss e<strong>in</strong> Objekt<br />

der Klasse Color erzeugt und mithilfe der Methode<br />

void setColor(Color c)<br />

dem grafischen Kontext zugewiesen werden.<br />

• Die Ausgabe erfolgt solange <strong>in</strong> der neuen Farbe, bis dem Kontext e<strong>in</strong>e neue Farbe<br />

zugeordnet wird.<br />

• Mit Color getColor() wird die aktuelle Farbe abgefragt.<br />

11.2 Grafische Grundelemente 11-39


Verwendung von Farben<br />

Beispiel:<br />

public void pa<strong>in</strong>t(Graphics g) {<br />

g.setColor(Color.red);<br />

g.drawStr<strong>in</strong>g("Zeichenkette",200,500);<br />

g.setColor(new Color(200,200,0));<br />

g.drawOval(50,400,60,160);<br />

...<br />

}<br />

11.2 Grafische Grundelemente 11-40


Die Klasse SystemColor<br />

• Die Klasse SystemColor stellt e<strong>in</strong>e Reihe von Farben zur Verfügung, die den<br />

Farben des Desktops entsprechen. Damit können Anwendungen entwickelt werden,<br />

die im Aussehen an die Betriebssystemumgebung angepasst s<strong>in</strong>d.<br />

• Beispiele:<br />

◦ SystemColor.desktop<br />

H<strong>in</strong>tergrundfarbe des Desktops<br />

◦ SystemColor.w<strong>in</strong>dow<br />

H<strong>in</strong>tergrundfarbe für Fenster<br />

◦ SystemColor.text<br />

H<strong>in</strong>tergrundfarbe für Text<br />

11.2 Grafische Grundelemente 11-41


<strong>Grafikprogrammierung</strong> <strong>in</strong> <strong>Java</strong>:<br />

Fensterklassen<br />

11.1 Grundlagen<br />

11.2 Grafische Grundelemente<br />

11.3 Fensterklassen<br />

11.4 Ereignisse und Widgets<br />

11.5 Applets<br />

11.6 Die Sw<strong>in</strong>g-Klassen<br />

11.3 Fensterklassen 11-42


Fensterklassen<br />

Das AWT enthält e<strong>in</strong>e Reihe von Fensterklassen, die über e<strong>in</strong>e Vererbungsl<strong>in</strong>ie<br />

mite<strong>in</strong>ander verbunden s<strong>in</strong>d. An der Spitze steht die Klasse Component:<br />

• Component<br />

◦ Conta<strong>in</strong>er<br />

∗ Panel<br />

- Applet<br />

∗ W<strong>in</strong>dow<br />

- Frame<br />

- Dialog<br />

· FileDialog<br />

◦ Button<br />

◦ Canvas<br />

◦ Checkbox<br />

11.3 Fensterklassen 11-43


Fensterklassen<br />

• Component ist e<strong>in</strong>e abstrakte Klasse, deren Objekte Programmelemente darstellen,<br />

die e<strong>in</strong>e Größe und e<strong>in</strong>e Position besitzen und die Ereignisse senden und auf<br />

Ereignisse reagieren können.<br />

• Conta<strong>in</strong>er ist ebenfalls e<strong>in</strong>e abstrakte Klasse. Sie erlaubt es, <strong>in</strong>nerhalb e<strong>in</strong>er<br />

Komponente weitere Komponenten aufzunehmen. Conta<strong>in</strong>er stellt Methoden,<br />

um Komponenten h<strong>in</strong>zuzufügen oder zu entfernen, bereit. Mit den<br />

LayoutManager-Klassen werden die Komponenten positioniert.<br />

11.3 Fensterklassen 11-44


Fensterklassen<br />

• Panel ist die e<strong>in</strong>fachste konkrete Klasse mit den Eigenschaften von Component<br />

und Conta<strong>in</strong>er.<br />

• Applet ist e<strong>in</strong>e direkte Unterklasse von Panel. E<strong>in</strong> Applet besitzt also die<br />

Fähigkeiten der Klassen Component und Conta<strong>in</strong>er. Diese Klasse spielt e<strong>in</strong>e<br />

entscheidende Rolle <strong>in</strong> der Entwicklung von Applets.<br />

• Die Klasse W<strong>in</strong>dow abstrahiert e<strong>in</strong> Top-Level-W<strong>in</strong>dow ohne Rahmen, Titelleiste<br />

und Menü. Sie ist für Anwendungen geeignet, die die Kontrolle über das gesamte<br />

Fenster benötigen.<br />

• Frame repräsentiert e<strong>in</strong> Top-Level-W<strong>in</strong>dow mit Rahmen, Titelleiste und<br />

optionalem Menü. E<strong>in</strong>em Frame kann e<strong>in</strong> Icon zugeordnet werden, das angezeigt<br />

wird, wenn e<strong>in</strong> Fenster m<strong>in</strong>imiert wird.<br />

11.3 Fensterklassen 11-45


Aufrufen und Schließen e<strong>in</strong>es Fensters<br />

• Um e<strong>in</strong> Fenster auf dem Bildschirm anzuzeigen, muss zunächst e<strong>in</strong>e geeignete<br />

Fensterklasse <strong>in</strong>stanziiert werden. Dafür kommen Klassen wie W<strong>in</strong>dow, Frame,<br />

Dialog, Applet und FileDialog <strong>in</strong> Frage. Die Klassen haben unterschiedliche<br />

Konstruktoren.<br />

• Nach der Instanziierung wird die Methode<br />

setVisible(boolean visible)<br />

aufgerufen, um das Fenster anzuzeigen. Wird true übergeben, wird das Fenster<br />

angezeigt, andernfalls geschlossen.<br />

• Um e<strong>in</strong> Fenster zu schließen, s<strong>in</strong>d die Methoden setVisible(false) und<br />

dispose() aufzurufen.<br />

11.3 Fensterklassen 11-46


Eigenschaften e<strong>in</strong>es Fensters<br />

• Größe und Position, geerbt von Component<br />

• Aktivierungskomponente, geerbt von Component<br />

• Fensterelemente<br />

◦ Titelleiste, Menü, Icon, Mauscursor, Standardfont, Vorder- und H<strong>in</strong>tergrundfarbe<br />

• Die Eigenschaften e<strong>in</strong>es Fensters können mithilfe spezieller Methoden gesetzt und<br />

abgefragt werden.<br />

• Beispiel: Objekte der Klasse Frame besitzen e<strong>in</strong>en Rahmen, e<strong>in</strong>e Titelleiste und<br />

optional e<strong>in</strong> Menü, Objekte der Klasse W<strong>in</strong>dow h<strong>in</strong>gegen nicht.<br />

11.3 Fensterklassen 11-47


<strong>Grafikprogrammierung</strong> <strong>in</strong> <strong>Java</strong>:<br />

Ereignisse und Widgets<br />

11.1 Grundlagen<br />

11.2 Grafische Grundelemente<br />

11.3 Fensterklassen<br />

11.4 Ereignisse und Widgets<br />

11.5 Applets<br />

11.6 Die Sw<strong>in</strong>g-Klassen<br />

11.4 Ereignisse und Widgets 11-48


Ereignisgesteuerte Programmierung<br />

• Ereignisse s<strong>in</strong>d beispielsweise das Drücken e<strong>in</strong>er Taste, die Betätigung des<br />

Rollbalkens oder die Bewegung der Maus.<br />

• Jedes Ereignis besitzt e<strong>in</strong>e Quelle (Source).<br />

• E<strong>in</strong> Ereignis kann von Beobachtern (Listener) wahrgenommen werden. Die<br />

Anmeldung von Beobachtern zur Benachrichtigung vom E<strong>in</strong>treten e<strong>in</strong>es Ereignisses<br />

ist frei programmierbar und muss immer explizit erfolgen.<br />

• Es ist nicht festgelegt, <strong>in</strong> welcher Reihenfolge die Beobachter vom E<strong>in</strong>treten e<strong>in</strong>es<br />

Ereignisses <strong>in</strong>formiert werden. Sichergestellt ist lediglich, dass jeder Beobachter<br />

e<strong>in</strong>e Kopie des ursprünglichen Ereignisses erhält.<br />

11.4 Ereignisse und Widgets 11-49


Ereignisgesteuerte Programmierung<br />

• Bei der Verbreitung von Ereignissen ist zwischen den Modi s<strong>in</strong>gle-cast und<br />

multi-cast zu unterscheiden. Für S<strong>in</strong>gle-Cast-Ereignisse wird der Beobachter mit<br />

e<strong>in</strong>er setxxListener-Methode gesetzt, für Multi-Cast-Ereignisse wird e<strong>in</strong><br />

Beobachter mit e<strong>in</strong>er addxxListener-Methode der Menge der Beobachter<br />

h<strong>in</strong>zugefügt.<br />

• E<strong>in</strong>e Adapter-Klasse ist e<strong>in</strong>e Klasse, die e<strong>in</strong>e gegebene Schnittstelle implementiert,<br />

<strong>in</strong>dem sie jede abstrakte Methode durch e<strong>in</strong>en leeren Rumpf realisiert.<br />

Adapter-Klassen werden verwendet, wenn von e<strong>in</strong>er Schnittstelle lediglich e<strong>in</strong> Teil<br />

der Methoden benötigt wird, der Rest aber un<strong>in</strong>teressant ist. In diesem Fall leitet<br />

man e<strong>in</strong>e neue Klasse aus der Adapter-Klasse ab und überlagert nur die<br />

erforderlichen Methoden.<br />

11.4 Ereignisse und Widgets 11-50


Ereignisklassen<br />

• EventObject<br />

◦ AWTEvent<br />

∗ ComponentEvent<br />

- FocusEvent<br />

- InputEvent<br />

- KeyEvent<br />

- MouseEvent<br />

- Conta<strong>in</strong>erEvent<br />

- W<strong>in</strong>dowEvent<br />

∗ ActionEvent<br />

∗ AdjustmentEvent<br />

∗ ItemEvent<br />

∗ TextEvent<br />

11.4 Ereignisse und Widgets 11-51


EventListener-Schnittstellen<br />

• EventListener<br />

◦ FocusListener<br />

◦ ActionListener<br />

◦ AdjustmentListener<br />

◦ ItemListener<br />

◦ TextListener<br />

◦ KeyListener<br />

◦ MouseListener<br />

◦ MouseMotionListener<br />

◦ W<strong>in</strong>dowListener<br />

◦ Conta<strong>in</strong>erListener<br />

◦ ComponentListener<br />

11.4 Ereignisse und Widgets 11-52


Low-Level-Events<br />

Beispiel: W<strong>in</strong>dow-Events<br />

• w<strong>in</strong>dowOpened<br />

• w<strong>in</strong>dowActivated, w<strong>in</strong>dowDeactivated<br />

• w<strong>in</strong>dowClosed<br />

• w<strong>in</strong>dowClos<strong>in</strong>g<br />

• w<strong>in</strong>dowIconified, w<strong>in</strong>dowDeiconified<br />

11.4 Ereignisse und Widgets 11-53


Widgets<br />

Fensterelemente mit E<strong>in</strong>- und/oder Ausgabefunktionalität werden als Widgets<br />

(w<strong>in</strong>dow gadgets) bezeichnet. Die Anordnung der Widgets <strong>in</strong> e<strong>in</strong>em Fenster wird<br />

durch den Layout-Manager durchgeführt. Widgets s<strong>in</strong>d beispielsweise:<br />

• Label<br />

• Rollbalken<br />

• Schaltflächen (buttons)<br />

• Checkboxen und Checkboxgruppen (radio buttons)<br />

11.4 Ereignisse und Widgets 11-54


Widgets<br />

• Textfelder und Textbereiche<br />

• Auswahlboxen<br />

• Listen<br />

• Canvas<br />

• Panels<br />

• Dateidialogboxen (nicht für Applets)<br />

• Menüs (nicht für Applets)<br />

11.4 Ereignisse und Widgets 11-55


Schritte zur Realisierung e<strong>in</strong>es Widgets<br />

• Schnittstelle angeben<br />

• Widget deklarieren und <strong>in</strong>itialisieren<br />

• Widget dem Layout h<strong>in</strong>zufügen<br />

• Beobachter registrieren<br />

• Ereignis behandeln<br />

Man beachte, dass mehrere Widgettypen dieselbe Ereignisklasse verwenden, z. B.<br />

benutzen Schaltflächen und Textfelder die Klasse ActionListener.<br />

11.4 Ereignisse und Widgets 11-56


Beispiel: Rollbalken<br />

Als erstes Beispiel betrachten wir jetzt die Programmierung e<strong>in</strong>es Rollbalkens.<br />

import java.awt.*;<br />

import java.awt.event.*;<br />

public class W<strong>in</strong>dowBl<strong>in</strong>d extends Frame<br />

implements AdjustmentListener {<br />

private Scrollbar schieber;<br />

private <strong>in</strong>t schieberWert;<br />

11.4 Ereignisse und Widgets 11-57


public W<strong>in</strong>dowBl<strong>in</strong>d() {<br />

setLayout(new FlowLayout());<br />

setBackground(Color.white);<br />

schieber = new Scrollbar(Scrollbar.HORIZONTAL,0,1,0,101);<br />

add(schieber);<br />

addW<strong>in</strong>dowListener(new W<strong>in</strong>dowClos<strong>in</strong>gAdapter());<br />

schieber.addAdjustmentListener(this);<br />

}<br />

11.4 Ereignisse und Widgets 11-58


public void pa<strong>in</strong>t(Graphics g) {<br />

g.drawStr<strong>in</strong>g("Rollbalkenwert ist " + schieberWert,120,200);<br />

g.setColor(Color.red);<br />

g.drawRect(40,80,60,100);<br />

g.fillRect(40,80,60,schieberWert);<br />

g.setColor(Color.blue);<br />

g.drawRect(120,80,60,100);<br />

g.fillRect(120,80 + schieberWert,60,100 - schieberWert);<br />

g.setColor(Color.green);<br />

g.drawRect(200,80,60,100);<br />

g.fillRect(200,80,60,100 - schieberWert);<br />

}<br />

11.4 Ereignisse und Widgets 11-59


public void adjustmentValueChanged(AdjustmentEvent e) {<br />

schieberWert = schieber.getValue();<br />

repa<strong>in</strong>t();<br />

}<br />

11.4 Ereignisse und Widgets 11-60


public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

W<strong>in</strong>dowBl<strong>in</strong>d f = new W<strong>in</strong>dowBl<strong>in</strong>d();<br />

f.setSize(400,300);<br />

f.setVisible(true);<br />

}<br />

}<br />

11.4 Ereignisse und Widgets 11-61


Beispiel: Label und Button<br />

... implements ActionListener {<br />

private Label title;<br />

private Button knopf;<br />

private <strong>in</strong>t anzahl = 0;<br />

public Konstruktor() {<br />

setLayout(new FlowLayout());<br />

title = new Label("Zählknopf:");<br />

knopf = new Button("Drück mich!");<br />

add(title);<br />

add(knopf);<br />

knopf.addActionListener(this);<br />

}<br />

11.4 Ereignisse und Widgets 11-62


public void pa<strong>in</strong>t(Graphics g) {<br />

g.drawStr<strong>in</strong>g("Der Knopf wurde " + anzahl +<br />

" mal gedrückt.",10,80);<br />

}<br />

public void actionPerformed(ActionEvent event) {<br />

anzahl++;<br />

repa<strong>in</strong>t();<br />

}<br />

}<br />

11.4 Ereignisse und Widgets 11-63


Weitere Widgets<br />

• Textfield:<br />

ActionListener, addActionListener<br />

void actionPerformed(ActionEvent event)<br />

• Checkbox, Checkboxgroup:<br />

ItemListener, addItemListener<br />

void itemStateChanged(ItemEvent event)<br />

• Choice:<br />

ItemListener, addItem, addItemListener<br />

void itemStateChanged(ItemEvent event)<br />

11.4 Ereignisse und Widgets 11-64


<strong>Grafikprogrammierung</strong> <strong>in</strong> <strong>Java</strong>:<br />

Applets<br />

11.1 Grundlagen<br />

11.2 Grafische Grundelemente<br />

11.3 Fensterklassen<br />

11.4 Ereignisse und Widgets<br />

11.5 Applets<br />

11.6 Die Sw<strong>in</strong>g-Klassen<br />

11.5 Applets 11-65


• Anwendungen (Applikationen)<br />

Anwendungen und Applets<br />

◦ Anwendungen bilden eigenständige Programme. Zur Ausführung benötigen sie<br />

nur den <strong>Java</strong>-Interpreter und die .class-Dateien der beteiligten Klassen.<br />

◦ Jede Klasse, die die Methode public static void ma<strong>in</strong> enthält, kann als<br />

Anwendung benutzt werden.<br />

• Applets (little applications)<br />

◦ Applets s<strong>in</strong>d kle<strong>in</strong>e Programme, die <strong>in</strong> e<strong>in</strong>e Html-Seite e<strong>in</strong>gebettet s<strong>in</strong>d und nur<br />

<strong>in</strong>nerhalb e<strong>in</strong>es Web-Browsers oder e<strong>in</strong>es Applet-Viewers ausgeführt werden<br />

können.<br />

◦ Applets werden nicht durch die Methode ma<strong>in</strong> gestartet, sondern müssen aus<br />

der Klasse Applet abgeleitet und entsprechend konstruiert werden.<br />

11.5 Applets 11-66


import java.awt.*;<br />

import java.applet.*;<br />

E<strong>in</strong> kle<strong>in</strong>es Applet: <strong>Java</strong>-Datei<br />

public class M<strong>in</strong>imalApplet extends Applet {<br />

}<br />

public void pa<strong>in</strong>t(Graphics g) {<br />

g.drawStr<strong>in</strong>g("Test-Ausgabe",0,20);<br />

}<br />

11.5 Applets 11-67


E<strong>in</strong> kle<strong>in</strong>es Applet: Html-Seite<br />

<br />

<br />

Applet-Test<br />

<br />

<br />

<br />

Hier steht das Applet.<br />

<br />

<br />

11.5 Applets 11-68


Anwendungen und Applets<br />

• E<strong>in</strong> Applet wird immer aus der Klasse Applet abgeleitet. Bei e<strong>in</strong>er Anwendung ist<br />

es dagegen gleichgültig, woraus die Hauptklasse abgeleitet wird.<br />

• E<strong>in</strong>e Anwendung wird gestartet, <strong>in</strong>dem vom <strong>Java</strong>-Interpreter die Methode ma<strong>in</strong><br />

aufgerufen wird. Das Starten e<strong>in</strong>es Applets wird dadurch erreicht, dass der Browser<br />

oder der Applet-Viewer die Applet-Klasse <strong>in</strong>stanziiert und die Methoden <strong>in</strong>it und<br />

start aufruft.<br />

• Aus Gründen der Sicherheit darf e<strong>in</strong> Applet <strong>in</strong> der Regel weder auf Dateien des<br />

lokalen Rechners zugreifen noch externe Programme auf dem Rechner starten.<br />

11.5 Applets 11-69


Anwendungen und Applets<br />

• E<strong>in</strong> Applet arbeitet immer ereignisorientiert. Im Gegensatz dazu kann e<strong>in</strong>e<br />

Anwendung auf die Behandlung von Ereignissen verzichten und alle E<strong>in</strong>- und<br />

Ausgaben textbasiert durchführen.<br />

• Im Vergleich zu Anwendungen bieten Applets e<strong>in</strong>ige zusätzliche Möglichkeiten.<br />

11.5 Applets 11-70


Die Klasse Applet<br />

Die Klasse Applet steht <strong>in</strong> der Vererbungshierarchie unter der Klasse Component<br />

und Conta<strong>in</strong>er. Sie besitzt damit deren Eigenschaften.<br />

• Component<br />

◦ Conta<strong>in</strong>er<br />

∗ Panel<br />

- Applet<br />

Bezüglich der Reaktion auf Ereignisse und die Registrierung und Programmierung von<br />

Listener-Klassen verhält sich e<strong>in</strong> Applet wie jedes andere Fenster.<br />

11.5 Applets 11-71


• <strong>in</strong>it(): Initialisierung e<strong>in</strong>es Applets<br />

• start(): Start e<strong>in</strong>es Applets<br />

• stop(): Stopp e<strong>in</strong>es Applets,<br />

z. B. beim Laden e<strong>in</strong>er anderen Seite.<br />

Methoden<br />

start und stop können mehrfach während der Lebensdauer e<strong>in</strong>es Applets<br />

aufgerufen werden.<br />

• pa<strong>in</strong>t(Graphics g): Methode zum Zeichnen<br />

• destroy(): Beenden e<strong>in</strong>es Applets<br />

11.5 Applets 11-72


Beispiel: Rollbalken<br />

Als Beispiel schreiben wir das Rollbalkenprogramm als Applet.<br />

import java.awt.*;<br />

import java.awt.event.*;<br />

import java.applet.Applet;<br />

public class W<strong>in</strong>dowBl<strong>in</strong>d extends Applet<br />

implements AdjustmentListener {<br />

private Scrollbar schieber;<br />

private <strong>in</strong>t schieberWert;<br />

11.5 Applets 11-73


public void <strong>in</strong>it () {<br />

setBackground(Color.white);<br />

schieber = new Scrollbar(Scrollbar.HORIZONTAL,0,1,0,101);<br />

add(schieber);<br />

schieber.addAdjustmentListener(this);<br />

}<br />

11.5 Applets 11-74


public void pa<strong>in</strong>t(Graphics g) {<br />

showStatus("Rollbalkenwert ist " + schieberWert);<br />

g.setColor(Color.red);<br />

g.drawRect(40,80,60,100);<br />

g.fillRect(40,80,60,schieberWert);<br />

g.setColor(Color.blue);<br />

g.drawRect(120,80,60,100);<br />

g.fillRect(120,80 + schieberWert,60,100 - schieberWert);<br />

g.setColor(Color.green);<br />

g.drawRect(200,80,60,100);<br />

g.fillRect(200,80,60,100 - schieberWert);<br />

}<br />

11.5 Applets 11-75


public void adjustmentValueChanged(AdjustmentEvent e) {<br />

schieberWert = schieber.getValue();<br />

repa<strong>in</strong>t();<br />

}<br />

}<br />

11.5 Applets 11-76


Anwendungen und Applets<br />

Dies s<strong>in</strong>d die wesentlichen Schritte, um e<strong>in</strong>e Anwendung <strong>in</strong> e<strong>in</strong> Applet zu konvertieren.<br />

Die Anwendung darf nur Elemente benutzen, die auch für Applets erlaubt s<strong>in</strong>d.<br />

• Html-Seite erzeugen<br />

• ma<strong>in</strong>-Methode löschen<br />

• Aus dem Paket java.applet importieren, JApplet statt JFrame erweitern<br />

• Konstruktor <strong>in</strong> <strong>in</strong>it umbenennen, ggf. start, stop, destroy schreiben<br />

• Layout festlegen<br />

• Bei mehreren Klassen: jar-Datei erzeugen<br />

11.5 Applets 11-77


Anwendungen und Applets<br />

Dies s<strong>in</strong>d die wesentlichen Schritte, um e<strong>in</strong> Applet <strong>in</strong> e<strong>in</strong>e Anwendung zu konvertieren.<br />

Das Applet darf ke<strong>in</strong>e speziellen Methoden der applet-Klasse verwenden.<br />

• import applet löschen<br />

• frame statt applet erweitern<br />

• <strong>in</strong>it als Konstruktor schreiben<br />

• ma<strong>in</strong>-Methode erzeugen<br />

• Methode zum Fenster schließen h<strong>in</strong>zufügen<br />

• Layout festlegen<br />

11.5 Applets 11-78


<strong>Grafikprogrammierung</strong> <strong>in</strong> <strong>Java</strong>:<br />

Die Sw<strong>in</strong>g-Klassen<br />

11.1 Grundlagen<br />

11.2 Grafische Grundelemente<br />

11.3 Fensterklassen<br />

11.4 Ereignisse und Widgets<br />

11.5 Applets<br />

11.6 Die Sw<strong>in</strong>g-Klassen<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-79


Die <strong>Java</strong> Foundation Classes<br />

Seit der Version 1.2 des JDK werden die grafischen Fähigkeiten von <strong>Java</strong> unter dem<br />

Begriff <strong>Java</strong> Foundation Classes (JFC) zusammengefasst. Die drei wichtigsten<br />

Bestandteile s<strong>in</strong>d:<br />

• Das Abstract W<strong>in</strong>dow Toolkit (AWT) stellt elementare Grafik- und<br />

Fensterfunktionen auf der Basis der jeweiligen Zielmasch<strong>in</strong>e zur Verfügung.<br />

• Das Sw<strong>in</strong>g Toolset bietet darüber h<strong>in</strong>ausgehende Möglichkeiten zur Konstruktion<br />

komplexer grafischer Oberflächen. Insbesondere wird e<strong>in</strong> „pluggable look and feel“<br />

ermöglicht.<br />

• Die dritte wichtige Komponente ist die <strong>Java</strong> 2D API (Klassen für zweidimensionale<br />

Grafikverarbeitung) mit diversen Grafikoperationen und Bildbearbeitungsrout<strong>in</strong>en.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-80


Die <strong>Java</strong> Foundation Classes<br />

Die Klassen lassen sich <strong>in</strong> vier Gruppen e<strong>in</strong>teilen:<br />

• Komponenten enthalten die Bestandteile der Fenster. Komponenten s<strong>in</strong>d<br />

beispielsweise Beschriftungen (label), Auswahlfelder und Knöpfe (buttons).<br />

• Behälter (conta<strong>in</strong>er) bestehen aus Komponenten, die auch selbst Komponenten<br />

enthalten können. Beispielsweise s<strong>in</strong>d die Objekte der Klassen JFrame und<br />

JW<strong>in</strong>dow Behälter.<br />

• Layout-Manager, Fonts und Farben bestimmen die Anordnung und das Aussehen<br />

der Komponenten <strong>in</strong> e<strong>in</strong>em Behälter.<br />

• Mit den Ereignisklassen werden mögliche Ereignisse, Beobachter und Reaktionen<br />

festgelegt.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-81


Die <strong>Java</strong> Foundation Classes<br />

• Die Sw<strong>in</strong>g-Bibliothek ersetzt und erweitert die Komponenten- und Behälterklassen<br />

des AWTs.<br />

• Die AWT-Klassen zu Schrift, Farbe und Layout-Manager sowie die Ereignisklassen<br />

werden weiterverwendet.<br />

• Die AWT-Klassen bef<strong>in</strong>den sich im Paket java.awt, die Sw<strong>in</strong>gklassen <strong>in</strong><br />

javax.sw<strong>in</strong>g.<br />

• Die Klassen der Sw<strong>in</strong>g-Bibliothek beg<strong>in</strong>nen <strong>in</strong> der Regel mit dem Buchstaben J.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-82


AWT und Sw<strong>in</strong>g im Vergleich<br />

• Im AWT wird der Peer-Ansatz verfolgt: Alle AWT-Komponenten reichen die<br />

auszuführenden Aktionen an plattformspezifische GUI-Objekte, sogenannte Peers,<br />

weiter. Komponenten, die solche Peer-Objekte benötigen, werden als<br />

schwergewichtig bezeichnet. Diese Komponenten sehen auf unterschiedlichen<br />

Betriebssystemen unterschiedlich aus. Es können nur die Funktionalitäten<br />

bereitgestellt werden, die auf dem jeweiligen Betriebssystem zur Verfügung stehen.<br />

• Fast alle Sw<strong>in</strong>g-Komponenten s<strong>in</strong>d vollständig <strong>in</strong> <strong>Java</strong> geschrieben und werden<br />

deshalb leichtgewichtig genannt. Form und Funktion s<strong>in</strong>d daher weitgehend<br />

unabhängig vom Betriebssystem. Die Oberfläche kann plattformunabhängig<br />

gestaltet werden und ist noch zur Laufzeit veränderbar (pluggable look and feel).<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-83


Wiederholung: E<strong>in</strong> e<strong>in</strong>faches AWT-Beispiel<br />

import java.awt.*;<br />

public class FrameOhneInhaltAWT {<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

Frame fenster = new Frame();<br />

fenster.setTitle("E<strong>in</strong> AWT-Fenster");<br />

fenster.setLocation(500,400);<br />

fenster.setSize(300,150);<br />

fenster.setVisible(true);<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-84


import javax.sw<strong>in</strong>g.*;<br />

E<strong>in</strong> e<strong>in</strong>faches Sw<strong>in</strong>g-Beispiel<br />

public class FrameOhneInhaltSw<strong>in</strong>g {<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

JFrame fenster = new JFrame();<br />

fenster.setTitle("E<strong>in</strong> Sw<strong>in</strong>g-Fenster");<br />

fenster.setLocation(500,400);<br />

fenster.setSize(300,150);<br />

fenster.setVisible(true);<br />

fenster.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-85


AWT und Sw<strong>in</strong>g im Vergleich<br />

• Es wird aus unterschiedlichen Paketen importiert:<br />

import java.awt.* bzw. import javax.sw<strong>in</strong>g.*.<br />

• Die Behälterklassen s<strong>in</strong>d verschieden: Frame bzw. JFrame.<br />

• In der Sw<strong>in</strong>g-Variante gibt es e<strong>in</strong>e e<strong>in</strong>fache Möglichkeit zum Schließen e<strong>in</strong>es<br />

Fensters: setDefaultCloseOperation.<br />

• Beim Lauf erzeugt die Sw<strong>in</strong>gklasse e<strong>in</strong>en grauen H<strong>in</strong>tergrund.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-86


E<strong>in</strong>e abgeleitete Sw<strong>in</strong>g-Klasse<br />

import javax.sw<strong>in</strong>g.*;<br />

public class FrameOhneInhalt extends JFrame {<br />

}<br />

public FrameOhneInhalt () { }<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

FrameOhneInhalt fenster = new FrameOhneInhalt();<br />

fenster.setTitle("Frame ohne Inhalt");<br />

fenster.setSize(300,150);<br />

fenster.setVisible(true);<br />

fenster.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-87


E<strong>in</strong> Fenster mit Text<br />

public class FrameMitText extends JFrame {<br />

Conta<strong>in</strong>er c;<br />

// Conta<strong>in</strong>er dieses Frames<br />

JLabel beschriftung; // Label, das im Frame ersche<strong>in</strong>en soll<br />

public FrameMitText() {<br />

c = getContentPane();<br />

c.setLayout(new FlowLayout());<br />

beschriftung = new JLabel("Label-Text im Frame");<br />

c.add(beschriftung);<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

FrameMitText fenster = new FrameMitText();<br />

fenster.setTitle("Frame mit Text im Label");<br />

fenster.setSize(300,150); fenster.setVisible(true);<br />

fenster.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);<br />

}}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-88


E<strong>in</strong>ordnung der Sw<strong>in</strong>gklassen<br />

• Component<br />

◦ Conta<strong>in</strong>er<br />

∗ Panel<br />

- Applet<br />

· JApplet<br />

∗ W<strong>in</strong>dow<br />

- JW<strong>in</strong>dow<br />

- Frame<br />

· JFrame<br />

- Dialog<br />

· JDialog<br />

∗ JComponent<br />

◦ Button, Label, weitere AWT-Komponenten<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-89


E<strong>in</strong>ordnung der Sw<strong>in</strong>gklassen<br />

• JComponent<br />

◦ JLabel<br />

◦ AbstractButton<br />

◦ JComboBox<br />

◦ JMenuBar<br />

◦ JList<br />

◦ JScrollbar<br />

◦ JProgressbar<br />

◦ JTextComponent<br />

◦ JPanel<br />

◦ JTable<br />

◦ ...<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-90


E<strong>in</strong>ordnung der Sw<strong>in</strong>gklassen<br />

• Die Sw<strong>in</strong>g-Behälter-Klassen JFrame, JW<strong>in</strong>dow, . . . s<strong>in</strong>d Erweiterungen der<br />

entsprechenden AWT-Klassen.<br />

• Die Sw<strong>in</strong>g-Komponenten-Klassen bilden e<strong>in</strong>e eigene Hierarchie unterhalb von<br />

Conta<strong>in</strong>er.<br />

• Alle Sw<strong>in</strong>g-Klassen stehen unterhalb von Conta<strong>in</strong>er und erben somit von<br />

Component und Conta<strong>in</strong>er.<br />

Die gleichzeitige Verwendung von<br />

AWT- und Sw<strong>in</strong>g-Komponenten ist zu vermeiden.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-91


Wiederholung: Die Klasse Component<br />

Die abstrakte Klasse Component steht an oberster Stelle der JFC-Hierachie. Sie stellt<br />

Basismethoden zur Verfügung, die alle AWT- und Sw<strong>in</strong>gkomponenten geme<strong>in</strong>sam<br />

nutzen können. Die wichtigsten s<strong>in</strong>d:<br />

• Color getBackground(), Color getForeground()<br />

• void setBackground(Color c), void setForeground(Color c)<br />

• Font getFont, void setFont(Font c)<br />

• <strong>in</strong>t getHeight(), <strong>in</strong>t getWidth()<br />

• void setSize(<strong>in</strong>t width, <strong>in</strong>t height)<br />

• setLocation(<strong>in</strong>t x, <strong>in</strong>t y)<br />

• boolean isEnabled(), void setEnabled(boolean b)<br />

• boolean isVisible(), void setVisible(boolean b)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-92


Wiederholung: Die Klasse Conta<strong>in</strong>er<br />

Behälter s<strong>in</strong>d spezielle Komponenten, die andere Komponenten enthalten können. Die<br />

Klasse Conta<strong>in</strong>er stellt demzufolge Methoden zum E<strong>in</strong>fügen, Verwalten und<br />

Entfernen von Komponenten zu Verfügung. Die Komponenten werden <strong>in</strong> e<strong>in</strong>er Liste<br />

geführt, wobei die Reihenfolge sich durch die Reihenfolge der E<strong>in</strong>fügungen ergibt oder<br />

durch e<strong>in</strong>en Listen<strong>in</strong>dex bestimmt werden kann. Die Liste wird zur Anordnung der<br />

Komponenten <strong>in</strong> dem Behälterobjekt benötigt.<br />

• Component add(Component comp)<br />

• Component add(Component comp, <strong>in</strong>t <strong>in</strong>dex)<br />

• Component[] getComponents()<br />

• void remove(Component comp)<br />

• void setLayout(LayoutManager mgr)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-93


Die Klasse JComponent<br />

Die abstrakte Klasse JComponent dient als Basisklasse für sämtliche<br />

Sw<strong>in</strong>gkomponenten mit Ausnahme der Klassen Component und Conta<strong>in</strong>er. Von<br />

diesen beiden Klassen erbt JComponent und überschreibt dabei e<strong>in</strong>ige Methoden.<br />

Komponenten können durchsichtig oder opaque (undurchsichtig) se<strong>in</strong> und mit e<strong>in</strong>em<br />

erläuternden Text, dem sog. Tooltip, versehen werden. Der Text ersche<strong>in</strong>t, wenn der<br />

Mauszeiger e<strong>in</strong>ige Sekunden auf der Komponente ruht.<br />

• boolean isOpaque()<br />

• void setOpaque(boolean b)<br />

• Str<strong>in</strong>g getToolTipText()<br />

• void setToolTipText(Str<strong>in</strong>g text)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-94


Die Klasse JComponent<br />

All Implemented Interfaces:<br />

ImageObserver, MenuConta<strong>in</strong>er, Serializable<br />

Direct Known Subclasses:<br />

AbstractButton, BasicInternalFrameTitlePane, Box, Box.Filler,<br />

JColorChooser, JComboBox, JFileChooser, JInternalFrame,<br />

JInternalFrame.JDesktopIcon, JLabel, JLayeredPane, JList,<br />

JMenuBar, JOptionPane, JPanel, JPopupMenu, JProgressBar,<br />

JRootPane, JScrollBar, JScrollPane, JSeparator, JSlider,<br />

JSp<strong>in</strong>ner, JSplitPane, JTabbedPane, JTable, JTableHeader,<br />

JTextComponent, JToolBar, JToolTip, JTree, JViewport<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-95


Komponenten: Inhalt und Anordnung<br />

E<strong>in</strong> Behälterobjekt enthält <strong>in</strong> der Regel e<strong>in</strong>e oder mehrere Komponenten. Die<br />

Komponenten können Texte, Bilder, Zeichnungen, . . . enthalten. Mithilfe e<strong>in</strong>es<br />

Layoutmanagers werden die Komponenten <strong>in</strong>nerhalb des Behälters angeordnet.<br />

• Mit der Klasse Font können Schriften ausgewählt werden.<br />

• Die Klasse Color stellt Farben zur Verfügung.<br />

• Die abstrakte Klasse Graphics bietet Möglichkeiten zur Erstellung von<br />

Zeichnungen.<br />

• Die Schnittstelle LayoutManager offeriert Methoden zur Anordnung der<br />

Komponenten. Die Schnittstelle Border und die Klasse BorderFactory bieten<br />

Möglichkeiten zur Gestaltung der Grenzen zwischen Komponenten.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-96


Die Klasse FlowLayout<br />

Bei Verwendung der Klasse FlowLayout werden die Komponenten fließend, d. h.<br />

zeilenweise von l<strong>in</strong>ks nach rechts, angeordnet. Innerhalb e<strong>in</strong>er Zeile werden die<br />

Komponenten zentriert. Zwischen den Zeilen bef<strong>in</strong>det sich e<strong>in</strong> Standardabstand von<br />

5 Pixeln, der aber geändert werden kann. Mit dem Parameter align kann bestimmt<br />

werden, ob die Komponenten l<strong>in</strong>ks- oder rechtsbündig bzw. zentriert dargestellt<br />

werden. hp und vp bestimmen die Abstände zwischen den Komponenten und Zeilen.<br />

• FlowLayout()<br />

• FlowLayout(<strong>in</strong>t align)<br />

• FlowLayout(<strong>in</strong>t align, <strong>in</strong>t hp, <strong>in</strong>t vp)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-97


Die Klasse BorderLayout<br />

Bei diesem Layout wird die Behälterfläche <strong>in</strong> die fünf Bereiche Nord, Ost, Süd, West<br />

und Zentrum aufgeteilt. In jedes dieser Gebiete kann e<strong>in</strong>e Komponente e<strong>in</strong>gefügt<br />

werden. Die Größe von Nord, Ost, Süd und West ergibt sich aus dem jeweiligen<br />

Objekt, während die Größe des Zentrums an die Gesamtgröße des Behälters angepasst<br />

wird. Beispielsweise wird durch add(...,BorderLayout.NORTH) e<strong>in</strong> Objekt im<br />

oberen Bereich h<strong>in</strong>zugefügt.<br />

• BorderLayout()<br />

• BorderLayout(<strong>in</strong>t hp, <strong>in</strong>t vp)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-98


Die Klasse GridLayout<br />

Die Behälterfläche wird gitterartig <strong>in</strong> z Zeilen und s Spalten aufgeteilt. Die Werte z<br />

und s werden bereits dem Konstruktor übergeben.<br />

• GridLayout()<br />

• GridLayout(<strong>in</strong>t z, <strong>in</strong>t s)<br />

• GridLayout(<strong>in</strong>t z, <strong>in</strong>t s, <strong>in</strong>t hp, <strong>in</strong>t vp)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-99


Die Klasse Graphics<br />

• Die abstrakte Klasse Graphics stellt zahlreiche Methoden bereit, die es<br />

ermöglichen, <strong>in</strong>nerhalb des Koord<strong>in</strong>atensystems e<strong>in</strong>er Komponente zu zeichnen.<br />

Hierzu zählen die Methoden, die wir bereits kennengelernt haben: drawL<strong>in</strong>e,<br />

drawRect, . . . . In e<strong>in</strong>em grafischen Kontext s<strong>in</strong>d die gegenwärtigen E<strong>in</strong>stellungen<br />

zu Schrift und Farbe sowie die zu bearbeitende Komponente gespeichert.<br />

• Die Klasse Graphics2D ist aus Graphics abgeleitet und erweitert diese um viele<br />

Aspekte, <strong>in</strong>sbesondere um solche zur Darstellung von zweidimensionalen<br />

Zeichnungen.<br />

• Für die Darstellung e<strong>in</strong>er e<strong>in</strong>zelnen Sw<strong>in</strong>g-Komponente ist der Repa<strong>in</strong>t-Manager<br />

zuständig. Er sorgt dafür, dass beim erstmaligen Ersche<strong>in</strong>en und bei Veränderungen<br />

die Methode public void pa<strong>in</strong>t(Graphics g) aufgerufen wird.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-100


Die Komponentenklasse JLabel<br />

Die Klasse JLabel dient zur Darstellung von Texten und Bildern.<br />

public class MyFrame extends JFrame {<br />

Conta<strong>in</strong>er c; // Conta<strong>in</strong>er dieses Frames<br />

JLabel lab; // Label, das im Frame ersche<strong>in</strong>en soll<br />

public MyFrame() {<br />

c = getContentPane();<br />

c.setLayout(new FlowLayout());<br />

Icon bild = new ImageIcon("xxx.jpg");<br />

lab = new JLabel("Text", bild, JLabel.CENTER);<br />

lab.setHorizontalTextPosition(JLabel.CENTER);<br />

lab.setVerticalTextPosition(JLabel.BOTTOM);<br />

c.add(lab);<br />

}<br />

...<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-101


Die Komponentenklasse AbstractButton<br />

Die abstrakte Klasse bietet verschiedene Arten von Schaltflächen und Knöpfen. Die<br />

wichtigsten Implementierungen s<strong>in</strong>d:<br />

• JButton<br />

• JToggleButton<br />

◦ JCheckBox<br />

◦ JRadioButton<br />

• JMenuItem<br />

◦ JMenu<br />

◦ JCheckBoxMenuItem<br />

◦ JRadioButtonMenuItem<br />

(e<strong>in</strong>fache Schaltfläche zum Auslösen von Aktionen)<br />

(Schalter mit zwei Zuständen)<br />

(Kennzeichnung durch Häkchen)<br />

(sich ausschließende Schalter)<br />

(Schaltflächen <strong>in</strong> e<strong>in</strong>em Menü)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-102


Beispiel: JRadioButton<br />

Conta<strong>in</strong>er c;<br />

JRadioButton rb[] = new JRadioButton[4];<br />

...<br />

public Konstruktor() {<br />

c = getContentPane();<br />

c.setLayout(new FlowLayout());<br />

ButtonGroup bg = new ButtonGroup();<br />

for (<strong>in</strong>t i = 0; i < 4; i++) {<br />

rb[i] = new JRadioButton("Box " + (i+1));<br />

bg.add(rb[i]);<br />

c.add(rb[i]);<br />

}<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-103


Die Komponentenklasse JComboBox<br />

• E<strong>in</strong> Objekt der Klasse JComboBox ist e<strong>in</strong>e aufklappbare Auswahlliste, die man<br />

mithilfe der Maus oder der Tastatur aufklappen und <strong>in</strong> der man e<strong>in</strong>en E<strong>in</strong>trag<br />

auswählen kann.<br />

• Angezeigt wird dabei jeweils der ausgewählte E<strong>in</strong>trag und e<strong>in</strong> Pfeil nach unten, der<br />

anzeigt, dass es sich um e<strong>in</strong>e aufklappbare Liste handelt.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-104


Beispiel: JComboBox<br />

Conta<strong>in</strong>er c;<br />

JComboBox vornamen, nachnamen;<br />

public Konstruktor() {<br />

c = getContentPane();<br />

c.setLayout(new FlowLayout());<br />

Str<strong>in</strong>g[] namen = {"Hans", "Klaus", "Sab<strong>in</strong>e", "Erika"};<br />

vornamen = new JComboBox(namen);<br />

nachnamen = new JComboBox();<br />

nachnamen.addItem("Meyer"); nachnamen.addItem("Müller");<br />

nachnamen.addItem("Schulze"); nachnamen.addItem("Lehmann");<br />

nachnamen.setSelectedIndex(2);<br />

c.add(vornamen);<br />

c.add(nachnamen);<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-105


Die Komponentenklasse JList<br />

• Im Unterschied zur JComboBox-Objekt stellt e<strong>in</strong> Objekt der Klasse JList e<strong>in</strong>e<br />

Auswahlliste dar, die bereits aufgeklappt ist und daher komplett angezeigt wird.<br />

• In e<strong>in</strong>em JComboBox-Objekt kann man nicht nur e<strong>in</strong>en e<strong>in</strong>zelnen, sondern auch<br />

mehrere E<strong>in</strong>träge auswählen.<br />

• Die ausgewählten E<strong>in</strong>träge werden markiert.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-106


Die Komponentenklasse JTextComponent<br />

Die abstrakte Klasse bietet verschiedene Möglichkeiten zur E<strong>in</strong>gabe von Text. Die<br />

wichtigsten Implementierungen s<strong>in</strong>d:<br />

• JTextArea<br />

• JTextField<br />

◦ JPasswordField<br />

• JTextPane<br />

◦ JHTMLPane<br />

(E<strong>in</strong>gabe mehrzeiliger Texte)<br />

(E<strong>in</strong>gabe e<strong>in</strong>zeiliger Texte)<br />

(E<strong>in</strong>gabe e<strong>in</strong>zeiliger geschützter Texte)<br />

(E<strong>in</strong>gabe von formatierten Texten)<br />

(z. B. HTML-Texte)<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-107


Die Komponentenklasse JScrollPane<br />

• Objekte der Klasse JScrollPane s<strong>in</strong>d <strong>in</strong> der Lage, andere Komponenten<br />

aufzunehmen und <strong>in</strong> e<strong>in</strong>en Darstellungsbereich e<strong>in</strong>zubetten, der mit horizontalen<br />

und vertikalen Bildlaufleisten ausgestattet ist.<br />

• Hierdurch wird e<strong>in</strong>e ausschnittsweise Sicht auf die Komponenten ermöglicht.<br />

• Der jeweilige Ausschnitt wird mit Schiebereglern (scrollbars), die sich am Bildrand<br />

bef<strong>in</strong>den, festgelegt.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-108


Die Komponentenklasse JPanel<br />

• Objekte der Klasse JPanel können andere Komponenten enthalten. Sie s<strong>in</strong>d daher<br />

eigentlich ke<strong>in</strong>e Komponenten, sondern Behälter.<br />

• JPanel ist die Basisklasse für Conta<strong>in</strong>er, die nicht Hauptfenster s<strong>in</strong>d.<br />

Standardmäßig verwendet JPanel das FlowLayout.<br />

• Objekte der Klasse JPanel werden zum Strukturieren von Behältern<br />

verwendet – und s<strong>in</strong>d aus dieser Sicht Komponenten anderer Behälter.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-109


Die Behälterklasse JFrame<br />

• Die Klasse JFrame ist die wichtigste Top-Level-Behälterklasse.<br />

• Sie erbt von Frame, ihre Objekte s<strong>in</strong>d daher Fenster mit Rahmen.<br />

• In der Titelleiste des Rahmens bef<strong>in</strong>den sich die üblichen System-Menü-E<strong>in</strong>träge.<br />

• Zusätzlich zu den Methoden von Frame stellt JFrame weitere zur Verfügung,<br />

z. B. zum Schließen von Fenstern.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-110


Die Behälterklasse JW<strong>in</strong>dow<br />

• Wie JFrame ist auch JW<strong>in</strong>dow e<strong>in</strong>e Top-Level-Behälterklasse.<br />

• Sie erbt von W<strong>in</strong>dow, die Objekte s<strong>in</strong>d daher rahmenlose Fenster.<br />

• E<strong>in</strong> JW<strong>in</strong>dow-Objekt kann e<strong>in</strong>em JFrame-Objekt oder e<strong>in</strong>em anderem<br />

JW<strong>in</strong>dow-Objekt gehören. In diesem Fall wird das JW<strong>in</strong>dow-Objekt mit se<strong>in</strong>em<br />

Besitzer geme<strong>in</strong>sam m<strong>in</strong>imiert und maximiert.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-111


Die Behälterklasse JDialog<br />

• Die Klasse JDialog wird dazu benutzt, um Dialogfenster darzustellen.<br />

• Dies s<strong>in</strong>d Fenster, die nur solange ersche<strong>in</strong>en, bis e<strong>in</strong> Dialog mit dem Benutzer/der<br />

Benutzer<strong>in</strong> abgewickelt wurde.<br />

• E<strong>in</strong> JDialog-Fenster kann e<strong>in</strong>em übergeordneten Fenster gehören. Dieses<br />

übergeordnete kann solange für Benutzere<strong>in</strong>gaben gesperrt werden, bis der Dialog<br />

im Dialogfenster beendet ist.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-112


Die Klassen JMenuBar und JToolBar<br />

• E<strong>in</strong>em JFrame-Objekt kann e<strong>in</strong>e Menüleiste h<strong>in</strong>zugefügt werden. Dies erfolgt mit<br />

Objekten der Klasse JMenuBar.<br />

• E<strong>in</strong>e Menüleiste verwaltet e<strong>in</strong>e Liste von Menüs vom Typ JMenu.<br />

• Neben Menüleisten sieht man häufig Werkzeugleisten (toolbars). Hierbei handelt es<br />

sich um spezielle Behälter, die meistens Button-Objekte enthalten, die häufig<br />

verwendete Funktionalitäten auslösen können.<br />

• E<strong>in</strong>e Werkzeugleiste kann als Objekt der Klasse JToolBar erzeugt werden.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-113


Die Klasse JApplet<br />

• Zur Programmierung von Applets stellt die Sw<strong>in</strong>g-Bibliothek die Klasse JApplet<br />

zur Verfügung.<br />

• JApplet ist direkt aus Applet abgeleitet.<br />

• Die Klasse JApplet steht also <strong>in</strong> der Hierachie unter Component, Conta<strong>in</strong>er<br />

und Applet und erbt daher die Methoden dieser Klassen.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-114


Pr<strong>in</strong>zipielle Vorgehensweise<br />

• Durch Instanziieren e<strong>in</strong>er (eigenen) Fensterklasse wird e<strong>in</strong> Fensterobjekt erzeugt.<br />

Für das Objekt werden Größe und Titel festgelegt, es wird sichtbar gemacht, ...<br />

Die Klasse geht <strong>in</strong> der Regel aus der Ableitung e<strong>in</strong>er Behälterklasse (zum Beispiel<br />

JFrame, JW<strong>in</strong>dow, ...) hervor.<br />

• Das Layout und der grafische Kontext werden festgelegt.<br />

• Die Komponenten werden dem Fensterobjekt h<strong>in</strong>zugefügt (zum Beispiel im<br />

Konstruktor der Fensterklasse).<br />

• Für jede Ereignisquelle werden e<strong>in</strong> oder mehrere Ereignisempfänger (Beobachter)<br />

sowie die Aktionen zur Ereignisbehandlung def<strong>in</strong>iert. Die Ereignisempfänger werden<br />

bei der zuständigen Ereignisquelle registriert.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-115


Wiederholung: Adapterklassen<br />

• E<strong>in</strong>e Adapterklasse implementiert e<strong>in</strong>e Schnittstelle durch leere Rümpfe.<br />

• Zu jeder Low-Level-Listener-Schnittstelle mit mehr als e<strong>in</strong>er Methode existiert e<strong>in</strong>e<br />

Adapterklasse. Ist XxxListener der Name der Schnittstelle, so heißt die<br />

Adapterklasse XxxAdapter. Man schreibt also<br />

statt<br />

class Me<strong>in</strong>Listener extends XxxAdapter<br />

class Me<strong>in</strong>Listener implements XxxListener.<br />

• Beispielsweise enthält die Schnittstelle ActionListener nur e<strong>in</strong>e Methode,<br />

W<strong>in</strong>dowListener jedoch – wie bereits gesehen – mehrere.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-116


Strukturierung von Behälter- und Beobachterklasse<br />

• Die Beobachterklasse wird als <strong>in</strong>nere Klasse realisiert.<br />

• Die Beobachterklasse wird als anonyme Klasse realisiert.<br />

• Die Fensterklasse wird selbst zur Beobachterklasse.<br />

• Die Beobachterklasse ist e<strong>in</strong>e selbstständige Klasse. Ihr muss der Behälter als<br />

Parameter übergeben werden.<br />

Wir erläutern die Möglichkeiten an e<strong>in</strong>em Beispiel zur Wechsel der H<strong>in</strong>tergrundfarbe.<br />

Die folgenden Programme wurden D. Ratz, J. Scheffler, D. Seese, J. Wiesenberger:<br />

Grundkurs Programmieren <strong>in</strong> <strong>Java</strong> entnommen.<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-117


Realisierung als <strong>in</strong>nere Klasse<br />

public class Farbwechsel1 extends JFrame {<br />

Conta<strong>in</strong>er c;<br />

JButton button;<br />

public Farbwechsel1() {<br />

c = getContentPane();<br />

button = new JButton("H<strong>in</strong>tergrundfarbe wechseln");<br />

c.add(button, BorderLayout.NORTH);<br />

ButtonListener bL = new ButtonListener();<br />

button.addActionListener(bL);<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-118


}<br />

class ButtonListener implements ActionListener {<br />

public void actionPerformed(ActionEvent e) {<br />

float zufall = (float) Math.random();<br />

Color grauton = new Color(zufall,zufall,zufall);<br />

c.setBackground(grauton);<br />

}<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

Farbwechsel1 fenster = new Farbwechsel1();<br />

fenster.setTitle("Farbwechsel");<br />

fenster.setSize(200,100);<br />

fenster.setVisible(true);<br />

fenster.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-119


Realisierung als anonyme Klasse<br />

public class Farbwechsel2 extends JFrame {<br />

Conta<strong>in</strong>er c;<br />

JButton button;<br />

public Farbwechsel2() {<br />

c = getContentPane();<br />

button = new JButton("H<strong>in</strong>tergrundfarbe wechseln");<br />

c.add(button, BorderLayout.NORTH);<br />

ActionListener bL = new ActionListener() {<br />

public void actionPerformed(ActionEvent e) { ... }<br />

};<br />

button.addActionListener(bL);<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) { ... }<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-120


Fensterklasse als Beobachterklasse<br />

public class Farbwechsel3 extends JFrame implements ActionListener {<br />

Conta<strong>in</strong>er c;<br />

JButton button;<br />

public Farbwechsel3() {<br />

c = getContentPane();<br />

button = new JButton("H<strong>in</strong>tergrundfarbe wechseln");<br />

c.add(button, BorderLayout.NORTH);<br />

button.addActionListener(this);<br />

}<br />

public void actionPerformed(ActionEvent e) { ... }<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) { ... }<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-121


Beobachterklasse als selbstständige Klasse<br />

public class Farbwechsel4 extends JFrame {<br />

Conta<strong>in</strong>er c;<br />

JButton button;<br />

public Farbwechsel4() {<br />

c = getContentPane();<br />

button = new JButton("H<strong>in</strong>tergrundfarbe wechseln");<br />

c.add(button, BorderLayout.NORTH);<br />

ButtonListener bL = new ButtonListener(c);<br />

button.addActionListener(bL);<br />

}<br />

}<br />

public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) { ... }<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-122


Beispiel: Fenster mit Menü- und Werkzeugleiste<br />

import java.awt.*;<br />

import java.awt.event.*;<br />

import javax.sw<strong>in</strong>g.*;<br />

public class Bilderrahmen extends JFrame {<br />

Conta<strong>in</strong>er c;<br />

JMenuBar menuBar;<br />

JMenu menu;<br />

JMenuItem menuItem;<br />

JToolBar toolBar;<br />

JButton button;<br />

JLabel bildLabel;<br />

// Conta<strong>in</strong>er dieses Frames<br />

// Menueleiste<br />

// Menue<br />

// Menue-E<strong>in</strong>trag<br />

// Werkzeugleiste<br />

// Knoepfe der Werkzeugleiste<br />

// Label das im Frame ersche<strong>in</strong>en soll<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-124


public Bilderrahmen() {<br />

c = getContentPane();<br />

MenuListener mL = new MenuListener();<br />

menuBar = new JMenuBar();<br />

menu = new JMenu("Bilder");<br />

menu.setMnemonic(KeyEvent.VK_B);<br />

menuItem = new JMenuItem("Hund");<br />

menuItem.setMnemonic(KeyEvent.VK_H);<br />

menuItem.addActionListener(mL);<br />

menuItem.setActionCommand("dog");<br />

menu.add(menuItem);<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-125


menuItem = new JMenuItem("Katze");<br />

menuItem.setMnemonic(KeyEvent.VK_K);<br />

menuItem.addActionListener(mL);<br />

menuItem.setActionCommand("cat");<br />

menu.add(menuItem);<br />

menuItem = new JMenuItem("Maus");<br />

menuItem.setMnemonic(KeyEvent.VK_M);<br />

menuItem.addActionListener(mL);<br />

menuItem.setActionCommand("mouse");<br />

menu.add(menuItem);<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-126


menuBar.add(menu);<br />

setJMenuBar(menuBar);<br />

ToolBarListener tL = new ToolBarListener();<br />

toolBar = new JToolBar("Rahmenfarbe");<br />

button = new JButton(new ImageIcon("images/rot.gif"));<br />

button.setToolTipText("roter Rahmen");<br />

button.addActionListener(tL);<br />

button.setActionCommand("rot");<br />

toolBar.add(button);<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-127


utton = new JButton(new ImageIcon("images/gruen.gif"));<br />

button.setToolTipText("gruener Rahmen");<br />

button.addActionListener(tL);<br />

button.setActionCommand("gruen");<br />

toolBar.add(button);<br />

button = new JButton(new ImageIcon("images/blau.gif"));<br />

button.setToolTipText("blauer Rahmen");<br />

button.addActionListener(tL);<br />

button.setActionCommand("blau");<br />

toolBar.add(button);<br />

bildLabel = new JLabel(new ImageIcon("images/dog.gif"));<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-128


}<br />

c.setBackground(Color.red);<br />

c.add(bildLabel, BorderLayout.CENTER);<br />

c.add(toolBar, BorderLayout.NORTH);<br />

class MenuListener implements ActionListener {<br />

public void actionPerformed(ActionEvent e) {<br />

bildLabel.setIcon(new ImageIcon("images/"+e.getActionCommand()+".gif"));<br />

}<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-129


class ToolBarListener implements ActionListener {<br />

public void actionPerformed(ActionEvent e) {<br />

if (e.getActionCommand() == "rot")<br />

c.setBackground(Color.red);<br />

else if (e.getActionCommand() == "gruen")<br />

c.setBackground(Color.green);<br />

else if (e.getActionCommand() == "blau")<br />

c.setBackground(Color.blue);<br />

}<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-130


public static void ma<strong>in</strong>(Str<strong>in</strong>g[] args) {<br />

Bilderrahmen fenster = new Bilderrahmen();<br />

fenster.setTitle("Bilderrahmen");<br />

fenster.setSize(180,280);<br />

fenster.setVisible(true);<br />

fenster.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);<br />

}<br />

}<br />

11.6 Die Sw<strong>in</strong>g-Klassen 11-131

Hurra! Ihre Datei wurde hochgeladen und ist bereit für die Veröffentlichung.

Erfolgreich gespeichert!

Leider ist etwas schief gelaufen!