Added 'con_move_to_mark' to move a container to the container holding a certain mark.

This commit is contained in:
Ingo Bürk 2015-04-15 18:36:45 +02:00
parent 9ab4216787
commit 475671ae2a
3 changed files with 62 additions and 21 deletions

View File

@ -210,6 +210,12 @@ void con_disable_fullscreen(Con *con);
*/ */
void con_move_to_workspace(Con *con, Con *workspace, bool fix_coordinates, bool dont_warp); void con_move_to_workspace(Con *con, Con *workspace, bool fix_coordinates, bool dont_warp);
/**
* Moves the given container to the given mark.
*
*/
bool con_move_to_mark(Con *con, const char *mark);
/** /**
* Returns the orientation of the given container (for stacked containers, * Returns the orientation of the given container (for stacked containers,
* vertical orientation is used regardless of the actual orientation of the * vertical orientation is used regardless of the actual orientation of the

View File

@ -1100,12 +1100,10 @@ void cmd_unmark(I3_CMD, char *mark) {
} }
DLOG("removed all window marks"); DLOG("removed all window marks");
} else { } else {
Con *con; Con *con = con_by_mark(mark);
TAILQ_FOREACH(con, &all_cons, all_cons) { if (con != NULL) {
if (con->mark && strcmp(con->mark, mark) == 0) { FREE(con->mark);
FREE(con->mark); con->mark_changed = true;
con->mark_changed = true;
}
} }
DLOG("removed window mark %s\n", mark); DLOG("removed window mark %s\n", mark);
} }

View File

@ -70,20 +70,10 @@ Con *con_new(Con *parent, i3Window *window) {
return new; return new;
} }
/* static void _con_attach(Con *con, Con *parent, Con *previous, bool ignore_focus) {
* Attaches the given container to the given parent. This happens when moving
* a container or when inserting a new container at a specific place in the
* tree.
*
* ignore_focus is to just insert the Con at the end (useful when creating a
* new split container *around* some containers, that is, detaching and
* attaching them in order without wanting to mess with the focus in between).
*
*/
void con_attach(Con *con, Con *parent, bool ignore_focus) {
con->parent = parent; con->parent = parent;
Con *loop; Con *loop;
Con *current = NULL; Con *current = previous;
struct nodes_head *nodes_head = &(parent->nodes_head); struct nodes_head *nodes_head = &(parent->nodes_head);
struct focus_head *focus_head = &(parent->focus_head); struct focus_head *focus_head = &(parent->focus_head);
@ -170,6 +160,20 @@ add_to_focus_head:
con_force_split_parents_redraw(con); con_force_split_parents_redraw(con);
} }
/*
* Attaches the given container to the given parent. This happens when moving
* a container or when inserting a new container at a specific place in the
* tree.
*
* ignore_focus is to just insert the Con at the end (useful when creating a
* new split container *around* some containers, that is, detaching and
* attaching them in order without wanting to mess with the focus in between).
*
*/
void con_attach(Con *con, Con *parent, bool ignore_focus) {
_con_attach(con, parent, NULL, ignore_focus);
}
/* /*
* Detaches the given container from its current parent * Detaches the given container from its current parent
* *
@ -697,7 +701,9 @@ void con_disable_fullscreen(Con *con) {
con_set_fullscreen_mode(con, CF_NONE); con_set_fullscreen_mode(con, CF_NONE);
} }
static bool _con_move_to_con(Con *con, Con *target, bool fix_coordinates, bool dont_warp) { static bool _con_move_to_con(Con *con, Con *target, bool behind_focused, bool fix_coordinates, bool dont_warp) {
Con *orig_target = target;
/* Prevent moving if this would violate the fullscreen focus restrictions. */ /* Prevent moving if this would violate the fullscreen focus restrictions. */
Con *target_ws = con_get_workspace(target); Con *target_ws = con_get_workspace(target);
if (!con_fullscreen_permits_focusing(target_ws)) { if (!con_fullscreen_permits_focusing(target_ws)) {
@ -801,7 +807,7 @@ static bool _con_move_to_con(Con *con, Con *target, bool fix_coordinates, bool d
/* 4: re-attach the con to the parent of this focused container */ /* 4: re-attach the con to the parent of this focused container */
Con *parent = con->parent; Con *parent = con->parent;
con_detach(con); con_detach(con);
con_attach(con, target, false); _con_attach(con, target, behind_focused ? NULL : orig_target, !behind_focused);
/* 5: fix the percentages */ /* 5: fix the percentages */
con_fix_percent(parent); con_fix_percent(parent);
@ -882,6 +888,35 @@ static bool _con_move_to_con(Con *con, Con *target, bool fix_coordinates, bool d
return true; return true;
} }
/*
* Moves the given container to the given mark.
*
*/
bool con_move_to_mark(Con *con, const char *mark) {
Con *target = con_by_mark(mark);
if (target == NULL) {
DLOG("found no container with mark \"%s\"\n", mark);
return false;
}
/* For floating target containers, we just send the window to the same workspace. */
if (con_is_floating(target)) {
DLOG("target container is floating, moving container to target's workspace.\n");
con_move_to_workspace(con, con_get_workspace(target), true, false);
return true;
}
/* For split containers, we use the currently focused container within it.
* This allows setting marks on, e.g., tabbed containers which will move
* con to a new tab behind the focused tab. */
if (con_is_split(target)) {
DLOG("target is a split container, descending to the currently focused child.\n");
target = TAILQ_FIRST(&(target->focus_head));
}
return _con_move_to_con(con, target, false, true, false);
}
/* /*
* Moves the given container to the currently focused container on the given * Moves the given container to the currently focused container on the given
* workspace. * workspace.
@ -900,6 +935,8 @@ static bool _con_move_to_con(Con *con, Con *target, bool fix_coordinates, bool d
* *
*/ */
void con_move_to_workspace(Con *con, Con *workspace, bool fix_coordinates, bool dont_warp) { void con_move_to_workspace(Con *con, Con *workspace, bool fix_coordinates, bool dont_warp) {
assert(workspace->type == CT_WORKSPACE);
Con *source_ws = con_get_workspace(con); Con *source_ws = con_get_workspace(con);
if (workspace == source_ws) { if (workspace == source_ws) {
DLOG("Not moving, already there\n"); DLOG("Not moving, already there\n");
@ -907,7 +944,7 @@ void con_move_to_workspace(Con *con, Con *workspace, bool fix_coordinates, bool
} }
Con *target = con_descend_focused(workspace); Con *target = con_descend_focused(workspace);
_con_move_to_con(con, target, fix_coordinates, dont_warp); _con_move_to_con(con, target, true, fix_coordinates, dont_warp);
} }
/* /*