Java 中的进度条 + MVC =?

Jas*_*n S 5 java model-view-controller swing progress-bar

所以我在 Java Swing 中有这个漂亮的 MVC 架构应用程序,现在我想添加一个进度条,我对将 JProgressBar 合并到我的视图中的良好设计方法感到困惑。我是不是该:

  • 将 DefaultBoundedRangeModel 添加到我的控制器状态,然后将其导出?

    class Model {
      final private DefaultBoundedRangeModel progress
        = new DefaultBoundedRangeModel();
    
      public void getProgressModel() { return progress; }
      public void setProgressCount(int i) { progress.setValue(i); }
    }
    
    class Controller {
      Model model;
      int progressCount;
      void doSomething()
      {
         model.setProgressCount(++progressCount);
      }
    }
    
    class View {
      void setup(Model m)
      {
        JProgressBar progressBar = /* get or create progress bar */  ;
        progressBar.setModel(m.getProgressModel());
      }
    }
    
    /* dilemma: Model allows progress to be exported so technically
     all of the progress state could be set by someone else; should it be put
     into a read-only wrapper? */
    
    Run Code Online (Sandbox Code Playgroud)
  • 使用 JGoodies Binding 尝试将 JProgressBar 的视觉状态连接到我的模型状态?

    class Model {
      private int progress;
    
      public void getProgressCount() { return progress; }
      public void setProgressCount(int i) { progress = i; }
    }
    
    class View {
      void setup(Model m)
      {
        ProgressBar progressBar = /* get or create progress bar */  ;
        CallSomeMagicMethodToConnect(m, "progressCount", progressBar, "value");
        // is there something that works like the above?
        // how do I get it to automatically update???
      }
    }
    
    Run Code Online (Sandbox Code Playgroud)
  • 或者是其他东西???

编辑:更具体地说:有人能给我指出一个 Java 应用程序的真实源代码的好例子,它有一个包含进度条的状态栏,并且有一个不错的 MVC 实现吗?

Ran*_*ron 3

不(对 1)和不(对 2)。最起码,我是这么想的。

否(至 1):首先,DefaultBoundedRangeModel 是一个 javax.swing 类。在我看来,这些类在模型中没有地位。例如,考虑一下存在于服务器上并通过 RMI 访问的模型 - 突然将 javax.swing 类放在那里似乎“不正确”。然而,真正的问题是您将模型的一部分(有界模型)提供给其他人,而无法控制触发的事件或发出的查询。

否(对2):呃。绑定很有趣,但(至少在我看来)应该用于 UI 模型和 UI 组件之间的同步,而不是数据模型和 UI 模型之间的同步。再次考虑一下,如果您的数据模型位于通过 RMI 访问的远程服务器上,会发生什么情况。

所以呢?好吧,这只是一个建议,但我会添加一个事件侦听器接口并添加标准事件侦听器订阅方法(addListner(...)、removeListener(...))。当我有更新时,我会从模型中调用这些侦听器。当然,我会确保记录调用线程(或者说无法确定),以便客户端(在本例中为 UI)能够正确同步(invokeLater 和朋友)。由于监听器服务将由控制器公开,这将允许模型存在于任何地方(甚至允许远程调用或池化监听器)。此外,这会将模型与 UI 分离,从而可以构建更多包含它的模型(翻译器/装饰器/依赖模型)。

希望这可以帮助。