Mvp View知道模型

我正在尝试使用MVP,我注意到我的视图必须知道模型不应该发生在我认为的MVP中。

这是一个例子:

public partial class TestForm : Form, ITestView { public void LoadList(IEnumerable data) { testPresenterBindingSource.DataSource = data; } } public interface ITestView { event EventHandler Load; void LoadList(IEnumerable data); } public class TestPresenter { private ITestView view; public TestPresenter(ITestView view) { this.view = view; view.Load += View_Load; } private void View_Load(object sender, EventArgs e) { var data = // get from model view.LoadList(data); } } 

问题是在TestForm中我需要引用AppSignature。 在我看到的所有教程中,都有一些简单的例子,例如public void LoadList(IEnumerable data) ,其中不需要引用模型。 但是DataGridView如何发布当前行数据呢?

您的表单是一个视图,它不是演示者。 因此它应该实现接口ITestView

 public interface ITestView { event EventHandler Load; void LoadList(IEnumerable data); } 

您的Presenter是订阅视图事件并使用视图属性读取和更新视图的人:

 public class TestPresenter { private ITestView view; public TestPresenter(ITestView view) { this.view = view; view.Load += View_Load; } private void View_Load(object sender, EventArgs e) { List signatures = // get from model List signatureDtos = // map domain class to dto view.LoadList(signatureDtos); } } 

正如我已经说过的那样,你形成了一个观点,它对演示者和模型一无所知:

 public partial class TestForm : Form, ITestView { public event EventHandler Load; private void ButtonLoad_Click(object sender, EventArgs e) { if (Load != null) Load(this, EventArgs.Empty); } public void LoadList(IEnumerable data) { // populate grid view here } } 

如何处理域类的引用? 通常我提供只查看简单数据(字符串,整数,日期等),或者我创建数据传输对象,传递给视图(您可以将它们命名为FooView,FooDto等)。 您可以使用AtoMapper之类的东西轻松映射它们:

 List signatureDtos = Mapper.Map, List>(signatures); 

只要交互仅限于数据绑定,View就可以具有Model的知识。 即View不应该试图直接操纵Model。 View将始终将用户输入重定向到Presenter,Presenter将负责进一步的操作。 如果Presenter执行的任何操作导致Model状态发生更改,Model将通过数据绑定通知View。 模型将完全不知道View的存在。

可以在Presenter中获取DataSource并设置其DataSource吗? 例如演示者代码:

 Public void LoadData() { _view.Data.DataSource = Business.GetData().ToList(); } 

表格代码:

 Public BindingSource Data { get { return this.bsData; } } 

多亏了我不需要添加对View的任何引用,但我没有在任何其他来源中看到该解决方案。