开发者

MVP Flow question

I am implementing the MVP pattern with Windows Form and I have a question about the current implementation as I am trying to fit this into a more complex architecture. Right now I have a total agnostic view with properties, a presenter that get injected the view in the constructor and the view which has an instance of the presenter. This is the code: View

public class MyView : IMyView
{
   public MyView()
   {
      var presenter = new MyPresenter(this);
      presenter.Init();
   }
}

This is the Presenter

public class MyPresenter
{
   private IMyView view;
   private MyModel model;
   //
   public MyPresenter(IMyView view)
   {
      // injection
      this.view = view;
   }
}

In this way I can accomplish two tasks:

  • Call methods on the Presenter from the View
  • Interact with the View from the Presenter Now, I have two questions:
  • To orchestrate everything I am using the IoC container so that I can easily write code like this one:

    var view = ioc.Resolve<IMyView>();
    var presenter = ioc.Resolve<MyPresenter>(); //view injected
    NavigationService.Show(presenter.View);
    

    So far so good.

  • First question: how I can get back the Model from the Presenter when the job is done? The presenter used by the View is not the same I am using from the IoC container as the View instantiate a new Presenter by itself ... so the model exposed by the Presenter is not the same used by the Presenter instantiated in the View

  • Second question: how I can pass an existing model to this MVP triad when I have one? For example how can I make this code working for a Details V开发者_开发技巧iew where the Model is coming from a Repository?


To have a more clean approach inject the model to the presenter, too

public class MyPresenter
{
   private IMyView view;
   private MyModel model;

   public MyPresenter(IMyView view, MyModel model)
   {
      this.view = view;
      this.model = model
   }
}

By doing this you always have a reference to the model outside of the presenter where you created it.

When you are doing it like this, you can always choose which model you want to use. For example if your Backend (your model) is not finished, you could write a Mock-Model (when you use an interface for the model) to test your presenter and your view.

Hope this helped


Based on that I will change everything by inverting the dependencies. The view now doesn't create an instance of a presenter but it gets one injected by the presenter itself in the following way:

public MyPresenter(IView myView, Model myModel)
{
   this.View = myView;
   this.View.Presenter = this;
   this.Model = myModel;
}

So far, so good. Now on the View side, the Presenter is exposed as a Write Only property so that it can't be changed by the View, but it can be only used:

public class MyView : IView
{
   public MyPresenter Presenter { get; private set; }
}

So far so good. Now the IoC will do this:

var view = IoC.Resolve<IView>();
var model = repository.GetModel(); // or new Model();
var presenter = IoC.Resolve<MyPresenter>(); //view and model injected
presenter.ShowView();
var result = presenter.Model;

For me, it looks nice but I just want to be sure that I am not breaking the MVP logic.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜