|
6 | 6 |
|
7 | 7 | extern "C" IMAGE_DOS_HEADER __ImageBase; |
8 | 8 |
|
9 | | -HWND tray_icon_hwnd = NULL; |
| 9 | +namespace { |
| 10 | + HWND tray_icon_hwnd = NULL; |
10 | 11 |
|
11 | | -// Message code that Windows will use for tray icon notifications. |
12 | | -UINT wm_icon_notify = 0; |
| 12 | + // Message code that Windows will use for tray icon notifications. |
| 13 | + UINT wm_icon_notify = 0; |
13 | 14 |
|
14 | | -// Contains the Windows Message for taskbar creation. |
15 | | -UINT wm_taskbar_restart = 0; |
16 | | -UINT wm_run_on_main_ui_thread = 0; |
| 15 | + // Contains the Windows Message for taskbar creation. |
| 16 | + UINT wm_taskbar_restart = 0; |
| 17 | + UINT wm_run_on_main_ui_thread = 0; |
17 | 18 |
|
18 | | -NOTIFYICONDATAW tray_icon_data; |
19 | | -static bool about_box_shown = false; |
| 19 | + NOTIFYICONDATAW tray_icon_data; |
| 20 | + bool tray_icon_created = false; |
20 | 21 |
|
21 | | -HMENU h_menu = nullptr; |
22 | | -HMENU h_sub_menu = nullptr; |
| 22 | + bool about_box_shown = false; |
| 23 | + |
| 24 | + HMENU h_menu = nullptr; |
| 25 | + HMENU h_sub_menu = nullptr; |
| 26 | +} |
23 | 27 |
|
24 | 28 | // Struct to fill with callback and the data. The window_proc is responsible for cleaning it. |
25 | 29 | struct run_on_main_ui_thread_msg { |
@@ -77,6 +81,16 @@ LRESULT __stdcall tray_icon_window_proc(HWND window, UINT message, WPARAM wparam |
77 | 81 | break; |
78 | 82 | } |
79 | 83 | break; |
| 84 | + // Shell_NotifyIcon can fail when we invoke it during the time explorer.exe isn't present/ready to handle it. |
| 85 | + // We'll also never receive wm_taskbar_restart message if the first call to Shell_NotifyIcon failed, so we use |
| 86 | + // WM_WINDOWPOSCHANGING which is always received on explorer startup sequence. |
| 87 | + case WM_WINDOWPOSCHANGING: |
| 88 | + { |
| 89 | + if(!tray_icon_created) { |
| 90 | + tray_icon_created = Shell_NotifyIcon(NIM_ADD, &tray_icon_data) == TRUE; |
| 91 | + } |
| 92 | + break; |
| 93 | + } |
80 | 94 | default: |
81 | 95 | if (message == wm_icon_notify) { |
82 | 96 | switch(lparam) { |
@@ -110,7 +124,7 @@ LRESULT __stdcall tray_icon_window_proc(HWND window, UINT message, WPARAM wparam |
110 | 124 | } |
111 | 125 | break; |
112 | 126 | } else if (message == wm_taskbar_restart) { |
113 | | - Shell_NotifyIcon(NIM_ADD, &tray_icon_data); |
| 127 | + tray_icon_created = Shell_NotifyIcon(NIM_ADD, &tray_icon_data) == TRUE; |
114 | 128 | break; |
115 | 129 | } |
116 | 130 | } |
@@ -154,6 +168,6 @@ void start_tray_icon() { |
154 | 168 | wcscpy_s(tray_icon_data.szTip, sizeof(tray_icon_data.szTip) / sizeof(WCHAR), L"PowerToys"); |
155 | 169 | tray_icon_data.uFlags = NIF_ICON | NIF_TIP | NIF_MESSAGE; |
156 | 170 |
|
157 | | - Shell_NotifyIcon(NIM_ADD, &tray_icon_data); |
| 171 | + tray_icon_created = Shell_NotifyIcon(NIM_ADD, &tray_icon_data) == TRUE; |
158 | 172 | } |
159 | 173 | } |
0 commit comments