Java语言-概念-事件处理模型

图形用户界面的操作通常是通过鼠标和键盘操作来实现的。通常一个键盘或鼠标操作会引发一个系统预先定义好的事件,用户程序只需编写代码,定义每个特定事件发生时程序应作出何种响应即可。这些代码将在它们对应的事件发生时由系统自动调用,这就是图形用户界面程序设计事件和事件响应的基本原理。事件处理技术是图形用户界面程序设计中一个非常重要的技术。消息处理、事件驱动是面向对象编程技术的主要特点。

事件处理机制

若使图形用户界面能够接收用户的操作,就必须给各个组件加上事件处理机制。在事件处理的过程中,主要涉及3类对象。
(1)Event(事件)。所谓事件,就是用户使用鼠标或键盘对窗口中的组件进行交互发生的一个操作。例如,单击按钮、输入文字、单击鼠标或键盘等。
(2)Event Sourse(事件源)。所谓事件源,就是能够产生事件的对象。如按钮、鼠标、文本框或键盘等。
(3)Event Handler(事件监听者或处理者)。Java程序把事件进行处理的方法放在一个类对象中,这个类对象就是事件监听者(listener)。当事件发生时,事件监听者便是被通知的对象。为此,它必须向一个或多个事件源注册,以便接受发生事件的通知。事件监听者还必须实现一些方法,用来接收和处理通知的事件。接收和处理事件的方你分别在java.awt.event的一系列的接口中定义。例如,ActionListener监听者接口中定义一个接收动作事件的方法。
再者,如果用户用鼠标单击按钮对象button,则该按钮button就是事件源,而Java运行时系统会生成ActionEvent类的对象actionEvent,该对象中描述了单击事件发生时的一些信息。然后,事件处理者对象将接收由Java运行时系统传递过来的事件对象actionEvent,并进行相应的处理。
每个事件源可以发出若干种不同类型的事件。为了对每种事件源发出事件的监听,对每个事件源指定事件监听者。这种处理机制是将用户界面和事件处理分开,使得程序结构更加清晰和自然。
事件监听器(处理者)通常是一个类,该类如果能够处理某种类型的事件,就必须实现与该事件类型相对应的接口。例如,一个JButtonHandler类之所以能够处理ActionEvent事件,原因在于它实现与ActionEvent事件对应的接口ActionListener。每个事件类都有一个与之相对应的接口。
在GUI程序设计中,处理发生在某个GUI组件上的XxxEvent事件的某种情况,其事件处理的通用编写流程如下:
(1)创建某种事件类的事件对象,并将它们加到容器中,该容器则实现了XxxListener接口的事件监听器类。
(2)注册当前容器为事件对象的监听者。注册监听者可采用事件源的addXxxListener()方法来实现。例如,M.addXxxListener(N)。
这是将N对象注册为M对象的监听者
(3)在注册为监听器的容器中,重新定义接口中的相应方法进行事件处理。
下面通过例子说明事件处理的具体过程。
【例】在一个窗口中摆放6个组件:4个标签和2个文本框。当文本框中的信息更改,将文本框中信息显示在第3、4个标签中。

package Swing;
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
public class Event_Exam extends JFrame implements ActionListener {
	static Event_Exam mainJFrame=new Event_Exam();
	static JLabel labl1,labl2;
	static JLabel showlb1=new JLabel("0");
	static JLabel showlb2=new JLabel("0.0");
	static JTextField text1,text2;
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		mainJFrame.setTitle("操作事件示例!");
		mainJFrame.setSize(200, 160);
		Container container=mainJFrame.getContentPane();
		container.setLayout(new FlowLayout());
		labl1=new JLabel("输入整数型:");
		container.add(labl1);
		text1=new JTextField("0",10);
		text1.addActionListener(mainJFrame);//把监听者mainJFrame向事件源text1注册
		container.add(text1);
		labl2=new JLabel("输入浮点数:");
		container.add(labl2);
		text2=new JTextField("0.0",10);
		text2.addActionListener(mainJFrame);//把监听者mainJFrame向事件源text2注册
		container.add(text2);
		showlb1.setForeground(Color.blue);
		showlb1.setHorizontalTextPosition(SwingConstants.LEFT);
		showlb2.setForeground(Color.green);
		showlb2.setHorizontalTextPosition(SwingConstants.LEFT);
		container.add(showlb1);
		container.add(showlb2);
		mainJFrame.setVisible(true);
	}
	public void actionPerformed(ActionEvent e) {//事件发生时的处理操作
		//提取文本框内容并显示在showlb1、showlb2中
		showlb1.setText("整数为"+text1.getText());
		showlb2.setText("浮点数为"+text2.getText());
	}
}

Java语言-概念-事件处理模型_第1张图片
该程序创建了1个窗口mainJFrame、4个标签和2个文本框,其中事件源为text1和text2文本框。为了编写事件处理程序,首先必须选择事件源的监听者。通常情况下,监听者由包含事件源的对象承担。由于mainJFrame中包含text1和text2,故由mainJFrame来担任监听者,让它具有事件处理能力的方式就是让类Event_Exam实现(implements)事件处理的接口(interface)。按钮触发的事件是由ActionListener接口监听的,因此,在类Event_Exam定义中必须添加“implements ActionListener”代码。
确定了事件源与监听者之后,接下来就是把监听者mainJFrame向事件源注册text1注册。其方法是用“text1.addActionListener(mainJFrame)”语句设置。当text1文本框信息更改时,它会创建一个代表此事件的对象,本例中是ActionEvent类型的对象,这个对象包含了此事件与它的引发者text1文本框等相关信息。
类在实现接口中,必须在类的定义接口里只声明未定义的所有方法。因为ActionListener接口只提供了一个actionPerformed()方法,该方法正是要把事件处理程序编写在里面的方法。本例的事件处理程序代码如下:
public void actionPerformed(ActionEvent e) {//事件发生时的处理操作
//提取文本框内容并显示在showlb1、showlb2中
showlb1.setText(“整数为”+text1.getText());
showlb2.setText(“浮点数为”+text2.getText());
}
由于actionPerformed()方法将会接收ActionEvent类型的对象e,这个对象正是事件源btn按钮被单击后所传过来的事件对象。因为程序中要用到ActionEvent类,所以必须用“import java.awt.event.*;”语句加载包含此类的类库。

事件处理类

在前面介绍的事件模型及事件处理机制中,涉及ActionEvent事件类,其实Java语言在java.awt.event包中定义了许多事件类用于处理各种用户操作所产生的事件,它们都继承自java.awt包中的AWTEvent类。
java.util.EventObject类是所有事件对象的基础父类,所有事件都是由它派生出来的。AWT的相关事件继承与java.awt.AWTEvent类,这些AWT事件分为两大类:低级事件和高级事件。

1.低价事件
低级事件是指基于组件和容器的事件,当一个组件上发生事件,如鼠标的进入、单击、拖放等,或组件的窗口开关等,触发组件事件。
(1)ComponentEvent组件事件:组件尺寸的变化、移动。
(2)ContainerEvent容器事件:组件增加、移动。
(3)WindowEvent窗口事件:包括用户单击关闭按钮,窗口得到与失去焦点,窗口最小化等。
(4)FocusEvent焦点事件:焦点的获得和丢失。
(5)KeyEvent键盘事件:键按下、释放。
(6)MouseEvent鼠标事件:包括鼠标按下、鼠标释放、鼠标单击等。

2.高级事件(语义事件)
高级事件是基于语义的事件,它可以不和特定的动作相关联,而依赖于触发此事件的类。例如,在JTextField中按Enter键会触发ActionEvent事件,滑动滚动条会触发AdjustmentEvent事件,选中项目列表的某一条就会触发ItemEvent事件。
(1)ActionEvent动作事件:对应一个动作事件,它不是代表一个具体的动作,而是一种语义。如按钮按下,在JTextField中按Enter键。
(2)AdjustmentEvent调节事件:在滚动条上移动滑块以调节数值。
(3)ItemEvent项目事件:选择项目,不选择“项目改变”。
(4)TextEvent文本事件:文本对象改变。
对于每个事件类,几乎都有相应的事件监听者。Java语言的事件监听者绝大多数都是以接口的形式给出的,这些接口都是继承自java.util.EventListener接口。
一个事件监听器对象负责处理一类事件。一类事件的每一张发生情况,分别由事件监听器对象中的一个方法来具体处理。在事件源和事件监听器对象中进行约定的接口类,被称为事件监听器的接口。事件监听器接口类的名称与事件类的名称相对应,例如,MouseEvent事件类的监听器接口名为MouseListener。

事件适配器

Java语言类的层次非常分明,它只支持单继承。为了实现多重继承的能力,Java用接口来实现,一个类可以实现多个接口,这种机制比多重继承具有更简单、更灵活、更强的功能。在AWT中就经常用到声明和实现多个接口。请记住:无论实现了几个接口,接口中已定义的方法就必须一一实现;如果对某事件不感兴趣,可以不具体实现其方法,而用空的方法体来代替,但所有方法都必须要写上。这样一来会有一些不便。为了解决这个问题,AWT使用了适配器(Adapter),Java语言为一些Listener接口提供了适配器类(Adapter)。可以通过继承事件所对应的Adapter类,重写所需要的方法,无关的方法则不用实现。事件适配器为提供了一种简单的实现监听的手段,可以缩短程序代码。

案例分析:银行系统事件类综合应用

Java语言-BankEvent_Exam

你可能感兴趣的:(Java语言)