From 1e143feab1e7f6cee1a3a48dc70eb1b353adc108 Mon Sep 17 00:00:00 2001 From: Michael Stapelberg Date: Sat, 22 Sep 2012 19:03:19 +0200 Subject: [PATCH] Close empty workspaces after cross-output move (+test) (Thanks chrysn) fixes #795 --- src/commands.c | 10 +++++++++- testcases/t/504-move-workspace-to-output.t | 20 ++++++++++++++++++++ 2 files changed, 29 insertions(+), 1 deletion(-) diff --git a/src/commands.c b/src/commands.c index 4a8258e2..2bbde9bf 100644 --- a/src/commands.c +++ b/src/commands.c @@ -1099,8 +1099,12 @@ void cmd_move_workspace_to_output(I3_CMD, char *name) { Con *content = output_get_content(output->con); LOG("got output %p with content %p\n", output, content); + Con *previously_visible_ws = TAILQ_FIRST(&(content->nodes_head)); + LOG("Previously visible workspace = %p / %s\n", previously_visible_ws, previously_visible_ws->name); + Con *ws = con_get_workspace(current->con); LOG("should move workspace %p / %s\n", ws, ws->name); + bool workspace_was_visible = workspace_is_visible(ws); if (con_num_children(ws->parent) == 1) { LOG("Creating a new workspace to replace \"%s\" (last on its output).\n", ws->name); @@ -1137,7 +1141,6 @@ void cmd_move_workspace_to_output(I3_CMD, char *name) { } /* detach from the old output and attach to the new output */ - bool workspace_was_visible = workspace_is_visible(ws); Con *old_content = ws->parent; con_detach(ws); if (workspace_was_visible) { @@ -1159,6 +1162,11 @@ void cmd_move_workspace_to_output(I3_CMD, char *name) { /* Focus the moved workspace on the destination output. */ workspace_show(ws); } + + /* Call the on_remove_child callback of the workspace which previously + * was visible on the destination output. Since it is no longer + * visible, it might need to get cleaned up. */ + CALL(previously_visible_ws, on_remove_child); } cmd_output->needs_tree_render = true; diff --git a/testcases/t/504-move-workspace-to-output.t b/testcases/t/504-move-workspace-to-output.t index 7a976271..c087f9f5 100644 --- a/testcases/t/504-move-workspace-to-output.t +++ b/testcases/t/504-move-workspace-to-output.t @@ -133,6 +133,26 @@ is($old_rect->{y}, $new_rect->{y}, 'y coordinate unchanged'); is($old_rect->{width}, $new_rect->{width}, 'width unchanged'); is($old_rect->{height}, $new_rect->{height}, 'height unchanged'); +################################################################################ +# Verify that empty workspaces get cleaned up when moving a different workspace +# to that output. +################################################################################ + +my $empty_ws = fresh_workspace(output => 0); +my $other_output_ws = fresh_workspace(output => 1); +cmd 'open'; + +($x0, $x1) = workspaces_per_screen(); +ok($empty_ws ~~ @$x0, 'empty_ws on fake-0'); +ok($other_output_ws ~~ @$x1, 'other_output_ws on fake-1'); + +cmd 'move workspace to output left'; + +($x0, $x1) = workspaces_per_screen(); +ok(!($empty_ws ~~ @$x0), 'empty_ws not on fake-0'); +ok(!($empty_ws ~~ @$x1), 'empty_ws not on fake-1'); +ok($other_output_ws ~~ @$x0, 'other_output_ws on fake-0'); + exit_gracefully($pid); done_testing;