`
vbsvb
  • 浏览: 15743 次
  • 性别: Icon_minigender_1
  • 来自: 苏州
最近访客 更多访客>>
社区版块
存档分类
最新评论

Swing组件集合的事件处理(六)

阅读更多

  请记住,Swing组件是构建在AWT库之上的,Swing组件库具有一些改进的功能从而使得事件处理更为简单。功能改进覆盖AWT核心事件处理特性之上,由基本的动作监听到焦点管理。 
  为了简化事件处理,Swing库使用Action接口扩展了原始的ActionListener接口来存储具有事件处理器的可视属性。这使得事件处理器的创建独立于可视化组件。然后,当Action在稍后与一个组件相关联时,组件直接由事件处理器自动获取信息(例如按钮标签)。这包括当Action被修改时更新标签的通知。AbstractAction与TextAction类实现了这个概念。 
  Swing库同时添加了KeyStroke类从而使得我们更容易的响应键盘事件。当一个特定的击键序列被按下时,我们可以通知组件必须响应特定的动作,而无需监听一个特定键的所有按键事件。这些击键到动作的映射存储在InputMap与ActionMap对象的组合中。当组件容器具有信息时,InputMap就会特例化ComponentInputMap。Swing文本组件借助于Keymap接口可以更容易的使用这些来存储击键到动作的映射。第16章更详细的描述了TextAction支持的映射,以及文本事件处理功能的其余部分。 
  KeyboardFocusManager与DefaultKeyboardFocusManager,借助于FocusTraversalPolicy及其实现的帮助,管理焦点子系统。InputVerifier用于用户输入验证。这些内容都会在本章稍后的Swing组件管理部分进行讨论。  Action接口是ActionListener接口的扩展,他可以非常灵活的用于定义与作为触发代理的组件相独立的共享事件处理器。这个接口实现了ActionListener,并且定义了一个查询表数据结构,其键值作为属性。然后,当Action与一个组件相关联时,这些显示属性会自动的传递到Action。下面是接口定义:  publicinterface Action implements ActionListener { // Constants publicfinalstatic String ACCELERATOR_KEY; publicfinalstatic String ACTION_COMMAND_KEY; publicfinalstatic String DEFAULT; publicfinalstatic String LONG_DESCRIPTION; publicfinalstatic String MNEMONIC_KEY; publicfinalstatic String NAME; publicfinalstatic String SHORT_DESCRIPTION; publicfinalstatic String SMALL_ICON; // Listenerspublicvoid addPropertyChangeListener(PropertyChangeListener listener); publicvoid removePropertyChangeListener(PropertyChangeListene r listener); // Propertiespublicboolean isEnabled(); publicvoid setEnabled(boolean newValue); // Other methodspublic Object getValue(String key); publicvoid putValue(String key, Object value); }
  因为Action仅是一个接口,Swing提供了一个类来实现这个接口,这就是AbstractAction。  AbstractAction类提供了Action接口的一个默认实现。这就是属性行为实现的地方。 
  使用Action
  一旦我们通过继承定义一个AbstractAction并且提供一个public void actionPerformed(ActionEvent actionEvent)方法,我们就可以将其传递给一些特殊的Swing组件。JCheckBox,JToggleButton,JMenuItem,JCheckBoxMenuItem以及JRadioButtonMenuItem提供了由动作创建组件的构造函数,而Swing文本组件通过Keymap,InputMap以及ActionMap对Action对象提供了内建支持。 
  当具有关联Action的组件被添加到相应的Swing容器中时,选中会触发Action的actionPerformed(ActionEvent actionEvent)方法的调用。组件的显示是通过添加到内部数据结构的属性元素来定义的。了为演示的需要,列表2-8提供了一个具有Print标签以及一个图标的Action。当其被激活时,会输出一个Hello, World消息。  import java.awt.event.*; import javax.swing.*; publicclass PrintHelloAction extends AbstractAction { privatestaticfinal Icon printIcon = new ImageIcon("Print.gif"); PrintHelloAction() { super("Print", printIcon); putValue(Action.SHORT_DESCRIPTION, "Hello, World"); } publicvoid actionPerformed(ActionEvent actionEvent) { System.out.println("Hello, World"); } }
  一旦定义了Action,我们就可以创建Action并将其与我们所希望的组件相关联。  在我们将Action与对象相关联之后,如果我们发现我们需要修改Action的属性,我们只需要在一个地方修改其设置 。因为所有的属性都是绑定的,他们会传播到使用Action的任意组件。例如,禁止Action(printAction.setEnabled(false))将会禁止分别在JMenu与JToolBar上所创建的JMenuItem与JButton。相应的,通过printAction.putValue(Action.NAME, "Hello, World")修改Action的名字将会修改相关联组件的文本标签。 
  图2-6JToolBar与JMenu上的PrintHelloAction的样子。可选中的按钮用来允许或是禁止Action,同时也可以修改其名字。 
  
  此示例的完整代码显示在列表2-9中。不要担心工具栏与菜单栏的创建。我们将会在第6章对其进行详细的讨论。  /** * */package swingstudy.ch02; import java.awt.BorderLayout; import java.awt.EventQueue; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.swing.Action; import javax.swing.JButton; import javax.swing.JFrame; import javax.swing.JMenu; import javax.swing.JMenuBar; import javax.swing.JMenuItem; import javax.swing.JPanel; import javax.swing.JToolBar; /** * @author lenovo * */publicclass ActionTester { /** * @param args */publicstaticvoid main(String[] args) { // TODO Auto-generated method stub Runnable runner = new Runnable() { publicvoid run() { JFrame frame = new JFrame("Action Sample"); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOS E); final Action printAction = new PrintHelloAction(); JMenuBar menuBar = new JMenuBar(); JMenu menu = new JMenu("File"); menuBar.add(menu); menu.add(new JMenuItem(printAction)); JToolBar toolBar = new JToolBar(); toolBar.add(new JButton(printAction)); JButton enableButton = new JButton("Enable"); ActionListener enableActionListener = new ActionListener() { publicvoid actionPerformed(ActionEvent event) { printAction.setEnabled(true); } }; enableButton.addActionListener(enableActionListene r); JButton disableButton = new JButton("Disable"); ActionListener disableActionListener = new ActionListener() { publicvoid actionPerformed(ActionEvent event) { printAction.setEnabled(false); } }; disableButton.addActionListener(disableActionListe ner); JButton relabelButton = new JButton("Relabel"); ActionListener relabelActionListener = new ActionListener() { publicvoid actionPerformed(ActionEvent event) { printAction.putValue(Action.NAME, "Hello, World"); } }; relabelButton.addActionListener(relabelActionListe ner); JPanel buttonPanel = new JPanel(); buttonPanel.add(enableButton); buttonPanel.add(disableButton); buttonPanel.add(relabelButton); frame.setJMenuBar(menuBar); frame.add(toolBar, BorderLayout.SOUTH); frame.add(buttonPanel, BorderLayout.NORTH); frame.setSize(300, 200); frame.setVisible(true); } }; EventQueue.invokeLater(runner); } }
  AbstractAction属性 正如表2-2所示,AbstractAction类有三个可用的属性。 其余的绑定属性通过putValue(String key, Object value)放置在查询表中。获取当前的keys属性设置可以使得我们查看可以进行哪些设置,而不需要进行单独请求。表2-3描述了可以用作键值的Action预定义常量集合。我们也可以添加我们自己的常量,从而在以后动作发生时进行查询。 常量 
  描述 NAME 
  Action名字,用作按钮标签 SMALL_ICON 
  Action图标,用作按钮标签 SHORT_DESCRIPTION 
  Action的简短描述;可以用作提示文本,但是默认情况下并不用 LONG_DESCRIPTION 
  Action的长描述;可以用作访问功能(查看第22章) ACCELERATOR 
  KeyStroke字符串;可以用Action的快捷键 ACTION_COMMAND_KEY 
  InputMap键;映射到与JComponent相关的ActionMap中的Action MNEMONIC_KEY 
  按键代码;可以用作Action的快捷键 DEFAULT 
  可以用于我们自定义属性的未用常量 一旦一个属性已经存放在查询表中,我们可以通过public Object getValue(String key)进行获取。其作用方式类似于java.util.Hashtable类或是java.util.Map接口,区别在于:如果表中存在一个键值,那么我们尝试存入一个具有null值的key/value对,则查询表会移除这个键值。  KeyStroke类以及特定JComponent的inputMap与actionMap属性提供了一个简单的替换可以向组件注册KeyListener对象并监听特定键的按下。KeyStroke使得我们可以定义一个简单的按键集合,例如Shift-Ctrl-P或是F4。然后我们可以通过将其注册到组件来激活按键,并且在组件识别出时通知按键进行动作,从而通知ActionListener。 
  在我们探讨如何创建按键之前,我们先来了解一下可以激活按键的不同条件,从而添加不同的输入映射。有三个条件可以激活已注册的按键,并JComponent中的四个常量可以提供帮助。第四个用于未定义的状态。表2-4中列出了可用的四个常量。 常量 
  描述 WHEN_FOCUSED 
  当实际的组件获得输入焦点时激活按键 WHEN_IN_FOCUSED_WINDOW 
  当组件所在的窗口获得输入焦点时激活按键 WHEN_ANCESTOR_OF_FOCUSED_COMPONENT 
  当在组件或是在组件的容器中按下时激活按键 UNDEFINED_CONDITION 
  用于没有定义条件的情况 构建按键
  KeyStroke类是AWTKeyStroke的子类,并且没有公开的构造函数。我们可以通过下面的方法来创建一个按键:  publicstatic KeyStroke getKeyStroke(char keyChar) publicstatic KeyStroke getKeyStroke(String representation) publicstatic KeyStroke getKeyStroke(int keyCode, int modifiers) publicstatic KeyStroke getKeyStroke(int keyCode, int modifiers, boolean onKeyRelease) publicstatic KeyStroke getKeyStrokeForEvent(KeyEvent keyEvent)
  列表中的第一个版本,public static KeyStroke getKeyStroke(char keyChar),可以使得我们由一个char变量创建按键,例如Z。  public static KeyStroke getKeyStroke(String representation)版本是最有趣的版本。他可以使得我们通过一个文本字符串来指定按键,例如"control F4"。字符串的标识符集合为shift, control, meta, alt, button1, button2与button3以及可以指定的多标识符。字符串的其余部分来自KeyEvent类的VK_*常量。例如,下面的代三为Ctrl-Alt-7定义了一个按键: public static KeyStroke getKeyStroke(int keyCode, int modifiers)public static KeyStroke getKeyStroke(int keyCode, int modifiers,boolean onKeyRelease)是两个最为直接的方法。他允许我们直接指定VK_*常量 以及用于标识符的InputEvent掩码(没有标识符时为0)。当没有指定时,onKeyRelease为false。 列表中的最后一个版本,public static KeyStroke getKeyStrokeForEvent(KeyEvent keyEvent),将特定的KeyEvent直接映射到KeyStroke。当我们希望允许用户使用按键来激活事件时,这个方法就十分有用。我们要求用户为某一事件按下一个键,然后注册KeyEvent,从而下次按键发生时,事件就会被激活。 注册按键
  在我们创建了按键之后,我们需要将其注册到组件。当我们向组件注册一个按键时,我们提供一个当按键按下(或是释放)时要调用的Action。注册要提供一个由按键到Action的映射。首先,我们通过getInputMap(condition)方法获取基于焦点激活条件组件的相应的InputMap。如果没有指定条件,则假定为WHEN_FOCUSED。然后我们在InputMap中添加一个由按键到文本字符串的映射: 如果我们知道已存在动作的动作字符串,我们就可以使用这个字符串;否则我们要定义这个字符串。然后我们使用ActionMap将字符串映射到Action: 我们可以通过共享ActionMap实例来在组件之间共享动作。列表2-10的例子中创建了四个按钮,每一个都注册了不同的按键以及不同的焦点激活条件。按钮标签表明了按键激活条件。Action只是简单的输出消息并激活按钮标签。  /** * */package swingstudy.ch02; import java.awt.EventQueue; import java.awt.GridLayout; import java.awt.event.ActionEvent; import java.awt.event.InputEvent; import java.awt.event.KeyEvent; import javax.swing.AbstractAction; import javax.swing.Action; import javax.swing.ActionMap; import javax.swing.InputMap; import javax.swing.JButton; import javax.swing.JComponent; import javax.swing.JFrame; import javax.swing.KeyStroke; /** * @author lenovo * */publicclass KeyStrokeSample { privatestaticfinal String ACTION_KEY = "theAction"; /** * @param args */publicstaticvoid main(String[] args) { // TODO Auto-generated method stub Runnable runner = new Runnable() { publicvoid run() { JFrame frame = new JFrame("KeyStroke Sample"); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOS E); JButton buttonA = new JButton("FOCUSED
control alt 7"); JButton buttonB = new JButton("FOCUS/RELEASE
VK_ENTER"); JButton buttonC = new JButton("ANCESTOR
VK_F4+SHIFT_MASK"); JButton buttonD = new JButton("WINDOW
' '"); Action actionListener = new AbstractAction() { publicvoid actionPerformed(ActionEvent event) { JButton source = (JButton)event.getSource(); System.out.println("Activated: "+source.getText()); } }; KeyStroke controlAlt7 = KeyStroke.getKeyStroke("control alt 7"); InputMap inputMap = buttonA.getInputMap(); inputMap.put(controlAlt7, ACTION_KEY); ActionMap actionMap = buttonA.getActionMap(); actionMap.put(ACTION_KEY, actionListener); KeyStroke enter = KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0, true); inputMap = buttonB.getInputMap(); inputMap.put(enter, ACTION_KEY); buttonB.setActionMap(actionMap); KeyStroke shiftF4 = KeyStroke.getKeyStroke(KeyEvent.VK_F4, InputEvent.SHIFT_MASK); inputMap = buttonC.getInputMap(JComponent.WHEN_ANCESTOR_OF_FO CUSED_COMPONENT); inputMap.put(shiftF4, ACTION_KEY); buttonC.setActionMap(actionMap); KeyStroke space = KeyStroke.getKeyStroke(' '); inputMap = buttonD.getInputMap(JComponent.WHEN_IN_FOCUSED_WIN DOW); inputMap.put(space, ACTION_KEY); buttonD.setActionMap(actionMap); frame.setLayout(new GridLayout(2,2)); frame.add(buttonA); frame.add(buttonB); frame.add(buttonC); frame.add(buttonD); frame.setSize(400, 200); frame.setVisible(true); } }; EventQueue.invokeLater(runner); } }
  图2-7显示了程序运行时的样子。 
  
  Swing库也可以使用KeyStroke对象用于一些内部功能。两个这样的功能为记忆键与快捷键,其工作如下:  在组件记忆键中,标签中的一个字符以下划线出现。当这个字符平台特定的热键组合被按下时,组件就会被激活。例如,在图2-8所示的窗体中按下Alt-A则会在Windows XP平台下选中About按钮。 
  菜单快捷键可以在菜单条目不可见的情况下激活条目。例如,在图2-8所示的窗体中按下Ctrl-P将会在File菜单不可见的情况下选中Print菜单条目。 
  
分享到:
评论

相关推荐

    Java Swing'组件集合

    关于swing组件的集合,刚刚接触这些的朋友看看,对swing组件有些了解

    经典Swing事例集合

    很多Swing经典事例,包扩各种组件、容器例子

    RComponent.Swing

    RComponent.Swing是RComponent为java开发人员提供的表现层Swing组件集合,100%java实现。提供完整的API,帮助文档。 丰富的Demo和Demo源码。提供免费技术支持。 1.RDatePicker 输入日期数据。 2.RIpAddressField ...

    JAVA教学(关于swing的使用)

    Swing是AWT的扩展,它提供了更强大和更灵活的组件集合。 除了我们已经熟悉的组件如按钮、 复选框和标签外, Swing还包括许多新的组件, 如选项板、 滚动窗口、树、表格。许多一些开发人员已经熟悉的组件,如按钮,在...

    swing-js:轻量级JavaScript组件的集合

    Swing.js是一个轻量级的javascript组件集合,可帮助减少对肿的第三方库的需求。 它的主要目标是: 尽可能减小文件大小。 允许独立加载组件(仅加载所需的组件)。 允许以任何顺序加载组件。 支持所有现代浏览器...

    JAVA Swing 全教程

    Swing包含250多个类,是组件和支持类的集合。Swing提供了40多个组件,是AWT组件的四倍。除提供替代AWT重量组件的轻量组件外,Swing还提供了大量有助于开发图形用户界面的附加组件。

    swing-material:Swing的材料设计组件和实用程序的集合

    摇摆材料Swing的材料设计组件和实用程序的集合。

    Java 界面组件案例集合 众多DEMO

    Java 界面组件案例集合 众多DEMO 适合新手和想学习java 界面开发的朋友使用

    基于集合的学生信息管理系统(含GUI)JAVA版

    是基于集合的学生信息管理系统,因此在批量处理信息时采用集合类对象来储存,本题采用的是ArrayList。 该系统有三大功能,分别是管理员、老师、学生。 管理员除了要实现自己的登录、查看个人信息和修改教师密码以外...

    Java项目实训+推箱子游戏2023版

    3.Swing组件的灵活应用; 4.IO流的应用,读取地图文件,解析地图内容; 5.音频文件的播放,实训播放背景音乐功能; 6.java事件的应用,如ActionListener,ItemListener等事件; 7.内部类的应用。 8.绘图功能的的灵活...

    AWT基础知识

    3. 为了保证程序的可移植性,AWT组件集遵循最大公约数原则,即AWT只拥有所有平台上都存在的组件的公有集合。有些常用的组件不支持,比如:表、树、进度条等。字体也只能支持4种。 为什么还需要学习AWT? 实际开发中...

    java从入门到精通视频教程(全94讲)学习笔记整理(齐全).docx

    坦克大战,简易QQ界面......P1第1讲-内容介绍....-事件处理.坦克大战3 -事件监听.坦克大战4 -事件总结.坦克大战5 -线程.坦克大战6 -线程.坦克大战7 -线程 -坦克大战8 -坦克大战9 -io编程.坦克大战10 -io编程

    OpenSwing---Java 常用控件集合

    对几乎所有的组件全部加入了JavaBeans处理, 使OpenSwing支持可视开发. 2005/04/17 将JNumberField最大长度,小数位长度修正成符合数据库定义的规范,如:NUMBER(10,2) 2005/04/21 修改了JNumberField的参数方式及不能...

    javaswing程序源码-java-book:《Java编程:综合入门》一书的源代码

    编程进行概述,阐述组件、事件、布局管理器的基本概念,然后依次对 Swing 组件、菜单、对话框、绘图等进行介绍。 第三部分(第22~27章)探究 Java API 库的部分内容,其中包括 java.lang 包和 java.util 包的大部分...

    j2sePPT教案与事例

    包括OOP概述、java语言概述、JAVA编程基础、类和对象、类的高级特性6、字符与字符串7、数组8、断言9、异常和垃圾收集10、内部类11、反射12、gui编程13、swing结构与布局管理器14、AWT事件模型15、swing用户界面组件...

    个人简易版坦克大战,能保存数据,但没音效

    java基础,使用一些Swing组件,线程,集合

    JAVA学习手册CHM版

    本书以初学者为核心,全面介绍了使用Java进行程序开发的各种...第3篇为高级篇,包括Swing基础知识、JDBC技术、Swing高级组件、GUI事件处理机制、网络程序设计;第4篇为实战篇,包括进销存管理系统、 企业内部通信系统。

    tomproject:有用的Java组件和算法的集合

    这些算法包括桌面应用程序内存管理器,Swing实用程序,Swing接口转换以及许多Swing的组件扩展。 TomProject最初将提供葡萄牙语和英语组件界面。 TomProject的一些功能: TomFrame提供了已配置的框架以供一般使用...

    java 核心技术卷一 光盘 资料

    这是一个txt文件,迅雷下载地址,复制,新建,下载就可以了 ...第8章 事件处理 第9章 Swing用户界面组件 第10章 部署应用程序和applet 第11章 异常、日志、断言和调试 第12章 泛型程序设计 第13章 集合 第14章 多线程

    Java综合实验---学生信息管理系统

    5) 使用迭代器遍历集合并输出集合的元素,将排序后输出的结果写入out.txt文件中,IO操作需要有异常处理; 例如:定义学生父类和不同阶段学生子类(本科生、研究生等),包含学生信息(学号、姓名、成绩或年龄等),...

Global site tag (gtag.js) - Google Analytics