写点什么

C#开发单实例应用程序并响应后续进程启动参数

  • 2024-07-08
    福建
  • 本文字数:1800 字

    阅读完需:约 6 分钟

C#默认的 WinForm 模板是不支持设置单实例的,也没有隔壁大哥 VB.NET 那样有个“生成单个实例应用程序”的勾选选项(VB 某些时候要比 C#更方便),实现单实例可以有多种方法:


  • 检测同名进程:Process.GetProcessesByName(Process.GetCurrentProcess().ProcessName),如果集合的 Length > 1 那就表明已有同名进程了,如果有需要还可以进一步检查该进程的路径;

  • 命名互斥锁:Mutex,网上介绍的很多都是这种方法;

  • 锁定文件:使用 File.Create 方法创建文件并在程序退出时释放,如果创建失败则表明已经有实例在运行;

  • VB.NET 方法:WindowsFormsApplicationBase,个人认为该方法最完美,可以接收后续进程的启动参数,还可以弹出前序进程的主窗体。


WindowsFormsApplicationBase 是一个 Microsoft.VisualBasic.ApplicationServices 命名空间下的类,是微软为 VB.NET 实现应用程序启动控制的类,其内部是以命名管道通信来实现的。既然是同一个爹的东西,C#拿过来用毫无违和感。Microsoft.VisualBasic 和 Microsoft.CSharp 一样,都是.NET Framework 中的一部分,不用担心会缺少运行环境。


WindowsFormsApplicationBase 类的一些常用属性和方法:

  • 属性 IsSingleInstance:设置当前进程是否为单实例进程,在构造方法中设置,如果是后续进程且为值 true,构造方法结束后会给前序进程发送启动参数,然后就退出进程了,不会执行到下面的 OnStartup;

  • 方法 OnStartup:首次启动后运行,返回 false 就会退出进程,后续进程永远不会运行到该方法;

  • 方法 OnStartupNextInstance:后续进程启动后的重写方法,前序进程会接收到后续进程的启动参数,弹出主窗体等;

  • 方法 OnCreateMainForm:创建主窗体的重写方法,必须指定主窗体。


创建一个单实例应用程序并响应后续进程参数的大概过程:

  • 创建一个项目名称为“SingleInstanceSample”的 Windows 窗体项目;

  • 添加引用“Microsoft.VisualBasic”;

  • 重命名“Form1”为“MainForm”;

  • 添加类“ApplicationBase.cs”,继承自“WindowsFormsApplicationBase”;

  • 修改“Program.cs”,从“ApplicationBase”启动。


各个类的代码如下:

  • Program.cs 

using System;using System.Windows.Forms;
namespace SingleInstanceSample{ internal static class Program { [STAThread] static void Main(string[] args) { Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false);
var app = new ApplicationBase(); app.Run(args); } }}
复制代码


  • ApplicationBase.cs

using Microsoft.VisualBasic.ApplicationServices;using System.IO;
namespace SingleInstanceSample{ internal class ApplicationBase : WindowsFormsApplicationBase { public ApplicationBase() : base(AuthenticationMode.Windows) { //指示进程为单进程:IsSingleInstance base.IsSingleInstance = true; base.SaveMySettingsOnExit = true; base.ShutdownStyle = ShutdownMode.AfterMainFormCloses; }
/// <summary> /// 首次启动后的重写方法,返回false就会退出进程, /// 比如可以显示登录窗体,登录失败返回false就不会运行到OnCreateMainForm /// </summary> protected override bool OnStartup(StartupEventArgs eventArgs) { base.OnStartup(eventArgs);
//处理当前进程的启动参数
return true; }
/// <summary> /// 后续进程启动后的重写方法 /// </summary> protected override void OnStartupNextInstance(StartupNextInstanceEventArgs eventArgs) { base.OnStartupNextInstance(eventArgs);
//处理后续进程的启动参数 }
/// <summary> /// 指定主窗体, /// 除非OnStartup返回false,否则必须指定主窗体 /// </summary> protected override void OnCreateMainForm() { base.MainForm = new MainForm(); } }}
复制代码


文章转载自:【一路向东】

原文链接:https://www.cnblogs.com/yiluxiangdong/p/18288392

体验地址:http://www.jnpfsoft.com/?from=infoq

用户头像

还未添加个人签名 2023-06-19 加入

还未添加个人简介

评论

发布
暂无评论
C#开发单实例应用程序并响应后续进程启动参数_C#_不在线第一只蜗牛_InfoQ写作社区