Use MetaStackTracker to avoid a round-trip XQueryTree()

With MetaStackTracker, it's no longer necessary to XQueryTree to
get a reasonably-up-to-date view of the server stacking order.

Add some comments explaining unclear aspects of
raise_window_relative_to_managed_windows() and with future possible
improvements.

http://bugzilla.gnome.org/show_bug.cgi?id=585984
This commit is contained in:
Owen W. Taylor 2009-06-16 08:44:17 -04:00
parent ef966854d5
commit 1f890672bb

View File

@ -960,41 +960,33 @@ stack_ensure_sorted (MetaStack *stack)
* This function is used to avoid raising a window above popup * This function is used to avoid raising a window above popup
* menus and other such things. * menus and other such things.
* *
* FIXME This is sort of an expensive function, should probably * The key to the operation of this function is that we are expecting
* do something to avoid it. One approach would be to reverse * at most one window to be added at a time. If xwindow is newly added,
* the stacking algorithm to work by placing each window above * then its own stack position will be too high (the frame window
* the others, and start by lowering a window to the bottom * is created at the top of the stack), but if we ignore xwindow,
* (instead of the current way, which works by placing each * then the *next* managed window in the stack will be a window that
* window below another and starting with a raise) * we've already stacked.
*
* We could generalize this and remove the assumption that windows
* are added one at a time by keeping an explicit ->stacked flag in
* MetaWindow.
*
* An alternate approach would be to reverse the stacking algorithm to
* work by placing each window above the others, and start by lowering
* a window to the bottom (instead of the current way, which works by
* placing each window below another and starting with a raise)
*/ */
static void static void
raise_window_relative_to_managed_windows (MetaScreen *screen, raise_window_relative_to_managed_windows (MetaScreen *screen,
Window xwindow) Window xwindow)
{ {
Window ignored1, ignored2;
Window *children; Window *children;
unsigned int n_children; int n_children;
int i; int i;
/* Normally XQueryTree() means "must grab server" but here meta_stack_tracker_get_stack (screen->stack_tracker,
* we don't, since we know we won't manage any new windows &children, &n_children);
* or restack any windows before using the XQueryTree results.
*/
meta_error_trap_push_with_return (screen->display);
XQueryTree (screen->display->xdisplay,
screen->xroot,
&ignored1, &ignored2, &children, &n_children);
if (meta_error_trap_pop_with_return (screen->display, TRUE) != Success)
{
meta_topic (META_DEBUG_STACK,
"Error querying root children to raise window 0x%lx\n",
xwindow);
return;
}
/* Children are in order from bottom to top. We want to /* Children are in order from bottom to top. We want to
* find the topmost managed child, then configure * find the topmost managed child, then configure
@ -1062,9 +1054,6 @@ raise_window_relative_to_managed_windows (MetaScreen *screen,
xwindow); xwindow);
meta_error_trap_pop (screen->display, FALSE); meta_error_trap_pop (screen->display, FALSE);
} }
if (children)
XFree (children);
} }
/** /**
@ -1073,6 +1062,10 @@ raise_window_relative_to_managed_windows (MetaScreen *screen,
* or XConfigureWindow on a few particular windows if we do and can figure * or XConfigureWindow on a few particular windows if we do and can figure
* out the minimum set of changes. After that, we set __NET_CLIENT_LIST * out the minimum set of changes. After that, we set __NET_CLIENT_LIST
* and __NET_CLIENT_LIST_STACKING. * and __NET_CLIENT_LIST_STACKING.
*
* FIXME: Now that we have a good view of the stacking order on the server
* with MetaStackTracker it should be possible to do a simpler and better
* job of computing the minimal set of stacking requests needed.
*/ */
static void static void
stack_sync_to_server (MetaStack *stack) stack_sync_to_server (MetaStack *stack)