|
17.2. The IBM SWT ToolkitThe Standard Widget Toolkit is a complete GUI library for Java, completely independent of Swing and AWT. It is implemented as a library of native methods, so it cannot be ported to any Java runtime unless that platform has the native part of the SWT library implemented for it. 17.2.1. Another GUI Toolkit. Why?The first question one should ask, perhaps, is why create an alternative GUI? Good question. The answer, according to the SWT FAQ,[3] primarily has to do with execution speed and look-and-feel similarity to native GUI applications on each platform.
If we may editorialize, we find neither reason particularly compelling, although the execution speed argument made some sense when the Eclipse project started. Swing is unlikely to win any performance awards, even though each version brings some improvements in speed.[4] Still, these reasons do not seem particularly compelling for such a large duplication of effort and functionality.
Whatever the reason, SWT exists. SWT works by providing a thin abstraction layer over native GUI features. It is a small GUI library. It is implemented using the Java Native Interface, so it requires that a native binary library be implemented for your platform. Fortunately, such implementations exist for all platforms Eclipse runs on. So if you can run Eclipse, you can write and run SWT applications. 17.2.2. Duplicated Effort. Why Cover It?The next logical question is, "If you think SWT is unnecessary with Swing already there, why cover it in your book?" Also a sensible question. The answer is that there is very little published literature on this library (a notable exception being Chapter 10 of The Java Developer's Guide to Eclipse by Shaver et al., from Addison-Wesley). Also, SWT provides the only fully functional GUI library that will work with the GNU Compiler for Java. As such, it is a major required component if you wish to write native compiled GUI applications on Linux systems. Of course, there is another reason. Anyone heavily into Linux is well aware of the political and philosophical debate about Free Software and Open Source. If the core values of Free Software are critical for you, you should be aware that the IBM Common Public License[5] under which Eclipse (and thus SWT) are published is a Free Software license. You get the source code, you may use it in your own products, and it imposes obligations similar to the GNU GPL,[6] but goes even further by requiring you to grant royalty-free licenses for any patents you hold in derivative works.
So you might choose SWT (or not) for political or philosophical reasons. Both authors still suggest Swing first because it is the official Java GUI library. When an employer wants to know if you can write a Java GUI application, he or she almost certainly means a Swing application. Philosophy is great, but it may not put the food on your table. You need to know that Swing is not Free Software (and neither is either of the major Java SDKs), and SWT is Free Software, but it is up to you to decide what best serves your interests.[7]
17.2.3. Portability: Better and WorseHow about portability? Well, it depends on what "portability" means to you. If portability means "looks and runs the same on all platforms," then Swing offers better portability. If portability means "runs on all platforms for which there is a Java runtime," then Swing offers better portability. If portability means "looks like a native application on all supported platforms," then SWT is your choice. Make your selection accordingly. Tip The bottom line: If you only learn one Java GUI, make it Swing. 17.2.4. The Rest of the ChapterThe rest of this chapter will be devoted to describing the basic classes of SWT by converting one of the application classes from the previous chapter from Swing to SWT. We will not attempt to explain the operating principles of GUIs. For an introduction to GUI programming, see the previous chapter on Swing. It introduces the concepts and programming principles for GUI programming in Java. SWT is functionally similar, although quite spartan, providing only basic windows, controls, and events. Eclipse also contains a family of higher level user interface classes, known collectively as JFace, that provide UI features such as dialogs, wizards, font handlers, and images. We will not cover JFace in this book. 17.2.5. SWT: Close to the MetalSWT breaks some of the Java contract. For example, you cannot rely on garbage collection to clean up SWT objects. Any SWT object you create with new must be explicitly destroyed with a call to the dispose() method. Why? Since SWT is implemented with native methods, the low-level implementation allocates native OS data structures and objects that must be explicitly freed. Since the Java garbage collector cannot be relied upon to collect objects at a certain time (or ever, for that matter), these allocations can result in memory leaks and address space conflicts. As we shall see, however, SWT is well designed to minimize the amount of this that you need to worry about. SWT is also close to the metal in the sense that it does not abstract the underlying message-based event system that drives both X Window and Microsoft Windows. If you have ever written an X Window or Microsoft Windows application in straight C (without a GUI framework library or class library), you have written a main() function that contains an event loop. SWT actually puts simple method calls around this core message queue event loop. We'll cover the details of this in the next section where we introduce the Display and Shell classes. 17.2.6. "Hello, world" SWT StyleSWT consists mainly of classes that represent controlssuch as buttons, text areas, scrollbars, and so onand layout managers which are much like layout managers in Swing. But there are two other classes: Display, which models the interface between your Java application and the underlying windowing system, and Shell, which effectively represents a single window. The application in Example 17.1 is a parallel to the simple Swing program in the last chapter (Example 16.1). This simple program, like its parallel in the Swing chapter, is deceptive. Sure, this is a lot of code to say "Hello, world" but it is because what we are setting up here is an event-driven program that must respond to any valid user input. 17.2.6.1 Setting Up to Run an SWT ApplicationOne advantage of Swing that we haven't pointed out up to now is that it is part of every Java runtime (well, not gcj; more on that later), so you have all the classes on your classpath without any special setup. Not so with SWT. The exact procedure for setting up to run an SWT application depends on what development environment you are using. There is an excellent set of directions for running an SWT application under Eclipse in the SWT FAQ.[8] No matter what your environment is, there is a basic series of steps:
Example 17.1. A simple SWT applicationimport org.eclipse.swt.*; import org.eclipse.swt.layout.*; import org.eclipse.swt.widgets.*; /** * @author mschwarz * * Sample SWT "Hello, world" application */ public class SWTHelloWorld { public static void main(String[] args) { Display disp = new Display(); Shell window = new Shell(disp); window.setLayout(new RowLayout()); Label label = new Label(window, SWT.NONE); label.setText("Hello, world."); window.setSize(320, 160); window.open(); while (!window.isDisposed()) { if (!disp.readAndDispatch()) { disp.sleep(); } } disp.dispose(); } } Let's go over these in a bit more detail. SWT was developed as a GUI library for the Eclipse project. It is distributed as part of Eclipse. There is no official standalone SWT package. The right way to obtain SWT is to download and (at least temporarily) install the Eclipse SDK. See Section 10.4 for details. If you have followed our sage advice and downloaded the GTK version of the Eclipse SDK, then you need to copy out the SWT JAR files. There are two files in the GTK version, and just one in the Motif version. The GTK version's files are swt.jar and swt-pi.jar. They are both in the eclipse/plugins/org.eclipse.swt.gtk_2.1.2/ws/gtk directory. You will need to have both of these JAR files on the classpath of any SWT application you are compiling or running. Remember that SWT is a JNI library. You must also have the native Linux shared libraries. These need to be made available to the Java native loader. The files you need are located in the eclipse/plugins/org.eclipse.swt.gtk_2.1.2/os/linux/x86 directory. The .so files there must be available to any running SWT application. There are a couple of ways to do this. First, as described in Section 5.7, you can set the LD_LIBRARY_PATH environment variable. You also can use the -D parameter for the runtime VM to set the java.library.path property. If you want to, you can copy these files out of the eclipse directory to some other location and then erase the eclipse directory with the lovable old standby, rm -rf eclipse. Oh, by the way, once you have compiled the sample code above and set your classpath and Java library path correctly, running the application produces the window shown in Figure 17.1. Figure 17.1. Running the SWT version of "Hello, world"
17.2.6.2 Anatomy of an SWT ApplicationBefore we launch into this discussion, we should point out that the Javadoc documentation for all SWT packages is available as part of the Eclipse Platform documentation.[9] You might want to use that resource along with this lightweight tutorial to fill in the gaps and shortcuts.
It should not be too surprising that there are similarities between SWT, AWT, and Swing. They all take different approaches to solving the same problem, namely how to control the complexity of a graphical event-driven application. Because the problem is the same, there can't help but be similarities between different solutions. By now you may have deduced that the Shell class is an analog to the JFrame class, and that SWT uses a system of layout managers not too different from Swing. If so, you are on the right track and well on your way to using SWT. If we had to summarize the difference in approaches between SWT and Swing, it would be that SWT tries to provide a small number of complex classes, and Swing tries to provide a large number of simpler classes. Obviously, this is a generalization, but everybody generalizes. Sorry. The Display is a class that provides the link to the underlying GUI system. Think of it as an abstraction of the interface to the windowing system. In almost all cases, an SWT application will have exactly one instance of Display. The Shell class represents a window. This class descends from a series of abstract parent classes, so if you look at the Javadoc for Shell and think it is simple, be sure to drill down into those parent classes! We'll discuss Shell quite a bit more as we go along. |
|