为什么要使用SWT?
SWT是一个IBM开发的跨平台GUI开发工具包至于为什么IBM要费劲自己另起炉灶开发一个GUI工具包而不是使用Sun现有的由AWT Swing Java D Java D等构成的Java GUI框架那就说来话长了
在SWT之前Sun已经提供了一个跨平台GUI开发工具包AWT (Abstract Windowing Toolkit) 虽然AWT框架也使用的是原生窗口部件(native widgets)但是它一直未能突破LCD问题LCD问题导致了一些主要平台特征的遗失如果你不明白的话(其实我也没明白)换句话说如果平台A有窗口部件(widgets)–而平台B有窗口部件(widgets)–那么跨平台的AWT框架只能提供这两个窗口部件集的交集
为解决这个问题Sun又创建了一个新的框架这个框架不再使用原生窗口部件而是使用仿真窗口部件(emulated widgets)这个方法虽然解决了LCD问题并且提供了丰富的窗口部件集但是它也带来了新的问题例如Swing应用程序的界面外观不再和原生应用程序的外观相似 虽然在JVM中这些Swing应用程序已经得到了最大程度的性能改善但是它们还是存在着其原生对应物所不具有的性能问题并且Swing应用程序消耗太多的内存这样Swing不适于一些小设备如PDA和移动电话等
IBM进行了尝试以彻底解决AWT和Swing框架带来的上述问题最终IBM创建了一个新的GUI库这就是SWTSWT框架通过JNI来访问原生窗口部件如果在宿主(host)平台上无法找到一个窗口部件SWT就会自动地模拟它
SWT应用程序的组成
一个SWT应用程序的基本组成部分为显示界面(Display)命令界面(Shell使命令进入并使运行初始化)和窗口部件(Widgets)Display负责管理事件循环和控制UI线程和其他线程之间的通讯Shell是应用程序中被操作系统窗口管理器管理的窗口每个SWT应用程序至少需要一个Display和大于等于个的Shell实例
图从不同的角度看SWT应用程序
图从不同的角度展示了SWT应用程序左侧的图是一个简化的UI对象的继承图中间的图展示了UI对象的容器结构(containment structure)右侧的图则是创建后的UI外观
如果一个应用程序使用了多个线程那么每个线程都使用的是Display对象分配给它自己的实例程序员可以使用静态方法DisplaygetCurent()来得到Display对象的当前活动的实例
Shell用于在特定的操作系统中表现窗口Shell可以最大化最小化或正常化Shell有两种类型第种是高层shell它是Display的子窗口同时它也是一个主窗口第类是对话shell这种shell要依赖于其他的shell窗口存在shell窗口最终成为上述那种类型要看在创建shell时传递给shell构造函数的是什么风格位(style bits)一个shell的默认值是DialogShell也就是说如果不带参数那默认就是一个对话shell而如果给参数赋予了一个Display对象则该shell将是一个高层shell
一些窗口部件的属性必须在创建它们的初期就要被设置这些窗口部件的属性就是前面所说的风格位(style bits)在SWT的类中风格位被定义为常数例如Button button = new Button( shell <styleBits> )可以使用或(OR)操作符|来设置多个风格位例如如果想设置一个带边界的压下按钮需要传递SWTPUSH | SWTBORDER作为风格位参数
进行SWT开发前的环境设置
为了进行SWT应用开发你需要把SWT库添加到类路径(classpath)上并设置必要的环境变量
首先你要在ECLIPSE_HOME\eclipse\plugins\orgeclipseswtwin_\ws\win目录下找到swtjar库文件注意这里的orgeclipseswtwin_目录是和Eclipse的版本有关的实在找不到你就用文件搜索功能吧然后依次打开下面窗口Project>Properies>JavaBuildPath>Libraries>Add Variable > Eclipse Home >Extend将swtjar文件加到类路径中
接着你肯定想编译这个SWT应用了但是会出现下面所示的运行异常出现这个异常的原因是swtjar库使用的是原生库你需要设置javalibrarypath环境变量来使用Java中的原生库
控制台(Console )的输出如下
javalangUnsatisfiedLinkError: no swtwin in javalibrarypath
at javalangClassLoaderloadLibrary(Unknown Source)
at javalangRuntimeloadLibrary(Unknown Source)
at javalangSystemloadLibrary(Unknown Source)
at orgeclipseswtinternalLibraryloadLibrary(Libraryjava:)
at orgeclipseswtinternalwinOS<clinit>(OSjava:)
at orgeclipseswtwidgetsDisplayinternal_new_GC(Displayjava:)
at orgeclipseswtgraphicsDeviceinit(Devicejava:)
at orgeclipseswtwidgetsDisplayinit(Displayjava:)
at orgeclipseswtgraphicsDevice<init>(Devicejava:)
at orgeclipseswtwidgetsDisplay<init>(Displayjava:)
at orgeclipseswtwidgetsDisplay<init>(Displayjava:)
at comswtdesignertrytrymain(trytryjava:)
Exception in thread main
按下面的步骤设置javalibrarypath变量依次打开Run> Run……> Java Applicaton> Project >Arguments > VM Arguments在VM Arguments中输入
Djavalibrarypath=c\eclipse\plugins\orgeclipseswtwin_\os\win\x
注意要输入你自己的swtjar所在的路径
小技巧加载原生库
如果你需要加载自己应用程序所使用的原生库可以使用RuntimegetPlatformloadLibrary(libraryname)方法