【问题标题】:How to make difference between textField.setText() and adding text to textField manually in java?如何区分 textField.setText() 和在 java 中手动向 textField 添加文本?
【发布时间】:2012-06-22 14:49:21
【问题描述】:

我的应用程序中有一个 textField,当用户单击 JList 中的一个项目时,它将以编程方式 (textField.setText() ) 启动。 以后用户将手动更改此值。 我坚持使用文档侦听器来检测此文本字段中的更改。 当以编程方式发生更改时,它必须什么都不做,但如果手动发生,它应该将背景更改为红色。

如何检测textField是手动填写还是textField.setText()填写?

txtMode.getDocument().addDocumentListener(new DocumentListener() {
        public void insertUpdate(DocumentEvent e) {
            if (!mode.equals(e.getDocument()))
            txtMode.setBackground(Color.red);
        }

        public void removeUpdate(DocumentEvent e) {
            if (mode.equals(e.getDocument()))
            txtMode.setBackground(Color.white);              
        }

        public void changedUpdate(DocumentEvent e) {
            //To change body of implemented methods
        }
    });

【问题讨论】:

    标签: java swing jtextfield documentlistener


    【解决方案1】:

    有两种方法

    • 删除 DocumentListener 之前的 setText("...") 添加 DocumentListener 如果完成则返回

    代码

    public void attachDocumentListener(JComponent compo){
          compo.addDocumentListener(someDocumentListener);
    }
    
    //similair void for remove....
    
    • 使用boolean 值禁用“如果需要”,但您必须更改DocumentListener 的内容

    例如

     txtMode.getDocument().addDocumentListener(new DocumentListener() {
        public void insertUpdate(DocumentEvent e) {
            if (!mode.equals(e.getDocument()))
    
            if (!updateFromModel){
               txtMode.setBackground(Color.red);
            }  
        }
    
        public void removeUpdate(DocumentEvent e) {
            if (mode.equals(e.getDocument()))
    
            if (!updateFromModel){
               txtMode.setBackground(Color.white);
            }  
        }
    
        public void changedUpdate(DocumentEvent e) {
            //To change body of implemented methods
        }
    });
    

    【讨论】:

    • 这里的问题是,有时 setText() 被不是您自己的代码的人调用。无论如何,这是我目前正在解决的问题。我希望他们可以在每个事件上都有一个 wasTriggeredByUser()。
    • @Trejkaz 请问如何,在哪里,为什么,有什么特殊原因,顺便说一句,文档是 JTextComponents 的模型,然后消费/触发模型之间的所有更改/事件以查看,反之亦然
    【解决方案2】:

    请记住,所有事件侦听器都在 Swing 事件线程上执行。因此,事情可能不会按照您希望的顺序进行。在这种情况下,任何解决方案都将是 hack-ish,因为您无法完全控制 swing 线程以及谁在其上发布事件。

    我想说的是:假设您选择使用一些标志来让您的听众知道这是一个程序性更改。这是可能的情况(我假设您遵循通过 invokeLater 从 swing 线程进行任何 UI 更新的良好规则):

    1. 设置标志以跳过事件
    2. 设置文本
    3. 将标志设置为假

    如果您在一次调用中完成所有操作,setText 将触发发布到事件队列末尾的更新事件,因此,当它们被执行时,该标志已经为 false。

    因此,您应该在一个 invokeLater 甚至是 invokeAndWait 调用中执行第 1 步和第 2 步,然后使用 invokeLater 发布另一个事件以取消设置标志。并祈祷您的用户不要这么快在这两个调用之间进行一些更改,否则,它们也将被视为程序化更改。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2023-04-08
      • 2020-05-12
      • 1970-01-01
      • 2019-10-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多