Click here to Skip to main content
15,878,852 members
Articles / Desktop Programming / WPF
Tip/Trick

A Desktop App that Works Unchanged for WPF or WinForms

Rate me:
Please Sign up or sign in to vote.
5.00/5 (5 votes)
16 Nov 2020CPOL3 min read 8.2K   189   8   9
Usable demo demonstrating some aspects of application architecture
This is a program proposal for a standard MVVM application architecture that you can use with small adjustments for your Windows desktop applications.

App with command-lines

Introduction

I recently asked myself why I have to make a preliminary decision when creating a project in Visual Studio about what type of user interface I would like to use later. Isn't it often claimed that a user interface must be interchangeable without affecting the other layers? So I started to look at what makes WinForms and WPF applications different and what they might have in common. I have re-analyzed my own old template application that I used myself for years, rebuilt it, and reduced it to the essentials.

The result of my attempts is a standard MVVM application that can be used unchanged for different types of user interfaces.

BasicApplication Demo

For this demo, the name of the user interface to be ultimately used can be transmitted via the command line. Two types of user interfaces have been implemented so far: WinForms and WPF. Also, the IsSingleInstance parameter can be used to specify whether this application can be started multiple times or not. This parameter can also be transferred via the command line.

Since the correct exception handling involves some difficulties (especially with WPF user interfaces), this demo is delivered with complete exception handling. The application itself is predefined as a Windows-application in the Visual Studio project settings, but it also works as a console-application. For tests of exception handling, various test exceptions were commented out and saved in the code. If you want to test exception handling, I recommend running the application without debugging (use Ctrl-F5) and as a console application (to see additional test output).

Using the Code

Download the source, extract it and open the solution in Visual Studio.

To debug, set BasicAplication as Startup project.
Here, you can see on the left a sequence of test-messages during a normal run and the project structure in Visual Studio to the right:

Visual Studio projects

The Run- and Stop-Buttons have no function. They are only for demonstrating button-handling.

Basic Principles

The "BasicApplication" start project with the "Program" and "AppStarter" classes can be used almost unchanged for other applications. Exceptions are the test displays, test exceptions, and possibly your own initializations and disposals, see the following code excerpt from BasicApplication.AppStarter:

C#
private void PrepareStart()
{
    // Optional general preparations, e.g. set up logging.

    // Console.WriteLine("AppStarter.PrepareStart throws");
    // throw new ApplicationException("Test Exception 5!");
}

// Should be run through in any case when the main-application is closed.
// Disposes BusinessLogicViewModel, BusinessLogic and possibly other resources.
private void Cleanup()
{
    if (this._app != null)
    {
        this._app.UIShutdown -= OnUIShutdown;
        this._app.UIStartup -= OnUIStartup;
    }
    try
    {
        this._businessLogicViewModel?.Dispose();
    }
    catch { }
    try
    {
        this._businessLogic?.Dispose();
    }
    catch { }

    // Put your own additional disposals here.

    Program.Say("Clean up done.");
}

Other points of interest are documented in the code so that there should be no need for further code snippets.

The Model and ViewModel projects and their classes only need to be adapted concerning business-specific requirements. The basic structure and all interface classes can also remain unchanged.

The project "DependencyInjection" as well as the class "Model.AppSettings" are just made for this demo. They help to make the demo work with command-line parameters and UI-injection.

If you plan to use the code in a production environment, you should remove the test-displays, test-exceptions, and console output, have your own "AppSettings", and finally decide, which UI to use so that dependency injection is no longer required.

Conclusion and Points of Interest

I know this article is more of an architecture discussion than a much-needed application. If you find this article helpful or if you have criticism or suggestions for improvement, I would be very happy to hear from you. Of course, it would be particularly interesting to see whether other UI types could be implemented or what the whole thing would look like on other project platforms.

History

  • 16th November, 2020: Initial version

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior)
Germany Germany
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions

 
QuestionA glimmer Pin
klinkenbecker17-Nov-20 16:14
klinkenbecker17-Nov-20 16:14 
I have a glimmer of how this hangs together, but the author assumes a lot of context is already known.

For me, that is not the case and some background information would be helpful. For example, it is opaque to me, from just looking at the code, how the business logic interacts with the view logic. I understand the architectural principles of MVVM, but the specifics here are opaque.

This opacity leads me to think there is a lot of noise in the code and that this is really much more complicated than it needs to be (without being able to say how it might be made simpler). It could well be that I am missing some vital piece of context that would make it all fall into place.
QuestionThe corrected sources are online! Pin
Erik Nagel17-Nov-20 4:27
Erik Nagel17-Nov-20 4:27 
QuestionGood idea but bad example Pin
GerVenson17-Nov-20 0:50
professionalGerVenson17-Nov-20 0:50 
AnswerRe: Good idea but bad example Pin
Erik Nagel17-Nov-20 1:40
Erik Nagel17-Nov-20 1:40 
QuestionEven more problems Pin
Klaus Luedenscheidt16-Nov-20 18:28
Klaus Luedenscheidt16-Nov-20 18:28 
AnswerRe: Even more problems Pin
Erik Nagel17-Nov-20 0:05
Erik Nagel17-Nov-20 0:05 
QuestionCannot be compiled at all? Pin
Member 1019550516-Nov-20 1:49
professionalMember 1019550516-Nov-20 1:49 
AnswerRe: Cannot be compiled at all? Pin
Erik Nagel16-Nov-20 5:49
Erik Nagel16-Nov-20 5:49 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.