java - 基本不确定进度条用法

标签 java swing progress-bar swingworker jprogressbar

我只是想在完成长时间下载时在框架的左下角设置一个不确定的 JProgressBar 动画。

我浏览了很多教程,但对我来说没有一个是清楚的。我只是想让它在后台下载文件时设置动画。在我尝试过的每一种方式中,它都不会在下载完成之后之前为进度条设置动画。

我需要帮助知道在哪里放置我的 download() 调用。

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);
  }
}

提前致谢!



解决方案

编辑:对于以后和我有类似问题的人来说,这是一个基本问题的基本解决方案。这不是我的逐字代码,而是一般草图。在 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() {
        progressBar.setVisible(false)
     }
  }

  new MyWorker().execute();

}

最佳答案

您当前的代码显示没有创建后台线程,而是显示您试图在 Swing 线程上对代码进行排队 Swing 线程中没有对这个问题很有意义(虽然有时你可能想这样做,但再次强调,不在这里)。成功的唯一方法是使用后台线程。标准甲骨文JProgressBar tutorialConcurrency in Swing经历了这一切。

基本的事情是您必须从 Swing Thread 更新 JProgressBar 将在后台线程中执行长时间运行的进程,例如 SwingWorker 对象提供的进程。我们无法在此处查看所有详细信息,因此我所能做的就是提供一个链接,但我们很乐意在您查看教程后帮助您了解详细信息。只需查看教程,如果仍然卡住,再回来提出您的具体问题。

编辑 1
你声明:

can I just create a new thread object within the buttonClicked() function?

是的,您可以在 buttonClicked() 方法 中创建一个 SwingWorker 对象并在那里执行它。

The thing is I have my API and library of all the functionality that I'm developing the GUI to, and it seems like a longwinded workaround to wrap that function call in a thread.

抱歉,我不知道您在这里说的是什么,也不知道您认为线程会导致什么问题。 buttonClicked() 方法可能必须 在 EDT 而不是后台线程中运行。

另请注意,在我的大多数更复杂的 Swing GUI 中,我经常在不同的(模型)对象中下载文件,并在与 GUI 对象( View )不同的对象(控件)中创建我的 SwingWorker。这样做可能看起来更复杂,但是当我这样做时,调试、维护和增强我的程序会很多,尤其是当我大量使用时允许我单独测试所有程序组件的接口(interface)。

编辑2
对您的解决方案发布的一些更正。您发布了:

public void buttonClicked() {
  class MyWorker extends SwingWorker(String, Object) {
     protected String runInBackground() {
       progressBar.setVisible(true);
       progressBar.setIndeterminate(true);

       // ...

有问题

  • doInBackground(),不是runInBackground()
  • 但更重要的是,您是从后台线程中进行 Swing 调用,这是永远不应该做的事情(除非调用是线程安全的,即使那样...)。

所以改变它:

public void buttonClicked() {
  progressBar.setVisible(true);
  progressBar.setIndeterminate(true);
  class MyWorker extends SwingWorker<String, Void> {
     protected String doInBackground() {

       // ...

关于java - 基本不确定进度条用法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10442406/

相关文章:

java - 无法使用 getResource() 将图像添加到按钮(使用 ant 获取 NullPointerException- 构建项目)

macos - 是否可以将 curl 设置为在进度条之前显示文件名?

java - maven本地缓存错误

java - 设置spring xd时发生非法反射访问操作

java - 匿名 JAX-RS 资源

java - 以毫秒为单位的 GPS 时间转换为 UTC 格式

java - JTable:显示包含列表的数据

c# - 我们如何使用 FtpWebRequest 显示上传进度条

flutter - 如何在 Flutter 转换之间显示进度轮/进度条?

java - 当没有消费者准备好时处理生产者线程