在下面的示例中,尝试在工作人员启动时打开对话框并在工作人员端关闭它。
不幸的是,在手动关闭对话框之前,不会执行done()
。
为什么?
package tests.javax.swing;
import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import javax.swing.AbstractAction;
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.SwingUtilities;
import javax.swing.SwingWorker;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Try_SwingWorker_Modality {
private static final Logger log = LoggerFactory.getLogger(Try_SwingWorker_Modality.class);
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
AbstractAction popupAction = new AbstractAction("popup") {
@Override
public void actionPerformed(ActionEvent e) {
JOptionPane.showMessageDialog(null, "popup");
}
};
final JDialog dialog = new JDialog((JFrame)null, true);
dialog.setLayout(new FlowLayout());
dialog.add(new JButton(popupAction));
dialog.pack();
dialog.setLocationRelativeTo(null);
SwingWorker<Object,Object> swingWorker = new SwingWorker<Object,Object>() {
@Override
protected Object doInBackground() throws Exception {
log.debug("doInBackground()");
return null;
}
@Override
protected void done() {
log.debug("done");
//dialog.dispose();
}
};
swingWorker.addPropertyChangeListener(new PropertyChangeListener() {
@Override
public void propertyChange(PropertyChangeEvent evt) {
log.debug("event = {}", evt);
if( "state".equals(evt.getPropertyName())) {
if( SwingWorker.StateValue.STARTED == evt.getNewValue() ) {
dialog.setVisible(true);
log.debug("after setVisible()");
}
else if( SwingWorker.StateValue.DONE == evt.getNewValue() ) {
dialog.dispose();
}
}
}
});
swingWorker.execute();
}
});
}
}
答案 0 :(得分:4)
您使用该代码冻结了SwingWorker的PropertyChangeListener。我永远不会在PCL中设置对话框。
相反,我在这里做:
swingWorker.execute();
dialog.setVisible(true);