< Day Day Up > |
This section explains how to implement three kinds of window- related event handlers: WindowListener , WindowFocusListener , and WindowStateListener . All three handle WindowEvent s. The methods in all three event handlers are implemented by the abstract WindowAdapter class. When the appropriate listener has been registered on a window (such as a frame or dialog), window events are fired just after the window is opened, closed, iconified , deiconified, activated, deactivated, maximized, or restored to normal, or gains or loses the focus. Opening a window means showing it for the first time; closing it means removing the window from the screen. Iconifying it means substituting a small icon on the desktop for the window; deiconifying means the opposite . A window is activated if it is a frame or a dialog that either is the focused window, or owns the focused window; deactivation is the opposite. Maximizing the window means increasing its size to the maximum allowable , in either the vertical direction, the horizontal direction, or both. The WindowListener interface defines methods to handle most window events, such as the events for opening and closing the window, activation and deactivation of the window, and iconification and deiconification of the window. The other two window listener interfaces, WindowFocusListener and WindowState- Listener , were introduced in release 1.4. WindowFocusListener contains methods to detect when the window has gained or lost the focus. WindowStateListener has a single method to detect a change to the state of the window, such as when the window is iconified, deiconified, maximized, or restored to normal. Version Note: Prior to release 1.4, focus-gained and focus-lost events were inferred by using the WindowListener methods windowActivated and windowDeactivated . This approach did not work with windows that were not frames or dialogs, because such windows never received those events. To determine a window's iconification, the ComponentListener methods componentHidden and componentShown were used. As of release 1.4, the methods defined in WindowFocusListener and WindowStateListener are preferred. While you can use the WindowListener methods to detect some window state, such as iconification, there are a couple reasons why a WindowStateListener might be preferable: It has only one method for you to implement, and it provides support for maximization. Note: Not all window managers support all window states. The 1.4 java.awt.Toolkit method isFrameStateSupported(int) [37] can be used to determine whether a particular window state is supported by a particular window manager. The WindowEventDemo example, described later in this section, shows how this method can be used.
A common use of window listeners is implementing custom window-closing behavior. For example, you might use a window listener to save data before closing the window, or to exit the program when the last window closes . You don't necessarily need to implement a window listener to specify what a window should do when the user closes it. By default, when the user closes a window the window becomes invisible. You can specify different behaviordisposing of the window, for exampleusing the JFrame or JDialog setDefaultCloseOperation method. If you decide to implement a window-closing handler, then you might want to use setDefaultCloseOperation(WindowConstants.DO_NOTHING_ON_CLOSE) to specify that your window listener takes care of all window-closing duties . See How to Make Frames (Main Windows) (page 236) in Chapter 7 for details on how to use setDefaultCloseOperation . Version Note: As of release 1.4, when the last displayable window within the Java Virtual Machine (VM) is disposed of, the VM may terminate. In previous releases, such as 1.3, the VM remained running even if all windows were disposed of. Note, however, that there can be a delay before the program exits automatically, and that under some circumstances the program might keep running. It is quicker and safer to explicitly exit the program using System. exit(int) . For more information, see "AWT Threading Issues" online at: http://java.sun.com/j2se/1.4.2/docs/api/java/awt/doc-files/AWTThreadIssues.html. Another common use of window listeners is to stop threads and release resources when a window is iconified, and to start up again when the window is deiconified. This way, you can avoid unnecessarily using the processor or other resources. For example, when a window that contains animation is iconified, it should stop its animation thread and free any large buffers. When the window is deiconified, it can start the thread again and recreate the buffers. Figure 15 demonstrates window events. A noneditable text area reports all window events that are fired by its window. This demo implements all methods in the WindowListener , WindowFocusListener , and WindowStateListener interfaces. You can find the demo's code in WindowEventDemo.java . Figure 15. The WindowEventDemo application.
Try This:
Here's the demo's window event-handling code: public class WindowEventDemo ... implements WindowListener, WindowFocusListener, WindowStateListener { static JFrame frame; JTextArea display; public WindowEventDemo() { ... frame.addWindowListener(this); frame.addWindowFocusListener(this); frame.addWindowStateListener(this); checkWM(); } //Some window managers don't support all window states. //For example, dtwm doesn't support true maximization, //but mimics it by resizing the window to be the size //of the screen. In this case the window does not fire //the MAXIMIZED_ constants on the window's state listener. //Microsoft Windows supports MAXIMIZED_BOTH, but not //MAXIMIZED_VERT or MAXIMIZED_HORIZ. public void checkWM() { Toolkit tk = frame.getToolkit(); if (!(tk.isFrameStateSupported(Frame.ICONIFIED))) { displayMessage( "Your window manager doesn't support ICONIFIED."); } if (!(tk.isFrameStateSupported(Frame.MAXIMIZED_VERT))) { displayMessage( "Your window manager doesn't support MAXIMIZED_VERT."); } if (!(tk.isFrameStateSupported(Frame.MAXIMIZED_HORIZ))) { displayMessage( "Your window manager doesn't support MAXIMIZED_HORIZ."); } if (!(tk.isFrameStateSupported(Frame.MAXIMIZED_BOTH))) { displayMessage( "Your window manager doesn't support MAXIMIZED_BOTH."); } else { displayMessage( "Your window manager supports MAXIMIZED_BOTH."); } } public void windowClosing(WindowEvent e) { displayMessage("WindowListener method called: windowClosing."); //A pause so user can see the message before //the window actually closes. ActionListener task = new ActionListener() { boolean alreadyDisposed = false; public void actionPerformed(ActionEvent e) { if (!alreadyDisposed) { alreadyDisposed = true; frame.dispose(); } else { //make sure the program exits System.exit(0); } } }; Timer timer = new Timer(500, task); //fire every half second timer.setInitialDelay(2000); //first delay 2 seconds timer.start(); } public void windowClosed(WindowEvent e) { //This will only be seen on standard output. displayMessage("WindowListener method called: windowClosed."); } public void windowOpened(WindowEvent e) { displayMessage("WindowListener method called: windowOpened."); } public void windowIconified(WindowEvent e) { displayMessage("WindowListener method called: windowIconified."); } public void windowDeiconified(WindowEvent e) { displayMessage("WindowListener method called: " + "windowDeiconified."); } public void windowActivated(WindowEvent e) { displayMessage("WindowListener method called: windowActivated."); } public void windowDeactivated(WindowEvent e) { displayMessage("WindowListener method called: " + "windowDeactivated."); } public void windowGainedFocus(WindowEvent e) { displayMessage("WindowFocusListener method called: " + "windowGainedFocus."); } public void windowLostFocus(WindowEvent e) { displayMessage("WindowFocusListener method called: " + "windowLostFocus."); } public void windowStateChanged(WindowEvent e) { displayStateMessage( "WindowStateListener method called: windowStateChanged.", e); } void displayMessage(String msg) { display.append(msg + newline); System.out.println(msg); } void displayStateMessage(String prefix, WindowEvent e) { int state = e.getNewState(); int oldState = e.getOldState(); String msg = prefix + newline + space + "New state: " + convertStateToString(state) + newline + space + "Old state: " + convertStateToString(oldState); display.append(msg + newline); System.out.println(msg); } String convertStateToString(int state) { if (state == Frame.NORMAL) { return "NORMAL"; } if ((state & Frame.ICONIFIED) != 0) { return "ICONIFIED"; } //MAXIMIZED_BOTH is a concatenation of two bits, so //we need to test for an exact match. if ((state & Frame.MAXIMIZED_BOTH) == Frame.MAXIMIZED_BOTH) { return "MAXIMIZED_BOTH"; } if ((state & Frame.MAXIMIZED_VERT) != 0) { return "MAXIMIZED_VERT"; } if ((state & Frame.MAXIMIZED_HORIZ) != 0) { return "MAXIMIZED_HORIZ"; } return "UNKNOWN"; } //Where the GUI is initialized: ... //Create and set up the window. frame = new JFrame("WindowEventDemo"); frame.setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOSE); ... } The Window Listener APITables 44 through 47 list the methods in the three window listener interfaces and the methods in the WindowEvent class. The methods from all three interfaces are available through the WindowAdapter class. Also refer to the API documentation for these interfaces and class online at:
Table 44. The WindowListener Interface
Table 45. The WindowFocusListener Interface (This interface was introduced in release 1.4.)
Table 46. The WindowStateListener Interface (This interface was introduced in release 1.4.)
Table 47. The WindowEvent Class
Examples That Use Window ListenersThe following examples use window listeners.
|
< Day Day Up > |