📜 ⬆️ ⬇️

Features of MVP implementation for Windows Forms

Good day!
Model-View-Presenter is a fairly well-known design pattern. At first glance, everything looks simple: there is a Model (Model), which contains all the business logic of the screen; A view / View that knows how to display certain data; The representative (Presenter), which is the link - responds to user actions in the View, changing the Model, and vice versa.
The complexity begins when the number of forms in the project becomes more than one.
This article discusses:
- a little bit of theory;
- common problems of implementing MVP (namely Passive View) under Windows Forms;
- features of the implementation of transitions between forms and the transfer of parameters, modal windows;
- using the IoC container and the Dependency Injection - DI template (namely, Constructor Injection);
- some features of testing MVP applications (using NUnit and NSubstitute);
- all this will occur on the example of a mini-project and will try to be visual.
The article covers:
- application of the Adapter pattern;
- a simple implementation of the Application Controller pattern.
Who is this article for?
Mainly for novice Windows Forms developers who have heard, but have not tried, or tried, but failed. Although I am sure that some tricks are applicable for WPF, and even for web development.

Formulation of the problem


We come up with a simple task - to implement 3 screens:
1) authorization screen;
2) the main screen;
3) modal screen change user name.
It should get something like this:



Some theory


MVP, like its parent, MVC (Model-View-Controller) is invented for the convenience of separating business logic from the way it is displayed.
')


On the Internet, you can find a lot of MVP implementations. By the way the data is delivered to the view, they can be divided into 3 categories:
- Passive View: View contains the minimal logic for displaying primitive data (strings, numbers), the rest is handled by Presenter;
- Presentation Model: not only primitive data can be transferred to the View, but also business objects;
- Supervising Controller: View is aware of the presence of the model and itself takes data from it.

Next will be considered a modification of Passive View. We describe the main features:
- View interface (IView), which provides a contract for displaying data;
- Presentation is a specific IView implementation that can display itself in a specific interface (be it Windows Forms, WPF or even a console) and knows nothing about who controls it. In our case, these are forms;
- Model - provides some business logic (examples: database access, repositories, services). It can be represented as a class or, again, as an interface and implementation;
- The representative contains a link to the View through the interface (IView), manages it, subscribes to its events, performs simple validation (verification) of the entered data; also contains a link to the model or its interface, passing data from the View to it and requesting updates.

Typical Representative Representative implementation
public class Presenter { private readonly IView _view; private readonly IService _service; public Presenter(IView view, IService service) { _view = view; _service = service; _view.UserIdChanged += () => UpdateUserInfo(); } private void UpdateUserInfo() { var user = _service.GetUser(_view.UserId); _view.Username = user.Username; _view.Age = user.Age; } } 

What advantages does the low connectivity of classes give us (use of interfaces, events)?
1. Allows relatively free to change the logic of any component without breaking the rest.
2. Great opportunities for unit testing. TDD fans should be thrilled.
Let's start!

How to organize projects?


We agree that the solution will consist of 4 projects:
- DomainModel - contains services and various repositories, in one word - model;
- Presentation - contains the application logic that is independent of the visual presentation, i.e. All Representatives, Views interfaces and other base classes;
- UI - Windows Forms application, contains only forms (implementation of the interfaces of Views) and startup logic;
- Tests - unit tests.

What to write in Main ()?


The standard implementation of running a Windows Forms application is as follows:

 private static void Main() { Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); Application.Run(new MainForm()); //    () } 

But we agreed that the Representatives would manage the Views, therefore I would like the code to look something like this:

 private static void Main() { Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); var presenter = new LoginPresenter(new LoginForm(), new LoginService()); // Dependency Injection presenter.Run(); } 

Let's try to implement the first screen:

Basic interfaces
 //      public interface IView { void Show(); void Close(); } // ,        public interface ILoginView : IView { string Username { get; } string Password { get; } event Action Login; //  "  " void ShowError(string errorMessage); } public interface IPresenter { void Run(); } //    public interface ILoginService { bool Login(User user); // true -  ,  false } 

Representation
 public class LoginPresenter : IPresenter { private readonly ILoginView _view; private readonly ILoginService _service; public LoginPresenter(ILoginView view, ILoginService service) { _view = view; _service = service; _view.Login += () => Login(_view.Username, _view.Password); } public void Run() { _view.Show(); } private void Login(string username, string password) { if (username == null) throw new ArgumentNullException("username"); if (password == null) throw new ArgumentNullException("password"); var user = new User {Name = username, Password = password}; if (!_service.Login(user)) { _view.ShowError("Invalid username or password"); } else { //  ,    (?) } } } 

It is easy to create a form and implement the ILoginView interface in it, just like writing the implementation of ILoginService. It should only be noted one feature:

 public partial class LoginForm : Form, ILoginView { // ... public new void Show() { Application.Run(this); } } 

This spell will allow our application to start, display the form, and on closing the form correctly complete the application. But we will come back to this.

And the tests will be?


From the moment of writing the representative (LoginPresenter), it is possible to immediately test-unit-test it without implementing any form or services.
For writing tests, I used the NUnit and NSubstitute libraries (the library for creating stub classes for their interfaces, mock).

Tests for LoginPresenter
 [TestFixture] public class LoginPresenterTests { private ILoginView _view; [SetUp] public void SetUp() { _view = Substitute.For<ILoginView>(); //    var service = Substitute.For<ILoginService>(); //    service.Login(Arg.Any<User>()) //    admin/password .Returns(info => info.Arg<User>().Name == "admin" && info.Arg<User>().Password == "password"); var presenter = new LoginPresenter(_view, service); presenter.Run(); } [Test] public void InvalidUser() { _view.Username.Returns("Vladimir"); _view.Password.Returns("VladimirPass"); _view.Login += Raise.Event<Action>(); _view.Received().ShowError(Arg.Any<string>()); //        } [Test] public void ValidUser() { _view.Username.Returns("admin"); _view.Password.Returns("password"); _view.Login += Raise.Event<Action>(); _view.DidNotReceive().ShowError(Arg.Any<string>()); //       } } 

The tests are pretty stupid, as is the application itself. But one way or another, they have been successfully passed.

Who and how will launch the second screen with the parameter?


As you can see, I did not write any code upon successful authorization. How can I launch the second screen? The first thing that comes to mind is:

 // LoginPresenter:   var mainPresenter = new MainPresenter(new MainForm()); mainPresenter.Run(user); 

But we agreed that representatives know nothing about representations except their interfaces. What to do?
The Application Controller pattern comes to the rescue (simplifiedly implemented), inside of which there is an IoC container that knows how to get an implementation object using the interface.
The controller is passed to each Representative by the constructor parameter (DI again) and implements approximately the following methods:

 public interface IApplicationController { IApplicationController RegisterView<TView, TImplementation>() where TImplementation : class, TView where TView : IView; IApplicationController RegisterService<TService, TImplementation>() where TImplementation : class, TService; void Run<TPresenter>() where TPresenter : class, IPresenter; } 

After a little refactoring, the launch of the application began to look like this:

 private static void Main() { Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); //       : var controller = new ApplicationController(new LightInjectAdapder()) .RegisterView<ILoginView, LoginForm>() .RegisterService<ILoginService, StupidLoginService>() .RegisterView<IMainView, MainForm>(); controller.Run<LoginPresenter>(); } 

A few words about new ApplicationController(new LightInjectAdapder()) . As an IoC container, I used the LightInject library, but not directly, but through an adapter (Adapter pattern), so that if I need to change the container to another, I could write another adapter and not change the controller logic. All the methods used are in most IoC libraries, difficulties should not arise.
We implement an additional interface
 IPresenter,   ,   Run  .       . 
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter
IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter
 IPresenter,   ,   Run  .       . 
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter
IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter
 IPresenter,   ,   Run  .       . 
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter
IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter
  1. IPresenter, , Run . .
    , , , :

    Controller.Run<MainPresener, User>(user); View.Close();

    ...
    View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
    , - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

    // LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

    . " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

    public new void Show() { ShowDialog(); }
    , , Form.

    ... ?
    , , :
    , ( ). , , - . [] , , . [] . .
    IoC- IContainer -.

    c Github ( Nuget-).

    , , - MVP, , , .

    . , , !
    , :
    - ( );
    - ( Event Aggregator);
    -

    ,
    , MVP
    Passive View
    Application Controller
    Application Controller Event Aggregator
    Application Controller
    MVP ,
    Presenter
  2. IPresenter, , Run . .
    , , , :

    Controller.Run<MainPresener, User>(user); View.Close();

    ...
    View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
    , - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

    // LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

    . " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

    public new void Show() { ShowDialog(); }
    , , Form.

    ... ?
    , , :
    , ( ). , , - . [] , , . [] . .
    IoC- IContainer -.

    c Github ( Nuget-).

    , , - MVP, , , .

    . , , !
    , :
    - ( );
    - ( Event Aggregator);
    -

    ,
    , MVP
    Passive View
    Application Controller
    Application Controller Event Aggregator
    Application Controller
    MVP ,
    Presenter
  3. IPresenter, , Run . .
    , , , :

    Controller.Run<MainPresener, User>(user); View.Close();

    ...
    View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
    , - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

    // LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

    . " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

    public new void Show() { ShowDialog(); }
    , , Form.

    ... ?
    , , :
    , ( ). , , - . [] , , . [] . .
    IoC- IContainer -.

    c Github ( Nuget-).

    , , - MVP, , , .

    . , , !
    , :
    - ( );
    - ( Event Aggregator);
    -

    ,
    , MVP
    Passive View
    Application Controller
    Application Controller Event Aggregator
    Application Controller
    MVP ,
    Presenter
  4. IPresenter, , Run . .
    , , , :

    Controller.Run<MainPresener, User>(user); View.Close();

    ...
    View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
    , - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

    // LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

    . " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

    public new void Show() { ShowDialog(); }
    , , Form.

    ... ?
    , , :
    , ( ). , , - . [] , , . [] . .
    IoC- IContainer -.

    c Github ( Nuget-).

    , , - MVP, , , .

    . , , !
    , :
    - ( );
    - ( Event Aggregator);
    -

    ,
    , MVP
    Passive View
    Application Controller
    Application Controller Event Aggregator
    Application Controller
    MVP ,
    Presenter
  5. IPresenter, , Run . .
    , , , :

    Controller.Run<MainPresener, User>(user); View.Close();

    ...
    View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
    , - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

    // LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

    . " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

    public new void Show() { ShowDialog(); }
    , , Form.

    ... ?
    , , :
    , ( ). , , - . [] , , . [] . .
    IoC- IContainer -.

    c Github ( Nuget-).

    , , - MVP, , , .

    . , , !
    , :
    - ( );
    - ( Event Aggregator);
    -

    ,
    , MVP
    Passive View
    Application Controller
    Application Controller Event Aggregator
    Application Controller
    MVP ,
    Presenter
IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

IPresenter, , Run . .
, , , :

Controller.Run<MainPresener, User>(user); View.Close();

...
View.Close() , , . , Application.Run(Form) Windows . , ExitThread Form.Closed , .
, - : Application.Run(ApplicationContext) , ApplicationContext.MainForm . , (instance) ApplicationContext ( DI) . :

// LoginForm public new void Show() { _context.MainForm = this; Application.Run(_context); } // MainForm public new void Show() { _context.MainForm = this; base.Show(); }

. " " Controller.Run<ChangeUsernamePresenter, User>(user) . - , ApplicationContext:

public new void Show() { ShowDialog(); }
, , Form.

... ?
, , :
, ( ). , , - . [] , , . [] . .
IoC- IContainer -.

c Github ( Nuget-).

, , - MVP, , , .

. , , !
, :
- ( );
- ( Event Aggregator);
-

,
, MVP
Passive View
Application Controller
Application Controller Event Aggregator
Application Controller
MVP ,
Presenter

Source: https://habr.com/ru/post/211899/


All Articles