Search code examples
c#winformsdesign-patternsmvp

MVP pattern in winforms - Handling events


I just started with C# and MVP design pattern. I'm in doubt about concrete implementation when it comes to event handling. I'm aware of that, view shouldn't know about presenter and presenter should control a view through view interface.

Let's say I have 2 text boxes and would like to check for errors. If an error occurs I want to change text box Text property. Is it wrong approach to create one EventHandler and use sender object to verify witch text box is user currently using?

Something like:

IView:

interface IMainView
{
    event KeyPressEventHandler KeyPressed;
}

View:

public partial class MainView : Form, IMainView
{
    public frmInterakcija()
    {
        InitializeComponent();
        this.textBox1.Name = "textBox1";
        this.textBox2.Name = "textBox2";
        new MainPresenter();
        Bind();
    }

    private void Bind()
    {

       this.textBox1.KeyPress += KeyPressed;
       this.textBox2.KeyPress += KeyPressed;
    }
}

Presenter:

class MainPresenter
{
    private IMainView _view;

    public MainPresenter(IMainView view) 
    {
        _view = view;
        this.initialize();

    }

    public void initialize()
    {
        _view.KeyPressed += _view_textBoxKeyPressed;
    }

    public void _view_textBoxKeyPressed(object sender, EventArgs e)
    {
        if (sender.GetType() == typeof(TextBox))
        {
            TextBox textBox = (TextBox)sender;
            if (textBox.Name.Equals("textbox1") 
                {...} // Do validation/changes on textbox1
            else ...

        }
    }
 }

Or instead of this above I should create event handler for every textbox I have and update/handle errors through properties? (this will make my code redundant I guess)

What would be right approach?


Solution

  • IMHO the presenter should be unaware of view specific objects (example textbox in your code). That kind of logic should not be in presenter. And presenter must not know about the Ids of controls in the UI, that's even worse. Remember one of the benefits of this should be that you can test the presenter by mocking the view, if you have UI specific code you won't be able to unit test the presenter.

    It does seem like two different events to me since you are doing different logic. I'd raise two different events and one would do validation, the other would do its own logic. The presenter won't have to check if the sender is textbox or the id of the textbox. Also what if you have another textbox, you'll need another if condition in this current implementation.

    Also, in the view, it should be new MainPresenter(this);