basic split containers

This commit is contained in:
Tony Crisci 2018-03-31 00:44:17 -04:00
parent 122b96abed
commit 7706d83160
10 changed files with 245 additions and 51 deletions

View file

@ -1,4 +1,5 @@
#define _POSIX_C_SOURCE 200809L
#include <assert.h>
#include <ctype.h>
#include <math.h>
#include <stdbool.h>
@ -100,6 +101,8 @@ void container_add_child(struct sway_container *parent,
parent, parent->type, parent->width, parent->height);
list_add(parent->children, child);
child->parent = parent;
// TODO: set focus for this container?
sway_input_manager_set_focus(input_manager, child);
}
struct sway_container *container_reap_empty(struct sway_container *container) {
@ -135,7 +138,7 @@ struct sway_container *container_remove_child(struct sway_container *child) {
}
}
child->parent = NULL;
return container_reap_empty(parent);
return parent;
}
void container_move_to(struct sway_container* container,
@ -322,7 +325,12 @@ static void apply_horiz_layout(struct sway_container *container,
wlr_log(L_DEBUG,
"Calculating arrangement for %p:%d (will scale %f by %f)",
child, child->type, width, scale);
view_set_position(child->sway_view, child_x, y);
if (child->type == C_VIEW) {
view_set_position(child->sway_view, child_x, y);
} else {
child->x = child_x;
child->y = y;
}
if (i == end - 1) {
double remaining_width = x + width - child_x;
@ -505,9 +513,9 @@ static struct sway_container *sway_output_from_wlr(struct wlr_output *output) {
return NULL;
}
static struct sway_container *get_swayc_in_direction_under(
struct sway_container *container, enum movement_direction dir,
struct sway_seat *seat, struct sway_container *limit) {
struct sway_container *container_get_in_direction(
struct sway_container *container, struct sway_seat *seat,
enum movement_direction dir) {
if (dir == MOVE_CHILD) {
return sway_seat_get_focus_inactive(seat, container);
}
@ -559,7 +567,6 @@ static struct sway_container *get_swayc_in_direction_under(
struct sway_container *wrap_candidate = NULL;
while (true) {
// Test if we can even make a difference here
bool can_move = false;
int desired;
int idx = index_child(container);
@ -589,7 +596,7 @@ static struct sway_container *get_swayc_in_direction_under(
}
if (next->children && next->children->length) {
// TODO consider floating children as well
return sway_seat_get_focus_inactive(seat, next);
return sway_seat_get_focus_by_type(seat, next, C_VIEW);
} else {
return next;
}
@ -619,21 +626,22 @@ static struct sway_container *get_swayc_in_direction_under(
wrap_candidate = parent->children->items[0];
}
if (config->force_focus_wrapping) {
return wrap_candidate;
return sway_seat_get_focus_by_type(seat, wrap_candidate, C_VIEW);
}
}
} else {
wlr_log(L_DEBUG,
"cont %d-%p dir %i sibling %d: %p", idx,
container, dir, desired, parent->children->items[desired]);
return parent->children->items[desired];
return sway_seat_get_focus_by_type(seat,
parent->children->items[desired], C_VIEW);
}
}
if (!can_move) {
container = parent;
parent = parent->parent;
if (!parent || container == limit) {
if (!parent) {
// wrapping is the last chance
return wrap_candidate;
}
@ -641,8 +649,71 @@ static struct sway_container *get_swayc_in_direction_under(
}
}
struct sway_container *container_get_in_direction(
struct sway_container *container, struct sway_seat *seat,
enum movement_direction dir) {
return get_swayc_in_direction_under(container, dir, seat, NULL);
struct sway_container *container_replace_child(struct sway_container *child,
struct sway_container *new_child) {
struct sway_container *parent = child->parent;
if (parent == NULL) {
return NULL;
}
int i = index_child(child);
// TODO floating
parent->children->items[i] = new_child;
new_child->parent = parent;
child->parent = NULL;
// Set geometry for new child
new_child->x = child->x;
new_child->y = child->y;
new_child->width = child->width;
new_child->height = child->height;
// reset geometry for child
child->width = 0;
child->height = 0;
return parent;
}
struct sway_container *container_split(struct sway_container *child,
enum sway_container_layout layout) {
// TODO floating: cannot split a floating container
if (!sway_assert(child, "child cannot be null")) {
return NULL;
}
struct sway_container *cont = container_create(C_CONTAINER);
wlr_log(L_DEBUG, "creating container %p around %p", cont, child);
cont->prev_layout = L_NONE;
cont->layout = layout;
cont->width = child->width;
cont->height = child->height;
cont->x = child->x;
cont->y = child->y;
/* Container inherits all of workspaces children, layout and whatnot */
if (child->type == C_WORKSPACE) {
struct sway_container *workspace = child;
// reorder focus
int i;
for (i = 0; i < workspace->children->length; ++i) {
((struct sway_container *)workspace->children->items[i])->parent =
cont;
}
// Swap children
list_t *tmp_list = workspace->children;
workspace->children = cont->children;
cont->children = tmp_list;
// add container to workspace chidren
container_add_child(workspace, cont);
// give them proper layouts
cont->layout = workspace->workspace_layout;
cont->prev_layout = workspace->prev_layout;
} else { // Or is built around container
container_replace_child(child, cont);
container_add_child(cont, child);
}
return cont;
}