Introduce con_get_fullscreen_covering_ws

This commit will also fix the following bugs:
1. click.c: Users could drag global fullscreen floating containers.
2. render.c: Floating containers would get rendered with a global fullscreen container in another
workspace.
This commit is contained in:
Orestis Floros 2018-08-22 14:02:27 +03:00
parent b3e69ed12a
commit efc78de4ee
No known key found for this signature in database
GPG Key ID: E9AD9F32E401E38F
7 changed files with 31 additions and 16 deletions

View File

@ -120,6 +120,14 @@ Con *con_parent_with_orientation(Con *con, orientation_t orientation);
*/ */
Con *con_get_fullscreen_con(Con *con, fullscreen_mode_t fullscreen_mode); Con *con_get_fullscreen_con(Con *con, fullscreen_mode_t fullscreen_mode);
/**
* Returns the fullscreen node that covers the given workspace if it exists.
* This is either a CF_GLOBAL fullscreen container anywhere or a CF_OUTPUT
* fullscreen container in the workspace.
*
*/
Con *con_get_fullscreen_covering_ws(Con *ws);
/** /**
* Returns true if the container is internal, such as __i3_scratch * Returns true if the container is internal, such as __i3_scratch
* *

View File

@ -254,7 +254,7 @@ static int route_click(Con *con, xcb_button_press_event_t *event, const bool mod
/* 3: For floating containers, we also want to raise them on click. /* 3: For floating containers, we also want to raise them on click.
* We will skip handling events on floating cons in fullscreen mode */ * We will skip handling events on floating cons in fullscreen mode */
Con *fs = (ws ? con_get_fullscreen_con(ws, CF_OUTPUT) : NULL); Con *fs = con_get_fullscreen_covering_ws(ws);
if (floatingcon != NULL && fs != con) { if (floatingcon != NULL && fs != con) {
/* 4: floating_modifier plus left mouse button drags */ /* 4: floating_modifier plus left mouse button drags */
if (mod_pressed && event->detail == XCB_BUTTON_CLICK_LEFT) { if (mod_pressed && event->detail == XCB_BUTTON_CLICK_LEFT) {

View File

@ -1282,7 +1282,7 @@ void cmd_focus_direction(I3_CMD, const char *direction) {
static void cmd_focus_force_focus(Con *con) { static void cmd_focus_force_focus(Con *con) {
/* Disable fullscreen container in workspace with container to be focused. */ /* Disable fullscreen container in workspace with container to be focused. */
Con *ws = con_get_workspace(con); Con *ws = con_get_workspace(con);
Con *fullscreen_on_ws = (focused && focused->fullscreen_mode == CF_GLOBAL) ? focused : con_get_fullscreen_con(ws, CF_OUTPUT); Con *fullscreen_on_ws = con_get_fullscreen_covering_ws(ws);
if (fullscreen_on_ws && fullscreen_on_ws != con && !con_has_parent(con, fullscreen_on_ws)) { if (fullscreen_on_ws && fullscreen_on_ws != con && !con_has_parent(con, fullscreen_on_ws)) {
con_disable_fullscreen(fullscreen_on_ws); con_disable_fullscreen(fullscreen_on_ws);
} }

View File

@ -509,6 +509,23 @@ Con *con_get_fullscreen_con(Con *con, fullscreen_mode_t fullscreen_mode) {
return NULL; return NULL;
} }
/*
* Returns the fullscreen node that covers the given workspace if it exists.
* This is either a CF_GLOBAL fullscreen container anywhere or a CF_OUTPUT
* fullscreen container in the workspace.
*
*/
Con *con_get_fullscreen_covering_ws(Con *ws) {
if (!ws) {
return NULL;
}
Con *fs = con_get_fullscreen_con(croot, CF_GLOBAL);
if (!fs) {
return con_get_fullscreen_con(ws, CF_OUTPUT);
}
return fs;
}
/** /**
* Returns true if the container is internal, such as __i3_scratch * Returns true if the container is internal, such as __i3_scratch
* *

View File

@ -310,16 +310,8 @@ static void handle_configure_request(xcb_configure_request_event_t *event) {
DLOG("Configure request!\n"); DLOG("Configure request!\n");
Con *workspace = con_get_workspace(con), Con *workspace = con_get_workspace(con);
*fullscreen = NULL; Con *fullscreen = con_get_fullscreen_covering_ws(workspace);
/* There might not be a corresponding workspace for dock cons, therefore we
* have to be careful here. */
if (workspace) {
fullscreen = con_get_fullscreen_con(workspace, CF_OUTPUT);
if (!fullscreen)
fullscreen = con_get_fullscreen_con(workspace, CF_GLOBAL);
}
if (fullscreen != con && con_is_floating(con) && con_is_leaf(con)) { if (fullscreen != con && con_is_floating(con) && con_is_leaf(con)) {
/* find the height for the decorations */ /* find the height for the decorations */

View File

@ -378,9 +378,7 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki
/* handle fullscreen containers */ /* handle fullscreen containers */
Con *ws = con_get_workspace(nc); Con *ws = con_get_workspace(nc);
Con *fs = (ws ? con_get_fullscreen_con(ws, CF_OUTPUT) : NULL); Con *fs = con_get_fullscreen_covering_ws(ws);
if (fs == NULL)
fs = con_get_fullscreen_con(croot, CF_GLOBAL);
if (xcb_reply_contains_atom(state_reply, A__NET_WM_STATE_FULLSCREEN)) { if (xcb_reply_contains_atom(state_reply, A__NET_WM_STATE_FULLSCREEN)) {
/* If this window is already fullscreen (after restarting!), skip /* If this window is already fullscreen (after restarting!), skip

View File

@ -232,7 +232,7 @@ static void render_root(Con *con, Con *fullscreen) {
continue; continue;
} }
Con *workspace = TAILQ_FIRST(&(content->focus_head)); Con *workspace = TAILQ_FIRST(&(content->focus_head));
Con *fullscreen = con_get_fullscreen_con(workspace, CF_OUTPUT); Con *fullscreen = con_get_fullscreen_covering_ws(workspace);
Con *child; Con *child;
TAILQ_FOREACH(child, &(workspace->floating_head), floating_windows) { TAILQ_FOREACH(child, &(workspace->floating_head), floating_windows) {
if (fullscreen != NULL) { if (fullscreen != NULL) {