Java Standard: Grafische Oberflächen mit Swing

Liste Bewertung: Diese Wikiseite besteht im Wesentlichen aus Listen und/oder Überschriften, wobei hier Fließtext stehen sollte. Es wird Hilfe zur Überarbeitung gewünscht.


Mit Swing hat Sun Microsystems eine API (Application Programming Interface, zu Deutsch Programmierschnittstelle) geschaffen um den Beschränkungen des AWT zu entkommen. Hierdurch können auch komplexe grafische Oberflächen wie Bäume oder Tabellen Verwendung finden. Swing - seit Java 1.2 zu finden im Paket javax.swing - benutzt hierbei jedoch zahlreiche Funktionalitäten des java.awt Paket so dass Vorkenntnisse im Bereich AWT sinnvoll sind.

Top-Level ContainerBearbeiten

Leichtgewichtige ContainerBearbeiten

KontrollelementeBearbeiten

Anzeigenelemente (Ausgabe)Bearbeiten

Textverarbeitung (Ein- und Ausgabe)Bearbeiten

LayoutManagerBearbeiten

Grafische OberflächenelementeBearbeiten

IconBearbeiten

Icon ist eine grafische Komponente für die Anzeige von - meist kleinen - Bildern.

ImageIconBearbeiten

ImageIcon ist eine direkte Unterklasse von Icon.

JLabelBearbeiten

 
JLabel

JLabel als äquivalent zu java.awt.Label und stellt eine "einfache" Beschriftung dar, welche optional um ein Icon erweitert werden kann. Eine JLabel Instanz kann hierbei einer anderen Komponente als Beschriftung über die Methode setLabelFor (JComponent) zugewiesen werden.

AbstractButtonBearbeiten

Mit AbstractButton werden die allgemeinen Eigenschaften von Schaltflächen bereitgestellt. Hierzu gehören:

  • setMnemonic zur Definition des Buchstabens über den per Tastatur die Schaltfläche aktiviert werden kann.
  • doClick zur Aktivierung der Schaltfläche ohne Benutzerinteraktion
  • setIcon um ein Bild der Schaltfläche hinzuzufügen. Hierzu kommen noch die Methoden setDisabledIcon, setSelectedIcon, setRolloverIcon, setDisabledSelectionIcon und setRolloverSelectedIcon zur genauen Steuerung.

JButtonBearbeiten

 
JButton

Der Typ JButton ist die Implementierung für eine "normale" Schaltfläche. Auf die Betätigung der Schaltfläche kann über einen ActionListener bzw. ein Action Objekt reagiert werden.

JToggleButtonBearbeiten

Ein JToggleButton ist eine Schaltfläche, welche beim ersten Betätigen aktiviert wird und ein zweites gesondertes Betätigen zur Deaktivierung benötigt.

JCheckBoxBearbeiten

 
JCheckBox

Eine JCheckBox ist ein Auswahlfeld, welches an- und ausgeschaltet werden kann.

JRadioButtonBearbeiten

Ein JRadioButton ist ein Auswahlfeld, welches an- und ausgeschaltet werden kann. JRadioButtons werden hierbei üblicherweise nur in Verbindung mit einer ButtonGroup verwendet.

 

ButtonGroupBearbeiten

Eine ButtonGroup dient dazu insbesonder RadioButtons zusammenzufassen, so dass nur eine JRadioButton aktiv ist.

BorderBearbeiten

Bei einem Border handelt es sich um einen Rahmen, der um beliebige andere grafische Komponenten gelegt werden kann.

JToolTipBearbeiten

Bei einem JToolTip handelt es sich um Tooltip-Element, wie man es von verschiedenen Programmen kennt. Es zeigt nach kurzem Zeitraum eine kurze Hilfe zu einem bestimmten Element an.

JTextComponentBearbeiten

JTextFieldBearbeiten

und JTextField erzeugt ein Textfeld

JPasswordFieldBearbeiten

Das JPasswordField ist ein spezielles JTextField, welches die Zeichen nicht auf dem Bildschirm darstellt, sondern ein alternatives Zeichen zeigt, das so genannte Echozeichen. Standardmäßig ist das ein Sternchen. So lassen sich Passwort-Felder anlegen, die eine Eingabe verbergen.

JFormattedTextFieldBearbeiten

Das formatierte Eingabefeld dient dazu, Eingaben nur in einer bestimmten vorgegebenen Form zuzulassen. Im Gegensatz zu anderen Sprachen werden dabei die fest definierten Zeichen mit als Inhalt zurückgegeben. Eine einfache Möglichkeit, Formatierungen vorzugeben ist der MaskFormatter.

JTextAreaBearbeiten

JTextPaneBearbeiten

JTextPane erzeugt einen Textcontainer, der nur dazu da ist, mit Text gefüllt zu werden. Der in ihm enthaltene Text ist nicht editierbar.

JEditorPaneBearbeiten

Mit Hilfe des JEditorPane kann ein bereits formatierter Text editiert werden. Das JEditorPane unterstützt als Formate RTF (Rich Text Format) und HTML.

JScrollBarBearbeiten

JScrollPaneBearbeiten

JProgressBarBearbeiten

Mit der JProgressBar lässt sich der Fortschritt einer Aktion visualisieren. Bei der Instanziierung wird eine Unter- und Obergrenze angegeben. Innerhalb der Aktion, deren Fortschritt visualisiert werden soll, muss der aktuelle Wert der JProgressBar in bestimmten Abständen inkrementiert werden.

JComboBoxBearbeiten

Die JComboBox beinhaltet verschiedene Einträge, die angewählt werden können.

JListBearbeiten

Das JList-Element beinhaltet eine Liste von Einträgen, die, wie in der JComboBox, angewählt werden können.

JViewPortBearbeiten

JMenuBarBearbeiten

In Swing können alle Hauptfenster mit Ausnahme von JWindow eine Menüleiste haben. Dabei handelt es sich um eine Instanz der Klasse JMenuBar, die dem Hauptfenster durch Aufruf von addJMenuBar hinzugefügt wird.

JMenuItemBearbeiten

Ein einzelnes Element innerhalb eines JMenu, beispielsweise "Datei-Drucken".

JMenuBearbeiten

Dient als Container für JMenuItems und JSeparators.

JCheckBoxMenuItemBearbeiten

Hat gegenüber dem JMenuItem den Vorteil, dass ein Haken beim aktuellen Status erscheint. Die entsprechenden Methoden sind: isSelected und setSelected

JRadioButtonMenuItemBearbeiten

JSeparatorBearbeiten

Die einzelnen Elemente eines JMenu können mit dem JSeparator in logische Gruppierungen unterteilt werden. Es handelt sich um eine Trennlinie.

JRootPaneBearbeiten

JLayeredPaneBearbeiten

JDesktopPaneBearbeiten

JInternalFrameBearbeiten

JDialogBearbeiten

JPopupMenuBearbeiten

Ein JPopupMenu wird meist als Kontextmenü genutzt und entsprechend z.B. über die Maus oder Tastatur aktiviert.

JToolBarBearbeiten

Eine Toolbar kann man vereinfacht als die kleinen Leisten mit Bildchen beschreiben, wie man sie in nahezu jeder Textverarbeitung sieht.

JTabbedPaneBearbeiten

 
JTabbedPane

JTabbedPane ermöglicht das Aufteilen der grafischen Oberfläche über sog. Reiter. Diese können beliebig positioniert und auch mit Icons versehen werden.

Codebeispiel

JSplitPaneBearbeiten

JSplitPane ermöglicht die Aufteilung der grafischen Oberflächen in zwei Bereiche, wahlweise horizontal oder vertikal. Standardmässig kann der Anwender hierbei die Größen der zwei Komponenten der JSplitPanel beliebig in Ihrer Größe ändern.

JTableBearbeiten

Eine JTable ermöglicht eine grafische Tabelle, optional auch mit Tabellenkopf.

BeispielBearbeiten

import javax.swing.table.DefaultTableModel;
import javax.swing.*;
import java.awt.BorderLayout;
import java.util.Vector;

public class GUIFilmTabelle extends JPanel {

  //Vektor für Spaltennamen
  private Vector columnNames = new Vector();

  //Vektor für Daten
  private Vector data = new Vector();

  public GUIFilmTabelle()
  {
    super(new BorderLayout());
    //TableModel: Tabellenmanipulation, Daten
    MyDefaultTableModel model = new MyDefaultTableModel(data, columnNames);
    //Tabelle: Anzeige
    JTable table = new JTable(model); 
    model = (MyDefaultTableModel) table.getModel();
    JComboBox comboBox = new JComboBox();
    comboBox.addItem("UP");
    comboBox.addItem("DOWN");
    table.getColumnModel().getColumn(1).setCellEditor(new DefaultCellEditor(comboBox));
    // ScrollPane zu JPanel hinzufügen
    add(new JScrollPane(table), BorderLayout.CENTER);    
  }
 
  // Inner class MyDefaultTableModel: Tabellen-Model
  public class MyDefaultTableModel extends DefaultTableModel {
    
    public MyDefaultTableModel(Vector data, Vector columnNames) {
      super(data, columnNames); 
      setDataVector(data,columnNames);
      this.addColumn("Name");
      this.addColumn("UP/DOWN");   
    }
    
    public Class getColumnClass(int col) {
      Vector v = (Vector) this.getDataVector().elementAt(0);
      return v.elementAt(col).getClass();
    }
       
    public boolean isCellEditable(int row, int col) {
      Class columnClass = getColumnClass(col);
      return columnClass != ImageIcon.class;
    }
  }
}

JTreeBearbeiten

Swing stellt eine Komponente für die Darstellung von Baumstrukturen zur Verfügung - JTree.

LayoutmanagerBearbeiten

BorderLayoutBearbeiten

Dieses Layout platziert Komponenten in 5 möglichen Bereichen: oben, unten, links, rechts, zentriert.

Beispiel zum BorderLayout:

 import java.awt.*;
 import java.awt.event.*;
 
 public class TestFrame extends Frame
 {
   public TestFrame () 
   {
     setTitle("BorderLayout-Beispiel");                              
     addWindowListener(new TestWindowListener());
     
     setLayout(new BorderLayout());                                      // BorderLayout setzen
     
     add(new Label("Centertruder", Label.CENTER), BorderLayout.CENTER);  // CENTER
     add(new Label("Westruder", Label.CENTER), BorderLayout.WEST);       // WEST
     add(new Label("Eastruder", Label.CENTER), BorderLayout.EAST);       // EAST
     add(new Label("Northtruder", Label.CENTER), BorderLayout.NORTH);    // NORTH
     add(new Label("Southtruder", Label.CENTER), BorderLayout.SOUTH);    // SOUTH
     
     setSize(300,150);
     setVisible(true);                           
   }
 
   class TestWindowListener extends WindowAdapter
   {
     public void windowClosing(WindowEvent e)
     {
       e.getWindow().dispose();                  
       System.exit(0);                            
     }    	
   }
   
   public static void main (String args[]) 
   {
     new TestFrame ();
   }
 }
 
(Screenshot: Linux/KDE)

FlowLayoutBearbeiten

Durch die Verwendung eines FlowLayouts werden alle GUI-Komponenten in eine Zeile der Reihe nach angehängt, bis diese durch deren Größe nicht mehr positioniert werden können. Sollte dies der Fall sein, so werden die folgenden Komponenten in die nächste Zeile versetzt. Beim FlowLayout kann jedoch kein Platz zwischen den einzelnen Grafikobjekten freigelassen werden (in der Hinsicht auf die Positionierung anderer Komponenten).

ViewportLayoutBearbeiten

GridLayoutBearbeiten

Dieses Layout bildet ein Gitter, dessen Zellen alle gleich groß sind. Die Anzahl der Spalten und Reihen, die dieses Gitter enthalten soll, kann spezifiziert werden. Pro Zelle kann dann genau eine Komponente zum Layout hinzugefügt werden. Die Komponenten werden in ihrer Größe gestreckt, damit sie die ganze Zelle ausfüllen. Außerdem kann ein horizontaler und vertikaler Abstand zwischen den einzelnen Zellen in Pixeln angegeben werden.

Beispiel zum GridLayout:

 import java.awt.*;
 import java.awt.event.*; 
 
 public class TestFrame extends Frame
 {
   public TestFrame () 
   {
     setTitle("GridLayout-Beispiel");                              
     addWindowListener(new TestWindowListener());
    
     setLayout(new GridLayout(4,3));              // GridLayout setzen
    
     for (int i=1; i<=10; i++)
     {
       add(new Label("Beschriftung" + i));  	
     }
    
     setSize(300,150);
     setVisible(true);                           
   }
 
   class TestWindowListener extends WindowAdapter
   {
     public void windowClosing(WindowEvent e)
     {
       e.getWindow().dispose();                  
       System.exit(0);                            
     }           
   }
  
   public static void main (String args[]) 
   {
     new TestFrame ();
   }
 }
 
(Screenshot: Linux/KDE)

GroupLayoutBearbeiten

ScrollPaneLayoutBearbeiten

Für gewöhnlich wird dieses Layout nie explizit benutzt. Stattdessen erzeugt man ein ScrollPanel, welches sich dann automatisch dieses Layout setzt, um die ScrollBars, die Eckkomponenten, den Inhalt und die Zeilen- und Spaltenheader zu setzen.

GridBagLayoutBearbeiten

Das GridBagLayout ist ein komplexer LayoutManager2[1], mit welchem eine Menge an Möglichkeiten geboten werden. Die eigentliche Ausrichtigung der Komponenten erfolgt über das GridBagConstraints Objekt, welches beim Hinzufügen zum Container anzugeben ist.

Beispiel zum GridBagLayout:

 import java.awt.*;
 import java.awt.event.*;
 
 public class TestFrame extends Frame
 { 
   GridBagLayout grid = new GridBagLayout();
   GridBagConstraints straints = new GridBagConstraints();
   Button button;
    
   public TestFrame () 
   {		  
     setTitle("GridBagLayout-Beispiel");
     setLayout(grid);                             // GridBagLayout setzen
     addWindowListener(new TestWindowListener());
    
     straints.gridx = straints.gridy = 0;
     straints.gridheight = straints.gridwidth = 1;
     straints.fill = GridBagConstraints.BOTH;
     button = new Button("Hallo");
     grid.setConstraints(button, straints);
     add(button);
 
     straints.gridy = 1;
     button = new Button("du");
     grid.setConstraints(button, straints);
     add(button);
 
     straints.gridx = 1;
     straints.gridy = 0;
     straints.gridheight=2;
     button = new Button("Welt!");
     grid.setConstraints(button, straints);
     add(button);
    
     straints.gridx = 0;
     straints.gridy = 2;
     straints.gridheight = 1;
     straints.gridwidth = 2;
     button = new Button("Was ist ein GridBag?");
     grid.setConstraints(button, straints);
     add(button);
        
     pack();
     setVisible(true);                           
   }
    
   class TestWindowListener extends WindowAdapter
   {
     public void windowClosing(WindowEvent e)
     {
       e.getWindow().dispose();                  
       System.exit(0);                            
     }           
   }
  
   public static void main (String args[]) 
   {
     new TestFrame ();
   }
 }
 
(Screenshot: Linux/KDE)

CardLayoutBearbeiten

Ein Layout, vergleichbar mit Karteikarten.

BoxLayoutBearbeiten

  • LINE_AXIS
  • PAGE_AXIS
  • X_AXIS
  • Y_AXIS

OverlayLayoutBearbeiten

Mit dem OverlayLayout ist es möglich mehrere Componenten übereinander anzuordnen.


SpringLayoutBearbeiten

"NullLayout"Bearbeiten

Ein NullLayout ist im eigentlichen Sinne kein Layout. Hierbei können die Elemente frei, mittels Positionsangaben, auf der Oberfläche positioniert werden. Beispiel zum "Null-Layout":

 import java.awt.*;
 import java.awt.event.*;
 
 public class TestFrame extends Frame
 {
   Label label;	
 	
   public TestFrame () 
   {
     setTitle("Null-Layout-Beispiel");                              
     addWindowListener(new TestWindowListener());
    
     setLayout(null);                                     // "Null-Layout" setzen
    
     for(int i=1; i<=5; i++)
     {
       label = new Label("Beschreibung" + i);
       label.setBounds(10+i*20, 20+i*(25-2*i), 100, 15);  // x, y, breite, höhe
       add(label);        	
     }
    
     setSize(300,150);
     setVisible(true);                           
   }
 
   class TestWindowListener extends WindowAdapter
   {
     public void windowClosing(WindowEvent e)
     {
       e.getWindow().dispose();                  
       System.exit(0);                            
     }           
   }
  
   public static void main (String args[]) 
   {
     new TestFrame ();
   }
 }
 
(Screenshot: Linux/KDE)

AktionenBearbeiten

Über die grafische Benutzeroberfläche setzt der Anwender Befehle zur Durchführung von Aktionen ab. Hierzu unterstützt Swing unter anderem Tastatur und Maus als Eingabegeräte. Die Ereignisse werden über Swing's Event Dispatch Thread an die für ein bestimmtes Ereignis (Event) registrierten Empfänger (EventListener) weitergeleitet. Einige Elemente von Swing, z. B. JMenuItem und JButton können hierbei die Low Level Events wie Mouse Clicked automatisch in semantisch höherwertige Semantic Events (z. B. ActionEvent) übersetzen welche dann wiederum durch den EDT an die jeweiligen Empfänger (ActionListener) weitergeleitet werden.

Um dem Programmierer die Nutzung von ActionEvents zu vereinfachen, unterstützt Swing daher mit dem Interface Action sowie dessen abstrakter Implementierung AbstractAction das sogenannte Command Pattern.

Damit der EDT nicht durch langwierige Operationen blockiert wird und die Oberfläche "hängt" (vgl. Responsiveness), ist es eine übliche Vorgehensweise, die langwierige Arbeit in einem Worker Thread durchzuführen. Hierzu bietet Swing die Klasse SwingWorker. Diese nimmt dem Programmierer die Koordination des EDT mit dem Worker Thread weitgehend ab.