From 6273bf2e94a777760fee5346c290fb6672a0cb70 Mon Sep 17 00:00:00 2001 From: Mikael Magnusson Date: Sat, 12 Jul 2014 05:19:41 +0200 Subject: [PATCH] Make RaiseLower work for the dock as well As a side effect, _NET_RESTACK_REQUEST now also allows specifying the dock as the sibling. --- openbox/event.c | 16 ++++++++++---- openbox/stacking.c | 64 ++++++++++++++++++++++++++++++++++++++++++++++-------- openbox/stacking.h | 4 ++-- 3 files changed, 69 insertions(+), 15 deletions(-) diff --git a/openbox/event.c b/openbox/event.c index 9f56030..350c148 100644 --- a/openbox/event.c +++ b/openbox/event.c @@ -1198,7 +1198,7 @@ static void event_handle_client(ObClient *client, XEvent *e) } if (e->xconfigurerequest.value_mask & CWStackMode) { - ObClient *sibling = NULL; + ObWindow *sibling = NULL; gulong ignore_start; gboolean ok = TRUE; @@ -1209,7 +1209,11 @@ static void event_handle_client(ObClient *client, XEvent *e) if (win && WINDOW_IS_CLIENT(win) && WINDOW_AS_CLIENT(win) != client) { - sibling = WINDOW_AS_CLIENT(win); + sibling = win; + } + else if (win && WINDOW_IS_DOCK(win)) + { + sibling = win; } else /* an invalid sibling was specified so don't restack at @@ -1560,13 +1564,17 @@ static void event_handle_client(ObClient *client, XEvent *e) "invalid source indication %ld", client->title, e->xclient.data.l[0]); } else { - ObClient *sibling = NULL; + ObWindow *sibling = NULL; if (e->xclient.data.l[1]) { ObWindow *win = window_find(e->xclient.data.l[1]); if (WINDOW_IS_CLIENT(win) && WINDOW_AS_CLIENT(win) != client) { - sibling = WINDOW_AS_CLIENT(win); + sibling = win; + } + if (WINDOW_IS_DOCK(win)) + { + sibling = win; } if (sibling == NULL) ob_debug_type(OB_DEBUG_APP_BUGS, diff --git a/openbox/stacking.c b/openbox/stacking.c index 58551b5..0ef900a 100644 --- a/openbox/stacking.c +++ b/openbox/stacking.c @@ -26,6 +26,8 @@ #include "window.h" #include "event.h" #include "debug.h" +#include "dock.h" +#include "config.h" #include "obt/prop.h" GList *stacking_list = NULL; @@ -567,14 +569,18 @@ void stacking_add_nonintrusive(ObWindow *win) /*! Returns TRUE if client is occluded by the sibling. If sibling is NULL it tries against all other clients. */ -static gboolean stacking_occluded(ObClient *client, ObClient *sibling) +static gboolean stacking_occluded(ObClient *client, ObWindow *sibling_win) { GList *it; gboolean occluded = FALSE; + ObClient *sibling = NULL; + + if (sibling_win && WINDOW_IS_CLIENT(sibling_win)) + sibling = WINDOW_AS_CLIENT(sibling_win); /* no need for any looping in this case */ if (sibling && client->layer != sibling->layer) - return occluded; + return FALSE; for (it = g_list_previous(g_list_find(stacking_list, client)); it; it = g_list_previous(it)) @@ -601,6 +607,21 @@ static gboolean stacking_occluded(ObClient *client, ObClient *sibling) break; /* we past its layer */ } } + } else if (WINDOW_IS_DOCK(it->data)) { + ObDock *dock = it->data; + if (RECT_INTERSECTS_RECT(dock->area, client->frame->area)) + { + if (sibling_win != NULL) { + if (DOCK_AS_WINDOW(dock) == sibling_win) { + occluded = TRUE; + break; + } + } + else if (config_dock_layer == client->layer) { + occluded = TRUE; + break; + } + } } return occluded; } @@ -608,14 +629,18 @@ static gboolean stacking_occluded(ObClient *client, ObClient *sibling) /*! Returns TRUE if client occludes the sibling. If sibling is NULL it tries against all other clients. */ -static gboolean stacking_occludes(ObClient *client, ObClient *sibling) +static gboolean stacking_occludes(ObClient *client, ObWindow *sibling_win) { GList *it; gboolean occludes = FALSE; + ObClient *sibling = NULL; + + if (sibling_win && WINDOW_IS_CLIENT(sibling_win)) + sibling = WINDOW_AS_CLIENT(sibling_win); /* no need for any looping in this case */ if (sibling && client->layer != sibling->layer) - return occludes; + return FALSE; for (it = g_list_next(g_list_find(stacking_list, client)); it; it = g_list_next(it)) @@ -643,14 +668,35 @@ static gboolean stacking_occludes(ObClient *client, ObClient *sibling) } } } + else if (WINDOW_IS_DOCK(it->data)) { + ObDock *dock = it->data; + if (RECT_INTERSECTS_RECT(dock->area, client->frame->area)) + { + if (sibling_win != NULL) { + if (DOCK_AS_WINDOW(dock) == sibling_win) { + occludes = TRUE; + break; + } + } + else if (config_dock_layer == client->layer) { + occludes = TRUE; + break; + } + } + } return occludes; } -gboolean stacking_restack_request(ObClient *client, ObClient *sibling, +gboolean stacking_restack_request(ObClient *client, ObWindow *sibling_win, gint detail) { gboolean ret = FALSE; + ObClient *sibling = NULL; + + if (sibling_win && WINDOW_IS_CLIENT(sibling_win)) + sibling = WINDOW_AS_CLIENT(sibling_win); + if (sibling && ((client->desktop != sibling->desktop && client->desktop != DESKTOP_ALL && sibling->desktop != DESKTOP_ALL) || @@ -674,7 +720,7 @@ gboolean stacking_restack_request(ObClient *client, ObClient *sibling, client->title, sibling ? sibling->title : "(all)"); /* if this client occludes sibling (or anything if NULL), then lower it to the bottom */ - if (stacking_occludes(client, sibling)) { + if (stacking_occludes(client, sibling_win)) { stacking_lower(CLIENT_AS_WINDOW(client)); ret = TRUE; } @@ -688,7 +734,7 @@ gboolean stacking_restack_request(ObClient *client, ObClient *sibling, case TopIf: ob_debug("Restack request TopIf for client %s sibling %s", client->title, sibling ? sibling->title : "(all)"); - if (stacking_occluded(client, sibling)) { + if (stacking_occluded(client, sibling_win)) { stacking_raise(CLIENT_AS_WINDOW(client)); ret = TRUE; } @@ -696,11 +742,11 @@ gboolean stacking_restack_request(ObClient *client, ObClient *sibling, case Opposite: ob_debug("Restack request Opposite for client %s sibling %s", client->title, sibling ? sibling->title : "(all)"); - if (stacking_occluded(client, sibling)) { + if (stacking_occluded(client, sibling_win)) { stacking_raise(CLIENT_AS_WINDOW(client)); ret = TRUE; } - else if (stacking_occludes(client, sibling)) { + else if (stacking_occludes(client, sibling_win)) { stacking_lower(CLIENT_AS_WINDOW(client)); ret = TRUE; } diff --git a/openbox/stacking.h b/openbox/stacking.h index c14aa2e..ebfa175 100644 --- a/openbox/stacking.h +++ b/openbox/stacking.h @@ -71,7 +71,7 @@ void stacking_below(struct _ObWindow *window, struct _ObWindow *below); /*! Restack a window based upon a sibling (or all windows) in various ways. @param client The client to be restacked - @param sibling Another client to compare to, or NULL to compare to all + @param sibling A window to compare to, or NULL to compare to all windows @param detail One of Above, Below, TopIf, BottomIf, Opposite @return TRUE if the client was restacked @@ -79,7 +79,7 @@ void stacking_below(struct _ObWindow *window, struct _ObWindow *below); how each detail works with and without a sibling. */ gboolean stacking_restack_request(struct _ObClient *client, - struct _ObClient *sibling, + struct _ObWindow *sibling_win, gint detail); #endif -- 1.9.1