1、第第7章章 图形用户界面的设计与实现图形用户界面的设计与实现7.1 图形用户界面概述图形用户界面概述7.2 用户自定义成分用户自定义成分7.3 Java的事件处理的事件处理7.4 GUI标准组件概述标准组件概述7.5 标签、按钮与动作事件标签、按钮与动作事件7.6 文本框、文本区域与文本事件文本框、文本区域与文本事件7.7 单、复选按钮,列表与选择事件单、复选按钮,列表与选择事件7.8 滚动条与调整事件滚动条与调整事件7.9 画布与鼠标、键盘事件画布与鼠标、键盘事件7.10 布局设计布局设计7.11 Panel与容器事件与容器事件7.12 Frame与窗口事件与窗口事件7.13 菜单的定义与使
2、用菜单的定义与使用7.14 对话框、组件事件与焦点事件对话框、组件事件与焦点事件7.15 小结小结习题习题本章介绍本章介绍Java程序中图形用户界面程序中图形用户界面(GUI)的设计与实的设计与实现。图形用户界面是程序与用户交互的窗口。每个现。图形用户界面是程序与用户交互的窗口。每个图形界面下的图形界面下的Java程序都必须设计、建立自己的图程序都必须设计、建立自己的图形用户界面并利用它接受用户的输入,向用户输出形用户界面并利用它接受用户的输入,向用户输出程序运行的结果。本章将介绍图形用户界面的基本程序运行的结果。本章将介绍图形用户界面的基本组成和主要操作,包括绘制图形,显示动画,使用组成和主
3、要操作,包括绘制图形,显示动画,使用AWT包各组件和实现包各组件和实现Java的事件处理功能等。的事件处理功能等。7.1 图形用户界面概述图形用户界面概述设计和构造用户界面,是软件开发中的一项重要工设计和构造用户界面,是软件开发中的一项重要工作。用户界面是计算机的使用者作。用户界面是计算机的使用者用户与计算机用户与计算机系统交互的接口,用户界面功能是否完善,使用是系统交互的接口,用户界面功能是否完善,使用是否方便,将直接影响到用户对应用软件的使用。图否方便,将直接影响到用户对应用软件的使用。图形用户界面形用户界面(graphics user interface)简称简称GUI,使,使用图形的方
4、式借助菜单、按钮等标准界面元素和鼠用图形的方式借助菜单、按钮等标准界面元素和鼠标操作,帮助用户方便地向计算机系统发出命令,标操作,帮助用户方便地向计算机系统发出命令,启动操作,并将系统运行的结果同样以图形的方式启动操作,并将系统运行的结果同样以图形的方式显示给用户。图形用户界面操作简便,省去了字符显示给用户。图形用户界面操作简便,省去了字符界面用户必须记忆各种命令的麻烦,已经成为目前界面用户必须记忆各种命令的麻烦,已经成为目前几乎所有应用软件的既成标准。所以,学习设计和几乎所有应用软件的既成标准。所以,学习设计和开发图形用户界面,是软件开发人员必修的一课。开发图形用户界面,是软件开发人员必修的
5、一课。随着图形用户界面的普及和界面元素标准化程度的随着图形用户界面的普及和界面元素标准化程度的提高,许多辅助设计和实现图形用户界面的方法和提高,许多辅助设计和实现图形用户界面的方法和工具也相应出现,例如,可视化编程方法允许设计工具也相应出现,例如,可视化编程方法允许设计人员直接绘出图形界面,然后交给专门的工具自动人员直接绘出图形界面,然后交给专门的工具自动编码生成这个图形界面,免除了开发者的许多编程编码生成这个图形界面,免除了开发者的许多编程负担,目前许多应用软件开发工具都具有可视化编负担,目前许多应用软件开发工具都具有可视化编程的功能。程的功能。Java语言中,为了方便图形用户界面的开发,设
6、计语言中,为了方便图形用户界面的开发,设计了专门的类库来生成各种标准图形界面元素和处理了专门的类库来生成各种标准图形界面元素和处理图形界面的各种事件。这个用来生成图形用户界面图形界面的各种事件。这个用来生成图形用户界面的类库就是的类库就是java.awt包。包。AWT是是abstract window toolkit(抽象窗口工具集抽象窗口工具集)的缩写。的缩写。所谓抽象,是因为所谓抽象,是因为Java是一种跨平台的语言,要求是一种跨平台的语言,要求Java程序能在不同的平台系统上运行,这对于图形程序能在不同的平台系统上运行,这对于图形用户界面尤其困难。为了达到这个目标,用户界面尤其困难。为了
7、达到这个目标,AWT类类库中的各种操作被定义成在一个并不存在的库中的各种操作被定义成在一个并不存在的“抽象抽象窗口窗口”中进行。正如中进行。正如Java虚拟机使得虚拟机使得Java程序独立程序独立于具体的软硬件平台一样,于具体的软硬件平台一样,“抽象窗口抽象窗口”使得开发使得开发人员所设计的界面独立于具体的界面实现。也就是人员所设计的界面独立于具体的界面实现。也就是说,开发人员用说,开发人员用AWT开发出的图形用户界面可以开发出的图形用户界面可以适用于所有的平台系统。当然,这仅是理想情况。适用于所有的平台系统。当然,这仅是理想情况。实际上实际上AWT的功能还不是很完全的功能还不是很完全,Jav
8、a程序的图程序的图形用户界面在不同的平台上形用户界面在不同的平台上(例如,在不同的浏览例如,在不同的浏览器中器中)可能会出现不同的运行效果,如窗口大小、可能会出现不同的运行效果,如窗口大小、字体效果将发生变化等。字体效果将发生变化等。首先考察一下图形用户界面的构成。首先考察一下图形用户界面的构成。简单地说,图形用户界面就是一组图形界面成分和简单地说,图形用户界面就是一组图形界面成分和界面元素的有机组合,这些成分和元素之间不但外界面元素的有机组合,这些成分和元素之间不但外观上有着包含、相邻、相交等物理关系,内在的也观上有着包含、相邻、相交等物理关系,内在的也有包含、调用等逻辑关系,它们互相作用、
9、传递消有包含、调用等逻辑关系,它们互相作用、传递消息,共同组成一个能响应特定事件、具有一定功能息,共同组成一个能响应特定事件、具有一定功能的图形界面系统。的图形界面系统。设计和实现图形用户界面的工作主要有两个:设计和实现图形用户界面的工作主要有两个:创建组成界面的各成分和元素,指定它们的属性创建组成界面的各成分和元素,指定它们的属性和位置关系,根据具体需要排列它们,从而构成完和位置关系,根据具体需要排列它们,从而构成完整的图形用户界面的物理外观。整的图形用户界面的物理外观。定义图形用户界面的事件和各界面元素对不同事定义图形用户界面的事件和各界面元素对不同事件的响应,从而实现图形用户界面与用户的
10、交互功件的响应,从而实现图形用户界面与用户的交互功能。能。Java中构成图形用户界面的各种元素和成分可以粗中构成图形用户界面的各种元素和成分可以粗略地被分为三类:容器、控制组件和用户自定义成略地被分为三类:容器、控制组件和用户自定义成分。分。1.容器容器容器是用来组织其他界面成分和元素的单元。一般容器是用来组织其他界面成分和元素的单元。一般说来一个应用程序的图形用户界面首先对应于一个说来一个应用程序的图形用户界面首先对应于一个复杂的容器,如一个窗口。这个容器内部将包含许复杂的容器,如一个窗口。这个容器内部将包含许多界面成分和元素,这些界面元素本身也可能又是多界面成分和元素,这些界面元素本身也可
11、能又是一个容器,这个容器再进一步包含它的界面成分和一个容器,这个容器再进一步包含它的界面成分和元素,依此类推就构成一个复杂的图形界面系统。元素,依此类推就构成一个复杂的图形界面系统。容器的引入有利于分解图形用户界面的复杂性,当容器的引入有利于分解图形用户界面的复杂性,当界面的功能较多时,使用层层相套的容器是非常有界面的功能较多时,使用层层相套的容器是非常有必要的。必要的。2.控制组件控制组件与容器不同,控制组件是图形用户界面的最小单位与容器不同,控制组件是图形用户界面的最小单位之一,它里面不再包含其他的成分。控制组件的作之一,它里面不再包含其他的成分。控制组件的作用是完成与用户的一次交互,包括
12、接收用户的一个用是完成与用户的一次交互,包括接收用户的一个命令命令(如菜单命令如菜单命令),接收用户的一个文本或选择输,接收用户的一个文本或选择输入,向用户显示一段文本或一个图形,等等。从某入,向用户显示一段文本或一个图形,等等。从某种程度上来说,控制组件是图形用户界面标准化的种程度上来说,控制组件是图形用户界面标准化的结果,目前常用的控制组件有选择类的单选按钮、结果,目前常用的控制组件有选择类的单选按钮、复选按钮、下拉列表;有文字处理类的文本框、文复选按钮、下拉列表;有文字处理类的文本框、文本区域;有命令类的按钮、菜单等。其中文本框、本区域;有命令类的按钮、菜单等。其中文本框、按钮和标签是前
13、面使用过的按钮和标签是前面使用过的GUI组件。组件。使用控制组件,通常需要如下的步骤:使用控制组件,通常需要如下的步骤:(1)创建某控制组件类的对象,指定其大小等属性。创建某控制组件类的对象,指定其大小等属性。(2)使用某种布局策略,将该控制组件对象加入到某使用某种布局策略,将该控制组件对象加入到某个容器中的某指定位置处。个容器中的某指定位置处。(3)将该组件对象注册给它所能产生的事件对应的事将该组件对象注册给它所能产生的事件对应的事件监听者,重载事件处理方法,实现利用该组件对件监听者,重载事件处理方法,实现利用该组件对象与用户交互的功能。象与用户交互的功能。严格说来,容器也是一种控制组件,因
14、为一个容器严格说来,容器也是一种控制组件,因为一个容器也可以被视为组件而包含在其他容器的内部。也可以被视为组件而包含在其他容器的内部。3.用户自定义成分用户自定义成分除了上述的标准图形界面元素,编程人员还可以根除了上述的标准图形界面元素,编程人员还可以根据用户的需要设计一些用户自定义的图形界面成分,据用户的需要设计一些用户自定义的图形界面成分,例如绘制一些几何图形、使用标志图案等。用户自例如绘制一些几何图形、使用标志图案等。用户自定义成分由于不能像标准界面元素一样被系统识别定义成分由于不能像标准界面元素一样被系统识别和承认,所以通常只能起到装饰、美化的作用,而和承认,所以通常只能起到装饰、美化
15、的作用,而不能响应用户的动作,也不具有交互功能。不能响应用户的动作,也不具有交互功能。7.2 用户自定义成分用户自定义成分本节主要介绍如何利用本节主要介绍如何利用Java类库中的类及其方法来类库中的类及其方法来绘制用户自定义的图形界面成分。编程人员可以利绘制用户自定义的图形界面成分。编程人员可以利用这些方法自由地绘制图形和文字,也可以将已经用这些方法自由地绘制图形和文字,也可以将已经存在的图形、动画等加载到当前程序中来。绘制图存在的图形、动画等加载到当前程序中来。绘制图形和文字将要用到前面已经接触过的类形和文字将要用到前面已经接触过的类Graphics。Graphics是是java.awt包中
16、一个类,其中包括了很多绘包中一个类,其中包括了很多绘制图形和文字的方法。当一个制图形和文字的方法。当一个Applet运行时,执行运行时,执行它的浏览器会自动为它创建一个它的浏览器会自动为它创建一个Graphics类的实例,类的实例,利用这个实例,就可以在利用这个实例,就可以在Applet中随意绘制图形和中随意绘制图形和文字。实际上文字。实际上Applet本身就是一个图形界面的容器。本身就是一个图形界面的容器。而如果希望在图形界面的而如果希望在图形界面的Java Application程序中程序中绘制图形,则需要创建一个绘制图形,则需要创建一个Canvas类的对象加入类的对象加入到这个到这个Ap
17、plication程序的图形界面容器中,程序的图形界面容器中,Canvas对象也拥有一个与对象也拥有一个与Applet类的类的paint()方法相同的方法相同的paint()方法,利用系统传递给这个方法,利用系统传递给这个paint()方法的方法的Graphics类参数对象就可以在类参数对象就可以在Application程序的图程序的图形用户界面中绘制各种图形和文字。形用户界面中绘制各种图形和文字。7.2.1 绘制图形绘制图形利用利用Graphics类可绘制的图形有直线、各种矩形、多类可绘制的图形有直线、各种矩形、多边形、圆和椭圆等。下面的例子综合了这些方法。边形、圆和椭圆等。下面的例子综合了
18、这些方法。例例 7-1 DrawFigures.java 1:import java.awt.*;2:import java.applet.Applet;3:public class DrawFigures extends Applet4:5:public void paint(Graphics g)6:7:g.drawLine(30,5,40,5);/画直线画直线8:g.drawRect(40,10,50,20);/画矩形框画矩形框(左上角左上角x坐标,坐标,左上角左上角y坐标,坐标,x轴尺寸,轴尺寸,y轴尺寸轴尺寸)9:g.fillRect(60,30,70,40);/画实心矩形画实心矩形
19、10:g.drawRoundRect(110,10,130,50,30,30);/画圆角矩画圆角矩形框形框11:g.drawOval(150,120,70,40);/画椭圆形框画椭圆形框(左上角左上角x坐标,左上角坐标,左上角y坐标,坐标,x轴尺寸,轴尺寸,y轴尺寸轴尺寸),若,若x轴尺寸与轴尺寸与y轴尺寸相等,则画出圆形轴尺寸相等,则画出圆形12:g.fillOval(190,160,70,40);/画实心椭圆画实心椭圆13:g.drawOval(90,100,50,40);/画椭圆框画椭圆框14:g.fillOval(130,100,50,40);/画实心椭圆画实心椭圆15:drawMyP
20、olygon(g);/自定义的画多边形的方法自定义的画多边形的方法16:g.drawString(They are figures!,100,220);17:18:public void drawMyPolygon(Graphics g)19:20:int xCoords=30,50,65,119,127;/保存多边形各点保存多边形各点x坐标的数组坐标的数组21:int yCoords=100,140,127,169,201;/保存多边形各点保存多边形各点y坐标的数组坐标的数组22:g.drawPolygon(xCoords,yCoords,5);/画自由多边形框画自由多边形框23:24:图图
21、7.1是例是例7-1的运行结果。从例的运行结果。从例7-1可以看出,要在可以看出,要在Java程序图形界面的容器中绘制图形,首先,需要程序图形界面的容器中绘制图形,首先,需要明确希望绘制的图形是什么,是圆、椭圆,还是直明确希望绘制的图形是什么,是圆、椭圆,还是直线,这由所选定的方法来确定;其次,需要指明所线,这由所选定的方法来确定;其次,需要指明所绘制图形或文字的大小和位置,这要通过相对于界绘制图形或文字的大小和位置,这要通过相对于界面容器的二维像素坐标来决定。面容器的二维像素坐标来决定。Java的屏幕坐标是的屏幕坐标是以像素为单位,容器的左上角被确定为横坐标以像素为单位,容器的左上角被确定为
22、横坐标(x轴轴)和纵坐标和纵坐标(y轴轴)的起点,向右和向下延伸坐标值递的起点,向右和向下延伸坐标值递增。增。图图 7.1 例例7-1的运行结果的运行结果绘制图形的方法很多,每种方法一般也有多种灵活绘制图形的方法很多,每种方法一般也有多种灵活的使用方式,这里不再赘述,读者可以查阅程序员的使用方式,这里不再赘述,读者可以查阅程序员手册中的详细规定。手册中的详细规定。除了除了Graphics类,类,Java中还定义了其他一些用来表示中还定义了其他一些用来表示几何图形的类,对绘制用户自定义成分也很有帮助。几何图形的类,对绘制用户自定义成分也很有帮助。例如,利用例如,利用Point表示一个像素点;利用
23、表示一个像素点;利用Dimension类表示宽和高;利用类表示宽和高;利用Rectangle类表示一个矩形;类表示一个矩形;利用利用Polygon类表示一个多边形;利用类表示一个多边形;利用Color类表示类表示颜色等,后面的例子中将利用这些系统定义的类绘颜色等,后面的例子中将利用这些系统定义的类绘图。图。7.2.2 显示文字显示文字从前面的例子中可以知道,从前面的例子中可以知道,Graphics类的方法类的方法drawString()可以在屏幕的指定位置显示一个字符可以在屏幕的指定位置显示一个字符串。串。Java中还有一个类中还有一个类Font,使用它可以获得更加,使用它可以获得更加丰富多彩
24、和逼真精确的字体显示效果。丰富多彩和逼真精确的字体显示效果。一个一个Font类的对象表示了一种字体显示效果,包括类的对象表示了一种字体显示效果,包括字体类型、字型和字号。下面的语句用于创建一个字体类型、字型和字号。下面的语句用于创建一个Font类的对象:类的对象:Font MyFont=new Font(TimesRoman,Font.BOLD,12);MyFont对应的是对应的是12磅磅TimesRoman类型的黑体字,类型的黑体字,其中指定字型时需要用到其中指定字型时需要用到Font类的三个常量:类的三个常量:Font.PLAIN,Font.BOLD,Font.ITALIC。如果希望使用该
25、如果希望使用该Font对象,则可以利用对象,则可以利用Graphics类的类的setFont()方法:方法:g.setFont(MyFont);如果希望指定控制组件,如按钮或文本框中的字体如果希望指定控制组件,如按钮或文本框中的字体效果,则可以使用控制组件的方法效果,则可以使用控制组件的方法setFont()。如设。如设btn是一个按钮对象,则语句:是一个按钮对象,则语句:btn.setFont(MyFont);将把这个按钮上显示的标签的字体改为将把这个按钮上显示的标签的字体改为12磅的磅的TimesRoman黑体字。黑体字。另外,与另外,与setFont()方法相对的方法相对的getFont
26、()方法将返回方法将返回当前当前Graphics或组件对象使用的字体。或组件对象使用的字体。例例 7-2 AvailableFonts.java1:import java.applet.*;2:import java.awt.*;3:4:public class AvailableFont extends Applet5:6:GraphicsEnvironment gl=GraphicsEnvironment.getLocalGraphicsEnvironment();7:String FontNames=gl.getAvailableFontFamilyNames();8:9:public
27、void paint(Graphics g)10:11:Font current,oldFont;12:13:oldFont=g.getFont();14:for(int i=0;iFontNames.length;i+)15:16:current=new Font(FontNamesi,Font.PLAIN,10);17:g.setFont(current);18:g.drawString(current.getName(),10+i%4*120,20+i/4*15);19:20:g.setFont(oldFont);21:22:在例在例7-2中,首先在第中,首先在第6句利用句利用java.
28、awt包的包的G r a p h i c s E n v i r o n m e n t 类 的 静 态 方 法类 的 静 态 方 法getLocalGraphicsEnvironment()获得代表获得代表Java程序程序运行的当前平台的图形环境的对象运行的当前平台的图形环境的对象gl,然后在第,然后在第7句调用句调用gl对象的对象的getAvailableFontFamilyNames()获获得当前平台上所有可以使用的字体名字,返回给字得当前平台上所有可以使用的字体名字,返回给字符串数组符串数组FontNames,该数组的每个元素是一,该数组的每个元素是一代表字体名的字符串。第代表字体名的
29、字符串。第13句首先获取并保存当前句首先获取并保存当前缺省的字体对象。第缺省的字体对象。第14到到19句的循环修改当前字体,句的循环修改当前字体,设置成一可用的字体并输出该字体的名称,每四个设置成一可用的字体并输出该字体的名称,每四个字体占用一行;其中第字体占用一行;其中第16句使用句使用Font类的构造函数类的构造函数创建新字体对象。最后,第创建新字体对象。最后,第20句把字体恢复成原来句把字体恢复成原来的缺省值。例的缺省值。例7-2的运行结果如图的运行结果如图7.2所示。所示。图图 7.2 例例7-2的运行结果的运行结果 7.2.3 控制颜色控制颜色Applet中显示的字符串或图形的颜色可
30、以用中显示的字符串或图形的颜色可以用Color类类的对象来控制,每个的对象来控制,每个Color对象代表一种颜色,用对象代表一种颜色,用户可以直接使用户可以直接使用Color类中定义好的颜色常量,也类中定义好的颜色常量,也可以通过调配红、绿、蓝三色的比例创建自己的可以通过调配红、绿、蓝三色的比例创建自己的Color对象。对象。Color类中定义有如下的三种构造函数:类中定义有如下的三种构造函数:public Color(int Red,int Green,int Blue);public Color(float Red,float Green,float Blue);public Color(
31、int RGB);不论使用哪个构造函数创建不论使用哪个构造函数创建Color对象,都需要指定对象,都需要指定新建颜色中新建颜色中R(红红)、G(绿绿)、B(蓝蓝)三色的比例。在三色的比例。在第一个构造函数中通过三个整型参数指定第一个构造函数中通过三个整型参数指定R,G,B,每个参数的取值范围在,每个参数的取值范围在0255之间;第二个构之间;第二个构造函数通过三个浮点参数指定造函数通过三个浮点参数指定R,G,B,每个参,每个参数的取值范围在数的取值范围在0.01.0之间;第三个构造函数通之间;第三个构造函数通过一个整型参数指明其过一个整型参数指明其RGB三色比例,这个参数三色比例,这个参数的的
32、07比特比特(取值范围为取值范围为0255)代表红色的比例,代表红色的比例,815比特代表绿色的比例,比特代表绿色的比例,1623比特代表蓝色比特代表蓝色的比例。例如下面的语句创建的是蓝色:的比例。例如下面的语句创建的是蓝色:Color blueColor=new Color(0,0,255);调用调用Graphics对象的对象的setColor()方法可以把当前的缺方法可以把当前的缺省颜色修改成新建的颜色,使此后调用该省颜色修改成新建的颜色,使此后调用该Graphics对象完成的绘制工作,如绘制图形、字符串等,都对象完成的绘制工作,如绘制图形、字符串等,都使用这个新建颜色:使用这个新建颜色:
33、g.setColor(blueColor);除了创建自己的颜色,也可以直接使用除了创建自己的颜色,也可以直接使用Color类中定类中定义好的颜色常量,如:义好的颜色常量,如:g.setColor(Color.cyan);Color类中共定义了类中共定义了13种静态颜色常量,包括种静态颜色常量,包括black,orange,pink,grey等,使用时只需以等,使用时只需以Color为前为前缀,非常方便。缀,非常方便。对于对于GUI的控制组件,它们有四个与颜色有关的方法的控制组件,它们有四个与颜色有关的方法分别用来设置和获取组件的背景色和前景色:分别用来设置和获取组件的背景色和前景色:publi
34、c void setBackground(Color c)public Color getBackground()public void setForeground()public Color getForeground()例例 7-3 UseColor.java1:import java.applet.Applet;2:import java.awt.*;3:4:public class UseColor extends Applet5:6:Color oldColor;7:String ParamName=red,green,blue;/三个三个HTML参数的名称参数的名称8:int RG
35、Barray=new int3;/保存三色比例的数组保存三色比例的数组9:10:public void init()11:12:for(int i=0;iParamName.length;i+)/取得取得HTML文件指定的三色文件指定的三色13:RGBarrayi=Integer.parseInt(getParameter(ParamNamei);14:15:public void paint(Graphics g)16:17:oldColor=g.getColor();/保存原有的缺省颜色保存原有的缺省颜色18:g.setColor(new Color(RGBarray0,RGBarray1
36、,RGBarray2);/置新颜色置新颜色19:g.drawString(How do you think about Current color:20:+g.getColor().toString(),10,20);/用新建颜用新建颜色显示该颜色的三色分量色显示该颜色的三色分量21:g.setColor(oldColor);/恢复原有颜色恢复原有颜色22:g.drawString(Back to old default color:+g.getColor().toString(),10,40);23:24:例例7-3的运行结果如图的运行结果如图7.3所示。所示。例例7-3利用利用HTML文件
37、传递给文件传递给Java Applet的三个参数的三个参数作为作为R,G,B三色的比例。第三色的比例。第18句用句用该该比例创建比例创建颜色,并用新颜色显示字符串颜色,并用新颜色显示字符串(包括新颜色中三色包括新颜色中三色的比例含量的比例含量)。第。第21句再恢复原来的缺省颜色。句再恢复原来的缺省颜色。图图 7.3 例例7-3的运行结果的运行结果 此程序对应的此程序对应的HTML文件如下:文件如下:UseColor 通过改变三个参数的数值通过改变三个参数的数值(应在应在0255之间之间),就可以,就可以指定不同的颜色而不需要重新编译指定不同的颜色而不需要重新编译Java Applet程序。程序
38、。7.2.4 显示图像显示图像由于图像的数据量要远远大于图形,所以一般不在由于图像的数据量要远远大于图形,所以一般不在程序中自行绘制图像,而是把已经存在于本机硬盘程序中自行绘制图像,而是把已经存在于本机硬盘或网络某地的二进制图像文件直接调入内存。图像或网络某地的二进制图像文件直接调入内存。图像文件有多种格式,如文件有多种格式,如bmp文件、文件、gif文件、文件、tiff文件文件等等,其中等等,其中gif是是Internet上常用的图像文件格式。上常用的图像文件格式。Java中可以利用中可以利用Graphics类的类的drawImage()方法显示方法显示图像,现考察下面的例子。图像,现考察下
39、面的例子。例例 7-4 DrawMyImage.java 1:import java.awt.*;2:import java.applet.Applet;3:public class DrawMyImage extends Applet4:5:Image myImage;6:public void init()7:8:myImage=getImage(getDocumentBase(),blackbrd.gif);9:10:public void paint(Graphics g)11:12:g.drawImage(myImage,0,0,this);13:14:例例7-4中,使用了中,使用了
40、Image类的对象类的对象myImage来保存二进来保存二进制的图像数据,其中制的图像数据,其中getImage()方法是系统为方法是系统为Applet类定义的方法,该方法将指定图像文件的内类定义的方法,该方法将指定图像文件的内容加载到内存的容加载到内存的Image对象中。对象中。getImage()方法有两方法有两个参数。第一个是图像文件所在的个参数。第一个是图像文件所在的URL地址,在上地址,在上例中由于图像文件与例中由于图像文件与HTML文件保存在同一路径下,文件保存在同一路径下,所以用所以用Applet类另一个方法类另一个方法getDocumentBase()来获来获取含有该取含有该A
41、pplet的的HTML文件的文件的URL地址。地址。getImage()的第二个参数是图像文件的文件名。的第二个参数是图像文件的文件名。Java可识别的图像文件格式有可识别的图像文件格式有bmp,gif,jpeg等。等。drawImage()是是Graphics类中用来显示图像的方法。类中用来显示图像的方法。它的第一个参数是保存有图像数据的它的第一个参数是保存有图像数据的Image对象。对象。第二、第三个参数是图像的左上角点坐标,它们决第二、第三个参数是图像的左上角点坐标,它们决定了图像在容器中的显示位置。最后一个参数是显定了图像在容器中的显示位置。最后一个参数是显示图像的容器对象。例示图像的
42、容器对象。例7-4中的中的this代表了当前的代表了当前的Applet对象。对象。7.2.5 实现动画效果实现动画效果动画曾是动画曾是Java Applet最吸引人的特性之一。用最吸引人的特性之一。用Java实现动画的原理与放映动画片类似,取若干相关的实现动画的原理与放映动画片类似,取若干相关的图像或图片,顺序、连续地在屏幕上先显示,后擦图像或图片,顺序、连续地在屏幕上先显示,后擦除,循环往复就可以获得动画的效果。参考下面的除,循环往复就可以获得动画的效果。参考下面的例子。例子。例例 7-5 ShowAnimator.java 1:import java.applet.Applet;2:imp
43、ort java.awt.*;3:4:public class ShowAnimator extends Applet5:6:Image m-Images;/保存图片序列的保存图片序列的Image数组数组7:int totalImages=18;/图片序列中的图片总数图片序列中的图片总数8:int currentImage=0;/当前时刻应该显示的图片当前时刻应该显示的图片 序号序号9:10:public void init()11:12:m-Images=new ImagetotalImages;13:/从当前目录下的从当前目录下的images子目录中将子目录中将Img001.gif到到 I
44、mg0018.gif的文件加载的文件加载14:for(int i=0;itotalImages;i+)15:m-Imagesi=getImage(getDocumentBase(),imagesImg00+(i+1)+.gif);16:17:public void start()18:19:currentImage=0;/从第一幅开始显示从第一幅开始显示20:21:public void paint(Graphics g)22:23:g.drawImage(m-ImagescurrentImage,50,50,this);/显示当前序号的图片显示当前序号的图片24:currentImage=+
45、currentImage%totalImages;/计算下一个应显示图片的序号计算下一个应显示图片的序号25:try26:Thread.sleep(50);/程序休眠程序休眠50毫秒毫秒27:28:catch(InterruptedException e)/处理执行休眠方法可能引发的异常处理执行休眠方法可能引发的异常29:30:showStatus(e.toString();31:32:repaint();/图片停留图片停留50毫秒后被擦除,重新调毫秒后被擦除,重新调 用用paint()显示下一张图片显示下一张图片33:34:例例7-5中使用了中使用了Thread.sleep()方法,目的是使
46、当前的方法,目的是使当前的程序线程休眠一段时间,以便每幅图片在下一幅图程序线程休眠一段时间,以便每幅图片在下一幅图片显示之前能在屏幕上逗留一小段时间,关于线程片显示之前能在屏幕上逗留一小段时间,关于线程的具体编程将在以后的章节详细介绍。第的具体编程将在以后的章节详细介绍。第14句到第句到第15句的循环使用句的循环使用Applet的的getImage()方法获取所有方法获取所有的的.gif图像文件图像文件(注意其目录注意其目录)。第。第21句到句到33句的句的paint()方法一次显示一幅图像,稍待片刻后再显示方法一次显示一幅图像,稍待片刻后再显示Image对象数组中的下一幅图像。图对象数组中的
47、下一幅图像。图7.4是例是例7-5的的运行结果。运行结果。图图 7.4 例例7-5的运行结果的运行结果在设计和实现程序的图形用户界面的过程中,绘制在设计和实现程序的图形用户界面的过程中,绘制用户自定义成分仅仅完成了一部分工作,它可以装用户自定义成分仅仅完成了一部分工作,它可以装饰、美化用户界面,但却无法接收程序运行过程中饰、美化用户界面,但却无法接收程序运行过程中的即时用户指令,不能提供与用户的动态交互。的即时用户指令,不能提供与用户的动态交互。Java中用来解决这个问题的机制是事件及其处理。中用来解决这个问题的机制是事件及其处理。7.3 Java的事件处理的事件处理图形用户界面之所以能为广大
48、用户所喜爱并最终成图形用户界面之所以能为广大用户所喜爱并最终成为事实上的标准,很重要的一点就在于它可以用更为事实上的标准,很重要的一点就在于它可以用更灵活、简便的方式来接收用户命令。用户在图形用灵活、简便的方式来接收用户命令。用户在图形用户界面中输入命令是通过移动鼠标对特定图形界面户界面中输入命令是通过移动鼠标对特定图形界面元素单击、双击鼠标键来实现的,为了能够接收用元素单击、双击鼠标键来实现的,为了能够接收用户的命令,图形用户界面的系统首先应该能够识别户的命令,图形用户界面的系统首先应该能够识别这些鼠标和键盘的操作并做出相应的响应。这些鼠标和键盘的操作并做出相应的响应。通常每一个键盘或鼠标操
49、作会引发一个系统预先定通常每一个键盘或鼠标操作会引发一个系统预先定义好的事件,用户程序只需要编制代码定义每个特义好的事件,用户程序只需要编制代码定义每个特定事件发生时程序应做出何种响应即可。这些代码定事件发生时程序应做出何种响应即可。这些代码会在它们对应的事件发生时由系统自动调用,这就会在它们对应的事件发生时由系统自动调用,这就是图形用户界面中事件和事件响应的基本原理。是图形用户界面中事件和事件响应的基本原理。Java中,除了键盘和鼠标操作,系统的状态改变、中,除了键盘和鼠标操作,系统的状态改变、标准图形界面元素等都可以引发事件,对这些事件标准图形界面元素等都可以引发事件,对这些事件分别定义处
50、理代码,就可以保证应用程序系统在不分别定义处理代码,就可以保证应用程序系统在不同的状况下都合理有效、有条不紊地正常工作。同的状况下都合理有效、有条不紊地正常工作。Java的事件处理机制中引入了委托事件模型的事件处理机制中引入了委托事件模型(如图如图7.5所示所示),不同的事件由不同的监听者处理。,不同的事件由不同的监听者处理。图图 7.5 委托事件模型委托事件模型图图7.5中,图形用户界面的每个可能产生事件的组件中,图形用户界面的每个可能产生事件的组件被称为事件源,不同事件源上发生的事件的种类不被称为事件源,不同事件源上发生的事件的种类不同。例如,同。例如,Button对象或对象或MenuIt