Java 如何使我的SwingWorker示例正常工作?
我已经做了自己的SwingWorker示例,以熟悉它的工作原理 我想做的是: 单击按钮时,我希望在任务完成之前显示一个进度条。我只想删除进度条并向对话框中添加一个字符串 单击按钮时,进度条会出现,但不会消失。(切勿在10秒后移除进度条,也不得将标签向上放置) 以下是SSCCE:Java 如何使我的SwingWorker示例正常工作?,java,swing,jdialog,swingworker,Java,Swing,Jdialog,Swingworker,我已经做了自己的SwingWorker示例,以熟悉它的工作原理 我想做的是: 单击按钮时,我希望在任务完成之前显示一个进度条。我只想删除进度条并向对话框中添加一个字符串 单击按钮时,进度条会出现,但不会消失。(切勿在10秒后移除进度条,也不得将标签向上放置) 以下是SSCCE: package swingtesting; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.
package swingtesting;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JProgressBar;
import javax.swing.SwingWorker;
public class SwingTesting {
/**
* Creates a frame that will hold a simple button to make use of SwingWorker
*/
public static void main(String[] args) {
// TODO code application logic here
JFrame frame = new JFrame();
JButton button = new JButton();
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
new GuiWorker().execute();
}
});
button.setText("Test Me");
frame.getContentPane().add(button);
frame.pack();
frame.setVisible(true);
}
}
class GuiWorker extends SwingWorker<Integer, Integer> {
/*
* This should just create a frame that will hold a progress bar until the
* work is done. Once done, it should remove the progress bar from the dialog
* and add a label saying the task complete.
*/
private JFrame frame = new JFrame();
private JDialog dialog = new JDialog(frame, "Swingworker test", true);
private JProgressBar progressBar = new JProgressBar();
public GuiWorker() {
progressBar.setString("Waiting on time");
progressBar.setStringPainted(true);
progressBar.setIndeterminate(true);
dialog.getContentPane().add(progressBar);
dialog.pack();
dialog.setVisible(true);
}
@Override
protected Integer doInBackground() throws Exception {
Thread.sleep(10000);
return 0;
}
@Override
protected void done() {
JLabel label = new JLabel("Task Complete");
dialog.getContentPane().remove(progressBar);
dialog.getContentPane().add(label);
}
}
package swingtesting;
导入java.awt.event.ActionEvent;
导入java.awt.event.ActionListener;
导入javax.swing.JButton;
导入javax.swing.JDialog;
导入javax.swing.JFrame;
导入javax.swing.JLabel;
导入javax.swing.JProgressBar;
导入javax.swing.SwingWorker;
公开课摇摆测试{
/**
*创建一个框架,其中包含一个简单的按钮以利用SwingWorker
*/
公共静态void main(字符串[]args){
//此处的TODO代码应用程序逻辑
JFrame=新JFrame();
JButton button=新JButton();
addActionListener(新建ActionListener()){
已执行的公共无效操作(操作事件e){
新建GuiWorker().execute();
}
});
setText(“测试我”);
frame.getContentPane().add(按钮);
frame.pack();
frame.setVisible(true);
}
}
类GuiWorker扩展了SwingWorker{
/*
*这应该只是创建一个框架,它将保存一个进度条,直到
*工作完成。完成后,应将进度条从对话框中删除
*并添加一个标签,说明任务已完成。
*/
私有JFrame=新JFrame();
私有JDialog对话框=新JDialog(框架,“Swingworker测试”,true);
private JProgressBar progressBar=新的JProgressBar();
公职人员(){
progressBar.setString(“等待时间”);
progressBar.SetStringPaint(真);
progressBar.SetUndeterminate(真);
dialog.getContentPane().add(progressBar);
dialog.pack();
对话框.setVisible(true);
}
@凌驾
受保护的整数doInBackground()引发异常{
睡眠(10000);
返回0;
}
@凌驾
受保护的void done(){
JLabel标签=新JLabel(“任务完成”);
dialog.getContentPane().remove(progressBar);
dialog.getContentPane().add(标签);
}
}
这里是代码的更新版本
import java.awt.EventQueue;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JProgressBar;
import javax.swing.SwingWorker;
public class SwingTesting {
public static void main(String[] args) {
EventQueue.invokeLater( new Runnable() {
@Override
public void run() {
JFrame frame = new JFrame();
JButton button = new JButton();
button.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
new GuiWorker().execute();
}
});
button.setText("Test Me");
frame.getContentPane().add(button);
frame.pack();
frame.setVisible(true);
}
} );
}
}
class GuiWorker extends SwingWorker<Integer, Integer> {
/*
* This should just create a frame that will hold a progress bar until the
* work is done. Once done, it should remove the progress bar from the dialog
* and add a label saying the task complete.
*/
private JFrame frame = new JFrame();
private JDialog dialog = new JDialog(frame, "Swingworker test", true);
private JProgressBar progressBar = new JProgressBar();
public GuiWorker() {
progressBar.setString("Waiting on time");
progressBar.setStringPainted(true);
progressBar.setIndeterminate(true);
dialog.getContentPane().add(progressBar);
dialog.pack();
dialog.setModal( false );
dialog.setVisible(true);
}
@Override
protected Integer doInBackground() throws Exception {
System.out.println( "GuiWorker.doInBackground" );
Thread.sleep(1000);
return 0;
}
@Override
protected void done() {
System.out.println("done");
JLabel label = new JLabel("Task Complete");
dialog.getContentPane().remove(progressBar);
dialog.getContentPane().add(label);
dialog.getContentPane().validate();
}
}
导入java.awt.EventQueue;
导入java.awt.event.ActionEvent;
导入java.awt.event.ActionListener;
导入javax.swing.JButton;
导入javax.swing.JDialog;
导入javax.swing.JFrame;
导入javax.swing.JLabel;
导入javax.swing.JProgressBar;
导入javax.swing.SwingWorker;
公开课摇摆测试{
公共静态void main(字符串[]args){
invokeLater(新的Runnable(){
@凌驾
公开募捐{
JFrame=新JFrame();
JButton button=新JButton();
addActionListener(新建ActionListener()){
@凌驾
已执行的公共无效操作(操作事件e){
新建GuiWorker().execute();
}
});
setText(“测试我”);
frame.getContentPane().add(按钮);
frame.pack();
frame.setVisible(true);
}
} );
}
}
类GuiWorker扩展了SwingWorker{
/*
*这应该只是创建一个框架,它将保存一个进度条,直到
*工作完成。完成后,应将进度条从对话框中删除
*并添加一个标签,说明任务已完成。
*/
私有JFrame=新JFrame();
私有JDialog对话框=新JDialog(框架,“Swingworker测试”,true);
private JProgressBar progressBar=新的JProgressBar();
公职人员(){
progressBar.setString(“等待时间”);
progressBar.SetStringPaint(真);
progressBar.SetUndeterminate(真);
dialog.getContentPane().add(progressBar);
dialog.pack();
dialog.setModal(false);
对话框.setVisible(true);
}
@凌驾
受保护的整数doInBackground()引发异常{
System.out.println(“GuiWorker.doInBackground”);
睡眠(1000);
返回0;
}
@凌驾
受保护的void done(){
系统输出打印项次(“完成”);
JLabel标签=新JLabel(“任务完成”);
dialog.getContentPane().remove(progressBar);
dialog.getContentPane().add(标签);
dialog.getContentPane().validate();
}
}
关键的一点是,设置模型对话框将阻止可见的对话框,直到该对话框被释放。因此,使其成为非模态修复了它+切换组件时内容窗格上的
validate
调用。我还调整了主方法以在EDT上运行,并添加了一些System.out调用。如果删除setModal(false)
调用,您将看到在关闭对话框之前不会打印这些语句无需将对话框设置为非模态。启动SwingWorker后只需显示对话框。这可以通过调用类(执行SwingWorker的类)完成,首先调用execute,然后显示对话框,也可以通过SwingWorker完成,但如果是从后者,则必须创建自己的伪执行方法来调用super的execute,然后显示对话框。请注意,不能重写execute()本身,因为它是final
例如
import java.awt.CardLayout;
import java.awt.Window;
import java.awt.Dialog.ModalityType;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.concurrent.ExecutionException;
import javax.swing.*;
@SuppressWarnings("serial")
public class SwingTesting2 {
private static void createAndShowGui() {
final JFrame frame = new JFrame("SwingTesting2");
final JDialog dialog = new JDialog(frame, "Dialog",
ModalityType.APPLICATION_MODAL);
final DialogPanel dialogPanel = new DialogPanel();
dialog.getContentPane().add(dialogPanel.getMainPanel());
dialog.pack();
dialog.setLocationRelativeTo(frame);
JButton button = new JButton(new AbstractAction("Test Me") {
@Override
public void actionPerformed(ActionEvent actEvt) {
final GuiWorker2 guiWorker = new GuiWorker2();
guiWorker.addPropertyChangeListener(new PropertyChangeListener() {
@Override
public void propertyChange(PropertyChangeEvent pcEvt) {
if (pcEvt.getPropertyName().equals("state")) {
if (pcEvt.getNewValue() == SwingWorker.StateValue.DONE) {
try {
dialogPanel.done(guiWorker.get());
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
} else if (pcEvt.getPropertyName().equals("progress")) {
dialogPanel.setProgress((Integer)pcEvt.getNewValue());
}
}
});
guiWorker.execute();
dialogPanel.start();
dialog.setVisible(true);
}
});
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(button);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
class GuiWorker2 extends SwingWorker<Integer, Integer> {
private static final int MAX_COUNT = 20;
private static final long SLEEP_TIME = 100;
private int count = 0;
@Override
protected Integer doInBackground() throws Exception {
while (count < MAX_COUNT) {
Thread.sleep(SLEEP_TIME);
count++;
setProgress((100 * count) / MAX_COUNT);
}
return count;
}
}
@SuppressWarnings("serial")
class DialogPanel {
public static final String PROGRESS_BAR = "Progress Bar";
public static final String DONE = "Done";
private static final int TIMER_DELAY = 2000;
private CardLayout cardLayout = new CardLayout();
private JPanel mainPanel = new JPanel(cardLayout);
private JLabel doneLabel = new JLabel("Done", JLabel.CENTER);
private JProgressBar progressBar = new JProgressBar();
public DialogPanel() {
progressBar.setString("Waiting on time");
progressBar.setStringPainted(true);
progressBar.setIndeterminate(false);
mainPanel.add(progressBar, PROGRESS_BAR);
mainPanel.add(doneLabel, DONE);
}
public void setProgress(Integer newValue) {
progressBar.setValue(newValue);
}
public void start() {
cardLayout.show(mainPanel, PROGRESS_BAR);
progressBar.setValue(0);
}
public void done(int countValue) {
doneLabel.setText(DONE + ". Count: " + countValue);
cardLayout.show(mainPanel, DONE);
new Timer(TIMER_DELAY, new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
Window win = SwingUtilities.getWindowAncestor(mainPanel);
win.dispose();
}
}){{setRepeats(false);}}.start();
}
public JPanel getMainPanel() {
return mainPanel;
}
}
导入java.awt.CardLayout;
导入java.awt.Window;
导入java.awt.Dialog.ModalityType;
导入java.awt.event.ActionEvent;
导入java.awt.event.ActionListener;
导入java.beans.PropertyChangeEvent;
导入java.beans.PropertyChangeListener;
导入java.util.concurrent.ExecutionException;
导入javax.swing.*;
@抑制警告(“串行”)
公开课摇摆测试2{
私有静态void createAndShowGui(){
最终JFrame=新JFrame(“SwingTesting2”);
最终JDialog对话框=新JDialog(框架,“对话框”,
ModalityType.APPLICATION