布局管理器
复合控件常常包含多个控件。可以使用以下两种方法安排这些控件:
绝对定位 —— 为每个控件设置明确的 X 和 Y 位置,并通过代码设置一定的宽度和高度。
托管定位 —— 每个控件的 X、Y、宽度和高度都是通过 LayoutManager 设置的。
在多数情况下,应该选择使用 LayoutManagers,因为很容易调整它们来适应可变大小的 GUI。SWT 也提供了一些布局管理器供您使用;在这一期的系列文章中,我们将讨论两种基本的布局管理器:FillLayout 和 GridLayout。在这两种情况下,每当重新设置复合控件的大小,都需要进行定位。
一些布局管理器常常是专为某一个复合控件分配的。一些布局管理器只使用它们自身的参数就可以控制,而另一些布局管理器还需要其他参数 —— LayoutData,该参数是在它们管理的复合控件中的每个控件上指定的。
FillLayout
FillLayout 以行或列的形式安排控件。每个控件所设置的大小将与填充该复合控件所需的宽度和高度相同,在这些控件之间,空间是平均分配的。一种特殊情况是:在仅有一个子控件时,该控件的大小被设置为填充整个父复合控件的大小。
清单 10 使用一个列 FillLayout 创建了一个复合控件。
清单 10. 使用 FillLayout 创建一列控件
2 import org.eclipse.swt.layouts.*;
3 :
4 Composite composite = ...;
5 FillLayout fillLayout = new FillLayout(SWT.VERTICAL);
6 composite.setLayout(fillLayout);
7
GridLayout
GridLayout 提供了一个功能更强大的布局方法,该方法类似于使用 HTML 表的方法。它创建了 2-D 网格的单元格。可以将控件放置在一个或多个单元格中(可以称之为单元格跨越)。单元格的大小可以是相等的,或者是网格宽度或高度的某个给定可变百分比。可以将控件添加到某一行的下一个可用列中,如果这一行中没有更多的列,那么该控件将移动到下一行的第一列中。
清单 11 创建了一个复合控件,该控件有两行和两个列,其中包含两个已标记的文本字段。这些列可以有不同的宽度。
清单 11. 创建一个控件表
2 import org.eclipse.swt.layouts.*;
3 :
4 Composite composite = ...;
5 GridLayout gridLayout = new GridLayout(2, false);
6 composite.setLayout(gridLayout);
7 Label l1 = new Label(composite, SWT.LEFT);
8 l1.settext("First Name: ");
9 Text first = new Text(composite, SWT.SINGLE);
10 Label l1 = new Label(composite, SWT.LEFT);
11 l2.setText("Last Name: ");
12 Text last = new Text(composite, SWT.SINGLE);
13
GridData
考虑一下这种情况:您需要指定每个控件如何使用其单元格中的剩余空间。为了给每个单元格提供这种精确控制,添加到 GridLayout 的托管复合控件的控件可以拥有 GridData 实例(LayoutData 的子类)。
清单 12 设置了这些文本字段,以便采用所有可用的剩余空间(根据前面的清单)。
清单 12. 配置一个扩展到所有可用空间的布局
2 first.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
3 last.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
4
构建一个运行程序
现在是时候来看一下我们已经在简单的可执行例子 Basic1 中讨论过的所有 SWT 控件了。请参阅 参考资料,以获得该应用程序的完整源代码。
SWT GUI 需要一个已配置好的环境来运行。这个环境是通过一个显示实例提供的,该实例提供了对主机操作系统显示设备的访问。这个显示实例允许您处理每个用户输入(鼠标或键盘)来处理您的 GUI。
清单 13 创建了一个环境和一个 GUI,并显示了这个 GUI。
清单 13. 创建一个 GUI 应用程序并启动它
2 :
3 Display display = new Display();
4 Shell shell = new Shell(display);
5 shell.setText("Shell Title");
6 // *** construct Shell children here ***
7 shell.open(); // open shell for user access
8 // process all user input events
9 while(!shell.isDisposed()) {
10 // process the next event, wait when none available
11 if(!display.readAndDispatch()) {
12 display.sleep();
13 }
14 }
15 display.dispose(); // must always clean up
16
此代码创建了一个类似于图 6 的窗口。
图 6. 示例应用程序

结束语
在 SWT 和 JFace 系列的第一期中,我们介绍了大多数基本 SWT 窗口小部件控件:标签、文本、按钮、复合控件和 shell。这些控件,与显示类(display class)相结合,允许创建全功能的 GUI。
本系列的第 2 部分将展示如何创建菜单,以及如何使用其他输入控件和信息显示控件,比如列表、树和表等。
代码下载 os-Basic1.java