aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Gabriel <mike.gabriel@das-netzwerkteam.de>2019-06-27 21:03:03 +0200
committerMike Gabriel <mike.gabriel@das-netzwerkteam.de>2019-06-27 21:03:03 +0200
commit1ebf7851994b3312d63bcf9e8f4f137128169261 (patch)
tree5a3f480a6373206e79c4a8f2797669e94bb05f5f
parent5858ebc6da54fe24ba6dab61f1478c812bfa6fb2 (diff)
parent032ed3511bd6d2ef78c75e9296586ad5d469c0f1 (diff)
downloadnx-libs-1ebf7851994b3312d63bcf9e8f4f137128169261.tar.gz
nx-libs-1ebf7851994b3312d63bcf9e8f4f137128169261.tar.bz2
nx-libs-1ebf7851994b3312d63bcf9e8f4f137128169261.zip
Merge branch 'uli42-pr/fix_fullscreen' into 3.6.x
Attributes GH PR #821: https://github.com/ArcticaProject/nx-libs/pull/821
-rw-r--r--nx-X11/programs/Xserver/hw/nxagent/Screen.c116
-rw-r--r--nx-X11/programs/Xserver/hw/nxagent/Window.c25
2 files changed, 110 insertions, 31 deletions
diff --git a/nx-X11/programs/Xserver/hw/nxagent/Screen.c b/nx-X11/programs/Xserver/hw/nxagent/Screen.c
index 6ec4b245f..44c89e03f 100644
--- a/nx-X11/programs/Xserver/hw/nxagent/Screen.c
+++ b/nx-X11/programs/Xserver/hw/nxagent/Screen.c
@@ -297,6 +297,35 @@ void nxagentSetPixmapFormats(ScreenInfo *screenInfo)
}
}
+/* check if possible_parent is parent of candidate */
+Bool nxagentIsParentOf(Display *d, XlibWindow possible_parent, XlibWindow candidate)
+{
+ XlibWindow parent, root, *children = NULL;
+ unsigned int num_children;
+
+ if (XQueryTree(d, candidate, &root, &parent, &children, &num_children))
+ {
+ if (children)
+ XFree((char *)children);
+
+ #ifdef TEST
+ fprintf(stderr, "%s: parent of full screen window [%p] root [%p] possible_parent [%p] candidate [%p]\n", __func__, parent, root, possible_parent, candidate);
+ #endif
+ return (parent == possible_parent);
+ }
+ else
+ {
+ return False;
+ }
+}
+
+/*
+ * Pressing the minimize keystroke while in fullscreen mode will call
+ * this function. It will unmap the fullscreen window and iconify the
+ * previously created icon window immediately. The window manager may
+ * decide how to show an iconified window. kwin e.g. shows it in the
+ * task bar.
+ */
void nxagentMinimizeFromFullScreen(ScreenPtr pScreen)
{
XUnmapWindow(nxagentDisplay, nxagentFullscreenWindow);
@@ -304,16 +333,20 @@ void nxagentMinimizeFromFullScreen(ScreenPtr pScreen)
if (nxagentIpaq)
{
XMapWindow(nxagentDisplay, nxagentIconWindow);
- XIconifyWindow(nxagentDisplay, nxagentIconWindow,
- DefaultScreen(nxagentDisplay));
}
- else
- {
- XIconifyWindow(nxagentDisplay, nxagentIconWindow,
+
+ XIconifyWindow(nxagentDisplay, nxagentIconWindow,
DefaultScreen(nxagentDisplay));
- }
}
+/*
+ * This is the opposite function to nxagentMinimizeFromFullscreen. It
+ * will map the fullscreen window and unmap the icon window. It is
+ * only called if fullscreen mode was active when the minimize
+ * keystroke was pressed.
+ * Some window managers tend to do 'interesting' things with the
+ * icon window, which we try to counterfeit here.
+ */
void nxagentMaximizeToFullScreen(ScreenPtr pScreen)
{
if (nxagentIpaq)
@@ -327,36 +360,51 @@ void nxagentMaximizeToFullScreen(ScreenPtr pScreen)
/*
XUnmapWindow(nxagentDisplay, nxagentIconWindow);
*/
+
+ Window root = RootWindow(nxagentDisplay, DefaultScreen(nxagentDisplay));
+
/*
-FIXME: We'll check for ReparentNotify and LeaveNotify events after XReparentWindow()
- in order to avoid the session window is iconified.
- We could avoid the session window is iconified when a LeaveNotify event is received,
- so this check would be unnecessary.
+FIXME: We'll check for ReparentNotify and LeaveNotify events after
+ XReparentWindow() in order to avoid the session window being
+ iconified. We could avoid the session window being iconified
+ when a LeaveNotify event is received, so this check would be
+ unnecessary.
*/
- struct timeval timeout;
- int i;
- XEvent e;
- XReparentWindow(nxagentDisplay, nxagentFullscreenWindow,
- RootWindow(nxagentDisplay, DefaultScreen(nxagentDisplay)), 0, 0);
+ /* only reparent if necessary. FIXME: also check if the desired coordinates match */
- for (i = 0; i < 100 && nxagentWMIsRunning; i++)
+ if (!nxagentIsParentOf(nxagentDisplay, root, nxagentFullscreenWindow))
{
- #ifdef TEST
- fprintf(stderr, "nxagentMaximizeToFullscreen: WARNING! Going to wait for the ReparentNotify event.\n");
- #endif
+ XReparentWindow(nxagentDisplay, nxagentFullscreenWindow,
+ root, 0, 0);
- if (XCheckTypedWindowEvent(nxagentDisplay, nxagentFullscreenWindow, ReparentNotify, &e))
+ for (int i = 0; i < 100 && nxagentWMIsRunning; i++)
{
- break;
- }
+ struct timeval timeout;
+ XEvent e;
- XSync(nxagentDisplay, 0);
+ #ifdef TEST
+ fprintf(stderr, "nxagentMaximizeToFullscreen: WARNING! Going to wait for the ReparentNotify event [%d].\n", i);
+ #endif
- timeout.tv_sec = 0;
- timeout.tv_usec = 50 * 1000;
+ if (XCheckTypedWindowEvent(nxagentDisplay, nxagentFullscreenWindow, ReparentNotify, &e))
+ {
+ break;
+ }
- nxagentWaitEvents(nxagentDisplay, &timeout);
+ XSync(nxagentDisplay, 0);
+
+ timeout.tv_sec = 0;
+ timeout.tv_usec = 50 * 1000;
+
+ nxagentWaitEvents(nxagentDisplay, &timeout);
+ }
+ }
+ else
+ {
+ #ifdef TEST
+ fprintf(stderr, "%s: FullscreenWindow already is child of root window - skipping reparenting,\n", __func__);
+ #endif
}
XMapRaised(nxagentDisplay, nxagentFullscreenWindow);
@@ -364,7 +412,19 @@ FIXME: We'll check for ReparentNotify and LeaveNotify events after XReparentWind
XIconifyWindow(nxagentDisplay, nxagentIconWindow,
DefaultScreen(nxagentDisplay));
- while (XCheckTypedWindowEvent(nxagentDisplay, nxagentFullscreenWindow, LeaveNotify, &e));
+ /* swallow all LeaveNotify events for the FullscreenWindow;
+ Normally this does not swallow anything these days, but when
+ using fvwm you see one of these events here. */
+ while (1)
+ {
+ XEvent e;
+ if (!XCheckTypedWindowEvent(nxagentDisplay, nxagentFullscreenWindow, LeaveNotify, &e))
+ break;
+ #ifdef TEST
+ fprintf(stderr, "%d: swallowing LeaveNotify event\m", __func__);
+ #endif
+ }
+
/*
XMapWindow(nxagentDisplay, nxagentIconWindow);
*/
@@ -1982,7 +2042,7 @@ N/A
}
else
{
- nxagentIconWindow = 0;
+ nxagentIconWindow = None;
}
/*
diff --git a/nx-X11/programs/Xserver/hw/nxagent/Window.c b/nx-X11/programs/Xserver/hw/nxagent/Window.c
index 78a5081f0..0e5def294 100644
--- a/nx-X11/programs/Xserver/hw/nxagent/Window.c
+++ b/nx-X11/programs/Xserver/hw/nxagent/Window.c
@@ -831,6 +831,11 @@ void nxagentSwitchAllScreens(ScreenPtr pScreen, Bool switchOn)
}
w = nxagentDefaultWindows[pScreen -> myNum];
+
+ /*
+ * override_redirect makes the window manager ignore the window and
+ * not add decorations, see ICCCM)
+ */
attributes.override_redirect = switchOn;
valuemask = CWOverrideRedirect;
XUnmapWindow(nxagentDisplay, w);
@@ -1003,14 +1008,28 @@ void nxagentSwitchAllScreens(ScreenPtr pScreen, Bool switchOn)
}
}
- if (nxagentOption(WMBorderWidth) > 0 && nxagentOption(WMTitleHeight) > 0)
+ /*
+ * FIXME: These are 0 most of the time nowadays. The effect is,
+ * that the window is moving a bit to right/bottom every time
+ * fullscreen mode is left. To fix this query the frame extents
+ * from the window manager via _NET_REQUEST_FRAME_EXTENTS
+ */
+
+ if (nxagentOption(WMBorderWidth) > 0)
{
nxagentChangeOption(X, nxagentOption(SavedX) - nxagentOption(WMBorderWidth));
- nxagentChangeOption(Y, nxagentOption(SavedY) - nxagentOption(WMTitleHeight));
}
else
{
nxagentChangeOption(X, nxagentOption(SavedX));
+ }
+
+ if (nxagentOption(WMTitleHeight) > 0)
+ {
+ nxagentChangeOption(Y, nxagentOption(SavedY) - nxagentOption(WMTitleHeight));
+ }
+ else
+ {
nxagentChangeOption(Y, nxagentOption(SavedY));
}
@@ -2635,7 +2654,7 @@ void nxagentMapDefaultWindows(void)
* Map the icon window.
*/
- if (nxagentIconWindow != 0)
+ if (nxagentIconWindow != None)
{
#ifdef TEST
fprintf(stderr, "nxagentMapDefaultWindows: Mapping icon window id [%ld].\n",