【问题标题】:getting source of KeyEvent获取 KeyEvent 的来源
【发布时间】:2012-10-24 09:57:48
【问题描述】:

我有两个文本字段(tf1 和 tf2),其中使用了 KeyEvent 来获取键入的字符。

JTextField tf1 = new JTextField(10);
        JTextField tf2 = new JTextField(10);
        tf1.setFocusable(true);
        tf2.setFocusable(true);
        //regerstring for event
        tf1.addKeyListener(new KeyHandler(tf1, tf2));
        tf2.addKeyListener(new KeyHandler(tf1, tf2));








 class KeyHandler extends KeyAdapter{
    JTextField tf1;
    JTextField tf2;
    KeyHandler(JTextField tf1, JTextField tf2){
    tf1 = this.tf1;
    tf2 = this.tf2;
    }
    public void keyTyped(KeyEvent e){
    char ch = e.getKeyChar();
    System.out.println(e.getKeyLocation());

    if(e.getSource() == tf1)
        System.out.println("tf1");
    else if (e.getSource() == tf2)
    System.out.println("tf2");

    }

我尝试过 KeyEvent 类的 getSource() 但它返回 JTextField 的对象,我必须区分 tf1 和 tf2。

如何在 keyTyped() 中获取关联的文本文件引用

【问题讨论】:

  • 为什么 getSource() 不起作用?
  • 为什么使用 KeyListener 而不是 DocumentListener 或 DocumentFilter?
  • @lewstherin 我建议文本字段在本地声明,而不是实例字段
  • @MadProgrammer 是的,好点。看起来答案已被编辑以反映它;)

标签: java swing jtextfield keylistener keyevent


【解决方案1】:

很难 100% 确定,但您似乎遇到了范围问题。您的密钥处理程序看不到您的字段。

public void someMethod() {
    JTextField tf1 = new JTextField(10);
    JTextField tf2 = new JTextField(10);

    KeyHandler handler = new KeyHandler();
    tf1.addKeyListener(handler);
    tf2.addKeyListener(handler);
}

public class KeyHandler extends KeyAdapter{
    public void keyTyped(KeyEvent e){
        // Error, tf1 is unknown...
        if (e.getSource() == tf1) {...}
    }
}

如果您希望能够比较您拥有的字段,您有两种选择。将字段声明为实例字段或通过其name 属性标识字段。

选项 1

public class SomeClass extends ... {
    private JTextField tf1;
    private JTextField tf2;
    public void someMethod() {
        JTextField tf1 = new JTextField(10);
        JTextField tf2 = new JTextField(10);

        KeyHandler handler = new KeyHandler();
        tf1.addKeyListener(handler);
        tf2.addKeyListener(handler);
    }

    public class KeyHandler extends KeyAdapter{
        public void keyTyped(KeyEvent e){
            // tf1 is now within scope :D
            if (e.getSource() == tf1) {...}
        }
    }
 }

选项 2

public void someMethod() {
    JTextField tf1 = new JTextField(10);
    tf1.setName("tf1");
    JTextField tf2 = new JTextField(10);
    tf2.setName("tf2");

    KeyHandler handler = new KeyHandler();
    tf1.addKeyListener(handler);
    tf2.addKeyListener(handler);
}

public class KeyHandler extends KeyAdapter{
    public void keyTyped(KeyEvent e){
        Object source = e.getSource();
        if (source instanceof JTextField) {
            JTextField field = (JTextField)source;
            String name = field.getName();
            if ("tf1".equals(name)) {
                // Hello TextField #1
            }
        }
    }
}

免责声明

现在,我不知道你为什么要做你想做的事,但KeyListeners 不是过滤或监视文本字段更改的最合适的选项。一方面,您无法保证以什么顺序调用您的侦听器,Document 字段可能会或可能不会在侦听器被触发之前更新。其次,如果用户将文本粘贴到字段中,它们不会被触发。

更好的选择是使用DocumentListener,可用于监视字段Document 的更改或DocumentFilter,可用于过滤发送到文档的内容。

【讨论】:

  • -100 重新发明轮子,错误的方式(我很清楚你喜欢 KeyListener,也许 AWTEvent 是更好的方式,只需要关注 Container),+1 Disclaimer
  • @mkorbel 实际上我没有,我更喜欢文档侦听器/过滤器和键绑定...在很大程度上要感谢您,这个问题含糊不清且没有上下文。我的意图是尝试引导 OP 喝水,然后给他们提供冰淇淋;)
  • @mkorbel 我有没有提到我同意你的看法
【解决方案2】:

【讨论】:

    【解决方案3】:

    比较地址如下:

    if (e.getSource() == tf1) { 
       // Source is the first text field
    }
    

    正如 MadProgrammer 指出的那样,您需要在创建范围之外使用文本字段的实例变量(在您的情况下为 tf1 和 tf2)

    【讨论】:

    • 从 OP 看来,tf1 & tf2 不是实例变量,而是在本地声明的,您可能需要指出这一点;)
    • Dorothy,恐怕我们不再使用 Javascript。您不能只访问外部范围内的变量:-)
    【解决方案4】:
    public void keyTyped(KeyEvent e) {
        // retries the typed character
        char ch = e.getKeyChar();
        System.out.println(ch);
        if (e.getComponent().getName().equals("TF1")) {
            // Key Typed in Text Field 1
        } else if (e.getComponent().getName().equals("TF2")) {
            // Key Typed in Text Field 2
        }
        // associated textfield of typed char
    }
    

    使用 tf1.setName("TF1") 设置单个文本框的名称

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-09-30
      • 2011-04-06
      • 1970-01-01
      • 2018-12-03
      • 1970-01-01
      • 2017-12-28
      相关资源
      最近更新 更多