This presentation introduces the main features of Swing, an UI development library for the Java ecosystem. The main focus of the slides is to show the basic features of Swing, such as:
- Main components (JFrame, JPanel, ...)
- Layout management (FlowLayout, BorderLayout, GridLayout, ...)
- Event handling
The presentation is took from the Java course I run in the bachelor-level informatics curriculum at the University of Padova.
2. Programmazione concorrente e distribuita
SUMMARY
Introducing Swing
Main components
Layout management
Event handling
2Riccardo Cardin
3. Programmazione concorrente e distribuita
INTRODUCTION
A little bit of history
Java 1.0 refers to the Abstract Window Toolkit (AWT)
for simple GUI programming
AWT delegates to the underlying OS the responsibility to
create graphical components («peers»)
Look and feel of target platform
It was very hard to create high-quality portable GUIs
Java 1.2 intoduces Swing
Graphic components are painted onto blank windows
The only functionality required from the underlying
windowing system is a way to put up windows and to paint
onto them
Build on top of AWT
3Riccardo Cardin
5. Programmazione concorrente e distribuita
INTRODUCTION
Swing features
A little bit slower than AWT
It’s not a real problem on modern machines
Rich and convenient set of user interface elements
Few dependencies on the underlying platform
Consistent user experience across platforms
Drawback: different look-and-feel from native GUIs
Many different look-and-feels (themes)
Metal, Ocean and Synth (JSE 5.0), Nimbus (JSE 7.0, vector
drawings)
Package javax.swing: it is considered a Java ext.
5Riccardo Cardin
7. Programmazione concorrente e distribuita
MAIN COMPONENTS
Frame
Top level window, Frame (AWT) or JFrame (Swing)
The only Swing component that is not painted on the canvas
Always use «J» components, which belong from Swing
7Riccardo Cardin
EventQueue.invokeLater(new Runnable() {
public void run() {
SimpleFrame frame = new SimpleFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
}
});
class SimpleFrame extends JFrame {
private static final int DEFAULT_WIDTH = 300;
private static final int DEFAULT_HEIGHT = 200;
public SimpleFrame() {
setSize(DEFAULT_WIDTH, DEFAULT_HEIGHT);
}
}
8. Programmazione concorrente e distribuita
MAIN COMPONENTS
Let me explain what’s going on in here...
By default a frame as size of 0 x 0 pixels, so
SimpleFrame set the size of the frame in its ctor
You have to define what should happen when the
user closes the application’s frame
JFrame.EXIT_ON_CLOSE: the program exit on close
Event dispatch thread
Finally, a frame has to be made visible, using
setVisible(true)
8Riccardo Cardin
EventQueue.invokeLater(new Runnable() {
public void run() {
// Configuration statement
}
});
You have to do ALWAYS
in this way!!!
9. Programmazione concorrente e distribuita
MAIN COMPONENTS
Frame hierarchy
Component / Windows
Component is the base class of
every GUI object
Resize and reshape actions
Frame properties
set / get methods
Toolkit class
Used to bind some components
to a particular native toolkit impl.
Adapter pattern
9Riccardo Cardin
Toolkit kit = Toolkit.getDefaultToolkit();
10. Programmazione concorrente e distribuita
MAIN COMPONENTS
Display information in a component
DO NOT DRAW DIRECTLY ONTO A FRAME!
A frame is considered a container for components
Use the content pane instead
Components are instances of JComponent / JPanel
Implement paintComponent method, that is called by the
event handler every time a window needs to be redrawn
10Riccardo Cardin
// Get the content pane and draw something on it
Container contentPane = frame.getContentPane();
Component c = /* . . . */;
contentPane.add(c);
class MyComponent extends JComponent {
public void paintComponent(Graphics g) {
// code for drawing
}}
11. Programmazione concorrente e distribuita
MAIN COMPONENTS
11Riccardo Cardin
Used to organize the
menu bar and
content pane and to
implement
look-and-feel
Used to add
Components and to
draw something
onto the frame
13. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
JDK has not form designer tools
You need to write code to position (lay out) the UI
components where you want them to be
Buttons, text fields, and other UI elements extend the
class Component.
Components can be placed inside containers, such as panel.
Containers can themselves be put inside other containers
Container extends Component
Composite pattern
13Riccardo Cardin
In general components are placed inside containers, and a layout
manager determines the position and sizes of the components in the
container
14. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
14Riccardo Cardin
Container class
stores references to
itself
16. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
Composite pattern
In Swing, the problem is that leaf components are
subclasses of composite class
16Riccardo Cardin
It is a composition
of Component
objects
17. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
Flowlayout
Elements are put in a row, sized at their preferred size
Default layout manager for a panel
If the horizontal space in the container is too small,
the layout uses multiple rows.
Elements are centered horizontally by default
Layout changes accordingly to container size
Constructor permits to specify:
Left, right or center alignment
Vertical or horizontal gaps
17Riccardo Cardin
Elements are put in
rows
18. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
Add 3 buttons to a JPanel
18Riccardo Cardin
public class BorderLayoutExample extends JFrame {
public BorderLayoutExample(String title) {
super(title);
// Set the size of the window
setSize(300, 200);
// Add component to frame
addComponentsToPane(getContentPane());
}
private void addComponentsToPane(final Container pane) {
// Panel with FlowLayout as default layout manager
JPanel controls = new JPanel();
controls.add(new JButton("Button 1"));
controls.add(new JButton("Button 2"));
controls.add(new JButton("Button 3"));
// Content pane of the frame, BorderLayout as default
pane.add(controls, BorderLayout.SOUTH);
}
19. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
BorderLayout
Defines 5 regions in which elements can be placed
Default layout manager of the JFrame content panel
BorderLayout.NORTH, BorderLayout.EAST...
Center is the default position
The edge components are laid first
When the container is resized, the dim. of
the edge components are unchanged
It grows all components to fill the
available space
Use an intermediate JPanel to contain the
elements
19Riccardo Cardin
20. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
Build a window with 3 buttons at the bottom
20Riccardo Cardin
public class BorderLayoutExample extends JFrame {
public BorderLayoutExample(String title) {
super(title);
// Set the size of the window
setSize(300, 200);
// Add component to frame
addComponentsToPane(getContentPane());
}
private void addComponentsToPane(final Container pane) {
// Panel with FlowLayout as default layout manager
JPanel controls = new JPanel();
controls.add(new JButton("Button 1"));
controls.add(new JButton("Button 2"));
controls.add(new JButton("Button 3"));
// Content pane of the frame, BorderLayout as default
pane.add(controls, BorderLayout.SOUTH);
}
21. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
GridLayout
Arranges all components in rows and columns like a
spreadsheet
All components are given the same size (also in case of
resizing of the window)
Usually used to model a small part of a UI, rather than the
whole windows
Components are added starting from the first entry in
the first row, then the second entry and so on
21Riccardo Cardin
// Get the content pane and draw something on it
// Valuing with a 0 the number of rows will allow the layout to
// use as many rows as necessary
panel.setLayout(new GridLayout(4, 4));
22. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
Build a windows with 4 buttons put in 2 rows
22Riccardo Cardin
public class GridLayoutExample extends JFrame {
public BorderLayoutExample(String title) {
super(title);
// Set the size of the window
setSize(300, 200);
// Add component to frame
addComponentsToPane(getContentPane());
}
private void addComponentsToPane(final Container pane) {
// Set GridLayout to the panelb
JPanel controls = new JPanel();
controls.setLayout(new GridLayout(2, 2));
controls.add(new JButton("Button 1"));
controls.add(new JButton("Button 2"));
controls.add(new JButton("Button 3"));
controls.add(new JButton("Button 4"));
pane.add(controls;
}
23. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
CardLayout
Used to model two or more components that share
the same display space
It is like playing card in a stack, where only the top
card (component) is visible at any time
You can ask for either the first or the last card
You can ask to flip the deck backwards or forwards
You can specify a card with a specific name
23Riccardo Cardin
24. Programmazione concorrente e distribuita
LAYOUT MANAGEMENT
Build a window with two cards
24Riccardo Cardin
public class CardLayoutExample extends JFrame {
// ...
private void addComponentsToPane(final Container pane) {
// ...
cards = new JPanel(new CardLayout());
cards.add(createCard1(), "Card 1");
cards.add(createCard2(), "Card 2");
}
private JPanel createCombo() {
// ...
// Add combo a listener
comboBox.addItemListener(new ItemListener() {
@Override
public void itemStateChanged(ItemEvent e) {
// Get the layout
CardLayout layuot = (CardLayout) cards.getLayout();
layuot.show(cards, (String) e.getItem());
}
});
We will introduce
listeners in a
moment
26. Programmazione concorrente e distribuita
EVENT HANDLING
An operating environment constantly monitors
events and reports them to the program
The program decides what to do in response to these
events
Keystrokes, mouse clicks, and so on
In Java (AWT) the developer has the full control on
how the events are transmitted from the event
source to events listeners
Every object can be an event listener (delegation model)
Event listeners register themself to an event source
Obsever pattern
Events are objects of type java.util.EventObject
26Riccardo Cardin
27. Programmazione concorrente e distribuita
EVENT HANDLING
Summarizing
A listener object implements a listener interface
An event source can register listener and send them
event objects
The event source sends events to every registered
listener
The listener, using the event info, reacts accordingly
27Riccardo Cardin
class MyListener implements ActionListener {
public void actionPerformed(ActionEvent event) {
// React to the event goes here
}
}
JButton button = new Jbutton("OK");
button.addActionListener(listener); // Registering a listener
28. Programmazione concorrente e distribuita
EVENT HANDLING
28Riccardo Cardin
An event source
registers a listener
Event
source
Event source notifies
the listener
The listener react
accordingly
31. Programmazione concorrente e distribuita
EVENT HANDLING
Let’s see a simple example
First of all, let’s create the buttons
To create a button, simply create a JButton object, giving to
it a label or an icon
31Riccardo Cardin
We will show a panel populated with three buttons. When a button is
clicked, we want the background color of the panel to change to a
particular color.
// Create the buttons
JButton blueButton = new JButton("Yellow");
JButton blueButton = new JButton("Blue");
JButton redButton = new JButton("Red");
// Add them to a panel (flow layout anyone?)
buttonPanel.add(yellowButton);
buttonPanel.add(blueButton);
buttonPanel.add(redButton);
32. Programmazione concorrente e distribuita
EVENT HANDLING
Let’s see a simple example
Then, let’s define button listeners
32Riccardo Cardin
class ColorAction implements ActionListener {
private Color backgroundColor; // The color to set to the panel
public ColorAction(Color c) {
backgroundColor = c;
}
public void actionPerformed(ActionEvent event) {
// set panel background color
}
}
// Create the listeners
ColorAction yellowAction = new ColorAction(Color.YELLOW);
ColorAction blueAction = new ColorAction(Color.BLUE);
ColorAction redAction = new ColorAction(Color.RED);
// Register listeners to buttons
yellowButton.addActionListener(yellowAction);
blueButton.addActionListener(blueAction);
redButton.addActionListener(redAction);
33. Programmazione concorrente e distribuita
EVENT HANDLING
Let’s see a simple example
A problem rises: how can a listener modify a property
of the panel?
Please, do not try to add listener’s func. to the frame
Violation of separation of concerns
Use inner classes instead!
33Riccardo Cardin
class ButtonFrame extends JFrame {
// The panel to change the color
private JPanel buttonPanel;
private class ColorAction implements ActionListener {
private Color backgroundColor;
public void actionPerformed(ActionEvent event) {
// Changing the color to the main class panel
buttonPanel.setBackground(backgroundColor);
}
}
}
34. Programmazione concorrente e distribuita
EVENT HANDLING
Let’s see a simple example
Can we go even further?
Let’s use anonymous inner classes to handle events
The inner class mechanism automatically generates a
constructor that stores all final variables that are used
Closure anyone?!
34Riccardo Cardin
public void makeButton(String name, final Color backgroundColor) {
JButton button = new JButton(name);
buttonPanel.add(button);
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent event) {
buttonPanel.setBackground(backgroundColor);
}
});
}
36. Programmazione concorrente e distribuita
EVENT HANDLING
Let’s see a simple example
If the anonymous inner class method calls one
method only, EventHandler class can be used
Reflection mechanism
The statement frame.loadData() is executed in response
of an event
The statement
frame.loadData(event.getSource.getText()) is
executed
36Riccardo Cardin
loadButton.addActionListener(
EventHandler.create(ActionListener.class, frame, "loadData"));
EventHandler.create(ActionListener.class, frame, "loadData",
"source.text");
37. Programmazione concorrente e distribuita
EVENT HANDLING
Not all events are simply as button clicks
The listener WindowListener interface, that handles
WindowEvent objects, has 7 methods
Probably you don’t need to defined them all!
Each AWT listener interfaces with more than one
method comes with a companion Adapter
Implements all methods with "do nothing" operations
37Riccardo Cardin
public interface WindowListener {
void windowOpened(WindowEvent e);
void windowClosing(WindowEvent e);
void windowClosed(WindowEvent e);
void windowIconified(WindowEvent e);
void windowDeiconified(WindowEvent e);
void windowActivated(WindowEvent e);
void windowDeactivated(WindowEvent e);
}
38. Programmazione concorrente e distribuita
EVENT HANDLING
Adapter pattern
Class adapter
Object adapter
38Riccardo Cardin
Target interface
Source interface
Adapt source interface
to target
39. Programmazione concorrente e distribuita
EVENT HANDLING
What if you need to share the same behaviour
in response to more than one event?
Use Action interface, that extends ActionListener
It encapsulates the description of the «command» and
parameters that are necessary to carry out the command
Command pattern
AbstractAction is an adapter class provided by the JDK
Then simply add the action to your UI components using
constructor
39Riccardo Cardin
void actionPerformed(ActionEvent event)
// Add a property to the action object indexed by key
void putValue(String key, Object value)
// Get a property indexed by key
Object getValue(String key)
new JButton(new MyAction());
44. Programmazione concorrente e distribuita
REFERENCES
Chap. 7 «Graphics Programming», Core Java Volume I -
Fundamentals, Cay Horstmann, Gary Cornell, 2012, Prentice Hall
Chap. 8 «Event Handling», Core Java Volume I - Fundamentals, Cay
Horstmann, Gary Cornell, 2012, Prentice Hall
Chap. 9 «User Interface Components with Swing», Core Java
Volume I - Fundamentals, Cay Horstmann, Gary Cornell, 2012,
Prentice Hall
How to Use FlowLayout
https://docs.oracle.com/javase/tutorial/uiswing/layout/flow.html
How to Use CardLayout
https://docs.oracle.com/javase/tutorial/uiswing/layout/card.html
How to Use Actions
https://docs.oracle.com/javase/tutorial/uiswing/misc/action.html
44Riccardo Cardin