diff --git a/patches/patchinstall.sh b/patches/patchinstall.sh index be375aad..a15e702f 100755 --- a/patches/patchinstall.sh +++ b/patches/patchinstall.sh @@ -6356,14 +6356,17 @@ fi # | # | This patchset fixes the following Wine bugs: # | * [#45968] user32: Implement CascadeWindows +# | * [#46197] user32: Implement TileWindows # | # | Modified files: # | * dlls/user32/mdi.c # | if test "$enable_user32_Implement_CascadeWindows" -eq 1; then patch_apply user32-Implement-CascadeWindows/0001-user32-Implement-CascadeWindows.patch + patch_apply user32-Implement-CascadeWindows/0002-user32-Implement-TileWindows.patch ( printf '%s\n' '+ { "katahiromz", "user32: Implement CascadeWindows.", 1 },'; + printf '%s\n' '+ { "Hirofumi Katayama", "user32: Implement TileWindows.", 1 },'; ) >> "$patchlist" fi diff --git a/patches/user32-Implement-CascadeWindows/0002-user32-Implement-TileWindows.patch b/patches/user32-Implement-CascadeWindows/0002-user32-Implement-TileWindows.patch new file mode 100644 index 00000000..afdddcba --- /dev/null +++ b/patches/user32-Implement-CascadeWindows/0002-user32-Implement-TileWindows.patch @@ -0,0 +1,226 @@ +From 37cf48e9f6ef877478a716748fd73b714dc0dc09 Mon Sep 17 00:00:00 2001 +From: Hirofumi Katayama +Date: Mon, 26 Nov 2018 09:09:52 +0900 +Subject: [PATCH] user32: Implement TileWindows + +Wine lacks the implementations of TileWindows +function of window arrangement. + +Wine-Bug: https://bugs.winehq.org/show_bug.cgi?id=46197 +Signed-off-by: Hirofumi Katayama +--- + dlls/user32/mdi.c | 181 ++++++++++++++++++++++++++++++++++++++++++++-- + 1 file changed, 176 insertions(+), 5 deletions(-) + +diff --git a/dlls/user32/mdi.c b/dlls/user32/mdi.c +index b430ecce623..2569835c5a4 100644 +--- a/dlls/user32/mdi.c ++++ b/dlls/user32/mdi.c +@@ -144,6 +144,10 @@ typedef struct + + static HBITMAP hBmpClose = 0; + ++static WCHAR shelltray[] = {'S','h','e','l','l','_','T','r','a','y','W','n','d',0}; ++static WCHAR progman[] = {'P','r','o','g','m','a','n',0}; ++ ++ + /* ----------------- declarations ----------------- */ + static void MDI_UpdateFrameText( HWND, HWND, BOOL, LPCWSTR); + static BOOL MDI_AugmentFrameMenu( HWND, HWND ); +@@ -1931,8 +1935,6 @@ WORD WINAPI + CascadeWindows (HWND hwndParent, UINT wFlags, const RECT *lpRect, + UINT cKids, const HWND *lpKids) + { +- static WCHAR shelltray[] = {'S','h','e','l','l','_','T','r','a','y','W','n','d',0}; +- static WCHAR progman[] = {'P','r','o','g','m','a','n',0}; + CASCADE_INFO info; + HWND hwnd, top, prev; + HMONITOR monitor; +@@ -2082,12 +2084,181 @@ WORD WINAPI CascadeChildWindows( HWND parent, UINT flags ) + * Success: Number of tiled windows. + * Failure: 0 + */ +-WORD WINAPI ++WORD WINAPI + TileWindows (HWND hwndParent, UINT wFlags, const RECT *lpRect, + UINT cKids, const HWND *lpKids) + { +- FIXME("(%p,0x%08x,...,%u,...): stub\n", hwndParent, wFlags, cKids); +- return 0; ++ HWND hwnd, hwndTop, hwndPrev; ++ CASCADE_INFO info; ++ RECT rcWork, rcWnd; ++ DWORD i, iRow, iColumn, cRows, cColumns, ret = 0; ++ INT x, y, cx, cy, cxNew, cyNew, cxWork, cyWork, cxCell, cyCell, cxMin2, cyMin3; ++ HDWP hDWP; ++ MONITORINFO mi; ++ HMONITOR hMon; ++ POINT pt; ++ ++ TRACE("(%p,0x%08x,...,%u,...)\n", hwndParent, wFlags, cKids); ++ ++ hwndTop = GetTopWindow(hwndParent); ++ ++ ZeroMemory(&info, sizeof(info)); ++ info.desktop = GetDesktopWindow(); ++ info.tray_wnd = FindWindowW(shelltray, NULL); ++ info.progman = FindWindowW(progman, NULL); ++ info.parent = hwndParent; ++ info.flags = wFlags; ++ ++ if (cKids == 0 || lpKids == NULL) ++ { ++ info.top = hwndTop; ++ EnumChildWindows(hwndParent, GetCascadeChildProc, (LPARAM)&info); ++ ++ info.top = NULL; ++ GetCascadeChildProc(hwndTop, (LPARAM)&info); ++ } ++ else ++ { ++ info.wnd_count = cKids; ++ info.wnd_array = (HWND *)lpKids; ++ } ++ ++ if (info.wnd_count == 0 || info.wnd_array == NULL) ++ return ret; ++ ++ if (lpRect) ++ { ++ rcWork = *lpRect; ++ } ++ else if (hwndParent) ++ { ++ GetClientRect(hwndParent, &rcWork); ++ } ++ else ++ { ++ pt.x = pt.y = 0; ++ hMon = MonitorFromPoint(pt, MONITOR_DEFAULTTOPRIMARY); ++ mi.cbSize = sizeof(mi); ++ GetMonitorInfoW(hMon, &mi); ++ rcWork = mi.rcWork; ++ } ++ ++ cxWork = rcWork.right - rcWork.left; ++ cyWork = rcWork.bottom - rcWork.top; ++ ++ cxMin2 = GetSystemMetrics(SM_CXMIN) * 2; ++ cyMin3 = GetSystemMetrics(SM_CYMIN) * 3; ++ ++ /* calculate the numbers and widths of columns and rows */ ++ if (info.flags & MDITILE_HORIZONTAL) ++ { ++ cColumns = info.wnd_count; ++ cRows = 1; ++ for (;;) ++ { ++ cxCell = cxWork / cColumns; ++ cyCell = cyWork / cRows; ++ if (cyCell <= cyMin3 || cxCell >= cxMin2) ++ break; ++ ++ ++cRows; ++ cColumns = (info.wnd_count + cRows - 1) / cRows; ++ } ++ } ++ else ++ { ++ cRows = info.wnd_count; ++ cColumns = 1; ++ for (;;) ++ { ++ cxCell = cxWork / cColumns; ++ cyCell = cyWork / cRows; ++ if (cxCell <= cxMin2 || cyCell >= cyMin3) ++ break; ++ ++ ++cColumns; ++ cRows = (info.wnd_count + cColumns - 1) / cColumns; ++ } ++ } ++ ++ hDWP = BeginDeferWindowPos(info.wnd_count); ++ if (hDWP == NULL) ++ goto cleanup; ++ ++ x = rcWork.left; ++ y = rcWork.top; ++ hwndPrev = NULL; ++ iRow = iColumn = 0; ++ for (i = info.wnd_count; i > 0;) /* in reverse order */ ++ { ++ --i; ++ hwnd = info.wnd_array[i]; ++ ++ if (IsZoomed(hwnd)) ++ ShowWindow(hwnd, SW_RESTORE | SW_SHOWNA); ++ ++ GetWindowRect(hwnd, &rcWnd); ++ cx = rcWnd.right - rcWnd.left; ++ cy = rcWnd.bottom - rcWnd.top; ++ ++ /* if we can change the window size */ ++ if (GetWindowLongPtrW(hwnd, GWL_STYLE) & WS_THICKFRAME) ++ { ++ cxNew = cxCell; ++ cyNew = cyCell; ++ /* shrink if we can */ ++ if (QuerySizeFix(hwnd, &cxNew, &cyNew)) ++ { ++ cx = cxNew; ++ cy = cyNew; ++ } ++ } ++ ++ hDWP = DeferWindowPos(hDWP, hwnd, HWND_TOP, x, y, cx, cy, SWP_NOACTIVATE); ++ if (hDWP == NULL) ++ { ++ ret = 0; ++ goto cleanup; ++ } ++ ++ if (info.flags & MDITILE_HORIZONTAL) ++ { ++ x += cxCell; ++ ++iColumn; ++ if (iColumn >= cColumns) ++ { ++ iColumn = 0; ++ ++iRow; ++ x = rcWork.left; ++ y += cyCell; ++ } ++ } ++ else ++ { ++ y += cyCell; ++ ++iRow; ++ if (iRow >= cRows) ++ { ++ iRow = 0; ++ ++iColumn; ++ x += cxCell; ++ y = rcWork.top; ++ } ++ } ++ hwndPrev = hwnd; ++ ++ret; ++ } ++ ++ EndDeferWindowPos(hDWP); ++ ++ if (hwndPrev) ++ SetForegroundWindow(hwndPrev); ++ ++cleanup: ++ if (cKids == 0 || lpKids == NULL) ++ HeapFree(GetProcessHeap(), 0, info.wnd_array); ++ ++ return (WORD)ret; + } + + +-- +2.17.1 + diff --git a/patches/user32-Implement-CascadeWindows/definition b/patches/user32-Implement-CascadeWindows/definition index 0e9a58e3..296c9395 100644 --- a/patches/user32-Implement-CascadeWindows/definition +++ b/patches/user32-Implement-CascadeWindows/definition @@ -1 +1,2 @@ Fixes: [45968] user32: Implement CascadeWindows +Fixes: [46197] user32: Implement TileWindows