diff options
-rw-r--r-- | include/layout.h | 7 | ||||
-rw-r--r-- | sway/commands.c | 8 | ||||
-rw-r--r-- | sway/input_state.c | 1 | ||||
-rw-r--r-- | sway/layout.c | 128 |
4 files changed, 92 insertions, 52 deletions
diff --git a/include/layout.h b/include/layout.h index 2d2a1113..f462bdb3 100644 --- a/include/layout.h +++ b/include/layout.h | |||
@@ -37,10 +37,13 @@ swayc_t *replace_child(swayc_t *child, swayc_t *new_child); | |||
37 | // a sibling, or to a floating window, or NULL | 37 | // a sibling, or to a floating window, or NULL |
38 | swayc_t *remove_child(swayc_t *child); | 38 | swayc_t *remove_child(swayc_t *child); |
39 | 39 | ||
40 | // 2 containers are swapped, they inherit eachothers geometry and focus | 40 | // 2 containers are swapped, they inherit eachothers focus |
41 | void swap_container(swayc_t *a, swayc_t *b); | 41 | void swap_container(swayc_t *a, swayc_t *b); |
42 | 42 | ||
43 | void move_container(swayc_t* container,swayc_t* root,enum movement_direction direction); | 43 | // 2 Containers geometry are swapped, used with `swap_container` |
44 | void swap_geometry(swayc_t *a, swayc_t *b); | ||
45 | |||
46 | void move_container(swayc_t* container, enum movement_direction direction); | ||
44 | void move_container_to(swayc_t* container, swayc_t* destination); | 47 | void move_container_to(swayc_t* container, swayc_t* destination); |
45 | 48 | ||
46 | // Layout | 49 | // Layout |
diff --git a/sway/commands.c b/sway/commands.c index 1d88e724..cd010913 100644 --- a/sway/commands.c +++ b/sway/commands.c | |||
@@ -351,13 +351,13 @@ static bool cmd_move(struct sway_config *config, int argc, char **argv) { | |||
351 | swayc_t *view = get_focused_container(&root_container); | 351 | swayc_t *view = get_focused_container(&root_container); |
352 | 352 | ||
353 | if (strcasecmp(argv[0], "left") == 0) { | 353 | if (strcasecmp(argv[0], "left") == 0) { |
354 | move_container(view,&root_container,MOVE_LEFT); | 354 | move_container(view,MOVE_LEFT); |
355 | } else if (strcasecmp(argv[0], "right") == 0) { | 355 | } else if (strcasecmp(argv[0], "right") == 0) { |
356 | move_container(view,&root_container,MOVE_RIGHT); | 356 | move_container(view,MOVE_RIGHT); |
357 | } else if (strcasecmp(argv[0], "up") == 0) { | 357 | } else if (strcasecmp(argv[0], "up") == 0) { |
358 | move_container(view,&root_container,MOVE_UP); | 358 | move_container(view,MOVE_UP); |
359 | } else if (strcasecmp(argv[0], "down") == 0) { | 359 | } else if (strcasecmp(argv[0], "down") == 0) { |
360 | move_container(view,&root_container,MOVE_DOWN); | 360 | move_container(view,MOVE_DOWN); |
361 | } else if (strcasecmp(argv[0], "container") == 0 || strcasecmp(argv[0], "window") == 0) { | 361 | } else if (strcasecmp(argv[0], "container") == 0 || strcasecmp(argv[0], "window") == 0) { |
362 | // "move container to workspace x" | 362 | // "move container to workspace x" |
363 | if (!checkarg(argc, "move container/window", EXPECTED_EQUAL_TO, 4) || | 363 | if (!checkarg(argc, "move container/window", EXPECTED_EQUAL_TO, 4) || |
diff --git a/sway/input_state.c b/sway/input_state.c index a7febc08..2743a9ea 100644 --- a/sway/input_state.c +++ b/sway/input_state.c | |||
@@ -297,6 +297,7 @@ void pointer_mode_update(void) { | |||
297 | && !pointer_state.view->is_floating) { | 297 | && !pointer_state.view->is_floating) { |
298 | // Swap them around | 298 | // Swap them around |
299 | swap_container(pointer_state.view, initial.ptr); | 299 | swap_container(pointer_state.view, initial.ptr); |
300 | swap_geometry(pointer_state.view, initial.ptr); | ||
300 | update_geometry(pointer_state.view); | 301 | update_geometry(pointer_state.view); |
301 | update_geometry(initial.ptr); | 302 | update_geometry(initial.ptr); |
302 | // Set focus back to initial view | 303 | // Set focus back to initial view |
diff --git a/sway/layout.c b/sway/layout.c index f04007ed..6e64257b 100644 --- a/sway/layout.c +++ b/sway/layout.c | |||
@@ -47,6 +47,20 @@ void add_child(swayc_t *parent, swayc_t *child) { | |||
47 | } | 47 | } |
48 | } | 48 | } |
49 | 49 | ||
50 | void insert_child(swayc_t *parent, swayc_t *child, int index) { | ||
51 | if (index > parent->children->length) { | ||
52 | index = parent->children->length; | ||
53 | } | ||
54 | if (index < 0) { | ||
55 | index = 0; | ||
56 | } | ||
57 | list_insert(parent->children, index, child); | ||
58 | child->parent = parent; | ||
59 | if (!parent->focused) { | ||
60 | parent->focused = child; | ||
61 | } | ||
62 | } | ||
63 | |||
50 | void add_floating(swayc_t *ws, swayc_t *child) { | 64 | void add_floating(swayc_t *ws, swayc_t *child) { |
51 | sway_log(L_DEBUG, "Adding %p (%d, %fx%f) to %p (%d, %fx%f)", child, child->type, | 65 | sway_log(L_DEBUG, "Adding %p (%d, %fx%f) to %p (%d, %fx%f)", child, child->type, |
52 | child->width, child->height, ws, ws->type, ws->width, ws->height); | 66 | child->width, child->height, ws, ws->type, ws->width, ws->height); |
@@ -161,7 +175,9 @@ void swap_container(swayc_t *a, swayc_t *b) { | |||
161 | if (b_parent->focused == b && a_parent != b_parent) { | 175 | if (b_parent->focused == b && a_parent != b_parent) { |
162 | b_parent->focused = a; | 176 | b_parent->focused = a; |
163 | } | 177 | } |
164 | // and their geometry | 178 | } |
179 | |||
180 | void swap_geometry(swayc_t *a, swayc_t *b) { | ||
165 | double x = a->x; | 181 | double x = a->x; |
166 | double y = a->y; | 182 | double y = a->y; |
167 | double w = a->width; | 183 | double w = a->width; |
@@ -176,48 +192,73 @@ void swap_container(swayc_t *a, swayc_t *b) { | |||
176 | b->height = h; | 192 | b->height = h; |
177 | } | 193 | } |
178 | 194 | ||
179 | //TODO: Implement horizontal movement. | 195 | // TODO fix workspace movement, as in |
180 | //TODO: Implement move to a different workspace. | 196 | // [a][b][c] => |move b| => [aa][cc] |
181 | void move_container(swayc_t *container,swayc_t* root,enum movement_direction direction) { | 197 | // [a][b][c] => |down | => [bbbbbb] |
182 | sway_log(L_DEBUG, "Moved window"); | 198 | // |
183 | swayc_t *temp; | 199 | void move_container(swayc_t *container, enum movement_direction dir) { |
184 | int i; | 200 | enum swayc_layouts layout; |
185 | int clength = root->children->length; | 201 | if (dir == MOVE_UP || dir == MOVE_DOWN) { |
186 | //Rearrange | 202 | layout = L_VERT; |
187 | for (i = 0; i < clength; ++i) { | 203 | } else if (dir == MOVE_LEFT || dir == MOVE_RIGHT) { |
188 | swayc_t *child = root->children->items[i]; | 204 | layout = L_HORIZ; |
189 | if (child->handle == container->handle){ | 205 | } else { |
190 | if (clength == 1){ | 206 | return; |
191 | //Only one container, meh. | 207 | } |
192 | break; | 208 | swayc_t *parent = container->parent; |
193 | } | 209 | swayc_t *child = container; |
194 | if (direction == MOVE_LEFT && i > 0){ | 210 | while (true) { |
195 | temp = root->children->items[i-1]; | 211 | sway_log(L_DEBUG, "container:%p, parent:%p, child %p,", |
196 | root->children->items[i] = temp; | 212 | container,parent,child); |
197 | root->children->items[i-1] = container; | 213 | if (parent->layout == layout) { |
198 | arrange_windows(&root_container,-1,-1); | 214 | int diff; |
199 | } | 215 | // When child == container the container is removed, |
200 | else if (direction == MOVE_RIGHT && i < clength-1){ | 216 | // so when inserting it back in, it needs to be -1, or 1 |
201 | temp = root->children->items[i+1]; | 217 | // inserts at 1-1 or 1+1 |
202 | root->children->items[i] = temp; | 218 | // 0 1 2 3 => 0 1 2 => 0 1 2 3 or 0 1 2 3 |
203 | root->children->items[i+1] = container; | 219 | // |0|1|2| => |0|2| => |1|0|2| or |0|2|1| |
204 | arrange_windows(&root_container,-1,-1); | 220 | // When child != container, no container is removed |
205 | 221 | // inserts at 1+0 or 1+1 | |
206 | } | 222 | // 0 1 2 3 => 0 1 2 3 4 or 0 1 2 3 4 |
207 | else if (direction == MOVE_UP){ | 223 | // |0|1|2| => |0|n|1|2| or |0|1|n|2| |
208 | sway_log(L_INFO, "Moving up not implemented"); | 224 | if (child == container) { |
225 | diff = dir == MOVE_LEFT || dir == MOVE_UP ? -1 : 1; | ||
226 | } else { | ||
227 | diff = dir == MOVE_LEFT || dir == MOVE_UP ? 0 : 1; | ||
209 | } | 228 | } |
210 | else if (direction == MOVE_DOWN){ | 229 | int desired = index_child(child) + diff; |
211 | sway_log(L_INFO, "Moving down not implemented"); | 230 | // Legal position |
231 | // when child == container, desired must be less then parent, | ||
232 | // when child != container, desired can be equal to parent length | ||
233 | if (desired >= 0 && desired - (child != container) < parent->children->length) { | ||
234 | // Case where we descend into a container | ||
235 | if (child == container) { | ||
236 | child = parent->children->items[desired]; | ||
237 | // Move container Into child container. | ||
238 | if (child->type == C_CONTAINER) { | ||
239 | parent = child; | ||
240 | desired = index_child(child->focused); | ||
241 | //reset geometry | ||
242 | container->width = container->height = 0; | ||
243 | } | ||
244 | } | ||
245 | swayc_t *old_parent = remove_child(container); | ||
246 | insert_child(parent, container, desired); | ||
247 | destroy_container(old_parent); | ||
248 | sway_log(L_DEBUG,"Moving to %p %d",parent, desired); | ||
249 | break; | ||
212 | } | 250 | } |
213 | |||
214 | break; | ||
215 | } | 251 | } |
216 | else if (child->children != NULL){ | 252 | child = parent; |
217 | move_container(container,child,direction); | 253 | parent = child->parent; |
254 | if (!parent || child->type == C_WORKSPACE) { | ||
255 | sway_log(L_DEBUG, "Failed to move container"); | ||
256 | return; | ||
218 | } | 257 | } |
219 | } | 258 | } |
220 | 259 | arrange_windows(parent->parent, -1, -1); | |
260 | update_visibility(parent->parent); | ||
261 | set_focused_container_for(parent->parent, container); | ||
221 | } | 262 | } |
222 | 263 | ||
223 | void move_container_to(swayc_t* container, swayc_t* destination) { | 264 | void move_container_to(swayc_t* container, swayc_t* destination) { |
@@ -469,7 +510,8 @@ swayc_t *get_swayc_in_direction_under(swayc_t *container, enum movement_directio | |||
469 | can_move = true; | 510 | can_move = true; |
470 | diff = target - self; | 511 | diff = target - self; |
471 | } | 512 | } |
472 | } else { | 513 | } |
514 | else { | ||
473 | if (dir == MOVE_LEFT || dir == MOVE_RIGHT) { | 515 | if (dir == MOVE_LEFT || dir == MOVE_RIGHT) { |
474 | if (parent->layout == L_HORIZ) { | 516 | if (parent->layout == L_HORIZ) { |
475 | can_move = true; | 517 | can_move = true; |
@@ -484,13 +526,7 @@ swayc_t *get_swayc_in_direction_under(swayc_t *container, enum movement_directio | |||
484 | } | 526 | } |
485 | 527 | ||
486 | if (can_move) { | 528 | if (can_move) { |
487 | for (i = 0; i < parent->children->length; ++i) { | 529 | int desired = index_child(container) + diff; |
488 | swayc_t *child = parent->children->items[i]; | ||
489 | if (child == container) { | ||
490 | break; | ||
491 | } | ||
492 | } | ||
493 | int desired = i + diff; | ||
494 | if (desired < 0 || desired >= parent->children->length) { | 530 | if (desired < 0 || desired >= parent->children->length) { |
495 | can_move = false; | 531 | can_move = false; |
496 | } else { | 532 | } else { |