事件的重点

时间:2013-04-10 13:00:37

标签: java swing events

这是我对Swing的问题:
想象框架有一个文本字段和一个按钮。在这个框架后面有一个带有一个字段的数据类。

  • textfield具有FocusListener,它使用FocusOut上的textfield中的值更新数据类字段
  • 按钮具有ActionListener,它在点击
  • 时将数据类发送到服务器

如果我修改了文本字段中的值并立即单击该按钮,则有时会将具有旧值的数据类发送到服务器。在我看来,无法保证在按钮的ActionPerformed事件之前处理TextOut的事件。如果是这样,有什么方法可以保护它吗?我的意思是一些干净的方式,如果没有必要的话,我不想对它全部肮脏。

4 个答案:

答案 0 :(得分:2)

只是为了好玩,一个穷人用InputVerifier实现的单向绑定:请注意,在传输焦点之前保证inputVerifier被访问(并且似乎在jdk的当前版本中工作 - 在旧版本中有一些问题) ),因此只要在提交操作中涉及焦点转移,在验证程序中进行任何更新都应该是安全的:

验证者和一些原始数据对象:

/**
 * Very simple uni-directional binding (component --> data) class.
 */
public static class BindingVerifier extends InputVerifier {

    private RawData data;
    private boolean first;
    public BindingVerifier(RawData data, boolean first) {
        this.data = data;
        this.first = first;
    }


    @Override
    public boolean shouldYieldFocus(JComponent input) {
        String text = ((JTextComponent) input).getText();
        if (first) {
            data.one = text;
        } else {
            data.two = text;
        }
        return true;
    }


    @Override
    public boolean verify(JComponent input) {
        return true;
    }

}

public static class RawData {
    String one;
    String two;
    public RawData(String one, String two) {
        this.one = one;
        this.two = two;
    }

    public String toString() {
        return one + "/" + two;
    }
}

用法:

final RawData data = new RawData(null, null);
JTextField first = new JTextField(20);
first.setInputVerifier(new BindingVerifier(data, true));
JTextField second = new JTextField(20);
second.setInputVerifier(new BindingVerifier(data, false));
Action commit = new AbstractAction("commit") {

    @Override
    public void actionPerformed(ActionEvent e) {
        System.out.println(data);
    }
};
JComponent form = new JPanel();
form.add(first);
form.add(second);
form.add(new JButton(commit));

答案 1 :(得分:1)

你可以这样做。我只给出一个伪代码。

private boolean check = false;

txtField FocusOutMethod {
 check = true;
}

button ActionPerformedMethod(){

 if(check){

      place your code that you want to execute in button click.

      check = false;
 }
}

这样,actionPerformed方法只会在focusOut方法的执行后运行你的代码。

答案 2 :(得分:1)

  • 在Swing中不可能,不能在一个监听器中排序事件,而不是在两个或多个监听器触发事件​​的情况下,
  

如果我在文本字段中修改值并立即单击该按钮,   具有旧值的数据类有时会发送到服务器。在我看来   无法保证文本字段的FocusOut事件将是   在ActionPerformed事件按钮之前处理。如果是这样,是否有一些   如何保护它的方式?我的意思是一些干净的方式,我不想全力以赴   如果没有必要,那就脏了。

  • 焦点是异步的,但在所有情况下触发正确的事件,问题可能在您的代码中

  • 监听器的某些组合可能导致无限循环(事件被触发延迟),然后你的控制器可以触发错误的事件命令

答案 3 :(得分:1)

  

如果我修改了文本字段中的值并立即单击该按钮,则有时会将具有旧值的数据类发送到服务器。在我看来,无法保证在按钮的ActionPerformed事件之前处理TextOut的事件。如果是这样,有什么方法可以保护它吗?

以不同方式设计表单。也就是说,当您单击按钮时,ActionListener应在窗体上的所有文本字段上调用getText()方法。