ProgressBar 不会改变它在 Java 中的值
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/5691979/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
ProgressBar doesn't change its value in Java
提问by Hoome
I have strange problem. I set a JProgressBar:
我有奇怪的问题。我设置了一个 JProgressBar:
private JProgressBar progressBar;
public void foo()
{
...
progressBar = new JProgressBar(0, 100);
progressBar.setValue(0);
progressBar.setStringPainted(true);
...
contentPane.add(progressBar);
...
}
But it changes only when I put setValue function it in some places in code, not everywhere:
但是只有当我将 setValue 函数放在代码中的某些地方时它才会改变,而不是无处不在:
public void foo2()
{
progressBar.setValue(100); //working
if(...)
{
System.out.println("These instructions are executing"); //working
progressBar.setValue(0); //not working
}
}
So, what am I doing wrong? Why the second instruction doesn't work?
那么,我做错了什么?为什么第二条指令不起作用?
回答by Martijn Courteaux
The value of the progress bar is really updated. But it isn't simply on the screen yet. Often, we use progress bars in loops. But, while you are in the loop, which you probably invoked by clicking a buttonit isn't painted. Why? Because you invoked it by clicking a button. When you click a button, all the code you've made for that button is being executed by the AWTEventThread
. This is the same thread that keep track of all the Swing components, and checks wether they have to be repainted. That is the thread that makes your JFrame come alive. When you hover a button and the color changes a bit, it's done by the AWTEventThread
.
进度条的值真的更新了。但它还不仅仅出现在屏幕上。通常,我们在循环中使用进度条。但是,当您处于循环中时,您可能通过单击按钮调用它并没有绘制它。为什么?因为您是通过单击按钮调用它的。当您单击一个按钮时,您为该按钮编写的所有代码都由AWTEventThread
. 这是跟踪所有 Swing 组件并检查它们是否必须重新绘制的同一个线程。这就是让您的 JFrame 活跃起来的线程。当您将鼠标悬停在按钮上并且颜色发生一些变化时,它是由AWTEventThread
.
So, while you are working in the loop, the AWTEventThread can't update the screen anymore.
因此,当您在循环中工作时,AWTEventThread 无法再更新屏幕。
This means there are two solutions:
这意味着有两种解决方案:
(Recommend) You should create a separate thread which executes the loop. This means the AWTEventThread can update the screen if necessary (when you call
bar.setValue(...);
)public void yourButtonClickMethod() { Runnable runner = new Runnable() { public void run() { //Your original code with the loop here. } }; Thread t = new Thread(runner, "Code Executer"); t.start(); }
Manually repaint the progress bar. I did it always with
bar.repaint();
but I'm wondering if it will work. I though it was that method. If that doesn't work, try:bar.update(bar.getGraphics());
.
(推荐)您应该创建一个单独的线程来执行循环。这意味着 AWTEventThread 可以在必要时更新屏幕(当您调用时
bar.setValue(...);
)public void yourButtonClickMethod() { Runnable runner = new Runnable() { public void run() { //Your original code with the loop here. } }; Thread t = new Thread(runner, "Code Executer"); t.start(); }
手动重绘进度条。我总是这样做,
bar.repaint();
但我想知道它是否会起作用。我虽然是那种方法。如果不行,请尝试:bar.update(bar.getGraphics());
。
回答by Lenymm
Even though this question was answered already I've found another way that actually worked for me. I was using the swing worker and using propertyChange(null)to update the progress bar was the easiest solution.
尽管已经回答了这个问题,但我还是找到了另一种对我有用的方法。我正在使用 Swing Worker 并使用propertyChange(null)更新进度条是最简单的解决方案。
Just wanted to offer this alternative.
只是想提供这个替代方案。