Provides a set of "lightweight" (all-Java language) components that, to the maximum degree possible, work the same on all platforms. For a programmer's guide to using these components, see Creating a GUI with JFC/Swing, a trail in The Java Tutorial. For other resources, see Related Documentation.
Typical Swing applications do processing in response to an event generated
from a user gesture. For example, clicking on a JButton notifies all
ActionListeners added to the JButton. As all events generated
from a user gesture are dispatched on the event dispatching thread, most
developers are not impacted by the restriction.
Where the impact lies, however, is in constructing and showing a Swing
application. Calls to an application's main method, or methods in
Applet, are not invoked on the event dispatching thread. As such,
care must be taken to transfer control to the event dispatching thread when
constructing and showing an application or applet. The preferred way to
transfer control and begin working with Swing is to use invokeLater.
The invokeLater method schedules a Runnable to be processed
on the event dispatching thread. The following two examples work equally well
for transferring control and starting up a Swing application:
import javax.swing.SwingUtilities;
public class MyApp implements Runnable {
public void run() {
// Invoked on the event dispatching thread.
// Construct and show GUI.
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new MyApp());
}
}
Or:
import javax.swing.SwingUtilities;
public class MyApp {
MyApp(String[] args) {
// Invoked on the event dispatching thread.
// Do any initialization here.
}
public void show() {
// Show the UI.
}
public static void main(final String[] args) {
// Schedule a job for the event-dispatching thread:
// creating and showing this application's GUI.
SwingUtilities.invokeLater(new Runnable() {
public void run() {
new MyApp(args).show();
}
});
}
}
This restriction also applies to models attached to Swing components. For
example, if a TableModel is attached to a JTable, the
TableModel should only be modified on the event dispatching thread.
If you modify the model on a separate thread you run the risk of exceptions
and possible display corruption.
Although it is generally safe to make updates to the UI immediately,
when executing on the event dispatch thread, there is an exception :
if a model listener tries to further change the UI before the UI has been
updated to reflect a pending change then the UI may render incorrectly.
This can happen if an application installed listener needs to update the UI
in response to an event which will cause a change in the model structure.
It is important to first allow component installed listeners to process this
change, since there is no guarantee of the order in which listeners may be
called.
The solution is for the application listener to make the change using
SwingUtilities.invokeLater so that any changes to UI rendering will
be done post processing all the model listeners installed by the component.
As all events are delivered on the event dispatching thread, care must be
taken in event processing. In particular, a long running task, such as
network io or computational intensive processing, executed on the event
dispatching thread blocks the event dispatching thread from dispatching any
other events. While the event dispatching thread is blocked the application
is completely unresponsive to user input. Refer to
javax.swing.SwingWorker for the preferred way to do such processing
when working with Swing.
More information on this topic can be found in the Swing tutorial, in particular the section on Concurrency in Swing.