返回介绍

13.16.2 事件和接收者类型

发布于 2024-10-15 23:56:29 字数 15204 浏览 0 评论 0 收藏 0

所有 AWT 组件都被改变成包含 addXXXListener() 和 removeXXXListener() 方法,因此特定的接收器类型可从每个组件中增加和删除。我们会注意到“XXX”在每个场合中同样表示自变量的方法,例如,addFooListener(FooListener fl)。下面这张表格总结了通过提供 addXXXListener() 和 removeXXXListener() 方法,从而支持那些特定事件的相关事件、接收器、方法以及组件。

事件,接收器接口及添加和删除方法 支持这个事件的组件

Event, listener interface and add- and remove-methods

Components supporting this event

ActionEvent
ActionListener
addActionListener( )
removeActionListener( )

Button , List , TextField, MenuItem, and its derivatives including CheckboxMenuItem , Menu, and PopupMenu

AdjustmentEvent
AdjustmentListener
addAdjustmentListener( )
removeAdjustmentListener( )

Scrollbar
Anything you create that implements the Adjustable interface

ComponentEvent
ComponentListener
addComponentListener( )
removeComponentListener( )

Component and its derivatives, including Button , Canvas , Checkbox , Choice , Container , Panel , Applet , ScrollPane , Window , Dialog , FileDialog, Frame , Label , List , Scrollbar , TextArea, and TextField

ContainerEvent
ContainerListener
addContainerListener( )
removeContainerListener( )

Container and its derivatives, including Panel , Applet , ScrollPane , Window , Dialog , FileDialog, and Frame

FocusEvent
FocusListener
addFocusListener( )
removeFocusListener( )

Component and its derivatives, including Button , Canvas , Checkbox , Choice , Container , Panel , Applet , ScrollPane , Window , Dialog , FileDialog, Frame Label , List , Scrollbar , TextArea, and TextField

KeyEvent
KeyListener
addKeyListener( )
removeKeyListener( )

Component and its derivatives, including Button , Canvas , Checkbox , Choice , Container , Panel , Applet , ScrollPane , Window , Dialog , FileDialog, Frame , Label , List , Scrollbar , TextArea, and TextField

MouseEvent (for both clicks and motion)
MouseListener
addMouseListener( )
removeMouseListener( )

Component and its derivatives, including Button , Canvas , Checkbox , Choice , Container , Panel , Applet , ScrollPane , Window , Dialog , FileDialog, Frame , Label , List , Scrollbar , TextArea, and TextField

MouseEvent[55] (for both clicks and motion)
MouseMotionListener
addMouseMotionListener( )
removeMouseMotionListener( )

Component and its derivatives, including Button , Canvas , Checkbox , Choice , Container , Panel , Applet , ScrollPane , Window , Dialog , FileDialog, Frame , Label , List , Scrollbar , TextArea, and TextField

WindowEvent
WindowListener
addWindowListener( )
removeWindowListener( )

Window and its derivatives, including Dialog , FileDialog, and Frame

ItemEvent
ItemListener
addItemListener( )
removeItemListener( )

Checkbox , CheckboxMenuItem , Choice , List, and anything that implements the ItemSelectable interface

TextEvent
TextListener
addTextListener( )
removeTextListener( )

Anything derived from TextComponent , including TextArea and TextField

⑤:即使表面上如此,但实际上并没有 MouseMotiionEvent(鼠标运动事件)。单击和运动都合成到 MouseEvent 里,所以 MouseEvent 在表格中的这种另类行为并非一个错误。

可以看到,每种类型的组件只为特定类型的事件提供了支持。这有助于我们发现由每种组件支持的事件,如下表所示:

组件类型 支持的事件

Component type

Events supported by this component

Adjustable

AdjustmentEvent

Applet

ContainerEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Button

ActionEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Canvas

FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Checkbox

ItemEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

CheckboxMenuItem

ActionEvent, ItemEvent

Choice

ItemEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Component

FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Container

ContainerEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Dialog

ContainerEvent, WindowEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

FileDialog

ContainerEvent, WindowEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Frame

ContainerEvent, WindowEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Label

FocusEvent, KeyEvent, MouseEvent, ComponentEvent

List

ActionEvent, FocusEvent, KeyEvent, MouseEvent, ItemEvent, ComponentEvent

Menu

ActionEvent

MenuItem

ActionEvent

Panel

ContainerEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

PopupMenu

ActionEvent

Scrollbar

AdjustmentEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

ScrollPane

ContainerEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

TextArea

TextEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

TextComponent

TextEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

TextField

ActionEvent, TextEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

Window

ContainerEvent, WindowEvent, FocusEvent, KeyEvent, MouseEvent, ComponentEvent

一旦知道了一个特定的组件支持哪些事件,就不必再去寻找任何东西来响应那个事件。只需简单地:

(1) 取得事件类的名字,并删掉其中的“Event”字样。在剩下的部分加入“Listener”字样。这就是在我们的内部类里需要实现的接收器接口。

(2) 实现上面的接口,针对想要捕获的事件编写方法代码。例如,假设我们想捕获鼠标的移动,所以需要为 MouseMotiionListener 接口的 mouseMoved() 方法编写代(当然还必须实现其他一些方法,但这里有捷径可循,马上就会讲到这个问题)。

(3) 为步骤 2 中的接收器类创建一个对象。随自己的组件和方法完成对它的注册,方法是在接收器的名字里加入一个前缀“add”。比如 addMouseMotionListener()。

下表是对接收器接口的一个总结:

接收器接口 接口中的方法

Listener interface
w/ adapter

Methods in interface

ActionListener

actionPerformed(ActionEvent)

AdjustmentListener

adjustmentValueChanged(
AdjustmentEvent)

ComponentListener
ComponentAdapter

componentHidden(ComponentEvent)
componentShown(ComponentEvent)
componentMoved(ComponentEvent)
componentResized(ComponentEvent)

ContainerListener
ContainerAdapter

componentAdded(ContainerEvent)
componentRemoved(ContainerEvent)

FocusListener
FocusAdapter

focusGained(FocusEvent)
focusLost(FocusEvent)

KeyListener
KeyAdapter

keyPressed(KeyEvent)
keyReleased(KeyEvent)
keyTyped(KeyEvent)

MouseListener
MouseAdapter

mouseClicked(MouseEvent)
mouseEntered(MouseEvent)
mouseExited(MouseEvent)
mousePressed(MouseEvent)
mouseReleased(MouseEvent)

MouseMotionListener
MouseMotionAdapter

mouseDragged(MouseEvent)
mouseMoved(MouseEvent)

WindowListener
WindowAdapter

windowOpened(WindowEvent)
windowClosing(WindowEvent)
windowClosed(WindowEvent)
windowActivated(WindowEvent)
windowDeactivated(WindowEvent)
windowIconified(WindowEvent)
windowDeiconified(WindowEvent)

ItemListener

itemStateChanged(ItemEvent)

TextListener

textValueChanged(TextEvent)

1. 用接收器适配器简化操作

在上面的表格中,我们可以注意到一些接收器接口只有唯一的一个方法。它们的执行是无轻重的,因为我们仅当需要书写特殊方法时才会执行它们。然而,接收器接口拥有多个方法,使用起来却不太友好。例如,我们必须一直运行某些事物,当我们创建一个应用程序时对帧提供一个 WindowListener,以便当我们得到 windowClosing() 事件时可以调用 System.exit(0) 以退出应用程序。但因为 WindowListener 是一个接口,我们必须执行其它所有的方法即使它们不运行任何事件。这真令人讨厌。

为了解决这个问题,每个拥有超过一个方法的接收器接口都可拥有适配器,它们的名我们可以在上面的表格中看到。每个适配器为每个接口方法提供默认的方法。(WindowAdapter 的默认方法不是 windowClosing(),而是 System.exit(0) 方法。)此外我们所要做的就是从适配器处继承并过载唯一的需要变更的方法。例如,典型的 WindowListener 我们会像下面这样的使用。

class MyWindowListener extends WindowAdapter {
  public void windowClosing(WindowEvent e) {
    System.exit(0);
  }
}

适配器的全部宗旨就是使接收器的创建变得更加简便。

但所谓的“适配器”也有一个缺点,而且较难发觉。假定我们象上面那样写一个 WindowAdapter:

class MyWindowListener extends WindowAdapter {
  public void WindowClosing(WindowEvent e) {
    System.exit(0);
  }
}

表面上一切正常,但实际没有任何效果。每个事件的编译和运行都很正常——只是关闭窗口不会退出程序。您注意到问题在哪里吗?在方法的名字里:是 WindowClosing(),而不是 windowClosing()。大小写的一个简单失误就会造成一个崭新的方法。但是,这并非我们关闭窗口时调用的方法,所以当然没有任何效果。

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文