From beb96ad18cfad44e54643af1af0f9900216e8b85 Mon Sep 17 00:00:00 2001 From: Albert Safin Date: Mon, 7 Oct 2019 06:13:43 +0000 Subject: [PATCH] Move container to marked workspace: refine corner case This commit should fix "move con to parent" trick (see below) in the case when con->parent->parent is a workspace. The trick: mark _a, focus parent, focus parent, mark _b, [con_mark=_a] move window to mark _b, [con_mark=_a] focus The trick got broken in commit 626af81232e6ca81abea22267f3330c16d804596 in order to fix an i3 crash (#2003). Reverting said commit fixes the trick. The crash is caused by the fact that empty workspace isn't considered a split (checked in src/con.c:1324), so the moved window ends up as a sibling of the target workspace, not as its child. --- src/con.c | 4 ++-- testcases/lib/i3test.pm.in | 2 +- testcases/t/243-move-to-mark.t | 1 + testcases/t/306-move-to-parent.t | 37 ++++++++++++++++++++++++++++++++ 4 files changed, 41 insertions(+), 3 deletions(-) create mode 100644 testcases/t/306-move-to-parent.t diff --git a/src/con.c b/src/con.c index 0f913e0a..e9f82cf4 100644 --- a/src/con.c +++ b/src/con.c @@ -1312,8 +1312,8 @@ bool con_move_to_mark(Con *con, const char *mark) { return true; } - if (target->type == CT_WORKSPACE) { - DLOG("target container is a workspace, simply moving the container there.\n"); + if (target->type == CT_WORKSPACE && con_is_leaf(target)) { + DLOG("target container is an empty workspace, simply moving the container there.\n"); con_move_to_workspace(con, target, true, false, false); return true; } diff --git a/testcases/lib/i3test.pm.in b/testcases/lib/i3test.pm.in index 740e13e9..161ddf79 100644 --- a/testcases/lib/i3test.pm.in +++ b/testcases/lib/i3test.pm.in @@ -1230,7 +1230,7 @@ sub create_layout { $r = $r . '{"swallows": [{'; $r = $r . '"class": "^' . "$char" . '$"'; - $r = $r . '}]},'; + $r = $r . '}]}' . ($depth == 0 ? "\n" : ','); } else { die "Could not understand $char"; } diff --git a/testcases/t/243-move-to-mark.t b/testcases/t/243-move-to-mark.t index b6ec462e..390da04d 100644 --- a/testcases/t/243-move-to-mark.t +++ b/testcases/t/243-move-to-mark.t @@ -361,6 +361,7 @@ does_i3_live; ############################################################################### # Given 'S' and 'M' where 'M' is a workspace and 'S' is on a different # workspace, then 'S' ends up as a tiling container on 'M'. +# See issue: #2003 ############################################################################### fresh_workspace; diff --git a/testcases/t/306-move-to-parent.t b/testcases/t/306-move-to-parent.t new file mode 100644 index 00000000..8610cff9 --- /dev/null +++ b/testcases/t/306-move-to-parent.t @@ -0,0 +1,37 @@ +#!perl +# vim:ts=4:sw=4:expandtab +# +# Please read the following documents before working on tests: +# • https://build.i3wm.org/docs/testsuite.html +# (or docs/testsuite) +# +# • https://build.i3wm.org/docs/lib-i3test.html +# (alternatively: perldoc ./testcases/lib/i3test.pm) +# +# • https://build.i3wm.org/docs/ipc.html +# (or docs/ipc) +# +# • http://onyxneon.com/books/modern_perl/modern_perl_a4.pdf +# (unless you are already familiar with Perl) +# +# Make sure the trick used to move the container to its parent works. +# https://github.com/i3/i3/issues/1326#issuecomment-349082811 +use i3test; + +cmp_tree( + msg => 'Move to parent when the parent is a workspace', + layout_before => 'a H[b*] c', + layout_after => 'a b* c', + cb => sub { + cmd 'mark _a, focus parent, focus parent, mark _b, [con_mark=_a] move window to mark _b, [con_mark=_a] focus'; + }); + +cmp_tree( + msg => 'Move to parent when the parent is a split', + layout_before => 'V[a H[b*] c]', + layout_after => 'V[a b* c]', + cb => sub { + cmd 'mark _a, focus parent, focus parent, mark _b, [con_mark=_a] move window to mark _b, [con_mark=_a] focus'; + }); + +done_testing;