Ticket #46717: xfwm4-stacking4nonX11.patch

File xfwm4-stacking4nonX11.patch, 5.9 KB (added by RJVB (René Bertin), 9 years ago)

only do a global restack of the target window...

  • src/screen.h

    diff --git a/src/screen.h b/src/screen.h
    index 668c932..e4206d2 100644
    a b struct _ScreenInfo 
    179179
    180180    guint compositor_timeout_id;
    181181#endif /* HAVE_COMPOSITOR */
     182    Window last_raise_sibling;
    182183};
    183184
    184185gboolean                 myScreenCheckWMAtom                    (ScreenInfo *,
  • src/stacking.c

    diff --git a/src/stacking.c b/src/stacking.c
    index a2a0e71..22b9cea 100644
    a b  
    4343static guint raise_timeout = 0;
    4444
    4545void
    46 clientApplyStackList (ScreenInfo *screen_info)
     46clientApplyStackList (ScreenInfo *screen_info, Client *client, StackingAction action )
    4747{
    4848    Window *xwinstack;
    4949    guint nwindows;
    5050    gint i;
    5151
    52     DBG ("applying stack list");
     52    DBG ("applying stack list, action=%s on window 0x%lx", (action==Raise)? "Raise" : ((action==Lower)? "Lower" : "Restack"), client->window );
    5353    nwindows = g_list_length (screen_info->windows_stack);
    5454
    5555    i = 0;
    clientApplyStackList (ScreenInfo *screen_info) 
    6868        {
    6969            c = (Client *) index->data;
    7070            xwinstack[i++] = c->frame;
    71             DBG ("  [%i] \"%s\" (0x%lx)", i, c->name, c->window);
     71            if ( !((action==Raise || action==Lower) && c->window!=client->window) )
     72            {
     73                DBG ("  [%i] \"%s\" (0x%lx)", i, c->name, c->window);
     74            }
    7275        }
    7376    }
    7477
    75     XRestackWindows (myScreenGetXDisplay (screen_info), xwinstack, (int) nwindows + 4);
     78    switch (action)
     79    {
     80        case Restack:
     81        default:
     82            // Restack the windows. This is the preferred action if the lowering/raising has to be done with respect to
     83            // a sibling window.
     84            XRestackWindows (myScreenGetXDisplay (screen_info), xwinstack, (int) nwindows + 4);
     85            break;
     86        case Raise:
     87            // Raise the windows inconditionally, working backwards (xwinstack[n-1] .. xwinstack[0]) as RestackWindows would do too.
     88            // This is the preferred action when raising a window on Mac OS X or MS Windows when the X server does not
     89            // manage all windows on the screen. Using Restack, the window would remain behind non X windows if it was
     90            // not already in front of them.
     91            for (i = nwindows ; i >= 0 ; --i)
     92            {
     93                if (xwinstack[i] == client->frame || i <= 3)
     94                {
     95                    XRaiseWindow (myScreenGetXDisplay (screen_info), xwinstack[i]);
     96                }
     97            }
     98            break;
     99        case Lower:
     100            // Lower the windows inconditionally, (xwinstack[0] .. xwinstack[n-1]).
     101            // This is the preferred action when lowering a window on Mac OS X or MS Windows when the X server does not
     102            // manage all windows on the screen. Using Restack, the window would remain in front of non X windows if it was
     103            // not already behind them.
     104            for (i = 0 ; i < nwindows ; ++i)
     105            {
     106                if (xwinstack[i] == client->frame || i <= 3)
     107                {
     108                    XLowerWindow (myScreenGetXDisplay (screen_info), xwinstack[i]);
     109                }
     110            }
     111            break;
     112    }
    76113
    77114    g_free (xwinstack);
    78115}
    clientRaise (Client * c, Window wsibling) 
    297334    transients = NULL;
    298335    sibling = NULL;
    299336
    300     if (c == screen_info->last_raise)
     337    if (c == screen_info->last_raise && (wsibling && wsibling == screen_info->last_raise_sibling))
    301338    {
    302         TRACE ("client \"%s\" (0x%lx) already raised", c->name, c->window);
     339        TRACE ("client \"%s\" (0x%lx) already raised w.r.t. sibling %lx", c->name, c->window, wsibling);
    303340        return;
    304341    }
    305342    TRACE ("raising client \"%s\" (0x%lx) over (0x%lx)", c->name, c->window, wsibling);
    clientRaise (Client * c, Window wsibling) 
    438475        }
    439476        /* Now, screen_info->windows_stack contains the correct window stack
    440477           We still need to tell the X Server to reflect the changes
     478           This is done using XRestackWindows when we're restacking w.r.t. wsibling, and using XRaiseWindow otherwise.
    441479         */
    442         clientApplyStackList (screen_info);
     480        clientApplyStackList (screen_info, (wsibling)? Restack : Raise);
    443481        clientSetNetClientList (c->screen_info, display_info->atoms[NET_CLIENT_LIST_STACKING], screen_info->windows_stack);
    444482        screen_info->last_raise = c;
     483        screen_info->last_raise_sibling = wsibling;
    445484    }
    446485}
    447486
    clientLower (Client * c, Window wsibling) 
    527566        }
    528567        /* Now, screen_info->windows_stack contains the correct window stack
    529568           We still need to tell the X Server to reflect the changes
     569           This is done using XRestackWindows when we're restacking w.r.t. wsibling, and using XLowerWindow otherwise.
    530570         */
    531         clientApplyStackList (screen_info);
     571        clientApplyStackList (screen_info, (wsibling)? Restack : Lower);
    532572        clientSetNetClientList (screen_info, display_info->atoms[NET_CLIENT_LIST_STACKING], screen_info->windows_stack);
    533573        clientPassGrabMouseButton (NULL);
    534574        clientPassFocus (screen_info, c, NULL);
    535575        if (screen_info->last_raise == c)
    536576        {
    537577            screen_info->last_raise = NULL;
     578            screen_info->last_raise_sibling = 0;
    538579        }
    539580    }
    540581}
  • src/stacking.h

    diff --git a/src/stacking.h b/src/stacking.h
    index c65b92d..f7cc19c 100644
    a b  
    3131#include "screen.h"
    3232#include "client.h"
    3333
    34 void                     clientApplyStackList                   (ScreenInfo *);
     34typedef enum StackingAction {Restack, Raise, Lower} StackingAction;
     35
     36void                     clientApplyStackList                   (ScreenInfo *, Client *, StackingAction);
    3537Client                  *clientGetLowestTransient               (Client *);
    3638Client                  *clientGetHighestTransientOrModalFor    (Client *);
    3739gboolean                 clientIsTopMost                        (Client *);