如何在单击桌面快捷方式时从系统托盘中恢复单个实例应用程序
本文关键字:恢复 单个 应用程序 实例 系统 单击 桌面 快捷方式 | 更新日期: 2023-09-27 18:15:33
这是我的项目示例。
App.xaml.cs
using BackgroundApplication.Single_Instance_App;
using System.ComponentModel;
using System.Windows;
namespace BackgroundApplication
{
public partial class App : Application
{
private System.Windows.Forms.NotifyIcon _notifyIcon;
private bool _isExit;
protected override void OnStartup(StartupEventArgs e)
{
WpfSingleInstance.Make("MyWpfApplication", this);
base.OnStartup(e);
}
}
}
WpfSingleInstance.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows;
namespace BackgroundApplication.Single_Instance_App
{
public class WpfSingleInstance
{
internal static void Make(String name, Application app)
{
EventWaitHandle eventWaitHandle = null;
String eventName = Environment.MachineName + "-" + Environment.CurrentDirectory.Replace('''', '-') + "-" + name;
bool isFirstInstance = false;
try
{
eventWaitHandle = EventWaitHandle.OpenExisting(eventName);
}
catch
{
// it's first instance
isFirstInstance = true;
}
if (isFirstInstance)
{
eventWaitHandle = new EventWaitHandle(
false,
EventResetMode.AutoReset,
eventName);
ThreadPool.RegisterWaitForSingleObject(eventWaitHandle, waitOrTimerCallback, app, Timeout.Infinite, false);
// not need more
eventWaitHandle.Close();
}
else
{
eventWaitHandle.Set();
// For that exit no interceptions
Environment.Exit(0);
}
}
private static void waitOrTimerCallback(Object state, Boolean timedOut)
{
Application app = (Application)state;
app.Dispatcher.BeginInvoke(new activate(delegate () {
Application.Current.MainWindow.Activate();
}), null);
}
private delegate void activate();
}
}
MainWindow.xaml.cs
using Microsoft.Win32;
using System.Windows.Forms;
namespace BackgroundApplication
{
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
private System.Windows.Forms.NotifyIcon _notifyIcon;
private void CloseCustomButton_Click(object sender, RoutedEventArgs e)
{
this.ShowInTaskbar = false;
this.Hide();
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
_notifyIcon = new System.Windows.Forms.NotifyIcon();
_notifyIcon.DoubleClick += (s, args) => NormalMainWindow();
_notifyIcon.Icon = BackgroundApplication.Properties.Resources.MyIcon;
_notifyIcon.Visible = true;
_notifyIcon.BalloonTipText = "Background Processing is running";
_notifyIcon.BalloonTipTitle = "Information";
_notifyIcon.ShowBalloonTip(50);
CreateContextMenu();
}
private void CreateContextMenu()
{
_notifyIcon.ContextMenuStrip = new System.Windows.Forms.ContextMenuStrip();
_notifyIcon.ContextMenuStrip.Items.Add("Background Application").Click += (s, e) => NormalMainWindow();
_notifyIcon.ContextMenuStrip.Items.Add("Maximize").Click += (s, e) => MaxMainWindow();
_notifyIcon.ContextMenuStrip.Items.Add("Minimize").Click += (s, e) => MinMainWindow();
_notifyIcon.ContextMenuStrip.Items.Add("Exit").Click += (s, e) => ExitApplication();
}
private void NormalMainWindow()
{
if (this.IsVisible)
{
if (this.WindowState == WindowState.Minimized)
{
this.WindowState = WindowState.Normal;
this.ShowInTaskbar = true;
}
this.Activate();
}
else
{
this.Show();
}
}
private void MaxMainWindow()
{
if (this.IsVisible)
{
if (this.WindowState == WindowState.Normal)
{
this.WindowState = WindowState.Maximized;
this.ShowInTaskbar = true;
}
this.Activate();
}
else
{
this.Show();
this.WindowState = WindowState.Maximized;
this.Activate();
}
}
private void MinMainWindow()
{
if (this.IsVisible)
{
if ((this.WindowState == WindowState.Normal) || (this.WindowState == WindowState.Maximized))
{
this.WindowState = WindowState.Minimized;
this.ShowInTaskbar = true;
}
this.Activate();
}
else
{
return;
}
}
private void ExitApplication()
{
_isExit = true;
System.Windows.Application.Current.Shutdown();
_notifyIcon.Dispose();
_notifyIcon = null;
}
}
}
对于单实例应用程序是完全可以的&托盘系统。
但是我如何从系统托盘中恢复这个应用程序时,点击桌面快捷方式(通过点击"后台应用程序。exe")????
看看创建单实例应用程序的正确方法是什么?
基本上,这个想法是当你启动应用程序的第二个实例,并检测到你已经在运行时,你广播一个窗口消息,你的其他实例(真正的实例)将捕获,然后将自己带回前台。第二个实例在发送消息后立即退出。
试试这个:
[DllImport("user32.dll")]
private static extern IntPtr FindWindow(String lpClassName, String lpWindowName);