Teil 5: Benutzeroberflächen 5.2 Einführung GUI-Programmierung Prof. Dr. Max Mühlhäuser FG Telekooperation TU Darmstadt



Ähnliche Dokumente
Funktionale und Objekt-Orientierte Programmierkonzepte

GUI Programmierung mit JAVA Swing

Java I Vorlesung 11 Graphische Oberflächen mit Swing

Zentrale Objekte zur Programmierung graphischer Benutzeroberflächen (GUI)

Objektorientierte Software-Entwicklung

Telecooperation/RBG. Grundlagen der Informatik 1 Thema 21: GUI und verschachtelte Klassen. Dr. Guido Rößling

Objektorientierte Programmierung

GUI Programmierung in Java

Einführung in die Informatik: Programmierung und Software-Entwicklung, WS 11/12. Kapitel 7. Grafische Benutzeroberflächen

GRAFISCHE BENUTZERSCHNITTSTELLEN

Institut für Programmierung und Reaktive Systeme. GUIs mit Swing. Markus Reschke

Hochschule der Medien Prof. Uwe Schulz 14. Juli 2010 Klausur Informatik, EDV-Nr Seite 1 von 5. Teil 2: Aufgaben

GUI-Programmierung. Teil I. Unterlagen zum Modul OOP mit Java V by MOU2/BFH-TI. Berner Fachhochschule Technik und Informatik

NTB Druckdatum:

Graphische Benutzungsoberflächen

Einstieg in die Informatik mit Java

Einführung in die Informatik: Programmierung und Software-Entwicklung, WS 15/16. Kapitel 7. Grafische Benutzeroberflächen 1

JButton, JCheckBox, JRadioButton. Programmieren II. Vorlesung 7. Handout S. 1. Dr. Klaus Höppner. Hochschule Darmstadt Sommersemester 2009.

Universität Paderborn Prof. Dr. Stefan Böttcher. Abschluss von Kapitel 2: Programmierung Grafischer Oberflächen mit der Swing-Bibliothek

Übungen zu Einführung in die Informatik: Programmierung und Software-Entwicklung: Lösungsvorschlag

Programmieren II. Java im Vergleich zu anderen Sprachen. Einführung: GUI. Einführung: Grafische Benutzeroberflächen. Dr.

Prof. Dr. Oliver Haase Karl Martin Kern Achim Bitzer. Programmiertechnik GUI-Programmierung mit Swing

Grafische Benutzeroberflächen mit Swing

2A Basistechniken: Weitere Aufgaben

Abteilung Informatik, JFC/Swing 2004 Diego Schmidlin V2.2

Swing Lernen am Code Teil 1

Ziel dieses Kapitels: Einführung in die Grundzüge der Programmierung graphischer Benutzeroberflächen (engl.: "graphical user interface", GUI) in Java

11. GUI-Programmierung mit SWING Überblick

Softwaretechnik (Medieninformatik): GUIs mit Swing Überblick

Grundlagen der Programmierung APPLETS

Einführung in die Programmierung für NF. Grafische Benutzeroberflächen

AK-Automatisierungs und Kommunikationstechnik TI Technische Informatik. NWT Netzwerktechnik

Funktionale und objektorientierte Programmierkonzepte

Kapitel 8: Grafische Benutzerschnittstellen

Ziele. Kapitel 8: Grafische Benutzerschnittstellen. AWT und Swing. Ziele (2)

Java Kurs für Anfänger Einheit 4 Klassen und Objekte

Programmiertechnik GUI Programmierung mit Java Swing

Benutzeroberflächen. Java Teil 4

Grafikausgabe mit dem Abstract- Windowing-Toolkit. Eine Einführung

Objektorientierte Programmierung

WPF Steuerelemente Listbox, ComboBox, ListView,

EAD II Übung 5. Graphische Benutzungsoberfläche mit BlueJ

Java Game Development Fabian Birzele Programmierpraktikum 2008 / 2009

Einführung in GUI-Programmierung. javax.swing

Applets. Applets. Applets. Applet: Java-Programm Eingebettet in einer HTML-Seite Ausführung von einem Java-fähigen Web-Browser oder sog.

Mediator 9 - Lernprogramm

Kap. 35 Swing: Grundlagen Kap Swing: Hauptfenster

Einführung: Grafische Benutzeroberflächen. Programmieren II. Dr. Klaus Höppner. Hochschule Darmstadt Sommersemester / 22

Erstellen von x-y-diagrammen in OpenOffice.calc

Graphical User Interfaces

Graphic Coding. Klausur. 9. Februar Kurs A

Einführung in die Java- Programmierung

Windows. Workshop Internet-Explorer: Arbeiten mit Favoriten, Teil 1

Einführung in GUI-Programmierung. javax.swing

Einführung in die Programmierung

Javakurs für Fortgeschrittene

Java: Vererbung. Teil 3: super()

Delegatesund Ereignisse

U08 Entwurfsmuster (II)

Ereignisbehandlung 21

Fachgebiet Informationssysteme Prof. Dr.-Ing. N. Fuhr. Programmierung Prof. Dr.-Ing. Nobert Fuhr. Übungsblatt Nr. 6

Arbeiten mit UMLed und Delphi

Drei-Schichten-Architektur. Informatik B - Objektorientierte Programmierung in Java. Vorlesung 16: 3-Schichten-Architektur 1 Fachkonzept - GUI

Animationen erstellen

Erstellen einer Collage. Zuerst ein leeres Dokument erzeugen, auf dem alle anderen Bilder zusammengefügt werden sollen (über [Datei] > [Neu])

Rock-Band. Einleitung. Scratch. In diesem Projekt lernst du, wie du deine eigenen Musikinstrumente programmieren kannst! Activity Checklist

Outlook. sysplus.ch outlook - mail-grundlagen Seite 1/8. Mail-Grundlagen. Posteingang

Hinweise zum Übungsblatt Formatierung von Text:

Techniken der Projektentwicklung

Lehrer: Einschreibemethoden

Dokumentation des Projektes Tic Tac Toe

Folge 18 - Vererbung

Professionelle Seminare im Bereich MS-Office

PowerPoint: Text. Text

J.1. J.1 GUI-Programmierung in in Java Prof. Dr. Rainer Manthey Informatik II 1

GUIs in Java und ihre Programmierung

Java Lab 2006/12/13 Client

Schritt 1 - Ein Spielfeld

Factory Method (Virtual Constructor)

Teil 1: Grundeigenschaften von Rechnern und Software

Java Kurs für Anfänger Einheit 5 Methoden

Ist eine Softwarekomponente, die dem Benutzer eines Computers die Interaktion mit der Maschine über grafische Symbole erlaubt

Dieses Tutorial gibt eine Übersicht der Form Klassen von Struts, welche Besonderheiten und Unterschiede diese aufweisen.

Bitte wenden. Name: KURSARBEIT NR. 4 (10 DIFF GA) Seite 1

Programmieren in Java

Downloadfehler in DEHSt-VPSMail. Workaround zum Umgang mit einem Downloadfehler

Computeranwendung und Programmierung (CuP)

Bedienung des Web-Portales der Sportbergbetriebe

Java Projekt: Tic Tac Toe + GUI

Abwesenheitsnotiz im Exchange Server 2010

SWT. -The Standard Widget Toolkit- Inhaltsverzeichnis. Thomas Wilhelm SWT. 1. Was ist SWT?

Softwaretechnik (Medieninformatik): GUIs mit Swing Überblick

Client-Server-Beziehungen

16 Zeichnen in Swing-Komponenten , Prof. Dr. D. Ratz

Software-Engineering und Optimierungsanwendungen in der Thermodynamik

Handbuch. Artologik EZ-Equip. Plug-in für EZbooking version 3.2. Artisan Global Software

MORE Profile. Pass- und Lizenzverwaltungssystem. Stand: MORE Projects GmbH

Session 1: Classes and Applets

Transkript:

Grundzüge der Informatik 1 Teil 5: Benutzeroberflächen 5.2 Einführung GUI-Programmierung Prof. Dr. Max Mühlhäuser FG Telekooperation TU Darmstadt

AWT und SWING AWT = Abstract Window Toolkit Package java.awt Benutzt Steuerelemente des darunterliegenden Betriebssystems Native Code (= direkt für die Maschine geschrieben, keine VM) schnell Aussehen (Look) hängt vom System ab: Unterschiedliche Schriften, Portabilität eingeschränkt SWING Package javax.swing (Teil der Java Foundation Classes) Merkmal: Swing-Klassen beginnen mit J : JButton,... vollständig in Java programmiert, eigener Look baut auf AWT auf verwendet ein Minimum an systemspezifischen Komponenten 2

Komponenten Einige oft verwendete Komponenten und für welche Interaktionsaufgaben sie verwendet werden: Anzeigen von Text und Symbolen JLabel Auslösen von Aktionen JButton JMenu 3

Eingabe von Text JTextField Komponenten Auswahl aus einer festen Menge von Optionen JCheckBox gegenseitig ausschließend: JRadioButton Auswahl aus einer variablen Menge JList JComboBox Button oder TextField + ausklappbare Listbox 4

Menschliche Faktoren Beim Entwurf interaktiver Programme gibt es neben der funktionalen Vollständigkeit und Korrektheit viele zusätzliche Aspekte zu beachten Dazu gehört die Art und Weise der Interaktion und wie leicht sie zu erlernen und benutzen ist Richtlinien für gute GUIs sind u.a.: Vermeide Modi. Allgemein sinnvolle Operationen sollten immer verfügbar sein. Biete einfache und durchgängige Interaktionssequenzen an. Überfordere den Benutzer nicht durch zu viele Optionen. Zeige bei jeder Interaktionsstufe klar die verfügbaren Optionen. Gib dem Benutzer angemessene Rückmeldungen. Gib dem Benutzer die Möglichkeit, Fehler problemlos rückgängig zu machen. 5

GUI-Framework Container Komponenten Ereignisse Anwendungslogik Anatomie einer GUI-Applikation Methodenaufrufe auf Komponente Listener Zustand: wert=3 Netz von kooperierenden Objekten mit klar festgelegten Zuständigkeiten: Komponenten Container Ereignisse Listener Layout Legt die Anordnung der Komponenten fest Look & Feel Legt das Aussehen der Komponenten fest getrennt: Anwendungslogik 6

Sequentielle Programme Fäden (Threads) haben Anfang, definierte Ausführungssequenz und Ende. Zu jedem Zeitpunkt ist genau eine Anweisung aktiv. Ein Faden (Thread) ist ein einzelner sequentieller Kontrollfluss in einem Programm. Programm Faden Nebenläufige Programme Programme können mehrere Fäden besitzen. Mehrere Programmteile können so quasi gleichzeitig ablaufen. Programm Fäden 7

Fäden (Threads) Fäden (Threads) nutzen die Ressourcen des Prozesses mit, in dem sie ablaufen besitzen keine eigenen Speichersegmente verfügen über einen eigenen Registersatz (incl. Programmzähler und Statusregister) sowie einen eigenen Stack werden oft auch als leichtgewichtige Prozesse (lightweight processes) bezeichnet. GUI-Applikationen besitzen neben dem Haupt-Thread einen sogenannten Event-Dispatching Thread. Dieser Thread ruft Methoden der Anwendung auf, wenn bestimmte Ereignisse auftreten. (Callback) Die Ereignisbehandlungsroutinen in der Anwendung werden sequentiell ausgeführt. Das Zeichnen von Komponenten wird ebenfalls im Kontext dieses Threads ausgeführt. 8

main Programmiermodell Anwendung GUI-Framework (SWING) main Komponente einfügen AWT-EventQueue AWT-EventQueue AWT-EventQueue Ereignis: Komponente zeichnen Ereignis: Benutzereingabe 9

Fenster import javax.swing.jframe; public class GUITest extends JFrame { // The height of the window in pixels public static final int WIDTH = 400; // The width of the window in pixels public static final int HEIGHT = 300; // Constructs a new window with a given title public GUITest(String title) { super(title); // Starts the test application. Creates a new window and displays it public static void main(string args[]) { // Construct a new window. It is initially invisible GUITest thewindow = new GUITest("My first GUI Application"); // Set width and height of the window thewindow.setsize(width, HEIGHT); // Open the window thewindow.show(); System.out.println("Exiting main..."); 10

Fenster Wir beobachten... main() wird verlassen, das Programm läuft aber weiter. Mehrere Fäden. Der Event-Dispatching Thread läuft weiter. Klick auf Schließen-Button beendet das Programm nicht. Ereignisverarbeitung fehlt. Genaueres dazu später. 11

Container Container und Komponenten JFrame: top level container benutzt Fenster vom Betriebssystem JPanel: intermediate container dient zum Gruppieren und Anordnen von Komponenten Verschachtelung möglich JLabel, JButton,...: atomare Komponenten präsentieren dem Benutzer Informationen erlauben oft Interaktion und Eingabe (Steuerelemente) Container-Hierarchie JFrame JPanel JLabel Selbst die einfachste Anwendung besteht aus einer Hierarchie von Containern und Komponenten (Darstellung vereinfacht. Die Container zwischen JFrame und JPanel werden hier nicht weiter betrachtet) JFrame... JPanel JLabel 12

Komponenten Hinzufügen von Komponenten Der JFrame erzeugt automatisch ein JPanel, das contentpane. contentpane Darin kann die Anwendung neue Komponenten einfügen. Die Komponenten werden eingefügt, während das Fenster noch unsichtbar ist. Also zwischen dem Erstellen des Fenster-Objekts mit new und dem Öffnen mit show(). JLabels stellen Text oder/und Symbole dar sind passive Komponenten, erlauben keine Interaktion JFrame... JPanel JLabel 13

import java.awt.container; import javax.swing.jframe; import javax.swing.jlabel; Labels public class GUITest extends JFrame { public GUITest(String title) { super(title); // Retrieve the area where one can add elements Container pane = getcontentpane(); // Create a new label that displays help information JLabel label = new JLabel( "Press the [X] in the top right corner to exit"); // Add the label to the content of the window pane.add(label);... 14

import java.awt.container; import javax.swing.jbutton; import javax.swing.jframe; import javax.swing.jlabel; Buttons public class GUITest extends JFrame { public GUITest(String title) { super(title); Container pane = getcontentpane(); JLabel label = new JLabel( "Press the [Exit] or [X] in the top right corner to exit"); pane.add(label); // Create a new push button that may be used in addition to the [X] JButton button = new JButton("Exit"); // Add the button to the content of the window pane.add(button);... 15

Layout Wir beobachten... Der Text ist nicht mehr sichtbar, denn der Button liegt darüber! Layout-Management ist der Prozess, die Größe und Position von Komponenten zu bestimmen. Das gewünsche Layout wird durch zuordnen eines Layout- Objekts zum Container festgelegt: Container pane = getcontentpane(); pane.setlayout(new GridLayout(ROWS, COLS)); Die Layout-Klasse implementiert das Interface LayoutManager. 16

GridLayout Vordefinierte Layouts Ordnet die Komponenten in einem rechteckigen Gitter an. Die Reihenfolge des Einfügens der Komponenten bestimmt ihre Anordnung. BorderLayout Positioniert in 5 Regionen jeweils maximal eine Komponente Die Regionen N, E, S und W werden so klein wie möglich gehalten. Der restliche Platz entfällt auf CENTER. Zuordnung zu einer Region durch zusätzlichen Parameter beim Aufruf von Container.add: add(new Button("SOUTH"), BorderLayout.SOUTH); Weitere Layouts: BoxLayout, FlowLayout, GridBagLayout,... 17

import java.awt.container; import java.awt.gridlayout; import javax.swing.jbutton; import javax.swing.jframe; import javax.swing.jlabel; GridLayout public class GUITest extends JFrame { public GUITest(String title) { super(title); Container pane = getcontentpane(); // Define a LayoutManager that places new elements properly // onto the pane. Here we use a grid with 3 rows and 1 column. pane.setlayout(new GridLayout(3, 1)); JLabel label = new JLabel( "Press the [Exit] or [X] in the top right corner to exit"); pane.add(label); JButton button = new JButton("Exit"); pane.add(button);... 18

Ereignisse (Events) Jedesmal, wenn der Benutzer eine Taste drückt oder die Maus bewegt, tritt ein Ereignis auf. Steuerelemente können Maus- und Tastatur-Ereignisse verarbeiten und neue Ereignisse erzeugen. Beispiel: Befindet sich der Mauszeiger über einem Button und die Maustaste wird losgelassen, dann wird ein ActionEvent erzeugt. Ereignisse werden durch Event-Objekte beschrieben Die zugehörigen Klassen sind von java.awt.awtevent abgeleitet. (für GUI; allgemeiner: java.util.eventobject) Der Typ gibt Auskunft über die Art des Ereignisses: ActionEvent: Benutzer klickt einen Button, drückt Return in einem Textfeld, wählt einen Menüeintrag,... WindowEvent: Benutzer schließt Fenster,...... Die Attribute geben zusätzliche Informationen über das Ereignis, z.b. welcher Button gedrückt wurde. 19

Listener Mehrere Listener können sich bei einer Ereignis-Quelle (event source) registieren und werden von diesem Zeitpunkt an über Ereignisse eines bestimmten Typs informiert. event source event object event listener event listener event listener Programmieren eines Listeners: Das Klasse des Empfänger-Objekts (event listener) muss das dem Ereignistypen entsprechende Interface implementieren. Z.B. für ActionEvents das Interface ActionListener. Die Klasse muss alle Methoden des Interface implementieren. Der Klient registriert nun das Empfänger-Objekt bei der Ereignis- Quelle. Z.B. mittels addactionlistener 20

Ereignisse import java.awt.container; import java.awt.gridlayout; import java.awt.event.actionevent; import java.awt.event.actionlistener; import javax.swing.jbutton; import javax.swing.jframe; import javax.swing.jlabel; public class GUITest extends JFrame { public GUITest(String title) { super(title); Container pane = getcontentpane(); pane.setlayout(new GridLayout(3, 1)); JLabel label = new JLabel( "Press the [Exit] or [X] in the top right corner to exit"); pane.add(label); pane.add(new JButton("Exit")); // Create another button that changes the text of the Label JButton button = new JButton("Change Label Text"); // Now, define what should happen if the button is pressed button.addactionlistener(new ChangeButtonListener()); pane.add(button); private class ChangeButtonListener implements ActionListener { public void actionperformed(actionevent event) { System.out.println("Change Label Text was clicked");... 21

View-Updates Die durch Komponenten dargestellten Informationen und ihr Aussehen können durch Aufrufen ihrer Methoden verändert werden. JLabel-API (Auszug): void settext(string) String gettext() void sethorizontalalignment(int) int gethorizontalalignment() void setverticalalignment(int) int getverticalalignment() Setzen oder auslesen des dargestellten Texts Textausrichtung: LEFT, CENTER oder RIGHT Textausrichtung: TOP, CENTER oder BOTTOM 22

import java.awt.container; import java.awt.gridlayout; import java.awt.event.actionevent; import java.awt.event.actionlistener; import javax.swing.jbutton; import javax.swing.jframe; import javax.swing.jlabel; public class GUITest extends JFrame { private JLabel infolabel; public GUITest(String title) { super(title); Ereignisse Container pane = getcontentpane(); pane.setlayout(new GridLayout(3, 1)); infolabel = new JLabel( "Press the [Exit] or [X] in the top right corner to exit"); pane.add(infolabel); pane.add(new JButton("Exit")); // Create another button that changes the text of the Label JButton button = new JButton("Change Label Text"); // Now, define what should happen if the button is pressed button.addactionlistener(new ChangeButtonListener()); pane.add(button); private class ChangeButtonListener implements ActionListener { public void actionperformed(actionevent event) { infolabel.settext("you clicked the button! Now [Exit] or [X]");... 23

Window-Events Beim Klicken auf den Schließen-Button soll das Programm nun korrekt beendet werden. Registrieren eines WindowListeners interface WindowListener: void windowactivated(windowevent e) void windowclosed(windowevent e) void windowclosing(windowevent e) void windowdeactivated(windowevent e) void windowdeiconified(windowevent e) void windowiconified(windowevent e) void windowopened(windowevent e) Window wurde aktiviert Fenster wurde nach dispose() geschlossen Benutzer hat auf Schließen geklickt Fenster wurde deaktiviert Fenster wurde de-minimiert Fenster wurde minimiert Fenster wurde gerade geöffnet 24

Adapter Beim Verwenden von Interfaces müssen immer alle Methoden implementiert werden. Das ist oft unpraktisch, deshalb existieren Adapter. WindowAdapter implementiert WindowListener definiert alle Methoden mit leerem Rumpf und somit ohne Verhalten ist eine abstrakte Klasse. Der anwendungsspezifische Event-Handler wird nun von WindowAdapter abgeleitet und überschreibt nur die interessanten Methoden. 25

WindowEvents import java.awt.container; import java.awt.gridlayout; import java.awt.event.actionevent; import java.awt.event.actionlistener; import javax.swing.jbutton; import javax.swing.jframe; import javax.swing.jlabel; import java.awt.event.windowadapter; import java.awt.event.windowevent; public class GUITest extends JFrame { private JLabel infolabel; public GUITest(String title) { super(title); // Now, also define that the [X] terminates the program correctly addwindowlistener(new MyWindowListener()); Container pane = getcontentpane(); pane.setlayout(new GridLayout(3, 1)); infolabel = new JLabel( "Press the [Exit] or [X] in the top right corner to exit"); pane.add(infolabel); // Create a new push button that may be used in addition to the [X] JButton button = new JButton("Exit"); // Define that the program should exit if you click the button button.addactionlistener(new ExitButtonListener()); pane.add(button); 26

WindowEvents // Create another button that changes the text of the Label button = new JButton("Change Label Text"); // Now, define what should happen if the button is pressed button.addactionlistener(new ChangeButtonListener()); pane.add(button); private class ChangeButtonListener implements ActionListener { public void actionperformed(actionevent event) { infolabel.settext("you clicked the button! Now [Exit] or [X]"); // Exit the program when the window close button is clicked class MyWindowListener extends WindowAdapter { public void windowclosing(windowevent e) { System.exit(0); // Exit the program when the Exit -button is clicked class ExitButtonListener implements ActionListener { public void actionperformed(actionevent event) { System.exit(0); public static void main(string args[]) { GUITest thewindow = new GUITest("My first GUI Application"); thewindow.setsize(width, HEIGHT); thewindow.show(); public static final int WIDTH = 400; public static final int HEIGHT = 300; 27

Zusammenfassung Bisher betrachtet: Client-Seite Erzeugen von Komponenten und Layout Implementieren von Listenern = Ereignis-Senken Im folgenden: Komponenten-Seite Programmieren eigener Komponenten Implementieren von Ereignis-Quellen und erzeugen von Events Darstellung von Komponenten (zeichnen) 28

Eigene Komponenten Darstellung von Komponenten Die Darstellung jeder Komponente ist letztendlich durch eine Reihe von Zeichenbefehlen realisiert. Eine Komponente muss neu gezeichnet werden, wenn eines der folgenden Ereignisse eintritt: Die Komponente wurde eben geöffnet oder war durch ein darrüberliegendes Objekt verdeckt und ist jetzt wieder sichtbar. Das Neuzeichnen wird durch das Framework angefordert. Ein Zustand der Komponente, die sich auf ihr Erscheinungsbild auswirkt, hat sich verändert. Das Neuzeichnen wird explizit z.b. in einer Set- Methode der Komponente angefordert. Diese Vorgehensweise wird oft als Damage/Repair-Prinzip bezeichnet. 29

Zeichnen Das Framework initiiert das Neuzeichnen einer Komponente durch den Aufruf ihrer Methode paintcomponent(). import java.awt.graphics; import java.awt.color; import java.awt.fontmetrics; import javax.swing.jcomponent; class MyButton extends JComponent { // The text displayed on the button private String text = "Button"; /** * Paints the component. * @param g the Graphics context in which to paint */ public void paintcomponent(graphics g) { System.out.println("SWING requests a repaint"); Im Grunde handelt es sich hierbei wieder um Ereignisverarbeitung. 30

Das Graphics-Objekt Graphics enthält Zustand (=Kontext) aktuelle Zeichenfläche (Bildschirmbereich) aktuelle Zeichenfarbe aktuelle Schrift... stellt Methoden zum Zeichnen bereit public void paintcomponent(graphics g) { // Set painting color to lightgray g.setcolor(color.lightgray); // Draw rectangle with a 3D-style raised border g.fill3drect(0, 0, getwidth(), getheight(), true); 31

Text Darstellen von Text // Set painting color to black g.setcolor(color.black); // Draw text at coordinates (20, 20) g.drawstring(text, 20, 20); Zentrieren von Text Ein FontMetrics-Objekt kapselt die Eigenschaften und Zeichengrößen einer Schriftart. height p ascent descent Ursprung 32

Zeichnen public void paintcomponent(graphics g) { // Set the fill color to lightgray and draw a 3D button with raised border g.setcolor(color.lightgray); g.fill3drect(0, 0, getwidth(), getheight(), true); // The FontMetrics object provided by getfontmetrics encapsulates // information about the rendering of the current font on the current screen FontMetrics fm = g.getfontmetrics(); // Set text color to black g.setcolor(color.black); // Draw text centered on the button g.drawstring( text, (getwidth()-fm.stringwidth(text))/2, (getheight()-fm.getheight())/2+fm.getascent()); 33

Maus-Ereignisse interface java.awt.event.mouselistener: void mouseentered(mouseevent e) void mouseexited(mouseevent e) void mousepressed(mouseevent e) void mousereleased(mouseevent e) void mouseclicked(mouseevent e) Der Mauszeiger hat die Komponente betreten Der Mauszeiger hat die Komponente verlassen Eine Maustaste wurde über der Komponente gedrückt Eine Maustaste wurde losgelassen Eine Maustaste wurde gedrückt und an der gleichen Stelle wieder losgelassen 34

Zustände eines Buttons Maus-Ereignisse p (pressed): Maustaste wurde über dem Button niedergedrückt und wird gehalten r (recessed): Der Button wird vertieft dargestellt Zustandsdiagramm: mousereleased mousepressed mouseexited p=0 r=0 p=1 r=1 p=1 r=0 mousereleased mouseentered 35

Maus-Ereignisse class MyButton extends JComponent implements MouseListener {... // Invoked when the mouse enters a component public void mouseentered(mouseevent e) { if (pressed) { recessed = true; repaint(); // Invoked when the mouse exits a component public void mouseexited(mouseevent e) { if (pressed) { recessed = false; repaint(); // Invoked when a mouse button has been pressed on a component public void mousepressed(mouseevent e) pressed = recessed = true; repaint(); // Invoked when a mouse button has been released on a component public void mousereleased(mouseevent e) { pressed = recessed = false; repaint(); public void mouseclicked(mouseevent e) { 36

Ereignis-Quellen Verwaltung der Listener Die Klasse EventListenerList verwaltet eine Liste von Tupeln (Klasse des Listener-Interface, Objektreferenz) Unsere Komponente kann die Verwaltung delegieren: /** * List of listeners interested in events generated by this component. * We delegate bookkeeping of event listeners to EventListenerList. */ private EventListenerList listenerlist = new EventListenerList(); /** * Adds an <code>actionlistener</code> to the button. * @param l the <code>actionlistener</code> to be added. */ public void addactionlistener(actionlistener l) { listenerlist.add(actionlistener.class, l); /** * Removes an <code>actionlistener</code> from the button. * @param l the listener to be removed. */ public void removeactionlistener(actionlistener l) { listenerlist.remove(actionlistener.class, l); 37

Ereignis-Quellen /** * Fires an <code>actionevent</code>. */ private void fireactionevent() { // Guaranteed to return a non-null array Object[] listeners = listenerlist.getlistenerlist(); // Create the event object ActionEvent actionevent = new ActionEvent( this, ActionEvent.ACTION_PERFORMED, "click"); // Notify the listeners for (int i=0; i<listeners.length; i+=2) ((ActionListener)listeners[i+1]).actionPerformed(actionEvent); Senden von Events an die Listener Das von listenerlist.getlistenerlist() gelieferte Array enthält alternierend Klassen-Objekte und Listener-Objekte. Die Klassen-Objekte beschreiben die Art des Ereignisses, für das sich der Listener interessiert. (z.b.: ActionListener.class) Das Listener-Objekt ist der Empfänger des Ereignisses. Eine einzelne ListenerList kann verwendet werden, um unterschiedliche Listener-Typen zu verwalten. In diesem Fall muss ein entsprechender Typtest im Schleifenrumpf hinzugefügt werden. 38

Auslösen des Ereignisses: Ereignis-Quellen mousereleased mousepressed mouseexited p=0 r=0 p=1 r=1 p=1 r=0 mousereleased :actionperformed mouseentered /** * Invoked when a mouse button has been released on a component. */ public void mousereleased(mouseevent e) { if (recessed) { fireactionevent(); repaint(); pressed = recessed = false; 39

Eigene Komponenten: Zusammenfassung Zeichnen: Damage/Repair-Prinzip Zeichenmethoden sollten nur im Kontext von paintcomponent() ausgeführt werden. repaint() zeichnet nicht unmittelbar, sondern es fordert das Neuzeichnen der Komponente an. Das Framework ruft daraufhin paintcomponent() vom Event-Dispatch-Thread aus auf und zeichnet bei Bedarf auch andere Komponenten neu. (z.b.: Rahmen, transparente Objekte) Ereignis-Quellen Die Verwaltung der Listener kann an EventListenerList delegiert werden. 40