对于我可以阅读的内容,它用于在swing应用程序中调度新线程以执行某些"后台"工作,但使用此而不是"普通"线程有什么好处?
使用新的Thread是不一样的,当它完成时使用SwingUtilities.invokeLater调用一些GUI方法?...
我在这里错过了什么?
http://en.wikipedia.org/wiki/SwingWorker
http://java.sun.com/products/jfc/tsc/articles/threads/threads2.html
这是针对那里的摇摆专家.我花了相当多的时间来解决这个问题,所以我需要几行来解释这个问题.
我有一个独立的java swing应用程序(java 6).在我的应用程序中,我有一个带有单选按钮组的框架.我有一个链接到组中所有按钮的操作.该操作检查以查看选择了哪个单选按钮并执行某些操作."工作"涉及一些背景计算以及我的应用程序中的两个其他框架中的一些绘画.后台计算是多线程的.
我想在用户选择其中一个单选按钮时显示进度条.但是,当选择单选按钮时,在发生对单选按钮的操作时,进度条永远不会出现.我尝试了jdialog类型的进度条,玻璃窗格等.在"工作"全部完成之前,它们都没有出现.这似乎是因为Swing没有完成对单选按钮的绘制,直到相应动作中的"工作"完成.由于EDT一次只做一件事,因此从不显示进度条对话框(或玻璃窗格).
然后我尝试使用SwingWorker来完成所有这些"工作".启动进度条(或激活玻璃窗格),启动SwingWorker并关闭SwingWorker的done()方法中的进度条(或停用玻璃窗格).这似乎提升了进度条很好,但是作为"工作"一部分的绘画有时候没有完成,留下了一些绘画工件(paintComponent方法非常复杂,所以不想在这里重现).如果我调整窗口大小,工件就会消失.事实上,如果我使用扩展Thread而不是SwingWorker的类,就会发生这种情况.这都是因为Swing不是线程安全的,我试图从除EDT之外的线程进行GUI工作.我明白那一部分.
我该怎么办?"工作"大约需要30秒,如果没有向用户显示程序正在运行的某种迹象,那么这似乎太长了.我也尝试将光标更改为等待光标并遇到与上述相同的问题.我唯一能做的就是禁用框架并将框架的标题设置为"work ......"等文本.
以前有人见过这个问题吗?
我有正在处理的银行gui应用程序,我的jdialog的setvisible方法似乎有问题.在用户撤回有效金额后,我弹出一个简单的对话框,其中显示"正在进行交易".在我的dobackground方法中,我继续轮询以检查是否已收到交易.我尝试使用swingworker,我不明白为什么它不起作用.如果我删除setvisible调用它工作正常,那么为什么setvisible导致系统挂起?这是我的jbutton mouselistener中的代码:
SwingWorker<String,Integer> worker = new SwingWorker<String,Integer>(){
JDialog waitForTrans = new JDialog((JFrame)null,true);
public String doInBackground() throws Exception {
waitForTrans.add(new JLabel("Updating balance in system. Please Wait..."));
waitForTrans.setMinimumSize(new Dimension(300,100));
waitForTrans.setDefaultCloseOperation(DISPOSE_ON_CLOSE);
waitForTrans.setVisible(true);
Bank.getInstance().sendTransaction(currentPin,"-"+withdraw);
while(!Bank.getInstance().hasCompletedTransaction){
}
return null;
}
public void done(){
try {
this.get();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
waitForTrans.setVisible(false);
newField.setText(String.valueOf(Bank.getInstance().getAccountList().get(currentPin).getBalance()));
}
};
worker.execute();
Run Code Online (Sandbox Code Playgroud) 从SecondaryLoop的文档中,不清楚何时应该使用这个新功能而不是SwingWorker,一些有趣的案例会很有用.
我只是想在进行长时间下载时在框架的左下角设置一个不确定的JProgressBar动画.
我看了很多教程,其中没有一个对我很清楚.我只是想在后台下载文件时让它具有动画效果.每个我试过这种方式,它不会动画进度条,直到后下载完成.
我需要帮助知道下载()调用的位置.
class MyFunClass extends JFrame {
JProgressBar progressBar = new JProgressBar();
public void buttonClicked() {
progressBar.setVisible(true);
progressBar.setIndeterminate(true);
SwingUtilities.invokeLater(new Runnable() {
public void run() {
progressBar.setIndeterminate(true);
progressBar.setVisible(true);
// Do I do my download() in here??
}});
// Do download() here???
progressBar.setVisible(false);
}
}
Run Code Online (Sandbox Code Playgroud)
提前致谢!
编辑:对于那些将来遇到类似问题的人来说,这是基本问题的基本解决方案.这不是我的代码,而是一般草图.内部buttonClicked():
public void buttonClicked() {
class MyWorker extends SwingWorker(String, Object) {
protected String doInBackground() {
progressBar.setVisible(true);
progressBar.setIndeterminate(true);
// Do my downloading code
return "Done."
}
protected void done() { …Run Code Online (Sandbox Code Playgroud) 我有一个Java应用程序,使用SwingWorker更新GUI中的标签和进度条,它很好用.但是,我想在此设置中添加一项功能.
我的摇摆工作者执行具有长度的任务n,并且它重复该任务m时间.现在我的GUI只是告诉我这个任务被重复了多少次,但是我想告诉我我们所处的任务的长度.说,n=300并且m=50,我想要像:
Task 49 is at 248 ()
Task has been repeated 48 times
Run Code Online (Sandbox Code Playgroud)
我应该在SwingWorker中修改什么?
/**
*
* @author digitaldust
*/
public class Model extends SwingWorker<Integer, Integer> {
private HashMap<String, Number> GUIparams;
private int session;
private int ticks;
Model(HashMap<String, Number> KSMParams) {
GUIparams = KSMParams;
session = (Integer)GUIparams.get("experimentsInSession");
ticks = (Integer)GUIparams.get("howManyTicks");
}
/**
* Actual simulation
*/
@Override
protected Integer doInBackground() throws Exception {
int i=0;
while(!isCancelled() && i<session){
i++;
int ii=0; …Run Code Online (Sandbox Code Playgroud) 我有一个SwingWorker在后台与服务器通信,然后更新一个JFrame.我正在调试我的应用程序,并注意到即使在SwingWorker完成其工作后,其线程仍然存在.它悬挂在Unsafe.park(java.lang.Object)本机方法上.我进一步调查了这一点,发现SwingWorker我的应用程序中的所有其他内容在完成后都会执行相同的操作.我可以提供源代码,如果有人想要它,但我不认为这是必要的,因为问题看起来很一般.
我在没有调试器的情况下运行应用程序,问题仍然存在.这是SwingWorker线程的转储:
"SwingWorker-pool-2-thread-1" daemon prio=6 tid=0x03219800 nid=0xd74 waiting on
condition [0x04b7f000]
java.lang.Thread.State: WAITING (parking)
at sun.misc.Unsafe.park(Native Method)
- parking to wait for <0x22ec63d8> (a java.util.concurrent.locks.Abstra
ctQueuedSynchronizer$ConditionObject)
at java.util.concurrent.locks.LockSupport.park(Unknown Source)
at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject
.await(Unknown Source)
at java.util.concurrent.LinkedBlockingQueue.take(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor.getTask(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)
Run Code Online (Sandbox Code Playgroud)
我制作了一个示例程序,SwingWorker它使用了应用程序中通常使用的方式.这个程序有同样的问题.这是代码:
package swingworkerlocktest;
import java.util.List;
import javax.swing.JFrame;
import javax.swing.JTextArea;
import javax.swing.SwingWorker;
public class SwingWorkerLockTest {
public static …Run Code Online (Sandbox Code Playgroud) 在测试使用Swingworker的一些实时仿真代码时,我注意到我的GUI似乎总是以30 fps运行,不多也不少.每次用户与应用程序交互时(如鼠标移动)或调用Swingworker的process()方法时,我都会更新GUI.Swingworker现在没有做任何事情,它只是从GUI抓取鼠标位置并通过publish()和process()方法将其作为克隆发回(我只是这样做,看看我能做什么和能做什么在线程之间进行通信时要做,因为多线程对我来说仍然是一个新手.我在任何地方都没有定时器,Swingworker的process()方法在GUI上调用repaint(),所以我想知道是什么原因导致GUI以30 fps更新?是否可能默认情况下GUI中的vsync处于活动状态,或者它是Swingworker中process()方法的某些行为?最后:有没有办法获得更高的帧速率?
这是一个表现出这种行为的sscce:
public class SimGameTest implements Runnable {
public static void main(String[] args) {
SwingUtilities.invokeLater(new SimGameTest());
}
@Override
public void run() {
MainWindow mainWindow = new MainWindow(new Game());
mainWindow.setLocationRelativeTo(null);
mainWindow.setVisible(true);
}
}
public class MainWindow extends JFrame {
private Game game;
private GamePanel gamePanel;
public MainWindow(Game game) {
this.game = game;
createAndShowGUI();
startGame();
}
private void startGame() {
GameSim gameSim = new GameSim(game, gamePanel);
gameSim.execute();
}
private void createAndShowGUI() {
setTitle("Sim game test");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setResizable(false);
JPanel contentPane = …Run Code Online (Sandbox Code Playgroud) 如何在使用具有长时间运行进程的SwingWorker时将View与模型分离,该进程应将更新发送回控制器?
我可以使用它SwingWorkers doInBackground()来保持EDT响应,通过调用例如model.doLongProcess()从那里伟大!
我遇到的问题是在流程完成之前尝试获取数据,以便根据进度更新视图.
我知道我可以通过使用SwingWorkers publish()方法来获取数据,但我认为这迫使我在其中编写doLongProcess()方法 的代码doInBackground().
作为MVC实现的参考我看起来有点像这样:
http://www.leepoint.net/notes-java/GUI/structure/40mvc.html
/ structure/calc-mvc/CalcMVC.java -- Calculator in MVC pattern.
// Fred Swartz -- December 2004
import javax.swing.*;
public class CalcMVC {
//... Create model, view, and controller. They are
// created once here and passed to the parts that
// need them so there is only one copy of each.
public static void main(String[] args) {
CalcModel model = new CalcModel();
CalcView view …Run Code Online (Sandbox Code Playgroud) java model-view-controller swing design-patterns swingworker
我想用Threads创建一个[1 Player vs PC]游戏.
我们的主板上有10*10两种颜色的形状,如下所示:

当玩家点击蓝色圆圈时,他们的颜色变成灰色.
在另一侧PC应该将所有RED矩形变为灰色.
WINNER是谁先清除他/她自己的形状.
播放器的代码工作正常但是,我的问题在于实现游戏的PC端,正如我在本文中所读到的,我应该使用SwingWorker在GUI中实现线程.这是我第一次使用SwingWorkers,我不知道它应该如何正常工作.
这是我的代码:
主类
public class BubblePopGame {
public static final Color DEFAULT_COLOR1 = Color.BLUE;
public static final Color DEFAULT_COLOR2 = Color.RED;
public BubblePopGame() {
List<ShapeItem> shapes = new ArrayList<ShapeItem>();
int Total = 10;
for (int i = 1; i <= Total; i++) {
for (int j = 1; j <= Total; j++) {
if ((i + j) % 2 == 0) {
shapes.add(new ShapeItem(new Ellipse2D.Double(i * 25, j …Run Code Online (Sandbox Code Playgroud) java ×10
swingworker ×10
swing ×9
concurrency ×1
frame-rate ×1
java-7 ×1
jprogressbar ×1
progress-bar ×1
radio-button ×1
visibility ×1