From 25c56f952fbf21f2c0870030807ed296da91a31b Mon Sep 17 00:00:00 2001 From: Jack251970 <1160210343@qq.com> Date: Sat, 7 Jun 2025 20:17:39 +0800 Subject: [PATCH 1/3] Display notify icon before loading plugins to tell users that Flow is loading --- Flow.Launcher/App.xaml.cs | 19 +++++++++++++++++++ Flow.Launcher/MainWindow.xaml.cs | 25 ++++++++----------------- 2 files changed, 27 insertions(+), 17 deletions(-) diff --git a/Flow.Launcher/App.xaml.cs b/Flow.Launcher/App.xaml.cs index cedced181f2..c2751dff79f 100644 --- a/Flow.Launcher/App.xaml.cs +++ b/Flow.Launcher/App.xaml.cs @@ -24,6 +24,7 @@ using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Hosting; using Microsoft.VisualStudio.Threading; +using NotifyIcon = System.Windows.Forms.NotifyIcon; namespace Flow.Launcher { @@ -32,6 +33,7 @@ public partial class App : IDisposable, ISingleInstanceApp #region Public Properties public static IPublicAPI API { get; private set; } + public static NotifyIcon NotifyIcon { get; private set; } public static bool LoadingOrExiting => _mainWindow == null || _mainWindow.CanClose; #endregion @@ -152,6 +154,20 @@ public static void Main() #endregion + #region Notify Icon + + private void InitializeNotifyIcon() + { + NotifyIcon = new NotifyIcon + { + Text = Constant.FlowLauncherFullName, + Icon = Constant.Version == "1.0.0" ? Launcher.Properties.Resources.dev : Launcher.Properties.Resources.app, + Visible = !_settings.HideNotifyIcon + }; + } + + #endregion + #region App Events #pragma warning disable VSTHRD100 // Avoid async void methods @@ -180,6 +196,9 @@ await API.StopwatchLogInfoAsync(ClassName, "Startup cost", async () => RegisterDispatcherUnhandledException(); RegisterTaskSchedulerUnhandledException(); + // Display notify icon before loading plugins to tell users that Flow is loading + InitializeNotifyIcon(); + var imageLoadertask = ImageLoader.InitializeAsync(); AbstractPluginEnvironment.PreStartPluginExecutablePathUpdate(_settings); diff --git a/Flow.Launcher/MainWindow.xaml.cs b/Flow.Launcher/MainWindow.xaml.cs index a77d6471c7a..3aeca045b25 100644 --- a/Flow.Launcher/MainWindow.xaml.cs +++ b/Flow.Launcher/MainWindow.xaml.cs @@ -27,7 +27,6 @@ using DataObject = System.Windows.DataObject; using Key = System.Windows.Input.Key; using MouseButtons = System.Windows.Forms.MouseButtons; -using NotifyIcon = System.Windows.Forms.NotifyIcon; using Screen = System.Windows.Forms.Screen; namespace Flow.Launcher @@ -47,11 +46,10 @@ public partial class MainWindow : IDisposable private readonly Settings _settings; private readonly Theme _theme; - // Window Notify Icon - private NotifyIcon _notifyIcon; - // Window Context Menu - private readonly ContextMenu _contextMenu = new(); + private static readonly ContextMenu _contextMenu = new(); + + // Window View Model private readonly MainViewModel _viewModel; // Window Event: Key Event @@ -243,7 +241,7 @@ private void OnLoaded(object sender, RoutedEventArgs _) } break; case nameof(MainViewModel.GameModeStatus): - _notifyIcon.Icon = _viewModel.GameModeStatus + App.NotifyIcon.Icon = _viewModel.GameModeStatus ? Properties.Resources.gamemode : Properties.Resources.app; break; @@ -256,7 +254,7 @@ private void OnLoaded(object sender, RoutedEventArgs _) switch (e.PropertyName) { case nameof(Settings.HideNotifyIcon): - _notifyIcon.Visible = !_settings.HideNotifyIcon; + App.NotifyIcon.Visible = !_settings.HideNotifyIcon; break; case nameof(Settings.Language): UpdateNotifyIconText(); @@ -317,7 +315,7 @@ private async void OnClosing(object sender, CancelEventArgs e) if (!CanClose) { CanClose = true; - _notifyIcon.Visible = false; + App.NotifyIcon.Visible = false; App.API.SaveAppAllSettings(); e.Cancel = true; await ImageLoader.WaitSaveAsync(); @@ -663,14 +661,7 @@ private void SoundPlay() private void InitializeNotifyIcon() { - _notifyIcon = new NotifyIcon - { - Text = Constant.FlowLauncherFullName, - Icon = Constant.Version == "1.0.0" ? Properties.Resources.dev : Properties.Resources.app, - Visible = !_settings.HideNotifyIcon - }; - - _notifyIcon.MouseClick += (o, e) => + App.NotifyIcon.MouseClick += (o, e) => { switch (e.Button) { @@ -1322,7 +1313,7 @@ protected virtual void Dispose(bool disposing) if (disposing) { _hwndSource?.Dispose(); - _notifyIcon?.Dispose(); + App.NotifyIcon?.Dispose(); animationSoundWMP?.Close(); animationSoundWPF?.Dispose(); ModernWpf.ThemeManager.Current.ActualApplicationThemeChanged -= ThemeManager_ActualApplicationThemeChanged; From 8a96103a6b6ebe9f7f4a7eb5a994a9932aca69c5 Mon Sep 17 00:00:00 2001 From: Jack251970 <1160210343@qq.com> Date: Sat, 7 Jun 2025 20:21:39 +0800 Subject: [PATCH 2/3] Dispose notify icon in App --- Flow.Launcher/App.xaml.cs | 7 +++++++ Flow.Launcher/MainWindow.xaml.cs | 1 - 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/Flow.Launcher/App.xaml.cs b/Flow.Launcher/App.xaml.cs index c2751dff79f..adf08df53fb 100644 --- a/Flow.Launcher/App.xaml.cs +++ b/Flow.Launcher/App.xaml.cs @@ -372,6 +372,13 @@ protected virtual void Dispose(bool disposing) if (disposing) { + // Dispose notify icon first to prevent it from showing balloon tip after main window is closed + if (NotifyIcon != null) + { + NotifyIcon.Visible = false; + NotifyIcon.Dispose(); + } + // Dispose needs to be called on the main Windows thread, // since some resources owned by the thread need to be disposed. _mainWindow?.Dispatcher.Invoke(_mainWindow.Dispose); diff --git a/Flow.Launcher/MainWindow.xaml.cs b/Flow.Launcher/MainWindow.xaml.cs index 3aeca045b25..100e916ef2c 100644 --- a/Flow.Launcher/MainWindow.xaml.cs +++ b/Flow.Launcher/MainWindow.xaml.cs @@ -1313,7 +1313,6 @@ protected virtual void Dispose(bool disposing) if (disposing) { _hwndSource?.Dispose(); - App.NotifyIcon?.Dispose(); animationSoundWMP?.Close(); animationSoundWPF?.Dispose(); ModernWpf.ThemeManager.Current.ActualApplicationThemeChanged -= ThemeManager_ActualApplicationThemeChanged; From 736d96ea95338500eee13cfcaed46e8277604dfc Mon Sep 17 00:00:00 2001 From: Jack251970 <1160210343@qq.com> Date: Mon, 16 Jun 2025 21:55:35 +0800 Subject: [PATCH 3/3] Use static function --- Flow.Launcher/App.xaml.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Flow.Launcher/App.xaml.cs b/Flow.Launcher/App.xaml.cs index 6b0736da154..6c5e699ba76 100644 --- a/Flow.Launcher/App.xaml.cs +++ b/Flow.Launcher/App.xaml.cs @@ -158,7 +158,7 @@ public static void Main() #region Notify Icon - private void InitializeNotifyIcon() + private static void InitializeNotifyIcon() { NotifyIcon = new NotifyIcon {