1

MVP 模式假设 View 向 Presenter 公开方法。例如在 View 中我们可以这样写:

public HasClickhandlers getButton() {
    return myBtn;
} 

并从演示者访问此方法,例如

view.getButton().addclickhanlder() ...

但是当我以这种风格构建我的应用程序时,我有很多不必要的代码。比如我要创建TablesViewand TablesPresenter(我决定TablesPresenterandTablesView是最小实体(minimal module),不能再分成更小的presenters和view,也不能更复杂)。然后,当我创建时TablesView,我想在这个视图中放入另一个自定义组件 - MyCustomTable。并且 Inside MyCustomTableput MyCustomHeader, inside MyCustomHeaderputMyCustomFilter等等(这个序列可能要长得多)......所以问题是当我想从 Presenter 访问输入的文本(按用户)里面MyCustomFilter时,我需要公开方法MyCustomFilter

//inside MyCustomFilter
public String getFilterText() {
   return textBox.getText();
}

然后在包含的小部件中MyCustomFilter- 即MyCustomHeader我需要公开此方法:

//inside MyCustomHeader
public String getFilterText() {
  return myCustomFilter.getFilterText();
}

在它之后,MyCustomTable我需要在里面公开这个方法:

//inside MyCustomTable
public String getFilterText() {
  return myCustomHeader.getFilterText();
}

之后,我需要在 内部(包含)公开getFilterText()方法,并且在所有这些操作之后,我的演示者可以访问内部的文本。有时这个序列更长。那么如何解决这个问题呢?可能是我不了解MVP的一些事情吗?TablesViewMyCustomTableMyCustomFilter

4

2 回答 2

2

您的视图没有理由不能返回其组件之一的视图,但您必须从组件化的角度考虑:这会破坏封装,然后您的视图会暴露其内部。

另外,请记住,GWT 中 MVP 最重要的好处之一是您可以轻松地模拟您的视图并对您的演示者进行单元测试,而不会出现GWTTestCase. 有一些权衡可以使您的代码易于测试/可模拟。

于 2012-05-13T21:08:16.583 回答
1

解决它的一种方法是使用接口。这样,您就可以公开组件的视图,而无需在视图和演示者之间创建紧密耦合。

这些方面的东西:

public interface CustomFilter {
   String getFilterText();
   // other methods that might be accessed from your presenter
}

public class MyCustomFilter implements CustomFilter {

    @Override
    public String getFilterText() {
        return textBox.getText();
    }
}

您可以对其他组件执行相同的操作:

自定义标题:

public interface CustomHeader {
   CustomFilter getFilter();
   // or String getFilterText()
   // other methods that might be accessed from your presenter
}

public class MyCustomHeader implements CustomHeader {

    @Override
    public CustomFilter getFilter() {
        return myCustomFilter;
    }
}

自定义表:

public interface CustomTable {
   CustomHeader getHeader();
   // or Sring getFilterText();
   // other methods that might be accessed from your presenter
}

public class MyCustomTable implements CustomTable {

    @Override
    public CustomHeader getHeader() {
        return myCustomHeader;
    }
}

您可以决定是否只想在每个接口中公开一个字符串或整个客户端组件的接口。如果您公开整个界面,您可能会在演示者中进行这样的调用,从而违反demeter 定律

getView().getTable().getHeader().getFilter().getFilterText(). 

可能更好的解决方案是在您的接口中定义字符串,将层次结构的调用委托给您的CustomFilter接口:getView().getTable().getFilterText();even getView().getFilterText().

使用接口的另一个好处是,您可以轻松地模拟它们以对您的演示者进行单元测试,甚至可以单独查看组件,并且您可以轻松地在 UI 组件的不同实现之间创建切换(例如针对智能手机优化的组件等)无需更改演示者中​​的任何内容

于 2012-05-14T07:44:02.170 回答