diff --git a/restore.c b/restore.c index 4950941..3ec7e84 100644 --- a/restore.c +++ b/restore.c @@ -201,7 +201,7 @@ void restore_tree(char *file_path) xcb_change_window_attributes(dpy, n->client->window, XCB_CW_EVENT_MASK, values); if (!IS_TILED(n->client)) { n->vacant = true; - update_vacant_state(n->parent); + propagate_vacant_state(n); } if (n->client->private) { update_privacy_level(n, true); diff --git a/tree.c b/tree.c index 2ca7d38..3410f65 100644 --- a/tree.c +++ b/tree.c @@ -274,7 +274,7 @@ void insert_node(monitor_t *m, desktop_t *d, node_t *n, node_t *f) break; } if (f->vacant) { - update_vacant_state(f->parent); + propagate_vacant_state(f); } if (f->client != NULL) { if (f->client->private) { @@ -938,7 +938,7 @@ void unlink_node(monitor_t *m, desktop_t *d, node_t *n) b->birth_rotation = p->birth_rotation; n->parent = NULL; free(p); - update_vacant_state(b->parent); + propagate_vacant_state(b); if (n == d->focus) { d->focus = history_get_node(d, n); @@ -1027,8 +1027,8 @@ bool swap_nodes(monitor_t *m1, desktop_t *d1, node_t *n1, monitor_t *m2, desktop n2->privacy_level = pl1; if (n1->vacant != n2->vacant) { - update_vacant_state(n1->parent); - update_vacant_state(n2->parent); + propagate_vacant_state(n1); + propagate_vacant_state(n2); } if (n1->client->private != n2->client->private) { @@ -1167,13 +1167,26 @@ void circulate_leaves(monitor_t *m, desktop_t *d, circulate_dir_t dir) focus_node(m, d, p->second_child); } -void update_vacant_state(node_t *n) +void set_vacant_state(node_t *n, bool value) { - if (n == NULL) - return; + n->vacant = value; - /* n is not a leaf */ - node_t *p = n; + if (value) { + unrotate_brother(n); + } else { + rotate_brother(n); + } + + propagate_vacant_state(n); +} + +void propagate_vacant_state(node_t *n) +{ + if (n == NULL) { + return; + } + + node_t *p = n->parent; while (p != NULL) { p->vacant = (p->first_child->vacant && p->second_child->vacant); diff --git a/tree.h b/tree.h index 25316c4..fd48de0 100644 --- a/tree.h +++ b/tree.h @@ -69,7 +69,8 @@ bool swap_nodes(monitor_t *m1, desktop_t *d1, node_t *n1, monitor_t *m2, desktop bool transfer_node(monitor_t *ms, desktop_t *ds, node_t *ns, monitor_t *md, desktop_t *dd, node_t *nd); node_t *closest_node(monitor_t *m, desktop_t *d, node_t *n, cycle_dir_t dir, client_select_t sel); void circulate_leaves(monitor_t *m, desktop_t *d, circulate_dir_t dir); -void update_vacant_state(node_t *n); +void set_vacant_state(node_t *n, bool value); +void propagate_vacant_state(node_t *n); void update_privacy_level(node_t *n, bool value); #endif diff --git a/window.c b/window.c index ce00809..2acf805 100644 --- a/window.c +++ b/window.c @@ -452,16 +452,10 @@ void set_floating(monitor_t *m, desktop_t *d, node_t *n, bool value) } n->split_mode = MODE_AUTOMATIC; - n->vacant = value; - update_vacant_state(n->parent); + set_vacant_state(n, value); - if (value) { - unrotate_brother(n); - } else { - rotate_brother(n); - if (d->focus == n) { - neutralize_obscuring_windows(m, d, n); - } + if (!value && d->focus == n) { + neutralize_obscuring_windows(m, d, n); } stack(n, (d->focus == n)); @@ -476,8 +470,7 @@ void set_fullscreen(monitor_t *m, desktop_t *d, node_t *n, bool value) client_t *c = n->client; n->split_mode = MODE_AUTOMATIC; - n->vacant = value; - update_vacant_state(n->parent); + set_vacant_state(n, value); if (value) { ewmh_wm_state_add(c, ewmh->_NET_WM_STATE_FULLSCREEN);