Skip to content

Tray icon / widget disappears after Explorer (taskbar) restarts - root cause + fix #35

Description

@amorel

Summary

After explorer.exe restarts (crash, Windows Update, or a manual shell restart), the tray icon and the embedded taskbar widget disappear, even though the process is still running. The only current workaround is to kill and relaunch the app — exactly what #34 reported ("I killed the process and re-ran the command and it shows fine now, not sure what the issue was").

Root cause

The widget embeds itself as a child of Shell_TrayWnd (via SetParent). When Explorer restarts, the taskbar window is destroyed, which destroys our child window outright — afterwards IsWindow(hwnd) returns false and GetParent returns 0. The UI thread is then stuck in GetMessageW with no window left, so:

  • WM_TIMER is never delivered again,
  • inter-thread SendMessage to the destroyed window is a no-op,
  • the "TaskbarCreated" broadcast never reaches us (a destroyed/child window doesn't receive it).

Confirmed empirically: a window-timer watchdog stops firing the instant Explorer restarts, and IsWindow on the widget handle is false afterwards while the process keeps running.

Reproduction

  1. Run the widget (it embeds into the taskbar).
  2. Restart Explorer (taskkill /f /im explorer.exe, or Task Manager -> Restart Windows Explorer).
  3. The process is still alive, but the tray icon and widget are gone until a manual relaunch.

Proposed fix

A dedicated watchdog thread (independent of the dead message loop) polls the Shell_TrayWnd handle; when it changes (Explorer restarted), it relaunches the widget as a fresh process that re-embeds into the new taskbar. The relaunched child waits on the single-instance mutex until the old instance exits, with a throttle to avoid a relaunch storm if Explorer is crash-looping.

In-process recovery isn't viable here because the window is genuinely destroyed and the UI thread can't recreate it from another thread; a clean relaunch is the robust path.

I have this implemented and tested (survives repeated Explorer restarts, re-embeds correctly each time). Happy to open a PR if you're open to this approach — or to a different one (e.g. in-process window recreation) if you'd prefer.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions