业精于勤,荒于嬉
全部博文(763)
分类: Java
2008-06-13 23:57:07
您可以通过本文了解对每个工具包的基本特性的介绍,以及使用每个工具包的优缺点。
简介
developerWorks 上另外一些作者已经展示了如何在 Swing 和 SWT 之间很好地进行迁移(参见 参考资料)。本文的目标是帮助您在开始开发项目之前确定选择使用哪个 GUI 工具包。
但是首先我们要弄清一个问题:为什么会有多个 Java™ GUI 工具包呢?最好的答案是,一个工具包并不能满足所有的要求,最近也不会开发一个可以满足所有要求的 GUI 工具包。每个工具包都有各自的优缺点,这样就可以根据自己的需求和目标用户来选择适当的工具包。
下面就让我们来学习有关这些工具包的知识。
AWT 概述
Abstract Windows Toolkit(AWT)是最原始的 Java GUI 工具包。AWT 的主要优点是,它在 Java 技术的每个版本上都成为了一种标准配置,包括早期的 Web 浏览器中的 Java 实现;另外它也非常稳定。这意味着我们不需要单独安装这个工具包,在任何一个 Java 运行环境中都可以使用它,这一点正是我们所希望的特性。
AWT 是一个非常简单的具有有限 GUI 组件、布局管理器和事件的工具包(参见 清单 1、清单 2 和 清单 3)。这是因为 Sun 公司决定为 AWT 使用一种最小公分母(LCD)的方法。因此它只会使用为所有 Java 主机环境定义的 GUI 组件。最终的结果非常不幸,有些经常使用的组件,例如表、树、进度条等,都不支持。对于需要更多组件类型的应用程序来说,我们需要从头开始创建这些组件。这是一个很大的负担。
清单 1. 基本的 AWT Class 树(全部在 java.awt 包中, “*” 表示抽象)
Object
CheckboxGroup
*Component
Button
Canvas
CheckBox
Choice
Container
Panel
Applet
ScrollPane
Window
Dialog
Frame
Label
List
TextComponent
TextArea
TextField
MenuComponent
MenuItem
CheckboxMenuItem
Menu
PopupMenu
注意:另外几个包中还有其他一些 AWT 组件,但是这是基本的组件集。
清单 2. AWT 提供了下面的布局管理器(全部在 java.awt 包中,“*” 表示接口)
*LayoutManager
FlowLayout
GridLayout
*LayoutManager2
BorderLayout
CardLayout
GridBagLayout
注意:另外几个包中还有一些 AWT 布局管理器,很多都是为它们进行布局的容器专门定制的,但是这是基本的布局管理器集。
清单 3. AWT 提供了以下事件(大部分在 java.awt.events 包中)
Object
EventObject
AWTEvent
ActionEvent
AdjustmentEvent
ComponentEvent
ContainerEvent
FocusEvent
InputEvent
KeyEvent
MouseEvent
MouseWheelEvent
PaintEvent
WindowEvent
HierarchyEvent
InputMethodEvent
InvocationEvent
ItemEvent TextEvent
注意:其他几个包中还有另外一些 AWT 事件,但是这是基本的事件集。这些是从更通用的事件生成的具体事件。
通常对于 AWT 来说(也适用于 Swing 和 SWT),每个事件类型都有一个相关的 XxxListener 接口(XxxAdapter 的实现可能为空),其中 Xxx 是去掉 Event 后缀的事件名(例如,KeyEvent 事件的接口是 KeyListener),用来把事件传递给处理程序。应用程序会为自己感兴趣处理的事件的事件源(GUI 组件或部件)进行注册。有时监听接口要处理多个事件。
AWT 的一个很好的特性是它通常可以对 GUI 组件自动进行销毁。这意味着您几乎不需要对组件进行销毁。一个例外是高级组件,例如对话框和框架。如果您创建了耗费大量主机资源的资源,就需要手动对其进行销毁。
AWT 组件是 “线程安全的(thread-safe)”,这意味着我们不需要关心在应用程序中是哪一个线程对 GUI 进行了更新。这个特性可以减少很多 GUI 更新的问题,不过使 AWT GUI 运行的速度更慢了。
AWT 让我们可以以自顶向下(top-down) 或自底向上(bottom-up) 或以任意组合顺序来构建 GUI。自顶向下的意思是在创建子组件之前首先创建容器组件;自底向上的意思是在创建容器(或父)组件之前创建子组件。在后一种情况中,组件的存在并不依赖于父容器,其父容器可以随时改变。
通常来说,AWT GUI 都是不可访问的。系统并没有为 AWT 程序员提供 API 来指定可访问性信息。可访问性(accessibility)处理的是残疾人可以怎样使用应用程序的问题。一个应用程序要想有很好的可访问性,必须与运行平台一起,让残疾人可以通过使用适当的辅助技术(提供其他用户接口的工具)来使用这些应用程序。很多政府和企业都有一些强制要求应用程序为实现可访问性而采用的标准。
Sun 希望 Java 语言能够成为一种 “编写一次就可以随处运行(write once, run everywhere,即 WORE)” 的环境。这意味着可以在一台机器上开发和测试 Java 代码(例如在 Windows® 上),然后不经测试就可以在另外一个 Java 主机上运行同样的 Java 代码。对于大部分情况来说,Java 技术都可以成功实现这种功能,但是 AWT 却是一个弱点。由于 AWT 要依赖于主机 GUI 的对等体(peer)控件(其中每个 AWT 组件都有一个并行的主机控件或者对等体)来实现这个 GUI,这个 GUI 的外观和行为(这一点更重要)在不同的主机上会有所不同。这会导致出现 “编写一次随处测试(write once, test everywhere,即 WOTE)” 的情况,这样就远远不能满足我们的要求了。
AWT 提供了一个丰富的图形环境,尤其是在 Java V1.2 及其以后版本中更是如此。通过 Graphics2D 对象和 Java2D、Java3D 服务,我们可以创建很多功能强大的图形应用程序,例如画图和制表包;结合使用 JavaSound,我们还可以创建非常有竞争力的交互式游戏。
Swing 概述
Java Swing 是 Java Foundation Classes(JFC)的一部分,它是试图解决 AWT 缺点的一个尝试。在 Swing 中,Sun 开发了一个经过仔细设计的、灵活而强大的 GUI 工具包。不幸的是,这意味着我们又要花一些时间来学习 Swing 了,对于常见的情况来说,Swing 有些太复杂了。
Swing 是在 AWT 组件基础上构建的。所有 Swing 组件实际上也是 AWT 的一部分。Swing 使用了 AWT 的事件模型和支持类,例如 Colors、Images 和 Graphics。Swing 组件、布局管理器以及事件总结如下(参见 清单 4、清单 5 和 清单 6)。正如您可以看到的一样,这些组件集比 AWT 提供的组件集更为广泛,与 SWT 组件集相比也毫不逊色。
清单 4. 基本的 Swing Class 树(全部在 javax.swing 包或其子包中,“*” 表示抽象类)
Object *Component Container *JComponent *AbstractButton JButton JMenuItem JCheckBonMenuItem JMenu JRadioButonMenuItem *JToggleButton JCheckBox JRadioButton Box Filler JColorChooser JComboBox JDesktopIcon JFileChooser JInternalFrame JLabel JLayeredPane JDesktopPane JList JMenuBar JOptionPane JPanel JPopupMenu JProgressBar JRootPane JScrollBar JScrollPane JSeparator JSlider JSplitPane JTabbedPane JTable JTableHeader *JTextComponent JEditorPane FrameEditorPane JTextPane JTextArea JtextField JPasswordField JToolBar JToolTip JTree JViewport ScrollableTabViewport Panel Applet JApplet Window Dialog JDialog Frame JFrame JWindow
注意:在另外几个包中还有其他一些 Swing 组件,但是这是基本的组件集。
清单 5. Swing 提供了以下 LayoutManagers(全部在 javax.swing 包或其子包中,“*” 表示接口)
*LayoutManager CenterLayout *LayoutManager2 BoxLayout OverlayLayout SpringLayout
注意:在另外几个包中还有其他一些 Swing 布局管理器,很多都是为它们所布局的容器而专门定制的,但是这是基本的布局管理器集。
清单 6. Swing 提供了以下事件(大部分在 javax.swing.events 包及其子包中)
Object EventObject AWTEvent AncestorEvent ComponentEvent InputEvent KeyEvent MenuKeyEvent MouseEvent MenuDragMouseEvent InternalFrameEvent
注意:在另外几个包中还有其他一些 AWT 事件,但是这是基本的事件集。这些是从更通用的事件生成的 “高级” 事件。
为了克服在不同主机上行为也会不同的缺点,Swing 将对主机控件的依赖性降至了最低。实际上,Swing 只为诸如窗口和框架之类的顶层 组件使用对等体。大部分组件(JComponent 及其子类)都是使用纯 Java 代码来模拟的。这意味着 Swing 天生就可以在所有主机之间很好地进行移植。因此,Swing 通常看起来并不像是本地程序。实际上,它有很多外观,有些模拟(尽管通常并不精确)不同主机的外观,有些则提供了独特的外观。
Swing 对基于对等体的组件使用的术语是重量级(heavyweight),对于模拟的组件使用的术语是轻量级(lightweight)。实际上,Swing 可以支持在一个 GUI 中混合使用重量级组件和轻量级组件,例如在一个 JContainer 中混合使用 AWT 和 Swing 控件,但是如果组件产生了重叠,就必须注意绘制这些控件的顺序。