开发者

Using Microsoft.VisualBasic.ApplicationServices to manage an application's single instance

I have managed to find 开发者_JS百科the following code from StackOverflow:

using Microsoft.VisualBasic.ApplicationServices;
using System.Windows.Forms;

namespace ExciteEngine2.MainApplication {

    public class SingleInstanceController: WindowsFormsApplicationBase {

        public delegate Form CreateMainForm();
        public delegate void StartNextInstanceDelegate(Form mainWindow);
        private readonly CreateMainForm formCreation;
        private readonly StartNextInstanceDelegate onStartNextInstance;

        public SingleInstanceController() {

        }
        public SingleInstanceController(AuthenticationMode authenticationMode)
            : base(authenticationMode) {

        }

        public SingleInstanceController(CreateMainForm formCreation, StartNextInstanceDelegate onStartNextInstance) {
            // Set whether the application is single instance
            this.formCreation = formCreation;
            this.onStartNextInstance = onStartNextInstance;
            IsSingleInstance = true;

            StartupNextInstance += this_StartupNextInstance;
        }

        private void this_StartupNextInstance(object sender, StartupNextInstanceEventArgs e) {
            if (onStartNextInstance != null) {
                onStartNextInstance(MainForm); 
                // This code will be executed when the user tries to start the running program again,
                // for example, by clicking on the exe file.
                // This code can determine how to re-activate the existing main window of the running application.
            }
        }

        protected override void OnCreateMainForm() {
            // Instantiate your main application form
            MainForm = formCreation();
        }

        //public void Run() {
        //  string[] commandLine = new string[0];
        //  base.Run(commandLine);
        //}

        protected override void OnRun() {
            base.OnRun();
        }

    }

}

And I have this in my Program.cs:

    private static Form CreateForm() {
        return new AppMDIRibbon();
    }

    private static void OnStartNextInstance(Form mainWindow)            
    {
        // When the user tries to restart the application again, the main window is activated again.
        mainWindow.WindowState = FormWindowState.Maximized;
    }

    [STAThread]
    static void Main(string[] args) {

        SingleInstanceController ApplicationSingleInstanceController = new SingleInstanceController(CreateForm, OnStartNextInstance);           
        ApplicationSingleInstanceController.Run(args);   

        #region Application Logic
        #endregion
    }

Now, I have a lot of application logic that I need BEFORE the Run():

        #region Application Logic
        //Uninstall
        foreach (string arg in args) {
            if (arg.Split('=')[0] == "/u") {
                ApplicationLogger.Info("Uninstallation command received.");
                Process.Start(new ProcessStartInfo(Environment.GetFolderPath(Environment.SpecialFolder.System) + "\\msiexec.exe", "/x " + arg.Split('=')[1]));
                return;
            }
        }

        SetupXPO();
        SetupLogging();

        Thread.CurrentThread.CurrentCulture = new CultureInfo("en-GB");
        Thread.CurrentThread.CurrentUICulture = new CultureInfo("en-GB");

        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);

        Application.ThreadException += Application_ThreadException;

        try {
            ApplicationLogger.Info("Setting Telerik Theme: " + ConfigurationManager.AppSettings["ThemeToUse"]);
            ThemeResolutionService.ApplicationThemeName = ConfigurationManager.AppSettings["ThemeToUse"];

        }
        catch (Exception ex) {
            ApplicationLogger.Error("Exception while setting Telerik Theme.", ex);
            ThemeResolutionService.ApplicationThemeName = "ControlDefault";

        }

        DevExpress.UserSkins.OfficeSkins.Register();
        DevExpress.UserSkins.BonusSkins.Register();
        DevExpress.Skins.SkinManager.EnableFormSkins();
        DevExpress.Skins.SkinManager.EnableMdiFormSkins();

        if (args.Contains("/dx")) {
            Application.Run(new AppMDIRibbonDX());
            ApplicationLogger.Info("Application (DX) started.");

        }
        else {
            Application.Run(new AppMDIRibbon());
            ApplicationLogger.Info("Application started.");

        }
        #endregion

How can I setup this logic? I'm using a commandline argument to actually start an alternate form. I'm using a commandline argument to cause an uninstallation and also calling some method to setup DB and logging. Similarly, I'm setting up culture and themes too. All this before the actual application run. Can anyone suggest?


If you simplify the Visual Basic-derived class you linked, you can just replace your current call to Application.Run(). This does depend on how you want to handle subsequent instances.

With the version below, just change you calls of: Application.Run(myForm) to SingleInstanceApplication.Run(myForm);

public sealed class SingleInstanceApplication : WindowsFormsApplicationBase
{
    private static SingleInstanceApplication _application;

    private SingleInstanceApplication()
    {
        base.IsSingleInstance = true;
    }

    public static void Run(Form form)
    {
        _application = new SingleInstanceApplication {MainForm = form};

        _application.StartupNextInstance += NextInstanceHandler;
        _application.Run(Environment.GetCommandLineArgs());
    }

    static void NextInstanceHandler(object sender, StartupNextInstanceEventArgs e)
    {
        // Do whatever you want to do when the user launches subsequent instances
        // like when the user tries to restart the application again, the main window is activated again.
        _application.MainWindow.WindowState = FormWindowState.Maximized;
    }
}

Then your Main() method contains your "Application Logic"

   [STAThread]
    static void Main(string[] args) {

        #region Application Logic
        //Uninstall
        foreach (string arg in args) {
            if (arg.Split('=')[0] == "/u") {
                ApplicationLogger.Info("Uninstallation command received.");
                Process.Start(new ProcessStartInfo(Environment.GetFolderPath(Environment.SpecialFolder.System) + "\\msiexec.exe", "/x " + arg.Split('=')[1]));
                return;
            }
        }

        SetupXPO();
        SetupLogging();

        Thread.CurrentThread.CurrentCulture = new CultureInfo("en-GB");
        Thread.CurrentThread.CurrentUICulture = new CultureInfo("en-GB");

        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);

        Application.ThreadException += Application_ThreadException;

        try {
            ApplicationLogger.Info("Setting Telerik Theme: " + ConfigurationManager.AppSettings["ThemeToUse"]);
            ThemeResolutionService.ApplicationThemeName = ConfigurationManager.AppSettings["ThemeToUse"];

        }
        catch (Exception ex) {
            ApplicationLogger.Error("Exception while setting Telerik Theme.", ex);
            ThemeResolutionService.ApplicationThemeName = "ControlDefault";

        }

        DevExpress.UserSkins.OfficeSkins.Register();
        DevExpress.UserSkins.BonusSkins.Register();
        DevExpress.Skins.SkinManager.EnableFormSkins();
        DevExpress.Skins.SkinManager.EnableMdiFormSkins();

        if (args.Contains("/dx")) {
            SingleInstanceApplication.Run(new AppMDIRibbonDX());
            ApplicationLogger.Info("Application (DX) started.");

        }
        else {
            SingleInstanceApplication.Run(new AppMDIRibbon());
            ApplicationLogger.Info("Application started.");

        }
        #endregion
    }
0

上一篇:

下一篇:

精彩评论

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

最新问答

问答排行榜