2014-09-29 49 views
1

我已经实现了一个JDialog,它沿着this previous question中的顶级答案的行。该代码的工作原理完全不同于以下事实:当提供无效输入时,只有一个需要时会发生两个PropertyChangedEvents。这导致下面的SSCCE的配方:JDialog属性更改了行为

import java.beans.PropertyChangeEvent; 
import java.beans.PropertyChangeListener; 
import javax.swing.*; 

public class Test{ 
    public Test(){ 
     JOptionPane optionPane = new JOptionPane(null, JOptionPane.OK_CANCEL_OPTION); 

     final JDialog dialog = new JDialog(new JFrame(), "Test", true); 
     dialog.setContentPane(optionPane); 

     optionPane.addPropertyChangeListener(new PropertyChangeListener() { 
      public void propertyChange(PropertyChangeEvent e) { 
       String prop = e.getPropertyName(); 

       if (dialog.isVisible() && (e.getSource() == optionPane) && (JOptionPane.VALUE_PROPERTY.equals(prop))){ 
        java.lang.System.out.println("Code Reached"); 
        optionPane.setValue(JOptionPane.UNINITIALIZED_VALUE); 
       } 
      } 
     }); 
     dialog.pack(); 
     dialog.setVisible(true); 
    } 

    public static void main(String[] args){ 
     new Test(); 
    } 
} 

从这SSCCE,能够以告诉第二,和不需要的,PropertyChangedEvent是由代码optionPane.setValue(JOptionPane.UNINITIALIZED_VALUE)线引起的;然而这个代码需要防止无效输入后的窗口锁定。有没有办法来防止JOptionPane.setValue()导致PropertyChangedEvent,或确定何时PropertyChangedEvent已由重置的JOptionPane的值,并防止if发生?谢谢。

回答

1

如果有可能为您禁用的事件监听器,你可以通过做:

A)设置(布尔)标记中的PropertyChangeListener对象

B)删除来自optionPane的eventlistener:

final PropertyChangeListener pcl = new PropertyChangeListener() { 
    public void propertyChange(PropertyChangeEvent e) { 
     String prop = e.getPropertyName(); 

     if (dialog.isVisible() && (e.getSource() == optionPane) && (JOptionPane.VALUE_PROPERTY.equals(prop))){ 
      java.lang.System.out.println("Code Reached"); 
      optionPane.setValue(JOptionPane.UNINITIALIZED_VALUE); 

      optionPane.removePropertyChangeListener(pcl); 
     } 
    } 
} 
optionPane.addPropertyChangeListener(pcl); 

但是,这取决于对话目的。如果关闭对话框,则选项B是好的。

编辑:

第二个事件是由optionPane.setValue(JOptionPane.UNINITIALIZED_VALUE)引起的,因此,如果您核对该值,它可以工作。

if (dialog.isVisible() 
     && e.getSource() == optionPane 
     && JOptionPane.VALUE_PROPERTY.equals(prop) 
     && !optionPane.getValue().equals(JOptionPane.UNINITIALIZED_VALUE)){ 

    java.lang.System.out.println("Code Reached"); 
    optionPane.setValue(JOptionPane.UNINITIALIZED_VALUE); 
} 
+0

目前我正在使用类似于A的解决方法,从而切换布尔型;然而这看起来像是一个狡猾的解决方案。不幸的是,我不能删除监听器,因为我希望JDialog保持在屏幕上,并且可点击,直到提供有效的输入(或者在提供的SSCCE的情况下,它需要保持不变)。 – Hungry 2014-09-29 10:54:41

+0

编辑是完美的,我不相信我没看见它! – Hungry 2014-09-29 11:59:14