How to architect a WinForms app for hardware control using the MVP pattern?

94 Views Asked by At

I am trying to write a WinForms app to control a moving XY stage. In my first attempt I wrote all my logic inside the Form class, I believe this is called "code-behind" and not recommended and I now understand why. I have built several basic applications using the MVP pattern and I want to rewrite my project.

My app will move a stage on a predefined routine, but also allow manual control, so 2 modes. The main components are the UI and stage controller (hardware) that takes serial input.

I want to display the XY location, without direct serial communication inside UI logic. This means there must be a Model of the stage controller, that runs in the background and provides constant feedback and events such as StageMoved or StageStopped.

In addition, my application may be in the MovingToEdge state but doesn't accept any user input until the stage has stopped. I solve this issue with an enum and switch statements for state and if statements inside checking stage movement. Sometimes, my application is "Busy..." and I don't want users to interrupt, such as calibration.

A high-level overview of my current architecture: my UI code only updates the state variable, which when changed, will trigger the function OnStateChange that has a switch statement for the state.

Example:

private void OnStartButtonClick(...) {
  switch (state) {
    case ApplicationStates.Idle:
      changeStateTo(ApplicationStates.MovingToEdge);
      break;
  }
}

// Keep UI responsive, because some methods may take
// long time such as moving the stage and waiting for
// it to stop.
private async Task OnStateChange() {
  switch (state) {
    case ApplicationStates.MovingToEdge:
      Console.WriteLine("Moving stage to edge");
      await Controller.MoveStageToEdge();
      Console.WriteLine("Stage stopped moving");
      break;
  }
}

// This function is called every 33ms
private void OnUpdateUITick(...) {
  switch (state) {
    case ApplicationStates.MovingToEdge:
      if (Controller.IsStageMoving())
        StartButton.Enabled = false;
      else
        StartButton.Enabled = true;
      break;
  }
}

How do I implement real-time feedback with MVP in Winforms?

0

There are 0 best solutions below