Skip to content

Commit 7a5ecf1

Browse files
na-na-hikasper93
authored andcommitted
video/out/w32_common: support --wid=0
Similar to X11, this makes mpv attach to the desktop wallpaper window (make the system create one if it does not yet exist) as parent, which makes mpv display as desktop wallpaper behind desktop icons. Lika an actual wallpaper, mpv will not receive any keyboard or mouse input in this mode. It can still be controlled through terminal and IPC.
1 parent b290781 commit 7a5ecf1

File tree

2 files changed

+42
-1
lines changed

2 files changed

+42
-1
lines changed
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
add `--wid=0` support for win32

video/out/w32_common.c

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,7 @@ struct vo_w32_state {
100100
HWND parent; // 0 normally, set in embedding mode
101101
HHOOK parent_win_hook;
102102
HWINEVENTHOOK parent_evt_hook;
103+
bool embed_desktop;
103104

104105
struct menu_ctx *menu_ctx;
105106

@@ -2025,6 +2026,36 @@ static void w32_api_load(struct vo_w32_state *w32)
20252026
(void *)GetProcAddress(uxtheme_dll, MAKEINTRESOURCEA(135));
20262027
}
20272028

2029+
static BOOL CALLBACK EnumWindowsProc(HWND hwnd, LPARAM lparam)
2030+
{
2031+
HWND *workerw = (HWND *)lparam;
2032+
HWND defview = FindWindowExW(hwnd, NULL, L"SHELLDLL_DefView", NULL);
2033+
if (defview) {
2034+
*workerw = FindWindowExW(NULL, hwnd, L"WorkerW", NULL);
2035+
return FALSE;
2036+
}
2037+
return TRUE;
2038+
}
2039+
2040+
// Find the "WorkerW" HWND to attach to, which is the desktop wallpaper HWND.
2041+
static HWND get_workerw_hwnd(void)
2042+
{
2043+
HWND progman = FindWindowW(L"Progman", NULL);
2044+
// 24H2 or later
2045+
HWND workerw = FindWindowExW(progman, NULL, L"WorkerW", NULL);
2046+
// Previous Windows versions
2047+
if (!workerw)
2048+
EnumWindows(EnumWindowsProc, (LPARAM)&workerw);
2049+
return workerw;
2050+
}
2051+
2052+
// Enter the "raised desktop" mode with wallpaper and icons on separate HWNDs.
2053+
static void set_raised_desktop(void)
2054+
{
2055+
HWND progman = FindWindowW(L"Progman", NULL);
2056+
SendMessageTimeout(progman, 0x052c, 0xd, 1, SMTO_NORMAL, 1000, NULL);
2057+
}
2058+
20282059
static MP_THREAD_VOID gui_thread(void *ptr)
20292060
{
20302061
struct vo_w32_state *w32 = ptr;
@@ -2035,8 +2066,13 @@ static MP_THREAD_VOID gui_thread(void *ptr)
20352066

20362067
w32_api_load(w32);
20372068

2038-
if (w32->opts->WinID >= 0)
2069+
if (w32->opts->WinID == 0) {
2070+
set_raised_desktop();
2071+
w32->parent = get_workerw_hwnd();
2072+
w32->embed_desktop = true;
2073+
} else if (w32->opts->WinID > 0) {
20392074
w32->parent = (HWND)(intptr_t)(w32->opts->WinID);
2075+
}
20402076

20412077
ATOM cls = get_window_class();
20422078
if (w32->parent) {
@@ -2148,6 +2184,10 @@ static MP_THREAD_VOID gui_thread(void *ptr)
21482184
ITaskbarList3_Release(w32->taskbar_list3);
21492185
if (ole_ok)
21502186
OleUninitialize();
2187+
// Some Windows versions do not redraw the desktop wallpaper when mpv exits,
2188+
// so force a redraw here.
2189+
if (w32->embed_desktop)
2190+
set_raised_desktop();
21512191
SetThreadExecutionState(ES_CONTINUOUS);
21522192
MP_THREAD_RETURN();
21532193
}

0 commit comments

Comments
 (0)