From 9380a75186f8d2adcf572a3741168f12351faa9b Mon Sep 17 00:00:00 2001 From: Orestis Floros Date: Tue, 9 Oct 2018 21:45:59 +0300 Subject: [PATCH] move.c: Fix move_to_output_directed problems - Use workspace_show that correctly updates _NET_CURRENT_DESKTOP, warps mouse. - Use TAILQ_INSERT_TAIL only for focus_head. Focus order is not related to direction. - Call con_focus only if con was focused before. See testcase for directional move with command criteria. - Correct first call of move_to_output_directed in tree_move which didn't call ipc_send_window_event("move", con) and ewmh_update_wm_desktop(). - Don't produce events when the move doesn't happen. Correct 276-ipc-window-move.t as well. --- src/move.c | 31 ++++++++++++++++++------------- testcases/t/276-ipc-window-move.t | 2 +- testcases/t/294-focus-order.t | 22 ++++++++++++++++++++-- 3 files changed, 39 insertions(+), 16 deletions(-) diff --git a/src/move.c b/src/move.c index 32178e6b..58ce488d 100644 --- a/src/move.c +++ b/src/move.c @@ -179,18 +179,16 @@ void insert_con_into(Con *con, Con *target, position_t position) { static void attach_to_workspace(Con *con, Con *ws, direction_t direction) { con_detach(con); con_fix_percent(con->parent); - CALL(con->parent, on_remove_child); con->parent = ws; if (direction == D_RIGHT || direction == D_DOWN) { TAILQ_INSERT_HEAD(&(ws->nodes_head), con, nodes); - TAILQ_INSERT_HEAD(&(ws->focus_head), con, focused); } else { TAILQ_INSERT_TAIL(&(ws->nodes_head), con, nodes); - TAILQ_INSERT_TAIL(&(ws->focus_head), con, focused); } + TAILQ_INSERT_TAIL(&(ws->focus_head), con, focused); /* Pretend the con was just opened with regards to size percent values. * Since the con is moved to a completely different con, the old value @@ -205,7 +203,6 @@ static void attach_to_workspace(Con *con, Con *ws, direction_t direction) { * */ static void move_to_output_directed(Con *con, direction_t direction) { - Con *old_ws = con_get_workspace(con); Output *current_output = get_output_for_con(con); Output *output = get_output_next(direction, current_output, CLOSEST_OUTPUT); @@ -222,17 +219,26 @@ static void move_to_output_directed(Con *con, direction_t direction) { return; } + Con *old_ws = con_get_workspace(con); + const bool moves_focus = (focused == con); attach_to_workspace(con, ws, direction); - - /* fix the focus stack */ - con_activate(con); + if (moves_focus) { + /* workspace_show will not correctly update the active workspace because + * the focused container, con, is now a child of ws. To work around this + * and still produce the correct workspace focus events (see + * 517-regress-move-direction-ipc.t) we need to temporarily set focused + * to the old workspace. */ + focused = old_ws; + workspace_show(ws); + con_focus(con); + } /* force re-painting the indicators */ FREE(con->deco_render_params); tree_flatten(croot); - - ipc_send_workspace_event("focus", ws, old_ws); + ipc_send_window_event("move", con); + ewmh_update_wm_desktop(); } /* @@ -321,11 +327,9 @@ void tree_move(Con *con, int direction) { } if (con->parent == con_get_workspace(con)) { - /* If we couldn't find a place to move it on this workspace, - * try to move it to a workspace on a different output */ + /* If we couldn't find a place to move it on this workspace, try + * to move it to a workspace on a different output */ move_to_output_directed(con, direction); - ipc_send_window_event("move", con); - ewmh_update_wm_desktop(); return; } @@ -370,6 +374,7 @@ void tree_move(Con *con, int direction) { * and move it to the next output. */ DLOG("Grandparent is workspace\n"); move_to_output_directed(con, direction); + return; } else { DLOG("Moving into container above\n"); position = (direction == D_UP || direction == D_LEFT ? BEFORE : AFTER); diff --git a/testcases/t/276-ipc-window-move.t b/testcases/t/276-ipc-window-move.t index f3606b4e..708963df 100644 --- a/testcases/t/276-ipc-window-move.t +++ b/testcases/t/276-ipc-window-move.t @@ -34,7 +34,7 @@ sub move_subtest { is($move[0]->{container}->{window}, $window->{id}, 'window id matches'); } -subtest 'move right', \&move_subtest, 'move right'; +subtest 'move left', \&move_subtest, 'move left'; subtest 'move to workspace', \&move_subtest, 'move to workspace ws_new'; done_testing; diff --git a/testcases/t/294-focus-order.t b/testcases/t/294-focus-order.t index c818f1d4..b5d3514a 100644 --- a/testcases/t/294-focus-order.t +++ b/testcases/t/294-focus-order.t @@ -16,7 +16,11 @@ # # Verify that the corrent focus stack order is preserved after various # operations. -use i3test; +use i3test i3_config => < 0); +$windows[3] = open_window; +fresh_workspace(output => 1); +$windows[2] = open_window; +$windows[1] = open_window; +$windows[0] = open_window; + +cmd '[id=' . $windows[3]->id . '] move right'; +confirm_focus('unfocused move from other output'); + ###################################################################### # Test that moving an unfocused container maintains the correct focus # order.