java MVC + vetoable / deferred属性

时间:2010-10-07 17:32:33

标签: java model-view-controller

我有一个接口FooModel和一个类DefaultFooModel,它们有一些简单的属性。我被困在boolean enable财产上,因为我希望将其作为可否决/推迟:

public interface FooModel {
   public boolean isEnabled();
   /** returns old value */
   public boolean setEnable(boolean enable); 

   public void addFooListener(FooModel.Listener listener);
   public void removeFooListener(FooModel.Listener listener);

   public interface Listener {
      public void onFooEnableUpdate(boolean newEnable, boolean oldEnable);
   }
}

我想要的是模型M是enable属性的中心访问点。但这是我想要发生的事件序列:

  1. view V(或模型M的任何用户)在任意线程上调用FooModel.setEnable(enable)
  2. FooModel可以:

    一个。立即以任意顺序在每个侦听器上调用onFooEnableUpdate(newEnable, oldEnable)

    湾启动一个潜在的长事件序列,由此另一个实体(例如控制器C)可以决定是否启用,并以某种方式让FooModel知道,从而可以更新enable属性,然后我们像往常一样在上面的(a)中继续。

  3. 问题是,我不知道如何去做。

    方法1:执行此操作的机制不应该是模型界面的一部分。相反,我的DefaultFooModel有一个接受FooController

    的实现
    public interface FooController {
       public void onFooEnableRequest(boolean newEnable, boolean oldEnable);
    }
    

    调用DefaultFooModel.setEnable()后,会调用FooController.onFooEnableRequest()。预计控制器会立即返回,但可以花时间消化请求,然后再调用DefaultFooModel.updateEnable(),这会导致真正的onFooEnableUpdate()被调用。

    方法2:在FooModel界面中构建一些内容,但我不确定是什么。

    方法3:不要在FooModel中构建任何东西,只需让它处理常规属性即可。而是让Controller监听FooModel.onFooEnableUpdate()并立即覆盖setEnable到旧值,然后稍后调用FooModel.setEnable()来设置新值。

    有什么建议吗?

1 个答案:

答案 0 :(得分:0)

使FooModel成为一个类而不是一个接口。

我认为使FooModel成为接口的问题是需要编码到监听器机制中的复杂逻辑。强制实现接口的任何人都必须实现监听器逻辑通常不是一个好主意。

相反,让FooModel成为一个类,自己实现监听器接口,并创造性地创建可以在需要实现更具体功能的地方重写的公共方法。

  • notifyListeners(boolean newEnable, boolean oldEnable)默认情况下通过调用以下方法通知所有侦听器,但可以被覆盖以不执行任何操作,或者有条件地通知
  • notifyListener(Listener listener, boolean newEnable, boolean oldEnable)通知特定的听众