Programatically minimising window gets incorrect results.
Mike McCormack
mike at codeweavers.com
Tue May 16 04:15:20 CDT 2006
Troy Rollo wrote:
> The attached C sample demonstrates two problems with using
> ShowWindow(hwnd,SW_SHOWMINIMIZED) to minimise a top level window. The tests
> were done in KDE, but the second problem has been confirmed in Gnome and I
> suspect the first also occurs there.
The problem is that we should ask the Window manager to minimize us.
There's a hack in CrossOver that "fixes" it, which I've attached. If
you're in a good mood, try getting it accepted into Wine. :)
I haven't tested that this patch works as is... however it should be
complete, and at least compiles.
Mike
-------------- next part --------------
diff --git a/dlls/x11drv/winpos.c b/dlls/x11drv/winpos.c
index 5fdde83..33370df 100644
--- a/dlls/x11drv/winpos.c
+++ b/dlls/x11drv/winpos.c
@@ -923,12 +923,42 @@ UINT WINPOS_MinMaximize( HWND hwnd, UINT
return swpFlags;
}
+/***********************************************************************
+ * X11DRV_WMMinimizeWindow
+ *
+ * See the ICCCM section 4.1.4. Changing Window State for more details.
+ * http://tronche.com/gui/x/icccm/sec-4.html#s-4.1.4
+ */
+static BOOL X11DRV_WMMinimizeWindow(HWND hwnd)
+{
+ XEvent xev;
+
+ TRACE("%p\n", hwnd);
+
+ wine_tsx11_lock();
+
+ xev.xclient.type = ClientMessage;
+ xev.xclient.window = X11DRV_get_whole_window( hwnd );
+ xev.xclient.message_type = x11drv_atom(WM_CHANGE_STATE);
+ xev.xclient.serial = 0;
+ xev.xclient.display = thread_display();
+ xev.xclient.send_event = True;
+ xev.xclient.format = 32;
+ xev.xclient.data.l[0] = IconicState;
+ xev.xclient.data.l[2] = 0;
+ XSendEvent(thread_display(), root_window, False, SubstructureNotifyMask, &xev);
+
+ wine_tsx11_unlock();
+
+ return TRUE;
+}
/***********************************************************************
* ShowWindow (X11DRV.@)
*/
BOOL X11DRV_ShowWindow( HWND hwnd, INT cmd )
{
+ Display *display = thread_display();
WND *wndPtr;
HWND parent;
LONG style = GetWindowLongW( hwnd, GWL_STYLE );
@@ -957,6 +987,19 @@ BOOL X11DRV_ShowWindow( HWND hwnd, INT c
swp |= SWP_SHOWWINDOW;
/* fall through */
case SW_MINIMIZE:
+
+ /* handle minimize a different way */
+ if ((root_window == DefaultRootWindow(display)) &&
+ GetAncestor(hwnd,GA_PARENT) == GetDesktopWindow())
+ {
+ if( !(style & WS_MINIMIZE) )
+ {
+ X11DRV_WMMinimizeWindow( hwnd );
+ WIN_SetStyle( hwnd, WS_MAXIMIZE, WS_MINIMIZE );
+ }
+ return wasVisible;
+ }
+
swp |= SWP_FRAMECHANGED;
if( !(style & WS_MINIMIZE) )
swp |= WINPOS_MinMaximize( hwnd, SW_MINIMIZE, &newPos );
diff --git a/dlls/x11drv/x11drv.h b/dlls/x11drv/x11drv.h
index d259c86..9e8c3d9 100644
--- a/dlls/x11drv/x11drv.h
+++ b/dlls/x11drv/x11drv.h
@@ -561,6 +561,7 @@ enum x11drv_atoms
XATOM_WM_PROTOCOLS,
XATOM_WM_DELETE_WINDOW,
XATOM_WM_TAKE_FOCUS,
+ XATOM_WM_CHANGE_STATE,
XATOM_KWM_DOCKWINDOW,
XATOM_DndProtocol,
XATOM_DndSelection,
diff --git a/dlls/x11drv/x11drv_main.c b/dlls/x11drv/x11drv_main.c
index f0269a9..322ffd7 100644
--- a/dlls/x11drv/x11drv_main.c
+++ b/dlls/x11drv/x11drv_main.c
@@ -123,6 +123,7 @@ static const char * const atom_names[NB_
"WM_PROTOCOLS",
"WM_DELETE_WINDOW",
"WM_TAKE_FOCUS",
+ "WM_CHANGE_STATE",
"KWM_DOCKWINDOW",
"DndProtocol",
"DndSelection",
More information about the wine-devel
mailing list