Download public void paint(Graphics g)

Document related concepts
no text concepts found
Transcript
Programming in Java
More about GUI
蔡文能
交通大學資訊工程學系
[email protected]
http://www.csie.nctu.edu.tw/~tsaiwn/java/
交通大學資訊工程學系
Java
More-GUI
Agenda
GUI (Graphical User Interface)
AWT Component (package java.awt )
Graphics and Events
Event Model
Listener interfaces and Adaptors
Events and Listeners for standard AWT events
Layout Manager?
Swing Library
交通大學資訊工程學系 蔡文能
5-第2頁
Java
More-GUI
Java UI functionality
Presenting a Graphical User Interface (GUI)
Playing sounds
 Applications can play sounds as well as Applets since JDK1.2.
Getting configuration information
 Users can specify configuration information to a program using commandline arguments (applications only) and parameters (applets only).
Saving user preferences using properties
 For information that applications need to save even when they're not
running, you can use properties. (not for Applets due to security
problem.)
Getting/displaying text using the standard input/output/error streams
 Standard input, output, and error are the old-fashioned way of presenting a
user interface.
 They're still useful for testing and debugging programs.
交通大學資訊工程學系 蔡文能
5-第3頁
Java
交通大學資訊工程學系 蔡文能
http://java.sun.com/j2se/1.4.1/docs/api/
More-GUI
5-第4頁
Java
More-GUI
The AWT Components
交通大學資訊工程學系 蔡文能
5-第5頁
Java
More-GUI
Example using AWT Component
 以下為 Java 的AWT 提供的Graphical UI (GUI) components (
圖型元件).
交通大學資訊工程學系 蔡文能
5-第6頁
Java
More-GUI
JFC/Swing
The Java Foundation Classes (JFC) API extends
the original Abstract Window Toolkit (AWT) by
adding a comprehensive set of graphical user
interface class libraries.
JFC/Swing components include:
Pluggable Look and Feel
Accessibility API
Java 2DTM API (Java 2 only)
Drag and Drop (Java 2 only)
AWT
Internationalization
交通大學資訊工程學系 蔡文能
5-第7頁
Java
More-GUI
Swing Library
交通大學資訊工程學系 蔡文能
5-第8頁
Java
More-GUI
Class javax.swing.JComponent
java.lang.Object
|
+--java.awt.Component
|
+--java.awt.Container
|
+--javax.swing.JComponent
交通大學資訊工程學系 蔡文能
5-第9頁
Java
JDK 1.0
8 packages
212 classes
JDK 1.1
JDK 1.2
JDK 1.3
JDK 1.4
23 packages
504 classes
59 packages
1520 classes
77 packages
1595 classes
103 packages
2175 classes
New Events
JFC/Swing
Inner class
Object
Serialization
Jar Files
Drag and
Drop
JNDI
Java Sound
Timer
Java2D
JDBC
Regular Exp
Logging
Assertions
NIO
131 packages
2656 classes
javax.activity,
javax.management
java.nio, javax.imageio,
javax.net, javax.print,
javax.security, org.w3c
CORBA
International
Reflection
More-GUI
JDK 1.5
javax.naming, javax.sound,
javax.transaction
RMI
javax.accessibility, javax.swing, org.omg
java.math, java.rmi, java.security, java.sql, java.text, java.beans
交通大學資訊工程學系 蔡文能
java.applet, java.awt, java.io, java.lang, java.net, java.util
5-第10頁
Java
More-GUI
What is MFC?
(Microsoft Foundation Classes)
C++ API for Microsoft Windows programming.
Object-oriented framework over Win32.
Provides a set of classes allowing an easy
application creation process.
It encapsulates most part of the Windows API.
交通大學資訊工程學系 蔡文能
5-第11頁
Java
More-GUI
MFC vs. JFC/Swing
Java Foundation Classes (Swing) are a set of Java class
libraries provided as part of the Java Platform to support
building graphics user interface (GUI) and graphics
functionality for client applications that will run on popular
platforms such as Microsoft Windows, Linux, and Mac
OSX.
JFC is needed when multiplatform compatibility is wanted.
Under Windows, MFC works better than JFC
交通大學資訊工程學系 蔡文能
5-第12頁
Java
More-GUI
Other Ways of Getting User Input
Sliders, Scrollbars, and Text Areas
 The Scrollbar class is used for both slider and scrollbar
functionality.
 The TextArea class simply provides an area to display or allow
editing of several lines of text.
 Text areas automatically include scrollbars.
交通大學資訊工程學系 蔡文能
5-第13頁
Java
More-GUI
The Basic Controls and events
基本控制元件: Buttons, Checkboxes, Choices,
Lists, Menus, and Text Fields
When a user activates one of these controls, it posts an
event.
 An object that contains the control can react to the event by
implementing the action() method. (AWT1.0舊的 event處理
方式)
Clicking a button.
Pressing Return in a text field.
 新的處理方式: (AWT1.1 event model)
該元件要先 addActionListener( 有處理能力的物件 ) 或向其他
Listener 註冊 (參看後面 slides)
交通大學資訊工程學系 蔡文能
5-第14頁
Java
More-GUI
Event driven (事件驅動)
Event (事件)
 使用者執行視窗程式時對視窗元件的動作,例如按一下按鈕
或鍵盤。
Event Handler (事件處理程式)
 程式執行中若發生事件,可以由指定的事件處理程式進行處理。
Delegation Event Model (委託式的事件處理模型)
 Java AWT1.1的事件處理模型, 包括:
事件來源(Event Source) – 發出事件物件的來源, 如視窗元件的按
鈕。
監聽者物件(Listener) – 被委託處理指定事件的物件。
動作
事件
事件來源
交通大學資訊工程學系 蔡文能
監聽者物件
5-第15頁
Java
More-GUI
MVC design pattern Overview
Model-View-Controller architecture decouples 3 aspects of
a user-interface
 Model: the data being displayed
 View: how the data is displayed
 Controller: how the user interacts with the displayed data
JFC/Swing variant of MVC:
separable model architecture.
Provides benefits of complete MV separation.
Easier to use because it bundles view and controller together.
交通大學資訊工程學系 蔡文能
5-第16頁
Java
More-GUI
More AWT Components
Creating Custom Components: Canvases
 The Canvas class lets you write custom Components. With your
Canvas subclass, you can draw custom graphics to the screen.
Labels
 A Label simply displays an unselectable line of text.
Containers: Windows, Panels, and Scroll Panes
 The AWT provides three types of containers, all are subclasses of
the Container class (which is a Component subclass).
The Window subclasses -- Dialog, FileDialog, and Frame -- provide
windows to contain components.
A Panel groups components within an area of an existing window.
A ScrollPane display a potentially large component in a limited
amount of space, using scrollbars to control which part of the
component is displayed.
交通大學資訊工程學系 蔡文能
5-第17頁
Java
More-GUI
Windows (1/2)
Includes Dialog, FileDialog, and Frame.
Frames (框窗) create normal, full-fledged windows.
Dialogs(對話窗) create windows which depends on
Frames and can be modal.
Example: The FileDialog(檔案對話盒) window for files:
交通大學資訊工程學系 蔡文能
5-第18頁
Java
More-GUI
Windows (2/2)
Dialog is a Window
交通大學資訊工程學系 蔡文能
Frame is a Window
javax.swing.JFrame
5-第19頁
Java
More-GUI
Applet is a Panel
交通大學資訊工程學系 蔡文能
5-第20頁
Java
More-GUI
ScrollPane is NOT a Panel
交通大學資訊工程學系 蔡文能
5-第21頁
Java
More-GUI
ScrollPane Example
 The JDK 1.1 AWT introduced the ScrollPane class, which
makes it easy for you to provide a scrolling area.
 The following picture shows an applet in which both the vertical
and horizontal scrollbars are needed.
交通大學資訊工程學系 蔡文能
5-第22頁
Java
More-GUI
How to Use ScrollPane
Creates a scroll pane and puts a child component in it:
ScrollPane sp1 = new ScrollPane();
sp1.add(anotherComponent);
You can also specify the scrollbar display policy in the ScrollPane:
ScrollPane sp2 = new ScrollPane(ScrollPane.SCROLLBARS_ALWAYS);
SCROLLBARS_AS_NEEDED
 The default value. Show each scrollbar only when it's needed.
SCROLLBARS_ALWAYS
Other
Constants
 Always show scrollbars.
SCROLLBARS_NEVER
 Never show scrollbars. You might use this option if you don't want
the user to directly control what part of the child component is
shown.
交通大學資訊工程學系 蔡文能
5-第23頁
Java
More-GUI
Components to be put into a ScrollPane
When implement a component to be put in a
ScrollPane:
Need to implement the child component's getPreferredSize
method so that it returns the dimensions needed to fully display the
component.
Implement the child component so that it works well when its
drawing area is larger than its preferred size.
 The component might draw itself in the center of its drawing
area, filling the extra space with a solid color.
When the component is being scrolled, you might notice flashing, or
flickering, in the display area.
交通大學資訊工程學系 蔡文能
5-第24頁
Java
More-GUI
Scrolling-related code from the previous applet:
//The component that will be scrolled.
class ScrollableCanvas extends Canvas {
...
Dimension preferredSize = new Dimension(600, 320);
Dimension minimumSize = new Dimension(10, 10);
public Dimension getMinimumSize() {
return minimumSize;
}
public Dimension getPreferredSize() {
return preferredSize;
}
public void paint(Graphics g) {
g.drawImage(image, 0, 0, getBackground(), this);
}
}
交通大學資訊工程學系 蔡文能
5-第25頁
Java
More-GUI
Other AWT Classes
The java.awt package supplies several classes to
represent sizes and shapes.
 Dimension : specifies the size of a rectangular area.
 Insets : specify how much padding should exist between the
outside edges of a container and the container's display area.
 Shape : include Point, Rectangle, and Polygon.
The Color class is useful for representing and
manipulating colors.
The Image class provides a way to represent image data.
 Applets can get Image objects for GIF and JPEG images using the
Applet getImage() methods.
…
交通大學資訊工程學系 蔡文能
5-第26頁
Java
More-GUI
Graphics and Events
The Graphics and Event classes are crucial to the
AWT drawing and event handling system.
 A Graphics object (圖形元件)represents a drawing context -without a Graphics object, no program can draw to the screen.
 An Event (事件)object represents a user action, such as a
mouse click.
交通大學資訊工程學系 蔡文能
5-第27頁
Java
More-GUI
Example: 英制公制轉換 (1/3)
http://java.sun.com/docs/books/tutorial/uiswing/components
/example-1dot4/Converter.java
File lists:
/* * A 1.4 application that requires the following files:
* ConversionPanel.java
* ConverterRangeModel.java
* FollowerRangeModel.java
* Unit.java
*/
交通大學資訊工程學系 蔡文能
5-第28頁
Java
More-GUI
Example:
英制公制轉換
(2/3)
兩個主要 class:
Converter
ConversionPanel
交通大學資訊工程學系 蔡文能
5-第29頁
Java
More-GUI
Example: 英制公制轉換 (3/3)
The Component Hierarchy
交通大學資訊工程學系 蔡文能
5-第30頁
Java
More-GUI
Drawing
How Drawing Requests Occur
 Use the repaint( ) method to request to be scheduled for drawing.
 Invoke the Component's update( ) method.
 Call the Component's paint( ) method. (default)
The Graphics Object
 The only argument to paint() and update() is a Graphics object.
 The Graphics class provides methods for the following:
Drawing and filling rectangles, arcs, lines, ovals, polygons, text, and
images.
Getting or setting the current color, font, or clipping area.
How to Draw
 The simplest way for a Component to draw itself is to put drawing code
in its paint() method.
public void paint(Graphics g) {
Dimension d = size();
g.drawRect(0,0, d.width - 1, d.height - 1);
}
交通大學資訊工程學系 蔡文能
5-第31頁
Java
More-GUI
AWT 1.0 Event Model
舊的方法
交通大學資訊工程學系 蔡文能
5-第32頁
Java
More-GUI
Default Methods for Each Component
舊的方法
action() (Event.ACTION_EVENT)
mouseEnter() (Event.MOUSE_ENTER)
mouseExit() (Event.MOUSE_EXIT)
mouseMove() (Event.MOUSE_MOVE)
mouseDown() (Event.MOUSE_DOWN)
mouseDrag() (Event.MOUSE_DRAG)
mouseUp() (Event.MOUSE_UP)
keyDown() (Event.KEY_PRESS or Event.KEY_ACTION)
keyUp() (Event.KEY_RELEASE or
Event.KEY_ACTION_RELEASE)
gotFocus() (Event.GOT_FOCUS)
lostFocus() (Event.LOST_FOCUS)
handleEvent() (all event types)
交通大學資訊工程學系 蔡文能
5-第33頁
Java
More-GUI
Example
舊的方法
public boolean action(Event e, Object arg) {
if (e.target instanceof TextField) {
setSliderValue(getValue());
controller.convert(this);
return true;
}
if (e.target instanceof Choice) { . . . }
return false;
}
public boolean handleEvent(Event e) {
if (e.target instanceof Scrollbar) {
textField.setText(String.valueOf(slider.getValue()));
controller.convert(this);
}
return super.handleEvent(e);
}
交通大學資訊工程學系 蔡文能
5-第34頁
Java
交通大學資訊工程學系 蔡文能
More-GUI
5-第35頁
Java
More-GUI
Another example (1/ 7)
//eventHandler.java
import java.awt.*;
class eventCanvas extends Canvas
{
boolean hasFocus;
需要寫一個簡單的
HTML 把這 Applet
叫起來
eventCanvas( int width, int height )
{ setBackground( Color.yellow );
resize( width, height );
hasFocus = false;
}
public boolean mouseUp( Event e, int x, int y )
{ eventHandler.reportEvent( "mouseUp" );
return true;
}
交通大學資訊工程學系 蔡文能
5-第36頁
Java
More-GUI
Another example (2/7 )
public boolean mouseDown( Event e, int x, int y )
{ eventHandler.reportEvent( "mouseDown" );
return true;
}
public boolean mouseDrag( Event e, int x, int y )
{ eventHandler.reportEvent( "mouseDrag" );
return true;
}
public boolean mouseEnter( Event e, int x, int y )
{ eventHandler.reportEvent( "mouseEnter" );
return true;
}
public boolean mouseExit( Event e, int x, int y )
{ eventHandler.reportEvent( "mouseExit" );
return true;
}
交通大學資訊工程學系 蔡文能
5-第37頁
Java
More-GUI
Another example (3/7 )
public boolean keyDown( Event e, int key )
{ String eventString = "keyDown: ";
String keyName, modifierName;
modifierName = getModifierName( e );
if ( modifierName != null )
eventString += modifierName;
keyName = getKeyName( key );
if ( keyName != null )
eventString += keyName;
else if (( key >= 32 ) && ( key <= 127 ))
eventString += new Character( (char)key ).toString();
else eventString += key;
eventHandler.reportEvent( eventString );
return true;
}
交通大學資訊工程學系 蔡文能
5-第38頁
Java
More-GUI
Another example (4/7 )
public String getModifierName( Event e )
{ if ( e.controlDown() ) return( "Control-" );
if ( e.metaDown() ) return( "Meta-" );
if ( e.shiftDown() ) return( "Shift-" );
case Event.F10: return "F10";
case Event.F11: return "F11";
case Event.F12: return "F12";
case Event.HOME: return "HOME";
case Event.END: return "END";
case Event.LEFT: return "Left Arrow";
case Event.RIGHT: return "Right
Arrow";
case Event.UP: return "Up Arrow";
case Event.DOWN: return
"DownArrow";
case Event.PGUP: return "Page Up";
case Event.PGDN: return "Page Down";
} //switch
return null;
}
public String getKeyName( int key )
{ switch ( key ) {
case Event.F1: return "F1";
case Event.F2: return "F2";
case Event.F3: return "F3";
case Event.F4: return "F4";
case Event.F5: return "F5";
case Event.F6: return "F6";
case Event.F7: return "F7";
case Event.F8: return "F8";
case Event.F9: return "F9";
return null;
}
交通大學資訊工程學系 蔡文能
5-第39頁
Java
More-GUI
Another example (5/7 )
public boolean keyUp( Event e, int key )
{ eventHandler.reportEvent( "keyUp" );
return true;
}
public boolean gotFocus(Event e, Object what)
{ hasFocus = true;
eventHandler.reportEvent( "gotFocus" );
repaint();
return true;
}
public boolean lostFocus(Event e, Object what)
{ hasFocus = false;
eventHandler.reportEvent( "lostFocus" );
repaint();
return true;
}
交通大學資訊工程學系 蔡文能
5-第40頁
Java
More-GUI
Another example (6/7 )
public void paint( Graphics g )
{ Rectangle r;
r = bounds();
g = getGraphics();
if ( hasFocus ) g.setColor( Color.red );
else g.setColor( Color.yellow );
g.drawRect( 0, 0, r.width-1, r.height-1 );
g.drawRect( 1, 1, r.width-3, r.height-3 );
}
} //class eventCanvas
交通大學資訊工程學系 蔡文能
5-第41頁
Java
More-GUI
Another example (7/7)
public class eventHandler extends java.applet.Applet
{ eventCanvas eCanvas;
static TextArea tArea;
public void init() {
add( new Label( "Click and type in this Canvas:" ) );
eCanvas = new eventCanvas( 200, 100 );
add( eCanvas );
add( new Label( "Here’s a list of canvas events:" ) );
tArea = new TextArea( 15, 30 );
add( tArea ); setVisible(true);
}
public static void reportEvent( String eventString )
{
tArea.appendText( eventString + "\r" );
}
需要寫一個簡單的
HTML 把這 Applet
叫起來
<HTML><body>
<applet
code=eventHandler.class
Width=555
Height=333>
</applet>
}
交通大學資訊工程學系 蔡文能
5-第42頁
Java
More-GUI
AWT 1.1. Event Model
In the 1.1 AWT event model, events are generated by event
sources.
 One or more listeners can register to be notified about events of a
particular kind from a particular source.
In every program that has an event handler, you'll see three bits of
code:
 Code that registers an instance of a listener.
someComponent.addActionListener(instanceOfMyClass);
 Declare the event handler implementing a listener interface.
public class MyClass implements ActionListener {
 The implementation of the methods in the listener interface.
public void actionPerformed(ActionEvent e) {
...//code that reacts to the action...
}
交通大學資訊工程學系 蔡文能
5-第43頁
Java
More-GUI
Example
public class MultiListener ... implements ActionListener {
//...
//where initialization occurs:
button1.addActionListener(this);
button2.addActionListener(this);
button2.addActionListener(new
Eavesdropper(bottomTextArea));
public void actionPerformed(ActionEvent e) {
topTextArea.append(e.getActionCommand() + "\n");
}
}
class Eavesdropper implements ActionListener {
...
public void actionPerformed(ActionEvent e) {
myTextArea.append(e.getActionCommand() + "\n");
}
}
交通大學資訊工程學系 蔡文能
5-第44頁
Java
More-GUI
Events
The Java standard class library contains several classes
that represent typical events
Certain objects, such as an applet or a graphical button,
generate (fire) an event when it occurs
Other objects, called listeners, respond to events
We can write listener objects to do whatever we want when
an event occurs
交通大學資訊工程學系 蔡文能
5-第45頁
Java
More-GUI
Listener Interfaces
We can create a listener object by writing a class that implements a
particular Listener interface
The Java standard class library contains several interfaces that
correspond to particular event categories
For example, the MouseListener interface contains methods that
correspond to mouse events
After creating the listener, we add the listener to the component that
might generate the event to set up a formal relationship between the
generator and listener
交通大學資訊工程學系 蔡文能
5-第46頁
Java
More-GUI
ActionListener
交通大學資訊工程學系 蔡文能
5-第47頁
Java
More-GUI
Problem of Using Listeners
AWT Listeners usually have several methods.
 If a class implements the listener, need to write all the methods.
//An example with cluttered but valid code.
public class MyClass implements MouseListener {
//...
someObject.addMouseListener(this);
//...
/* Empty method definitions are required. */
public void mousePressed(MouseEvent e) { }
public void mouseReleased(MouseEvent e) { }
public void mouseEntered(MouseEvent e) { }
public void mouseExited(MouseEvent e) { }
public void mouseClicked(MouseEvent e) {
//..Event handler implementation goes here...
}
}
交通大學資訊工程學系 蔡文能
5-第48頁
Java
More-GUI
Solution: Using Adaptors
Use Adaptor instead of Listener to simplify design.
/*
* An example of extending an adapter class instead of
* directly implementing a listener interface.
*/
public class MyClass extends MouseAdapter {
//...
someObject.addMouseListener(this);
//...
public void mouseClicked(MouseEvent e) {
//...Event handler implementation goes here...
}
}
交通大學資訊工程學系 蔡文能
5-第49頁
Java
交通大學資訊工程學系 蔡文能
More-GUI
5-第50頁
Java
More-GUI
Using Inner Classes
Use inner classes with adaptors to simplify design.
//An example of using an anonymous inner class.
public class MyClass extends Applet {
//...
someObject.addMouseListener( new MouseAdapter()
{
public void mouseClicked(MouseEvent e)
{
//..Event handler implementation
// .. goes here...
} // with Adapter, only methos we want
} );
//...
}
}
交通大學資訊工程學系 蔡文能
5-第51頁
Java
More-GUI
Listener interfaces
ActionListener
 actionPerformed(ActionEvent e)
AdjustmentListener
 adjustmentValueChanged(AdjustmentEvent e)
AncestorListener
 ancestorAdded(AncestorEvent event)
 ancestorMoved(AncestorEvent event)
 ancestorRemoved(AncestorEvent event)
AWTEventListener
 eventDispatched(AWTEvent event)
BeanContextMembershipListener
 childrenAdded(BeanContextMembershipEvent bcme)
 childrenRemoved(BeanContextMembershipEvent bcme)
...
交通大學資訊工程學系 蔡文能
5-第52頁
Java
More-GUI
Standard AWT Events (1/2)
Handling standard AWT events
Listener Interface
ActionListener
AdjustmentListener
ComponentListener
Adapter Class
none
none
ComponentAdapter
ContainerListener
ContainerAdapter
FocusListener
FocusAdapter
ItemListener
KeyListener
none
KeyAdapter
交通大學資訊工程學系 蔡文能
Methods
actionPerformed
adjustmentValueChanged
componentHidden
componentMoved
componentResized
componentShown
componentAdded
componentRemoved
focusGained
focusLost
itemStateChanged
keyPressed
keyReleased
keyTyped
5-第53頁
Java
More-GUI
Standard AWT Events (2/2)
Listener Interface
MouseListener
MouseMotionListener
TextListener
WindowListener
交通大學資訊工程學系 蔡文能
Adapter Class
MouseAdapter
Methods
mouseClicked
mouseEntered
mouseExited
mousePressed
mouseReleased
MouseMotionAdapter mouseDragged
mouseMoved
None
textValueChanged
WindowAdapter
windowActivated
windowClosed
windowClosing
windowDeactivated
windowDeiconified
windowIconified
windowOpened
5-第54頁
Java
More-GUI
Events Generated by AWT Components
The AWT events can be divided into two groups:
component-level (low-level) events and semantic events.
Component-Level Events
 Represent user or window-system actions such as a mouse click or
a key press, …
 ComponentEvent, FocusEvent, InputEvent, KeyEvent,
MouseEvent, ContainerEvent, WindowEvent
Semantic Events
 Represent higher-level functions or meanings of events such as
double-clicking a text-line, …
 ActionEvent, AdjustmentEvent, ItemEvent, TextEvent
Please see our text book: chap 7 , ..
交通大學資訊工程學系 蔡文能
5-第55頁
Java
More-GUI
Action Listener
Writing an action listener
 The ActionListener interface contains a single method.
void actionPerformed(ActionEvent)
No corresponding adapter class since there is only one method.
 An action event occurs,
When the user clicks a button,
When doubleclicks a list item,
When chooses a menu item,
When presses return in a text field,
 An action event handling code example :
public class Beeper ... implements ActionListener {
//...
//where initialization occurs:
button.addActionListener(this);
//...
public void actionPerformed(ActionEvent e) {
//…Make a beep sound...
}
}
交通大學資訊工程學系 蔡文能
5-第56頁
Java
More-GUI
Action Events
The ActionEvent class
 String getActionCommand()
Returns the string associated with this action.
Default string is the text displayed in the component.
 int getModifiers()
Returns an integer representing the modifier keys the user was
pressing when the action event occurred.
For example, if the user shift-selects a menu item, then the
following expression is nonzero:
actionEvent.getModifiers() & ActionEvent.SHIFT_MASK
交通大學資訊工程學系 蔡文能
5-第57頁
Java
More-GUI
ActionEvent methods
交通大學資訊工程學系 蔡文能
5-第58頁
Java
More-GUI
Adjustment Listener
Adjustment events notify you of changes in the value of
components that implement the adjustable interface.
The only AWT class that implements adjustable is
scrollbar.
There are five kinds of adjustment events:
 Track
 Unit increment, unit decrement
 Block increment, block decrement
The AdjustmentListener interface contains a single
method.
 No corresponding adapter class.
void adjustmentValueChanged(AdjustmentEvent)
交通大學資訊工程學系 蔡文能
5-第59頁
Java
More-GUI
Adjustment Events
The AdjustmentEvent class defines the following
handy methods:
 Adjustable getAdjustable()
Returns the component that generated the event.
 int getAdjustmentType()
Returns the type of adjustment that occurred.
The returned value is one of the following
UNIT_INCREMENT, UNIT_DECREMENT,
BLOCK_INCREMENT, BLOCK_DECREMENT, TRACK.
 int getValue()
Returns the value of the component just after the adjustment
occurred.
交通大學資訊工程學系 蔡文能
5-第60頁
Java
More-GUI
Component Listener
One or more component events are generated by a component
object.
 After the component is hidden, made visible, moved, or resized.
The component hidden and component visible events occur only as the
result of calls to a component's setVisible method.
 For example, a window might be miniaturized into an icon (iconified),
without a component hidden event being generated.
Component Listener Methods




void
void
void
void
componentHidden(ComponentEvent)
componentMoved(ComponentEvent)
componentResized(ComponentEvent)
componentShown(ComponentEvent)
交通大學資訊工程學系 蔡文能
5-第61頁
Java
More-GUI
Container Listener
Methods
 Void componentAdded(ContainerEvent)
 Void componentRemoved(ContainerEvent)
The ContainerEvent class defines two useful
methods:
 Component getChild()
 Container getContainer()
交通大學資訊工程學系 蔡文能
5-第62頁
Java
More-GUI
Focus Listener
Writing a focus listener
 Focus events are generated whenever a component gains or loses
the keyboard focus -- the ability to receive keyboard events.
 At most one component in the window system can have the
keyboard focus.
 You can request that a component get the focus by invoking the
Component`s requestFocus method.
 The FocusListener interface and its corresponding adapter
class, FocusAdapter, contain two methods:
void focusGained(FocusEvent)
void focusLost(FocusEvent)
交通大學資訊工程學系 蔡文能
5-第63頁
Java
More-GUI
Item Listener
Writing an Item Listener
 Item events are generated by components that implement the
ItemSelectable interface.
 The 1.1 AWT components that generate item events are
checkboxes, checkbox menu items, choices, and
lists.
 The ItemListener interface has just one method, so it has no
corresponding adapter class.
void itemStateChanged(ItemEvent)
Called by the AWT just after a state change in the listenedto component.
交通大學資訊工程學系 蔡文能
5-第64頁
Java
More-GUI
Item Events
The ItemEvent class defines the following handy
methods:
 Object getItem()
Returns the component-specific object associated with the item
whose state changed. Often this is a String containing the
text on the selected item. For an item event generated by a
List, this is an Integer that specifies the index of the
selected item.
 ItemSelectable getItemSelectable()
Returns the component that generated the item event.
 int getStateChange()
Returns the new state of the item. The ItemEvent class
defines two states: SELECTED and DESELECTED.
交通大學資訊工程學系 蔡文能
5-第65頁
Java
More-GUI
Key Listener
Writing a key listener
 Key events tell you when the user types at the keyboard.
 Two basic kinds of key events:
Typing of a Unicode character -- key typed event.
Pressing or releasing of a key on the keyboard -- key pressed and key
released event.
 Three methods:
void keyTyped(KeyEvent)
void keyPressed(KeyEvent)
void keyReleased(KeyEvent)
交通大學資訊工程學系 蔡文能
5-第66頁
Java
More-GUI
Key Events
The KeyEvent class defines the following useful
methods:
 int getKeyChar()
void setKeyChar(char)
Get or set the Unicode character associated with this event.
 int getKeyCode()
void setKeyCode(int)
Get or set the key code associated with this event. For
example, VK_A specifies the key labeled A, and VK_ESCAPE
specifies the ESCAPE key.
 void setModifiers(int)
Sets the state of the modifier keys for this event.
交通大學資訊工程學系 蔡文能
5-第67頁
Java
More-GUI
Mouse Listener
Writing a mouse listener
 Mouse events tell you when the user uses the mouse (or similar input
device) to interact with a component.
 Methods:
Void
void
void
void
void
mouseClicked(MouseEvent)
mouseEntered(MouseEvent)
mouseExited(MouseEvent)
mousePressed(MouseEvent)
mouseReleased(MouseEvent)
Mouse Events:
int getClickCount()
int getX()
int getY()
Point getPoint()
boolean isPopupTrigger()
交通大學資訊工程學系 蔡文能
5-第68頁
Java
More-GUI
import java.applet.Applet;
import java.awt.*;
public class Dots extends Applet
{
private final int APPLET_WIDTH = 200;
private final int APPLET_HEIGHT = 100;
private final int RADIUS = 6;
private Point clickPoint = null;
public void init()
{
DotsMouseListener listener = new
DotsMouseListener(this);
addMouseListener(listener);
setBackground (Color.black);
setSize (APPLET_WIDTH, APPLET_HEIGHT);
}
交通大學資訊工程學系 蔡文能
5-第69頁
Java
More-GUI
public void paint (Graphics page){
page.setColor (Color.green);
if (clickPoint != null)
page.fillOval (clickPoint.x - RADIUS,
clickPoint.y - RADIUS,
RADIUS * 2, RADIUS * 2);
}
public void setPoint (Point point)
{
clickPoint = point;
}
}
交通大學資訊工程學系 蔡文能
5-第70頁
Java
Class implementing listener interface
More-GUI
import java.applet.Applet;
import java.awt.*;
import java.awt.event.*;
class DotsMouseListener implements MouseListener
{
private Dots applet;
public DotsMouseListener (Dots applet)
{
this.applet = applet;
}
public void mouseClicked (MouseEvent event)
{
Point clickPoint = event.getPoint();
applet.setPoint (clickPoint);
applet.repaint();
}
交通大學資訊工程學系 蔡文能
5-第71頁
Java
More-GUI
//-----------------------------------------------------// Provide empty definitions for unused event methods.
//-----------------------------------------------------public void mousePressed (MouseEvent event) {}
public void mouseReleased (MouseEvent event) {}
public void mouseEntered (MouseEvent event) {}
public void mouseExited (MouseEvent event) {}
}// end of DotsMouseListener
交通大學資訊工程學系 蔡文能
5-第72頁
Java
More-GUI
Input Events
 The MouseEvent class extends InputEvent, which extends
ComponentEvent.
 InputEvent provides the following useful methods:
int getWhen()
boolean isAltDown()
boolean isControlDown()
boolean isMetaDown()
boolean isShiftDown()
int getModifiers()
交通大學資訊工程學系 蔡文能
5-第73頁
Java
More-GUI
Mouse Motion Listener
Writing a mouse motion listener
 Mouse motion events tell you when the user uses the mouse (or a
similar input device) to move the onscreen cursor.
 Methods:
void mouseDragged(MouseEvent)
void mouseMoved(MouseEvent)
交通大學資訊工程學系 蔡文能
5-第74頁
Java
More-GUI
Text Listener
Writing a text listener
 Text events are generated after the text in a text component has
changed somehow.
 The TextListener interface has just one method, so it has no
corresponding adapter class.
Void textValueChanged(TextEvent)
 Called by the AWT just after the text in the listened-to
component changes.
交通大學資訊工程學系 蔡文能
5-第75頁
Java
More-GUI
Window Listener
Writing a window listener
 Window events are generated by a window just after the window
is opened, closed, iconified, deiconified, activated, or deactivated.
 Methods:
void
void
void
void
void
void
void
windowOpened(WindowEvent)
windowClosing(WindowEvent)
windowClosed(WindowEvent)
windowIconified(WindowEvent)
windowDeiconified(WindowEvent)
windowActivated(WindowEvent)
windowDeactivated(WindowEvent)
交通大學資訊工程學系 蔡文能
5-第76頁
Java
More-GUI
Take a Break
Take a Break
Take a Break
Take a Break
Take a Break
Take a Break
Take a Break
Take a Break
交通大學資訊工程學系 蔡文能
5-第77頁
Java
More-GUI
What Is Layout Managers?
An object that controls the size and position of components
in a container.
Panel : default -- FlowLayout
Window : default -- GridLayout
交通大學資訊工程學系 蔡文能
5-第78頁
Java
More-GUI
How to Use BorderLayout
Example:
setLayout(new BorderLayout());
add("North", new Button("North"));
add("South", new Button("South"));
add("East", new Button("East"));
add("West", new Button("West"));
add("Center", new Button("Center"));
交通大學資訊工程學系 蔡文能
5-第79頁
Java
More-GUI
• If you use the one-argument version of add(), or if
you specify an invalid first argument, your
component might not be visible.
• BorderLayout puts no gap between the
components by default.
• Specify gaps (in pixels) using the following
constructor:
– public BorderLayout(int horizontalGap,
int verticalGap)
交通大學資訊工程學系 蔡文能
5-第80頁
Java
More-GUI
How to Use FlowLayout
setLayout(new FlowLayout());
add(new
add(new
add(new
add(new
add(new
Button("Button 1"));
Button("2"));
Button("Button 3"));
Button("Long-Named Button 4"));
Button("Button 5"));
Three constructors:
 public FlowLayout()
 public FlowLayout(int alignment)
alignment value : FlowLayout.LEFT,
FlowLayout.CENTER, or FlowLayout.RIGHT
 public FlowLayout(int alignment, int
horizontalGap,
int verticalGap)
Default gap is 5 pixels.
交通大學資訊工程學系 蔡文能
5-第81頁
Java
More-GUI
How to Use CardLayout
public class CardWindow extends Frame implements ItemListener
{
Panel cards;
final static String BUTTONPANEL = "Panel with Buttons";
final static String TEXTPANEL = "Panel with TextField";
public CardWindow() {
setLayout(new BorderLayout());
//Put the Choice in a Panel to get a nicer look.
Panel cp = new Panel();
Choice c = new Choice();
c.addItem(BUTTONPANEL);
c.addItem(TEXTPANEL);
c.addItemListener(this);
cp.add(c);
add("North", cp);
交通大學資訊工程學系 蔡文能
5-第82頁
Java
cards = new Panel();
cards.setLayout(new CardLayout());
Panel p1 =
p1.add(new
p1.add(new
p1.add(new
More-GUI
new Panel();
Button("Button 1"));
Button("Button 2"));
Button("Button 3"));
Panel p2 = new Panel();
p2.add(new TextField("TextField", 20));
cards.add(BUTTONPANEL, p1);
cards.add(TEXTPANEL, p2);
add("Center", cards);
. . .
}
public void itemStateChanged(ItemEvent evt) {
CardLayout cl = (CardLayout)(cards.getLayout());
cl.show(cards, (String)evt.getItem());
}
交通大學資訊工程學系 蔡文能
5-第83頁
Java
More-GUI
How to Use GridLayout
//Construct a GridLayout with 2 columns and
// an unspecified number of rows.
setLayout(new GridLayout(0,2));
add(new
add(new
add(new
add(new
add(new
Button("Button 1"));
Button("2"));
Button("Button 3"));
Button("Long-Named Button 4"));
Button("Button 5"));
Two constructors:
 public GridLayout(int rows, int columns)
At least one of the rows and columns arguments must be non-zero.
 public GridLayout(int rows, int columns, int
horizontalGap, int verticalGap)
交通大學資訊工程學系 蔡文能
5-第84頁
Java
More-GUI
GridBag Layout
Layout controls using a rectangular grid
 controls can span multiple rows or columns
 use constraints
(0,0)
(1,0)
(2,0)
Spans 3 columns
Spans 2 columns
交通大學資訊工程學系 蔡文能
5-第85頁
Java
More-GUI
GridBag Layout Constraints
gridx, gridy = upper left
corner of control
(0,0)
(1,0)
(2,0)
Spans 3 columns
Spans 2 columns
gridwidth = columns to span
gridheight = rows to span
weightx = how much of extra
space goes to this column
weighty = how much of extra
space goes to this row
fill = (none, H, V)
anchor = {NW, N, NE, E…}
交通大學資訊工程學系 蔡文能
5-第86頁
Java
More-GUI
How to Use GridBagLayout
Using GridBagLayout
GridBagLayout gridbag = new GridBagLayout();
GridBagConstraints c = new GridBagConstraints();
setLayout(gridbag);
//For each component to be added to this container:
//...Create the component...
//...Set instance variables in the
GridBagConstraints //
instance...
gridbag.setConstraints(theComponent, c);
add(theComponent);
交通大學資訊工程學系 蔡文能
5-第87頁
Java
More-GUI
GridBagContraints again (1/2)
 gridx,gridy
•
Specify the row and column at the upper left of the component.
• GridBagConstraints.RELATIVE (default value)
 gridwidth,gridheight
Specify the number of columns (for gridwidth) or rows (for gridheight) of the
component. The default value is 1.
GridBagConstraints.REMAINDER
GridBagConstraints.RELATIVE
 fill
GridBagConstraints.NONE (the default)
GridBagConstraints.HORIZONTAL
GridBagConstraints.VERTICAL
GridBagConstraints.BOTH
 ipadx,ipady
Specifies the internal padding. The default value is zero.
交通大學資訊工程學系 蔡文能
5-第88頁
Java
More-GUI
GridBagContraints again (2/2)
 insets
Specifies the external padding of the component.
Default is no external padding.
 anchor
Valid values are
GridBagConstraints.CENTER (the default),
GridBagConstraints.NORTH,
GridBagConstraints.NORTHEAST,
GridBagConstraints.EAST,
GridBagConstraints.SOUTHEAST,
GridBagConstraints.SOUTH,
GridBagConstraints.SOUTHWEST,
GridBagConstraints.WEST, and
GridBagConstraints.NORTHWEST.
 weightx,weighty
Used to determine how to distribute space among columns (weightx) and
among rows (weighty).
交通大學資訊工程學系 蔡文能
5-第89頁
Java
More-GUI
GridBagLayout Example (1/2)
protected void makebutton(String name, GridBagLayout gridbag,
GridBagConstraints c) {
Button button = new Button(name);
gridbag.setConstraints(button, c);
add(button);
}
public GridBagWindow() {
GridBagLayout gridbag = new GridBagLayout();
GridBagConstraints c = new GridBagConstraints();
setLayout(gridbag);
c.fill = GridBagConstraints.BOTH;
c.weightx = 1.0;
makebutton("Button1", gridbag, c);
makebutton("Button2", gridbag, c);
makebutton("Button3", gridbag, c);
c.gridwidth = GridBagConstraints.REMAINDER; //end of row
makebutton("Button4", gridbag, c);
交通大學資訊工程學系 蔡文能
5-第90頁
Java
More-GUI
GridBagLayout Example (2/2)
c.weightx = 0.0; //reset to the default
makebutton("Button5", gridbag, c); //another row
c.gridwidth = GridBagConstraints.RELATIVE; //next to last in row
makebutton("Button6", gridbag, c);
c.gridwidth = GridBagConstraints.REMAINDER; //end of row
makebutton("Button7", gridbag, c);
c.gridwidth = 1; //reset to the default
c.gridheight = 2;
c.weighty = 1.0;
makebutton("Button8", gridbag, c);
c.weighty = 0.0; //reset to the default
c.gridwidth = GridBagConstraints.REMAINDER; //end of row
c.gridheight = 1; //reset to the default
makebutton("Button9", gridbag, c);
makebutton("Button10", gridbag, c);
}
交通大學資訊工程學系 蔡文能
5-第91頁
Java
More-GUI
fill = GridBagConstraints.NONE
weight = 0
交通大學資訊工程學系 蔡文能
5-第92頁
Java
More-GUI
General Rules for Using Layout Managers
How to Choose a Layout Manager
 Display a component in as much space as it can get
BorderLayout
 Put the space-hungry component in the center.
GridBagLayout
 Set the constraints for the component so that fill=GridBagConstraints.BOTH.
GridLayout
 All components will be the same size.
 Display a few components in a compact row at their natural size
Using a Panel and using the Panel's default FlowLayout manager.
 Display a few same-sized components in rows and/or columns
GridLayout
How to Create a Layout Manager and Associate It with a Container
aContainer.setLayout(new CardLayout());
交通大學資訊工程學系 蔡文能
5-第93頁
Java
More-GUI
Doing Without a Layout Manager
public class NoneWindow extends Frame {
private boolean laidOut = false;
private Button b1, b2, b3;
public NoneWindow() {
super();
setLayout(null);
b1 = new Button("one"); add(b1);
b2 = new Button("two"); add(b2);
b3 = new Button("three"); add(b3);
}
public void paint(Graphics g) {
if (!laidOut) {
Insets insets = insets();
b1.reshape(50 + insets.left, 5 + insets.top, 50, 20);
b2.reshape(70 + insets.left, 35 + insets.top, 50, 20);
b3.reshape(130 + insets.left, 15 + insets.top, 50, 30);
laidOut = true;
}
} . . .
}
交通大學資訊工程學系
蔡文能
5-第94頁
Java
More-GUI
Overview of AWT Graphics Support
The Graphics Object
 paint(Graphics g), update(Graphics g)
 Two basic kinds of drawing
Primitive graphics (such as lines, rectangles, and text)
Images
 Provides a drawing context
The current drawing area
The current drawing color
The Coordinate System
The Four Forms of the repaint() Method




public void repaint()
public void repaint(long time)
public void repaint(int x, int y, int width, int height)
public void repaint(long time, int x, int y, int width, int height)
交通大學資訊工程學系 蔡文能
5-第95頁
Java
More-GUI
Drawing Shapes
The Graphics class drawing the following kinds of shapes:







Lines (drawLine())
Rectangles, (drawRect(), fillRect(), and clearRect())
Raised or lowered rectangles (draw3DRect() and fill3DRect())
Round-edged rectangles (drawRoundRect() and fillRoundRect())
Ovals (drawOval() and fillOval())
Arcs (drawArc() and fillArc())
Polygons (drawPolygon() and fillPolygon())
交通大學資訊工程學系 蔡文能
5-第96頁
Java
More-GUI
Example: Simple Rectangle Drawing
//In FramedArea (a Panel subclass):
public Insets getInsets() {
return new Insets(4,4,5,5);
}
public void paint(Graphics g) {
Dimension d = getSize();
Color bg = getBackground();
g.setColor(bg);
g.draw3DRect(0, 0, d.width - 1, d.height - 1, true);
g.draw3DRect(3, 3, d.width - 7, d.height - 7, false);
}
交通大學資訊工程學系 蔡文能
5-第97頁
Java
More-GUI
Example (cont.)
class CoordinateArea extends Canvas {
Point point = null;
CoordinatesDemo controller;
public CoordinateArea(CoordinatesDemo controller) {
super();
this.controller = controller;
addMouseListener(new MouseAdapter() {
public void mousePressed(MouseEvent e) {
int x=e.getX();
int y=e.getY();
if(point==null) { point=new Point(x, y); }
else { point.x=x; point.y=y; }
repaint();
}
});
}
public void paint(Graphics g) {
if(point != null) {
controller.updateLabel(point);
g.fillRect(point.x - 1, point.y - 1, 2, 2);
}
}
}
交通大學資訊工程學系 蔡文能
5-第98頁
Java
More-GUI
Example: Selected Area
Using a Rectangle to Indicate a Selected Area
class SelectionArea extends Canvas {
Rectangle currentRect = null;
RectangleDemo controller;
public SelectionArea(RectangleDemo controller) {
super();
this.controller = controller;
MyListener myListener = new MyListener();
addMouseListener(myListener);
addMouseMotionListener(myListener);
}
交通大學資訊工程學系 蔡文能
5-第99頁
Java
More-GUI
public void paint(Graphics g) {
//update has already cleared the previous rectangle,
//so we don't need to here.
//If currentRect exists, paint a rectangle on top.
if (currentRect != null) {
Dimension d = getSize();
Rectangle box = getDrawableRect(currentRect, d);
controller.updateLabel(box);
//Draw the box outline.
g.drawRect(box.x, box.y, box.width - 1, box.height - 1);
}
}
Rectangle getDrawableRect(Rectangle originalRect,
Dimension drawingArea) {
. . .
//Make sure rectangle width and height are positive.
. . .
//The rectangle shouldn't extend past the drawing area.
. . .
}
交通大學資訊工程學系 蔡文能
5-第100頁
Java
More-GUI
class MyListener extends MouseAdapter
implements MouseMotionListener {
public void mousePressed(MouseEvent e) {
int x = e.getX();
int y = e.getY();
currentRect = new Rectangle(x, y, 0, 0);
repaint();
}
public void mouseReleased(MouseEvent e) {updateSize(e);}
public void mouseDragged(MouseEvent e) {updateSize(e);}
public void mouseMoved(MouseEvent e) {}
void updateSize(MouseEvent e) {
int x = e.getX();
int y = e.getY();
currentRect.setSize(x-currentRect.x, y-currentRect.y);
repaint();
}
}
交通大學資訊工程學系 蔡文能
5-第101頁
Java
More-GUI
Working With Text
Drawing Text
 Using text-oriented Component
Label, TextField, or TextArea
Example: label.setText("Hello World!");
 If a Component isn't appropriate
Using the Graphics drawBytes(), drawChars(), or drawString()
methods.
Example: g.drawString("Hello World!", x, y);

g.drawString("Hello World!", x, y);
x and y specify the position of the lower left corner of the text.
The y coordinate specifies the baseline of the text.
d
交通大學資訊工程學系 蔡文能
5-第102頁
Java
More-GUI
Font and FontMetrics
Getting Information about a Font: FontMetrics
FontMetrics pickFont(Graphics g, String longString, int xSpace) {
boolean fontFits = false;
Font font = g.getFont();
FontMetrics fontMetrics = g.getFontMetrics();
int size = font.getSize();
String name = font.getName();
int style = font.getStyle();
while (!fontFits) {
if ( fontMetrics.getHeight()<=maxCharHeight &&
fontMetrics.stringWidth(longString)<=xSpace ) {
fontFits = true;
} else {
if (size <= minFontSize) {
fontFits = true;
}
else {
g.setFont(font = new Font(name, style, --size));
fontMetrics = g.getFontMetrics();
}
}
}
return fontMetrics;
}
交通大學資訊工程學系 蔡文能
5-第103頁
Java
More-GUI
FontMetrics






–
–
–
getAscent(), getMaxAscent()
getDescent(), getMaxDescent()
getHeight()
getWidth()
getMaxAdvance()
charWidth(int), charWidth(char)
charsWidth(char[], int, int)
stringWidth(String)
getWidths()
交通大學資訊工程學系 蔡文能
5-第104頁
Java
More-GUI
Using Images
Loading Images
 Using the getImage() Methods
It is easy to get an Image object for it if
 Image data is in GIF or JPEG format.
myImage = getImage(URL); // in an Applet subclass only
myImage = Toolkit.getDefaultToolkit().getImage(filenameOrURL);
Applets
 The Applet class supplies :
public Image getImage(URL url)
public Image getImage(URL url, String name)
 Example:
Image image1 = getImage(getCodeBase(), "imageFile.gif");
Image image2 = getImage(getDocumentBase(),"anImageFile.jpeg");
Image image3 = getImage(new
URL("http://java.sun.com/graphics/people.gif"));
Toolkit:
Toolkit toolkit = Toolkit.getDefaultToolkit();
Image image1 = toolkit.getImage("imageFile.gif");
Image image2 = toolkit.getImage(new
URL("http://java.sun.com/graphics/people.gif"));
交通大學資訊工程學系 蔡文能
5-第105頁
Java
More-GUI
MemoryImageSource
Creating Images with MemoryImageSource
The following code example calculates a 100x100 image representing a fade
from black to blue along the X axis and a fade from black to red along the Y
axis.
int w = 100; int h = 100;
int[] pix = new int[w * h];
int index = 0;
for (int y = 0; y < h; y++) {
int red = (y * 255) / (h - 1);
for (int x = 0; x < w; x++) {
int blue = (x * 255) / (w - 1);
pix[index++] = (255 << 24) | (red << 16) | blue;
}
}
Image img = createImage(
new MemoryImageSource(w, h, pix, 0, w));
交通大學資訊工程學系 蔡文能
5-第106頁
Java
More-GUI
Image Loading
Requesting and Tracking Image Loading:
MediaTracker and ImageObserver
 The MediaTracker class is sufficient for many
programs.
See the example improvingImageAnim
The ImageObserver interface lets you keep even closer
track of image loading than MediaTracker allows.
To use the ImageObserver interface, you implement the
ImageObserver imageUpdate() method.
交通大學資訊工程學系 蔡文能
5-第107頁
Java
More-GUI
imageUpdate in ImageObserver
Here is an example of imageUpdate() method:
public boolean imageUpdate(Image theimg, int infoflags,
int x, int y, int w, int h) {
if ((infoflags & (ERROR)) != 0) {
errored = true;
}
if ((infoflags & (WIDTH | HEIGHT)) != 0) {
positionImages();
}
boolean done = (
(infoflags & (ERROR | FRAMEBITS | ALLBITS)) != 0 );
// Repaint immediately if we are done,
// otherwise batch up repaint requests
// every 100 milliseconds
repaint(done ? 0 : 100);
//If done, no further updates required.
return !done;
}
交通大學資訊工程學系 蔡文能
5-第108頁
Java
More-GUI
Displaying Images
 Below is an applet that loads a single image and displays it twice,
using both code examples below :
g.drawImage(image, 0, 0, this);
g.drawImage(myImage, 90, 0, 300, 62, this);
交通大學資訊工程學系 蔡文能
5-第109頁
Java
More-GUI
Manipulating Images
The figure shows how image data is created:
An image filter is an ImageFilterobject
 Sitting between a producer and a consumer.
 Modifying the image data before the consumer gets it.
Image sourceImage;
...//Initialize sourceImage, using the Toolkit or Applet getImage() method.
ImageFilter filter = new SomeImageFilter();
ImageProducer producer = new FilteredImageSource(sourceImage.getSource(), filter);
Image resultImage = createImage(producer);
交通大學資訊工程學系 蔡文能
5-第110頁
Java
More-GUI
Example: Rotate an Image (1/2)
public class ImageRotator extends Applet {
. . .
RotatorCanvas rotator;
double radiansPerDegree = Math.PI / 180;
public void init() {
//Load the image.
Image image = getImage(getCodeBase(),
"../images/rocketship.gif");
...//Create the component that uses the image filter:
rotator = new RotatorCanvas(image);
. . .
add(rotator);
. . .
}
public boolean action(Event evt, Object arg) {
int degrees;
...//Get the number of degrees to rotate the image
//Convert to radians.
rotator.rotateImage((double)degrees * radiansPerDegree);
return true;
}
}
交通大學資訊工程學系 蔡文能
5-第111頁
Java
More-GUI
Example: Rotate an Image (2/2)
class RotatorCanvas extends Canvas {
Image sourceImage;
Image resultImage;
public RotatorCanvas(Image image) {
sourceImage = image;
resultImage = sourceImage;
}
public void rotateImage(double angle) {
ImageFilter filter = new RotateFilter(angle);
ImageProducer producer = new FilteredImageSource(
sourceImage.getSource(), filter);
resultImage = createImage(producer);
repaint();
}
public void paint(Graphics g) {
Dimension d = size();
int x = (d.width-resultImage.getWidth(this))/2;
int y = (d.height-resultImage.getHeight(this))/2;
g.drawImage(resultImage, x, y, this);
}
}
交通大學資訊工程學系 蔡文能
5-第112頁
Java
More-GUI
Another Suggestion
int [] thispixels = new thispixels[width*height];
PixelGrabber pg = new PixelGrabber(anImage, 0, 0,
width, height, thispixels, 0, width);
try {
pg.grabPixels();
} catch (InterruptedException e) {
System.err.println("waiting for pixels!");
return null;
}
Image destination = Elife.createImage(new
MemoryImageSource(width, height, thispixels, 0,
width));
交通大學資訊工程學系 蔡文能
5-第113頁
Java
More-GUI
Performing Animation
Creating the Animation Loop
 Every program that performs animation by drawing at regular
intervals needs an animation loop.
 This loop should be in its own thread and never be in the
paint() or update() method.
 Initializing Instance Variables
frameNumber represents the current frame. It's initialized to -1,
even though the first frame number is 0.
delay is the number of milliseconds between frames.
animatorThread is a Thread object, representing the thread in
which the animation loop runs.
frozen is a boolean value that's initialized to false. Set it to true
to indicate that the user has requested that the animation stop.
交通大學資訊工程學系 蔡文能
5-第114頁
Java
More-GUI
Example (1/2)
public class AnimatorClass
extends AComponentClass implements Runnable {
//In initialization code:
//From user-specified frames-per-second value,
//determine how long to delay between frames.
//In a method that does nothing but start the animation:
//Create and start the animating thread.
//In a method that does nothing but stop the animation:
//Stop the animating thread.
public boolean mouseDown(Event e, int x, int y) {
if ( /* animation is currently frozen */ ) {
//Call the method that starts the animation.
} else {
//Call the method that stops the animation.
}
}
交通大學資訊工程學系 蔡文能
5-第115頁
Java
More-GUI
Example (2/2)
public void run() {
// Lower this thread's priority so it can't
// interfere with other processing going on.
// Remember the starting time.
// Here's the animation loop:
while ( /* animation thread is still running */ ) {
// Advance the animation frame.
// Display it.
// Delay depending on how far we are behind.
}
}
public void paint(Graphics g) {
// Draw the current frame of animation.
}
}
交通大學資訊工程學系 蔡文能
5-第116頁
Java
More-GUI
Animation Loop
 Advances the frame number.
 Calls the repaint() method to request that the current frame of
animation be drawn.
 Sleeps for up to delay milliseconds.
while (/* animation thread is still running */) {
//Advance the animation frame.
frameNumber++;
//Display it.
repaint();
...//Delay depending on how far we are behind.
}
 Ensuring a Constant Frame Rate
long startTime = System.currentTimeMillis();
while (/* animation thread is still running */) {
...//Advance the animation frame and display it.
try {
startTime += delay;
Thread.sleep(Math.max(0,
startTime-System.currentTimeMillis()));
} catch (InterruptedException e) {
break;
}
}
交通大學資訊工程學系
蔡文能
5-第117頁
Java
More-GUI
 Behaving Politely
Allowing the user to stop (and restart) the animation, while the
applet or application is still visible.
 Implemented by overriding the mouseDown() method.
Suspending the animation whenever the applet or application is
known not to be visible.
 This is achieved by implementing the Applet stop() and
start() methods
交通大學資訊工程學系 蔡文能
5-第118頁
Java
More-GUI
Animating Graphics
An example applet that creates a moving a checkerboard
effect by painting alternate squares which are drawn by the
Graphics fillRect() method.
// Draw the rectangle if necessary.
if (fillSquare) {
g.fillRect(x, y, w, h);
fillSquare = false;
} else {
fillSquare = true;
}
交通大學資訊工程學系 蔡文能
5-第119頁
Java
More-GUI
Eliminating Flashing Problem
The flashing effect is the result of two facts:
 By default, the background of the animation is cleared
before the paint() method is called.
 The computation in the paint() method is complex
enough that it takes longer to compute and draw each
frame than the video screen's refresh rate.
Solution I 請參考
http://scv.bu.edu/Doc/Java/tutorial/ui/drawing/example/Update.java
交通大學資訊工程學系 蔡文能
5-第120頁
Java
More-GUI
Solution I
Eliminating Flashing: Overriding the update() Method
public void paint(Graphics g) {
update(g);
}
public void update(Graphics g) {
Color bg = getBackground();
Color fg = getForeground();
...//same as old paint() method
if (fillSquare) {
g.fillRect(x, y, w, h);
fillSquare = false;
} else {
g.setColor(bg);
g.fillRect(x, y, w, h);
g.setColor(fg);
fillSquare = true;
}
...//same as old paint() method
}
交通大學資訊工程學系 蔡文能
5-第121頁
Java
More-GUI
Solution II
Eliminating Flashing: Double Buffering
 Forcing the entire frame to be drawn at once.
First creating an undisplayed buffer -- backbuffer or offscreen
buffer.
Drawing to the buffer
Displaying the resulting image onscreen.
 To create an offscreen buffer with the AWT:
Creating an image of the proper size.
Getting a graphics context to manipulate the image.
請參考:
http://scv.bu.edu/Doc/Java/tutorial/ui/drawing/doubleBuffer.html
交通大學資訊工程學系 蔡文能
5-第122頁
Java
More-GUI
Example
//Where instance variables are declared:
Dimension offDimension;
Image offImage;
Graphics offGraphics;
. . .
public void update(Graphics g) {
. . .
//In the update() method, where d holds the size of
//the onscreen drawing area:
if( (offGraphics == null) ||
(d.width != offDimension.width) ||
(d.height != offDimension.height) ) {
offDimension = d;
offImage = createImage(d.width, d.height);
offGraphics = offImage.getGraphics();
}
//Erase the previous image.
offGraphics.setColor(getBackground());
offGraphics.fillRect(0, 0, d.width, d.height);
offGraphics.setColor(Color.black);
交通大學資訊工程學系 蔡文能
5-第123頁
Java
More-GUI
Animation: Displaying a Sequence of Images
Below are the ten images this applet uses.
交通大學資訊工程學系 蔡文能
5-第124頁
Java
More-GUI
Sample Code
. . .//Where instance variables are declared:
Image duke[10];
. . .//In the init() method:
for (int i = 1; i <= 10; i++) {
images[i-1] = getImage(getCodeBase(),
"../../../images/duke/T"+i+".gif");
}
. . .//In the update() method,
//instead of calling drawFrame():
offGraphics.drawImage(images[frameNumber % 10], 0, 0, this);
Problem: delay for each loading in drawImage().
Solution: Use MediaTracker to improve the performance
交通大學資訊工程學系 蔡文能
5-第125頁
Java
More-GUI
MediaTracker
Using MediaTracker to Download Images and Delay
Image Display
 To request a group of images be preloaded asynchronously, you
can use checkID(true) and checkAll(true).
 To load data synchronously (waiting for the data to arrive), use the
waitForID() and waitForAll() methods.
請參考 Java tutorial 裡的範例
交通大學資訊工程學系 蔡文能
improvingImageAnim
5-第126頁
Java
More-GUI
Speeding Up Image Loading
Loading images using URLs (as applets usually do) usually takes a
long time.
 Most of the time is taken up by initiating HTTP connections.
The key to avoiding this performance hit is to combine the images in a
single file.
 One simple way to combine images in a single file is to create an
image strip.
交通大學資訊工程學系 蔡文能
5-第127頁
Java
More-GUI
Image Clipping
To draw an image from the strip
 First set the clipping area to the size of one image.
 Then you draw the image strip, shifted to the left (if necessary) so
that only the image you want appears within the clipping area.
//imageStrip is the Image object representing the image strip.
//imageWidth is the size of an individual image in the strip.
//imageNumber is the number (from 0 to numImages)
// of the image to draw.
int stripWidth = imageStrip.getWidth(this);
int stripHeight = imageStrip.getHeight(this);
int imageWidth = stripWidth / numImages;
g.clipRect(0, 0, imageWidth, stripHeight);
g.drawImage(imageStrip, -imageNumber*imageWidth, 0, this);
交通大學資訊工程學系 蔡文能
5-第128頁
Java
Swing Library again
More-GUI
http://java.sun.com/docs/books/tutorial/uiswing/TOC.html#start
交通大學資訊工程學系 蔡文能
5-第129頁
Java
http://java.sun.com/docs/books/tutorial/
交通大學資訊工程學系 蔡文能
More-GUI
5-第130頁
Java
Swing Library
More-GUI
http://java.sun.com/docs/books/tutorial/uiswing/TOC.html#start
交通大學資訊工程學系 蔡文能
5-第131頁
Java
交通大學資訊工程學系 蔡文能
More-GUI
5-第132頁
Java
More-GUI
JFC/Swing GUI Components (1/6)
Top-Level Containers
Applet
交通大學資訊工程學系 蔡文能
Dialog
Frame
5-第133頁
Java
More-GUI
JFC/Swing GUI Components (2/6)
General-Purpose Containers
Tabbed Pane
Split Pane
Scroll Pane
Toolbar
交通大學資訊工程學系 蔡文能
Panel
5-第134頁
Java
More-GUI
JFC/Swing GUI Components (3/6)
Special-Purpose Containers
Internal Frame
Layered Pane
Root Pane
交通大學資訊工程學系 蔡文能
5-第135頁
Java
More-GUI
JFC/Swing GUI Components (4/6)
Basic Controls
Buttons
Menu
交通大學資訊工程學系 蔡文能
Combobox
Slider
List
Text Fields
5-第136頁
Java
More-GUI
JFC/Swing GUI Components (5/6)
Uneditable Information Displays
Progress Bar
Label
Tooltip
交通大學資訊工程學系 蔡文能
5-第137頁
Java
More-GUI
JFC/Swing GUI Components (6/6)
Editable Displays of Formatted Information
Table
Color Chooser
交通大學資訊工程學系 蔡文能
Text
Tree
File Chooser
5-第138頁
Java
More-GUI
Introduction to Java Programming
謝謝捧場
http://www.csie.nctu.edu.tw/~tsaiwn/java/
蔡文能
交通大學資訊工程學系 蔡文能
5-第139頁
Java
交通大學資訊工程學系 蔡文能
More-GUI
5-第140頁