C#應用程式只允許執行一個例項,多次執行的時候啟用當前例項,顯示其介面
阿新 • • 發佈:2019-01-31
很多時候,我們開發的程式,需要單例執行的的功能,即整個應用程式只允許同時執行最多一個例項,重複執行的時候,啟用當前實力,顯示其介面。
在C#程式中,其解決方案有多重,可以參照Charles Chen 的C#程式只允許執行一個例項的解決方案一文。
參照其文章,我決定使用呼叫Windows Api的方法,大致如下:
namespace BarCodeSystem
{
public static class Program
{
/// <summary>
/// Application Entry Point.
/// </summary>
[System.STAThreadAttribute()]
[System.Diagnostics.DebuggerNonUserCodeAttribute()]
[System.CodeDom.Compiler.GeneratedCodeAttribute("PresentationBuildTasks", "4.0.0.0")]
public static void Main()
{
Process instance = RunningInstance();
if (instance == null)
{
BarCodeSystem.App app = new BarCodeSystem.App();
app.InitializeComponent();
app.Run();
}
else
{
HandleRunningInstance(instance);
}
}
/// <summary>
/// 獲取程序
/// </summary>
/// <returns></returns>
public static Process RunningInstance()
{
Process current = Process.GetCurrentProcess();
Process[] processes = Process.GetProcessesByName(current.ProcessName);
foreach (Process process in processes)
{
if (process.Id != current.Id)
{
if (process.MainModule.FileName == current.MainModule.FileName)
{
return process;
}
}
}
return null;
}
/// <summary>
/// 處理程序
/// </summary>
/// <param name="instance"></param>
public static void HandleRunningInstance(Process instance)
{
MyProcess mp = new MyProcess();
IntPtr x = mp.GetMainWindowHandle(instance.Id);
Application.EnableVisualStyles();
//確保窗體不是最大化或者最小化
ShowWindowAsync(x, WS_SHOWNORMAL);
//將例項放置到前臺
SetForegroundWindow(instance.MainWindowHandle);
}
///<summary>
/// 該函式設定由不同執行緒產生的視窗的顯示狀態
/// </summary>
/// <param name="hWnd">視窗控制代碼</param>
/// <param name="cmdShow">指定視窗如何顯示。檢視允許值列表,請查閱ShowWlndow函式的說明部分</param>
/// <returns>如果函式原來可見,返回值為非零;如果函式原來被隱藏,返回值為零</returns>
[DllImport("User32.dll")]
private static extern bool ShowWindowAsync(IntPtr hWnd, int cmdShow);
/// <summary>
/// 該函式將建立指定視窗的執行緒設定到前臺,並且啟用該視窗。鍵盤輸入轉向該視窗,併為使用者改各種可視的記號。
/// 系統給建立前臺視窗的執行緒分配的許可權稍高於其他執行緒。
/// </summary>
/// <param name="hWnd">將被啟用並被調入前臺的視窗控制代碼</param>
/// <returns>如果視窗設入了前臺,返回值為非零;如果視窗未被設入前臺,返回值為零</returns>
[DllImport("User32.dll")]
private static extern bool SetForegroundWindow(IntPtr hWnd);
}
}
這裡,我自定義了Main函式,當然,也可以在專案中本來的Main函式中新增程式碼,達到相同的效果。
關於WPF專案如何自定義Main函式,可以參考這篇文章。