【问题标题】:JDialog doesn't trigger PropertyChangeListenerJDialog 不会触发 PropertyChangeListener
【发布时间】:2015-03-31 16:01:06
【问题描述】:

我的小程序中有两个类似的 JDialog,它们都作用于文本字段中给出的输入,并具有 Enter 和 Cancel 按钮。我在两个对话框中都添加了一个属性监听器,但是只有一个对话框触发了属性监听器,而不是第二个。使用我正在滥用且不知道的 PropertyListener 是否存在某种限制。我在下面展示了我的 propertyChange() 方法的代码。 addQuestionDialog 工作得非常好,但是 nameDialog 只是不会触发 propertyChange 事件,因为我添加的任何打印语句都没有出现在我的控制台中。起初我想也许条件 (JOptionPane.VALUE_PROPERTY.equals(prop) || JOptionPane.INPUT_VALUE_PROPERTY.equals(prop)) 从来都不是真的,但把这些从“if”块中取出并没有什么不同。其次,我想也许我只是没有为 nameDialog 添加属性侦听器,但我已经检查过了,它肯定已经添加了。我不知道还有什么可能导致该问题,因为 addQuestionDialog 几乎相似并且工作正常。

public void propertyChange(PropertyChangeEvent e) {
    String prop = e.getPropertyName();

    if (addQuestionDialog.isVisible() && (e.getSource() == addQuestionPane) && (JOptionPane.VALUE_PROPERTY.equals(prop) || JOptionPane.INPUT_VALUE_PROPERTY.equals(prop))) {
        Object value = addQuestionPane.getValue();
        if (value == JOptionPane.UNINITIALIZED_VALUE) {
            //ignore reset
            return;
        }

        //Reset the JOptionPane's value.
        //If you don't do this, then if the user
        //presses the same button next time, no
        //property change event will be fired.
        addQuestionPane.setValue(JOptionPane.UNINITIALIZED_VALUE);

        if (value.equals("Enter")) {
            String questionTypedText = questionTextField.getText();
            String mqlYesTypedText = mqlYesTextField.getText();
            String mqlNoTypedText = mqlNoTextField.getText();

            sqlModel.addQuestion(questionTypedText, mqlYesTypedText, mqlNoTypedText);
            questionTextField.setText("");
            mqlYesTextField.setText("");
            mqlNoTextField.setText("");
        } else { //user closed dialog or clicked cancel
            addQuestionDialog.setVisible(false);
        }
    }

    else if (nameDialog.isVisible() && (e.getSource() == namePane) && (JOptionPane.VALUE_PROPERTY.equals(prop) || JOptionPane.INPUT_VALUE_PROPERTY.equals(prop))) {
        Object value = namePane.getValue();
        System.out.println("Entered name dialog box");

        if (value == JOptionPane.UNINITIALIZED_VALUE) {
            //ignore reset
            return;
        }
        //reset value
        namePane.setValue(JOptionPane.UNINITIALIZED_VALUE);

        if (value.equals("Enter")) {
            System.out.println("gonna add new celeb from input");
            sqlModel.addCelebrity(alreadyAskedQuestions, columnValues, nameTextField.getText());
        }
        //else, user clicked cancel, in either case, close the Dialog box
        nameDialog.setVisible(false);
        initGUI();
    }
}

编辑:我尝试为 nameDialog 添加单独的 PropertyListener,但 nameDialog 仍然没有触发事件。

        nameDialog.addPropertyChangeListener(new PropertyChangeListener() {

                @Override
                public void propertyChange(PropertyChangeEvent e) {
                    String prop = e.getPropertyName();
                    if (nameDialog.isVisible() && (e.getSource() == namePane) && (JOptionPane.VALUE_PROPERTY.equals(prop) || JOptionPane.INPUT_VALUE_PROPERTY.equals(prop))) {
                        Object value = namePane.getValue();
                        System.out.println("Entered name dialog box");

                        if (value == JOptionPane.UNINITIALIZED_VALUE) {
                            //ignore reset
                            return;
                        }
                        //reset value
                        namePane.setValue(JOptionPane.UNINITIALIZED_VALUE);

                        if (value.equals("Enter")) {
                            System.out.println("gonna add new celeb from input");
                            sqlModel.addCelebrity(alreadyAskedQuestions, columnValues, nameTextField.getText());
                        }
                        //else, user clicked cancel, in either case, close the Dialog box
                        nameDialog.setVisible(false);
                        initGUI();  
                    }
                }
            });

【问题讨论】:

  • 您的问题本质上是“为什么我的代码没有按预期工作”之一。为了获得最佳和最快的答案,您需要创建并发布minimal example program or mcve
  • 另请注意,您自己可以在代码中为 JDialog 的 SwingPropertyChangeSupport 触发通知事件。例如,如果按下按钮,您可以调用firePropertyChange(...),但如果您这样做,请确保您将所有这些方法都放在包含侦听器的同一个对象上,否则不会发生任何事情。
  • 所以你想让我从头开始我的项目,这样我就可以发布一个更好的问题。我确信这个问题没有那么大,我想不出如何比我已经知道的更清楚地解释它。我只是想知道为什么一个对话框会触发属性更改,而第二个对话框不会。
  • 安德鲁,我不是要你做什么。但是,如果您没有很快得到答案,那么是的,我会建议您考虑从头开始编写一个新程序,该程序可以完全暴露您的问题,因为这是一个有用的工具,不仅是为了在这里提问,也是为了自己解决问题。你是否这样做对我没有任何影响,因为我不是提出这个问题的人。但我以前在你的位置上做过这件事,所以我尊重这个工具。

标签: java swing jdialog propertychangelistener


【解决方案1】:

我会简化代码来解决问题。

您似乎对两个不同的组件使用相同的侦听器,但行为不同。我建议将您的听众分成两个(或更多)实例。

只需为每个对话框关联一个侦听器,而不是试图找出它从哪里来。它将更容易理解正在发生的事情,并且总体上更容易阅读。

如果您要监控多个属性,并产生不同的结果,您甚至可以改用addPropertChangeListener(String propertyName, PropertyChangeListener listener),并为每个发射器、每个属性创建一个侦听器。

【讨论】:

  • 我尝试为 nameDialog 添加一个新的 PropertyListener,如我编辑的问题所示,但是 nameDialog 仍然不会触发事件。对不同的组件使用不同的侦听器总是最好的,因为我认为根据事件源拆分单个侦听器可以完成相同的工作。
  • 致 Gnoupi,1+ 为(对我而言)一个令人困惑的问题提供了一个体面的答案。 @AndrewBrick:希望这意味着您的问题现已得到充分回答,并且您知道如何从这里开始。请告诉我们最新情况是否如此。谢谢。
  • @AndrewBrick - 我看到您放置了一个新的 PropertyListener,但您保持其内容相同。在这种情况下,您不需要检查对话框是否可见,也不需要检查源。当你说它不触发事件时,你的意思是你在调试时从未进入 propertyChange 方法,或者你没有得到你在其中编码的动作?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-01-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多