بنقرة واحدة
wpf-tray-window-launch
Pattern for launching WPF windows from system tray icon interactions
التثبيت باستخدام Codex أو Claude انسخ هذا Prompt والصقه في Codex أو Claude أو مساعد آخر ليراجع صفحة Skill ويثبّتها لك.
القائمة
Pattern for launching WPF windows from system tray icon interactions
التثبيت باستخدام Codex أو Claude انسخ هذا Prompt والصقه في Codex أو Claude أو مساعد آخر ليراجع صفحة Skill ويثبّتها لك.
استنادا إلى تصنيف SOC المهني
| name | wpf-tray-window-launch |
| description | Pattern for launching WPF windows from system tray icon interactions |
| domain | desktop-ui |
| confidence | high |
| source | observed |
When building WPF applications with system tray integration, you need a consistent pattern for launching/showing windows in response to tray icon events (double-click, context menu items).
ElBruno.OllamaMonitor uses H.NotifyIcon.Wpf for tray integration (via NuGet package, wraps System.Windows.Forms.NotifyIcon).
TrayIconService holds direct references to window instances (not factories):
private readonly MainWindow _mainWindow;
private readonly MiniMonitorWindow _miniMonitorWindow;
Windows are constructed once in App.xaml.cs and passed to TrayIconService constructor.
Standard method for showing a window from tray (used by both windows):
private void ShowMiniMonitorWindow()
{
if (!_miniMonitorWindow.IsVisible)
{
_miniMonitorWindow.Show();
}
_miniMonitorWindow.Activate();
}
Key steps:
IsVisible firstShow() if hiddenActivate() to bring to front (handles minimized case implicitly)MainWindow variation includes explicit minimized state check:
if (_mainWindow.WindowState == System.Windows.WindowState.Minimized)
{
_mainWindow.WindowState = System.Windows.WindowState.Normal;
}
Windows implement PrepareForExit() + OnClosing override to hide instead of close:
private bool _allowClose;
public void PrepareForExit() => _allowClose = true;
protected override void OnClosing(CancelEventArgs e)
{
if (!_allowClose)
{
e.Cancel = true;
Hide();
return;
}
base.OnClosing(e);
}
This allows reopening windows without re-instantiation.
Wire tray icon events in TrayIconService constructor:
_notifyIcon.DoubleClick += (_, _) => ShowMiniMonitorWindow();
_notifyIcon.ContextMenuStrip.Opening += (_, _) => RefreshMenuText();
Context menu items use lambda handlers:
new ToolStripMenuItem("Show Mini Monitor", null, (_, _) => ToggleMiniWindowVisibility())
Menu items toggle window visibility with dynamic text:
private void ToggleMiniWindowVisibility()
{
if (_miniMonitorWindow.IsVisible)
{
_miniMonitorWindow.Hide();
return;
}
ShowMiniMonitorWindow();
}
private void RefreshMenuText()
{
_toggleMiniWindowMenuItem.Text = _miniMonitorWindow.IsVisible
? "Hide Mini Monitor"
: "Show Mini Monitor";
}
File: src/ElBruno.OllamaMonitor/Services/TrayIconService.cs
ShowWindow() implementation (MainWindow)ShowMiniMonitorWindow() implementationFile: src/ElBruno.OllamaMonitor/MiniMonitorWindow.xaml.cs
PrepareForExit() + OnClosing() overrideShow() — always call Activate() to handle already-visible-but-background windowsPrepareForExit() — without it, closing a window during app exit triggers unwanted hide logic