diff options
-rw-r--r-- | include/sway/desktop/transaction.h | 33 | ||||
-rw-r--r-- | include/sway/server.h | 5 | ||||
-rw-r--r-- | include/sway/tree/arrange.h | 22 | ||||
-rw-r--r-- | include/sway/tree/container.h | 10 | ||||
-rw-r--r-- | sway/commands.c | 2 | ||||
-rw-r--r-- | sway/commands/border.c | 2 | ||||
-rw-r--r-- | sway/commands/floating.c | 2 | ||||
-rw-r--r-- | sway/commands/fullscreen.c | 2 | ||||
-rw-r--r-- | sway/commands/gaps.c | 8 | ||||
-rw-r--r-- | sway/commands/layout.c | 2 | ||||
-rw-r--r-- | sway/commands/move.c | 25 | ||||
-rw-r--r-- | sway/commands/reload.c | 2 | ||||
-rw-r--r-- | sway/commands/resize.c | 6 | ||||
-rw-r--r-- | sway/commands/smart_gaps.c | 2 | ||||
-rw-r--r-- | sway/commands/split.c | 2 | ||||
-rw-r--r-- | sway/commands/swap.c | 9 | ||||
-rw-r--r-- | sway/config.c | 2 | ||||
-rw-r--r-- | sway/desktop/layer_shell.c | 3 | ||||
-rw-r--r-- | sway/desktop/output.c | 14 | ||||
-rw-r--r-- | sway/desktop/transaction.c | 35 | ||||
-rw-r--r-- | sway/desktop/xdg_shell.c | 8 | ||||
-rw-r--r-- | sway/desktop/xdg_shell_v6.c | 8 | ||||
-rw-r--r-- | sway/desktop/xwayland.c | 8 | ||||
-rw-r--r-- | sway/server.c | 5 | ||||
-rw-r--r-- | sway/tree/arrange.c | 78 | ||||
-rw-r--r-- | sway/tree/container.c | 24 | ||||
-rw-r--r-- | sway/tree/layout.c | 3 | ||||
-rw-r--r-- | sway/tree/view.c | 5 | ||||
-rw-r--r-- | sway/tree/workspace.c | 2 |
29 files changed, 139 insertions, 190 deletions
diff --git a/include/sway/desktop/transaction.h b/include/sway/desktop/transaction.h index 7ab80eb8..cee4afed 100644 --- a/include/sway/desktop/transaction.h +++ b/include/sway/desktop/transaction.h | |||
@@ -6,34 +6,25 @@ | |||
6 | /** | 6 | /** |
7 | * Transactions enable us to perform atomic layout updates. | 7 | * Transactions enable us to perform atomic layout updates. |
8 | * | 8 | * |
9 | * When we want to make adjustments to the layout, we create a transaction. | 9 | * A transaction contains a list of containers and their new state. |
10 | * A transaction contains a list of affected containers and their new state. | ||
11 | * A state might contain a new size, or new border settings, or new parent/child | 10 | * A state might contain a new size, or new border settings, or new parent/child |
12 | * relationships. | 11 | * relationships. |
13 | * | 12 | * |
14 | * Calling transaction_commit() makes sway notify of all the affected clients | 13 | * Committing a transaction makes sway notify of all the affected clients with |
15 | * with their new sizes. We then wait for all the views to respond with their | 14 | * their new sizes. We then wait for all the views to respond with their new |
16 | * new surface sizes. When all are ready, or when a timeout has passed, we apply | 15 | * surface sizes. When all are ready, or when a timeout has passed, we apply the |
17 | * the updates all at the same time. | 16 | * updates all at the same time. |
18 | */ | 17 | * |
19 | 18 | * When we want to make adjustments to the layout, we change the pending state | |
20 | struct sway_transaction; | 19 | * in containers, mark them as dirty and call transaction_commit_dirty(). This |
21 | 20 | * create and commits a transaction from the dirty containers. | |
22 | /** | ||
23 | * Create a new transaction. | ||
24 | */ | ||
25 | struct sway_transaction *transaction_create(void); | ||
26 | |||
27 | /** | ||
28 | * Add a container's pending state to the transaction. | ||
29 | */ | 21 | */ |
30 | void transaction_add_container(struct sway_transaction *transaction, | ||
31 | struct sway_container *container); | ||
32 | 22 | ||
33 | /** | 23 | /** |
34 | * Submit a transaction to the client views for configuration. | 24 | * Find all dirty containers, create and commit a transaction containing them, |
25 | * and unmark them as dirty. | ||
35 | */ | 26 | */ |
36 | void transaction_commit(struct sway_transaction *transaction); | 27 | void transaction_commit_dirty(void); |
37 | 28 | ||
38 | /** | 29 | /** |
39 | * Notify the transaction system that a view is ready for the new layout. | 30 | * Notify the transaction system that a view is ready for the new layout. |
diff --git a/include/sway/server.h b/include/sway/server.h index a3e32898..a017d1c4 100644 --- a/include/sway/server.h +++ b/include/sway/server.h | |||
@@ -47,10 +47,7 @@ struct sway_server { | |||
47 | bool debug_txn_timings; | 47 | bool debug_txn_timings; |
48 | 48 | ||
49 | list_t *transactions; | 49 | list_t *transactions; |
50 | 50 | list_t *dirty_containers; | |
51 | // When a view is being destroyed and is waiting for a transaction to | ||
52 | // complete it will be stored here. | ||
53 | list_t *destroying_containers; | ||
54 | }; | 51 | }; |
55 | 52 | ||
56 | struct sway_server server; | 53 | struct sway_server server; |
diff --git a/include/sway/tree/arrange.h b/include/sway/tree/arrange.h index 58235642..d6abcc81 100644 --- a/include/sway/tree/arrange.h +++ b/include/sway/tree/arrange.h | |||
@@ -11,26 +11,8 @@ void remove_gaps(struct sway_container *c); | |||
11 | void add_gaps(struct sway_container *c); | 11 | void add_gaps(struct sway_container *c); |
12 | 12 | ||
13 | /** | 13 | /** |
14 | * Arrange layout for all the children of the given container, and add them to | 14 | * Arrange layout for all the children of the given container. |
15 | * the given transaction. | ||
16 | * | ||
17 | * Use this function if you need to arrange multiple sections of the tree in one | ||
18 | * transaction. | ||
19 | * | ||
20 | * You must set the desired state of the container before calling | ||
21 | * arrange_windows, then don't change any state-tracked properties in the | ||
22 | * container until you've called transaction_commit. | ||
23 | */ | 15 | */ |
24 | void arrange_windows(struct sway_container *container, | 16 | void arrange_windows(struct sway_container *container); |
25 | struct sway_transaction *transaction); | ||
26 | |||
27 | /** | ||
28 | * Arrange layout for the given container and commit the transaction. | ||
29 | * | ||
30 | * This function is a wrapper around arrange_windows, and handles creating and | ||
31 | * committing the transaction for you. Use this function if you're only doing | ||
32 | * one arrange operation. | ||
33 | */ | ||
34 | void arrange_and_commit(struct sway_container *container); | ||
35 | 17 | ||
36 | #endif | 18 | #endif |
diff --git a/include/sway/tree/container.h b/include/sway/tree/container.h index a69da9db..11780916 100644 --- a/include/sway/tree/container.h +++ b/include/sway/tree/container.h | |||
@@ -144,6 +144,10 @@ struct sway_container { | |||
144 | 144 | ||
145 | bool destroying; | 145 | bool destroying; |
146 | 146 | ||
147 | // If true, indicates that the container has pending state that differs from | ||
148 | // the current. | ||
149 | bool dirty; | ||
150 | |||
147 | struct { | 151 | struct { |
148 | struct wl_signal destroy; | 152 | struct wl_signal destroy; |
149 | // Raised after the tree updates, but before arrange_windows | 153 | // Raised after the tree updates, but before arrange_windows |
@@ -303,4 +307,10 @@ void container_get_box(struct sway_container *container, struct wlr_box *box); | |||
303 | void container_floating_move_to(struct sway_container *con, | 307 | void container_floating_move_to(struct sway_container *con, |
304 | double lx, double ly); | 308 | double lx, double ly); |
305 | 309 | ||
310 | /** | ||
311 | * Mark a container as dirty if it isn't already. Dirty containers will be | ||
312 | * included in the next transaction then unmarked as dirty. | ||
313 | */ | ||
314 | void container_set_dirty(struct sway_container *container); | ||
315 | |||
306 | #endif | 316 | #endif |
diff --git a/sway/commands.c b/sway/commands.c index addd64a6..50d949d4 100644 --- a/sway/commands.c +++ b/sway/commands.c | |||
@@ -9,6 +9,7 @@ | |||
9 | #include "sway/commands.h" | 9 | #include "sway/commands.h" |
10 | #include "sway/config.h" | 10 | #include "sway/config.h" |
11 | #include "sway/criteria.h" | 11 | #include "sway/criteria.h" |
12 | #include "sway/desktop/transaction.h" | ||
12 | #include "sway/security.h" | 13 | #include "sway/security.h" |
13 | #include "sway/input/input-manager.h" | 14 | #include "sway/input/input-manager.h" |
14 | #include "sway/input/seat.h" | 15 | #include "sway/input/seat.h" |
@@ -322,6 +323,7 @@ struct cmd_results *execute_command(char *_exec, struct sway_seat *seat) { | |||
322 | cleanup: | 323 | cleanup: |
323 | free(exec); | 324 | free(exec); |
324 | free(views); | 325 | free(views); |
326 | transaction_commit_dirty(); | ||
325 | if (!results) { | 327 | if (!results) { |
326 | results = cmd_results_new(CMD_SUCCESS, NULL, NULL); | 328 | results = cmd_results_new(CMD_SUCCESS, NULL, NULL); |
327 | } | 329 | } |
diff --git a/sway/commands/border.c b/sway/commands/border.c index 6db85395..9c19e20a 100644 --- a/sway/commands/border.c +++ b/sway/commands/border.c | |||
@@ -42,7 +42,7 @@ struct cmd_results *cmd_border(int argc, char **argv) { | |||
42 | container_set_geometry_from_floating_view(view->swayc); | 42 | container_set_geometry_from_floating_view(view->swayc); |
43 | } | 43 | } |
44 | 44 | ||
45 | arrange_and_commit(view->swayc); | 45 | arrange_windows(view->swayc); |
46 | 46 | ||
47 | struct sway_seat *seat = input_manager_current_seat(input_manager); | 47 | struct sway_seat *seat = input_manager_current_seat(input_manager); |
48 | if (seat->cursor) { | 48 | if (seat->cursor) { |
diff --git a/sway/commands/floating.c b/sway/commands/floating.c index e6003521..6ab56c3b 100644 --- a/sway/commands/floating.c +++ b/sway/commands/floating.c | |||
@@ -37,7 +37,7 @@ struct cmd_results *cmd_floating(int argc, char **argv) { | |||
37 | container_set_floating(container, wants_floating); | 37 | container_set_floating(container, wants_floating); |
38 | 38 | ||
39 | struct sway_container *workspace = container_parent(container, C_WORKSPACE); | 39 | struct sway_container *workspace = container_parent(container, C_WORKSPACE); |
40 | arrange_and_commit(workspace); | 40 | arrange_windows(workspace); |
41 | 41 | ||
42 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 42 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
43 | } | 43 | } |
diff --git a/sway/commands/fullscreen.c b/sway/commands/fullscreen.c index 1a4d8b41..0b5beaa2 100644 --- a/sway/commands/fullscreen.c +++ b/sway/commands/fullscreen.c | |||
@@ -34,7 +34,7 @@ struct cmd_results *cmd_fullscreen(int argc, char **argv) { | |||
34 | view_set_fullscreen(view, wants_fullscreen); | 34 | view_set_fullscreen(view, wants_fullscreen); |
35 | 35 | ||
36 | struct sway_container *workspace = container_parent(container, C_WORKSPACE); | 36 | struct sway_container *workspace = container_parent(container, C_WORKSPACE); |
37 | arrange_and_commit(workspace->parent); | 37 | arrange_windows(workspace->parent); |
38 | 38 | ||
39 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 39 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
40 | } | 40 | } |
diff --git a/sway/commands/gaps.c b/sway/commands/gaps.c index 801fb179..3906eb70 100644 --- a/sway/commands/gaps.c +++ b/sway/commands/gaps.c | |||
@@ -43,7 +43,7 @@ struct cmd_results *cmd_gaps(int argc, char **argv) { | |||
43 | return cmd_results_new(CMD_INVALID, "gaps", | 43 | return cmd_results_new(CMD_INVALID, "gaps", |
44 | "gaps edge_gaps on|off|toggle"); | 44 | "gaps edge_gaps on|off|toggle"); |
45 | } | 45 | } |
46 | arrange_and_commit(&root_container); | 46 | arrange_windows(&root_container); |
47 | } else { | 47 | } else { |
48 | int amount_idx = 0; // the current index in argv | 48 | int amount_idx = 0; // the current index in argv |
49 | enum gaps_op op = GAPS_OP_SET; | 49 | enum gaps_op op = GAPS_OP_SET; |
@@ -124,7 +124,7 @@ struct cmd_results *cmd_gaps(int argc, char **argv) { | |||
124 | if (amount_idx == 0) { // gaps <amount> | 124 | if (amount_idx == 0) { // gaps <amount> |
125 | config->gaps_inner = val; | 125 | config->gaps_inner = val; |
126 | config->gaps_outer = val; | 126 | config->gaps_outer = val; |
127 | arrange_and_commit(&root_container); | 127 | arrange_windows(&root_container); |
128 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 128 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
129 | } | 129 | } |
130 | // Other variants. The middle-length variant (gaps inner|outer <amount>) | 130 | // Other variants. The middle-length variant (gaps inner|outer <amount>) |
@@ -155,7 +155,7 @@ struct cmd_results *cmd_gaps(int argc, char **argv) { | |||
155 | } else { | 155 | } else { |
156 | config->gaps_outer = total; | 156 | config->gaps_outer = total; |
157 | } | 157 | } |
158 | arrange_and_commit(&root_container); | 158 | arrange_windows(&root_container); |
159 | } else { | 159 | } else { |
160 | struct sway_container *c = | 160 | struct sway_container *c = |
161 | config->handler_context.current_container; | 161 | config->handler_context.current_container; |
@@ -169,7 +169,7 @@ struct cmd_results *cmd_gaps(int argc, char **argv) { | |||
169 | c->gaps_outer = total; | 169 | c->gaps_outer = total; |
170 | } | 170 | } |
171 | 171 | ||
172 | arrange_and_commit(c->parent ? c->parent : &root_container); | 172 | arrange_windows(c->parent ? c->parent : &root_container); |
173 | } | 173 | } |
174 | } | 174 | } |
175 | 175 | ||
diff --git a/sway/commands/layout.c b/sway/commands/layout.c index 9945fa5c..c446f1f9 100644 --- a/sway/commands/layout.c +++ b/sway/commands/layout.c | |||
@@ -49,7 +49,7 @@ struct cmd_results *cmd_layout(int argc, char **argv) { | |||
49 | } | 49 | } |
50 | 50 | ||
51 | container_notify_subtree_changed(parent); | 51 | container_notify_subtree_changed(parent); |
52 | arrange_and_commit(parent); | 52 | arrange_windows(parent); |
53 | 53 | ||
54 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 54 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
55 | } | 55 | } |
diff --git a/sway/commands/move.c b/sway/commands/move.c index a1c1e018..6ec050a8 100644 --- a/sway/commands/move.c +++ b/sway/commands/move.c | |||
@@ -6,7 +6,6 @@ | |||
6 | #include <wlr/types/wlr_output_layout.h> | 6 | #include <wlr/types/wlr_output_layout.h> |
7 | #include <wlr/util/log.h> | 7 | #include <wlr/util/log.h> |
8 | #include "sway/commands.h" | 8 | #include "sway/commands.h" |
9 | #include "sway/desktop/transaction.h" | ||
10 | #include "sway/input/cursor.h" | 9 | #include "sway/input/cursor.h" |
11 | #include "sway/input/seat.h" | 10 | #include "sway/input/seat.h" |
12 | #include "sway/output.h" | 11 | #include "sway/output.h" |
@@ -105,10 +104,8 @@ static struct cmd_results *cmd_move_container(struct sway_container *current, | |||
105 | // TODO: Ideally we would arrange the surviving parent after reaping, | 104 | // TODO: Ideally we would arrange the surviving parent after reaping, |
106 | // but container_reap_empty does not return it, so we arrange the | 105 | // but container_reap_empty does not return it, so we arrange the |
107 | // workspace instead. | 106 | // workspace instead. |
108 | struct sway_transaction *txn = transaction_create(); | 107 | arrange_windows(old_ws); |
109 | arrange_windows(old_ws, txn); | 108 | arrange_windows(destination->parent); |
110 | arrange_windows(destination->parent, txn); | ||
111 | transaction_commit(txn); | ||
112 | 109 | ||
113 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 110 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
114 | } else if (strcasecmp(argv[1], "to") == 0 | 111 | } else if (strcasecmp(argv[1], "to") == 0 |
@@ -144,10 +141,8 @@ static struct cmd_results *cmd_move_container(struct sway_container *current, | |||
144 | // TODO: Ideally we would arrange the surviving parent after reaping, | 141 | // TODO: Ideally we would arrange the surviving parent after reaping, |
145 | // but container_reap_empty does not return it, so we arrange the | 142 | // but container_reap_empty does not return it, so we arrange the |
146 | // workspace instead. | 143 | // workspace instead. |
147 | struct sway_transaction *txn = transaction_create(); | 144 | arrange_windows(old_ws); |
148 | arrange_windows(old_ws, txn); | 145 | arrange_windows(focus->parent); |
149 | arrange_windows(focus->parent, txn); | ||
150 | transaction_commit(txn); | ||
151 | 146 | ||
152 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 147 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
153 | } | 148 | } |
@@ -177,10 +172,8 @@ static struct cmd_results *cmd_move_workspace(struct sway_container *current, | |||
177 | } | 172 | } |
178 | container_move_to(current, destination); | 173 | container_move_to(current, destination); |
179 | 174 | ||
180 | struct sway_transaction *txn = transaction_create(); | 175 | arrange_windows(source); |
181 | arrange_windows(source, txn); | 176 | arrange_windows(destination); |
182 | arrange_windows(destination, txn); | ||
183 | transaction_commit(txn); | ||
184 | 177 | ||
185 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 178 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
186 | } | 179 | } |
@@ -238,12 +231,10 @@ static struct cmd_results *move_in_direction(struct sway_container *container, | |||
238 | container_move(container, direction, move_amt); | 231 | container_move(container, direction, move_amt); |
239 | struct sway_container *new_ws = container_parent(container, C_WORKSPACE); | 232 | struct sway_container *new_ws = container_parent(container, C_WORKSPACE); |
240 | 233 | ||
241 | struct sway_transaction *txn = transaction_create(); | 234 | arrange_windows(old_ws); |
242 | arrange_windows(old_ws, txn); | ||
243 | if (new_ws != old_ws) { | 235 | if (new_ws != old_ws) { |
244 | arrange_windows(new_ws, txn); | 236 | arrange_windows(new_ws); |
245 | } | 237 | } |
246 | transaction_commit(txn); | ||
247 | 238 | ||
248 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 239 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
249 | } | 240 | } |
diff --git a/sway/commands/reload.c b/sway/commands/reload.c index c6715f9c..cea6a94b 100644 --- a/sway/commands/reload.c +++ b/sway/commands/reload.c | |||
@@ -12,6 +12,6 @@ struct cmd_results *cmd_reload(int argc, char **argv) { | |||
12 | } | 12 | } |
13 | 13 | ||
14 | load_swaybars(); | 14 | load_swaybars(); |
15 | arrange_and_commit(&root_container); | 15 | arrange_windows(&root_container); |
16 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 16 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
17 | } | 17 | } |
diff --git a/sway/commands/resize.c b/sway/commands/resize.c index 2cf811d8..e657864c 100644 --- a/sway/commands/resize.c +++ b/sway/commands/resize.c | |||
@@ -268,7 +268,7 @@ static void resize_tiled(int amount, enum resize_axis axis) { | |||
268 | } | 268 | } |
269 | } | 269 | } |
270 | 270 | ||
271 | arrange_and_commit(parent->parent); | 271 | arrange_windows(parent->parent); |
272 | } | 272 | } |
273 | 273 | ||
274 | /** | 274 | /** |
@@ -338,7 +338,7 @@ static struct cmd_results *resize_adjust_floating(enum resize_axis axis, | |||
338 | view->height += grow_height; | 338 | view->height += grow_height; |
339 | } | 339 | } |
340 | 340 | ||
341 | arrange_and_commit(con); | 341 | arrange_windows(con); |
342 | 342 | ||
343 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 343 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
344 | } | 344 | } |
@@ -410,7 +410,7 @@ static struct cmd_results *resize_set_floating(struct sway_container *con, | |||
410 | view->height += grow_height; | 410 | view->height += grow_height; |
411 | } | 411 | } |
412 | 412 | ||
413 | arrange_and_commit(con); | 413 | arrange_windows(con); |
414 | 414 | ||
415 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 415 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
416 | } | 416 | } |
diff --git a/sway/commands/smart_gaps.c b/sway/commands/smart_gaps.c index f687e78e..7d27e571 100644 --- a/sway/commands/smart_gaps.c +++ b/sway/commands/smart_gaps.c | |||
@@ -23,7 +23,7 @@ struct cmd_results *cmd_smart_gaps(int argc, char **argv) { | |||
23 | "Expected 'smart_gaps <on|off>' "); | 23 | "Expected 'smart_gaps <on|off>' "); |
24 | } | 24 | } |
25 | 25 | ||
26 | arrange_and_commit(&root_container); | 26 | arrange_windows(&root_container); |
27 | 27 | ||
28 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 28 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
29 | } | 29 | } |
diff --git a/sway/commands/split.c b/sway/commands/split.c index c40f4d9f..313799da 100644 --- a/sway/commands/split.c +++ b/sway/commands/split.c | |||
@@ -16,7 +16,7 @@ static struct cmd_results *do_split(int layout) { | |||
16 | } | 16 | } |
17 | struct sway_container *parent = container_split(con, layout); | 17 | struct sway_container *parent = container_split(con, layout); |
18 | container_create_notify(parent); | 18 | container_create_notify(parent); |
19 | arrange_and_commit(parent->parent); | 19 | arrange_windows(parent->parent); |
20 | 20 | ||
21 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 21 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
22 | } | 22 | } |
diff --git a/sway/commands/swap.c b/sway/commands/swap.c index e052058f..2fc88308 100644 --- a/sway/commands/swap.c +++ b/sway/commands/swap.c | |||
@@ -1,7 +1,6 @@ | |||
1 | #include <strings.h> | 1 | #include <strings.h> |
2 | #include <wlr/util/log.h> | 2 | #include <wlr/util/log.h> |
3 | #include "sway/commands.h" | 3 | #include "sway/commands.h" |
4 | #include "sway/desktop/transaction.h" | ||
5 | #include "sway/tree/arrange.h" | 4 | #include "sway/tree/arrange.h" |
6 | #include "sway/tree/layout.h" | 5 | #include "sway/tree/layout.h" |
7 | #include "sway/tree/view.h" | 6 | #include "sway/tree/view.h" |
@@ -79,14 +78,10 @@ struct cmd_results *cmd_swap(int argc, char **argv) { | |||
79 | 78 | ||
80 | container_swap(current, other); | 79 | container_swap(current, other); |
81 | 80 | ||
82 | struct sway_transaction *txn = transaction_create(); | 81 | arrange_windows(current->parent); |
83 | arrange_windows(current->parent, txn); | ||
84 | |||
85 | if (other->parent != current->parent) { | 82 | if (other->parent != current->parent) { |
86 | arrange_windows(other->parent, txn); | 83 | arrange_windows(other->parent); |
87 | } | 84 | } |
88 | 85 | ||
89 | transaction_commit(txn); | ||
90 | |||
91 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | 86 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); |
92 | } | 87 | } |
diff --git a/sway/config.c b/sway/config.c index d2386f46..636f5f57 100644 --- a/sway/config.c +++ b/sway/config.c | |||
@@ -773,6 +773,6 @@ void config_update_font_height(bool recalculate) { | |||
773 | } | 773 | } |
774 | 774 | ||
775 | if (config->font_height != prev_max_height) { | 775 | if (config->font_height != prev_max_height) { |
776 | arrange_and_commit(&root_container); | 776 | arrange_windows(&root_container); |
777 | } | 777 | } |
778 | } | 778 | } |
diff --git a/sway/desktop/layer_shell.c b/sway/desktop/layer_shell.c index 16910c7e..91baa6f8 100644 --- a/sway/desktop/layer_shell.c +++ b/sway/desktop/layer_shell.c | |||
@@ -12,7 +12,6 @@ | |||
12 | #include "sway/layers.h" | 12 | #include "sway/layers.h" |
13 | #include "sway/output.h" | 13 | #include "sway/output.h" |
14 | #include "sway/server.h" | 14 | #include "sway/server.h" |
15 | #include "sway/tree/arrange.h" | ||
16 | #include "sway/tree/layout.h" | 15 | #include "sway/tree/layout.h" |
17 | #include "log.h" | 16 | #include "log.h" |
18 | 17 | ||
@@ -176,7 +175,7 @@ void arrange_layers(struct sway_output *output) { | |||
176 | sizeof(struct wlr_box)) != 0) { | 175 | sizeof(struct wlr_box)) != 0) { |
177 | wlr_log(WLR_DEBUG, "Usable area changed, rearranging output"); | 176 | wlr_log(WLR_DEBUG, "Usable area changed, rearranging output"); |
178 | memcpy(&output->usable_area, &usable_area, sizeof(struct wlr_box)); | 177 | memcpy(&output->usable_area, &usable_area, sizeof(struct wlr_box)); |
179 | arrange_and_commit(output->swayc); | 178 | container_set_dirty(output->swayc); |
180 | } | 179 | } |
181 | 180 | ||
182 | // Arrange non-exlusive surfaces from top->bottom | 181 | // Arrange non-exlusive surfaces from top->bottom |
diff --git a/sway/desktop/output.c b/sway/desktop/output.c index a2720885..a9808406 100644 --- a/sway/desktop/output.c +++ b/sway/desktop/output.c | |||
@@ -492,19 +492,21 @@ static void handle_destroy(struct wl_listener *listener, void *data) { | |||
492 | output->wlr_output->data = NULL; | 492 | output->wlr_output->data = NULL; |
493 | free(output); | 493 | free(output); |
494 | 494 | ||
495 | arrange_and_commit(&root_container); | 495 | arrange_windows(&root_container); |
496 | } | 496 | } |
497 | 497 | ||
498 | static void handle_mode(struct wl_listener *listener, void *data) { | 498 | static void handle_mode(struct wl_listener *listener, void *data) { |
499 | struct sway_output *output = wl_container_of(listener, output, mode); | 499 | struct sway_output *output = wl_container_of(listener, output, mode); |
500 | arrange_layers(output); | 500 | arrange_layers(output); |
501 | arrange_and_commit(output->swayc); | 501 | arrange_windows(output->swayc); |
502 | transaction_commit_dirty(); | ||
502 | } | 503 | } |
503 | 504 | ||
504 | static void handle_transform(struct wl_listener *listener, void *data) { | 505 | static void handle_transform(struct wl_listener *listener, void *data) { |
505 | struct sway_output *output = wl_container_of(listener, output, transform); | 506 | struct sway_output *output = wl_container_of(listener, output, transform); |
506 | arrange_layers(output); | 507 | arrange_layers(output); |
507 | arrange_and_commit(output->swayc); | 508 | arrange_windows(output->swayc); |
509 | transaction_commit_dirty(); | ||
508 | } | 510 | } |
509 | 511 | ||
510 | static void handle_scale_iterator(struct sway_container *view, void *data) { | 512 | static void handle_scale_iterator(struct sway_container *view, void *data) { |
@@ -515,7 +517,8 @@ static void handle_scale(struct wl_listener *listener, void *data) { | |||
515 | struct sway_output *output = wl_container_of(listener, output, scale); | 517 | struct sway_output *output = wl_container_of(listener, output, scale); |
516 | arrange_layers(output); | 518 | arrange_layers(output); |
517 | container_descendants(output->swayc, C_VIEW, handle_scale_iterator, NULL); | 519 | container_descendants(output->swayc, C_VIEW, handle_scale_iterator, NULL); |
518 | arrange_and_commit(output->swayc); | 520 | arrange_windows(output->swayc); |
521 | transaction_commit_dirty(); | ||
519 | } | 522 | } |
520 | 523 | ||
521 | struct sway_output *output_from_wlr_output(struct wlr_output *wlr_output) { | 524 | struct sway_output *output_from_wlr_output(struct wlr_output *wlr_output) { |
@@ -584,5 +587,6 @@ void output_enable(struct sway_output *output) { | |||
584 | output->damage_destroy.notify = damage_handle_destroy; | 587 | output->damage_destroy.notify = damage_handle_destroy; |
585 | 588 | ||
586 | arrange_layers(output); | 589 | arrange_layers(output); |
587 | arrange_and_commit(&root_container); | 590 | arrange_windows(&root_container); |
591 | transaction_commit_dirty(); | ||
588 | } | 592 | } |
diff --git a/sway/desktop/transaction.c b/sway/desktop/transaction.c index 2b3f87c3..d7ef7130 100644 --- a/sway/desktop/transaction.c +++ b/sway/desktop/transaction.c | |||
@@ -47,7 +47,7 @@ struct sway_transaction_instruction { | |||
47 | bool ready; | 47 | bool ready; |
48 | }; | 48 | }; |
49 | 49 | ||
50 | struct sway_transaction *transaction_create() { | 50 | static struct sway_transaction *transaction_create() { |
51 | struct sway_transaction *transaction = | 51 | struct sway_transaction *transaction = |
52 | calloc(1, sizeof(struct sway_transaction)); | 52 | calloc(1, sizeof(struct sway_transaction)); |
53 | transaction->instructions = create_list(); | 53 | transaction->instructions = create_list(); |
@@ -141,23 +141,8 @@ static void copy_pending_state(struct sway_container *container, | |||
141 | } | 141 | } |
142 | } | 142 | } |
143 | 143 | ||
144 | static bool transaction_has_container(struct sway_transaction *transaction, | 144 | static void transaction_add_container(struct sway_transaction *transaction, |
145 | struct sway_container *container) { | 145 | struct sway_container *container) { |
146 | for (int i = 0; i < transaction->instructions->length; ++i) { | ||
147 | struct sway_transaction_instruction *instruction = | ||
148 | transaction->instructions->items[i]; | ||
149 | if (instruction->container == container) { | ||
150 | return true; | ||
151 | } | ||
152 | } | ||
153 | return false; | ||
154 | } | ||
155 | |||
156 | void transaction_add_container(struct sway_transaction *transaction, | ||
157 | struct sway_container *container) { | ||
158 | if (transaction_has_container(transaction, container)) { | ||
159 | return; | ||
160 | } | ||
161 | struct sway_transaction_instruction *instruction = | 146 | struct sway_transaction_instruction *instruction = |
162 | calloc(1, sizeof(struct sway_transaction_instruction)); | 147 | calloc(1, sizeof(struct sway_transaction_instruction)); |
163 | instruction->transaction = transaction; | 148 | instruction->transaction = transaction; |
@@ -285,7 +270,7 @@ static bool should_configure(struct sway_container *con, | |||
285 | return true; | 270 | return true; |
286 | } | 271 | } |
287 | 272 | ||
288 | void transaction_commit(struct sway_transaction *transaction) { | 273 | static void transaction_commit(struct sway_transaction *transaction) { |
289 | wlr_log(WLR_DEBUG, "Transaction %p committing with %i instructions", | 274 | wlr_log(WLR_DEBUG, "Transaction %p committing with %i instructions", |
290 | transaction, transaction->instructions->length); | 275 | transaction, transaction->instructions->length); |
291 | transaction->num_waiting = 0; | 276 | transaction->num_waiting = 0; |
@@ -418,3 +403,17 @@ struct wlr_texture *transaction_get_saved_texture(struct sway_view *view, | |||
418 | *height = instruction->saved_buffer_height; | 403 | *height = instruction->saved_buffer_height; |
419 | return instruction->saved_buffer->texture; | 404 | return instruction->saved_buffer->texture; |
420 | } | 405 | } |
406 | |||
407 | void transaction_commit_dirty() { | ||
408 | if (!server.dirty_containers->length) { | ||
409 | return; | ||
410 | } | ||
411 | struct sway_transaction *transaction = transaction_create(); | ||
412 | for (int i = 0; i < server.dirty_containers->length; ++i) { | ||
413 | struct sway_container *container = server.dirty_containers->items[i]; | ||
414 | transaction_add_container(transaction, container); | ||
415 | container->dirty = false; | ||
416 | } | ||
417 | server.dirty_containers->length = 0; | ||
418 | transaction_commit(transaction); | ||
419 | } | ||
diff --git a/sway/desktop/xdg_shell.c b/sway/desktop/xdg_shell.c index fbeeb2e3..98c16faf 100644 --- a/sway/desktop/xdg_shell.c +++ b/sway/desktop/xdg_shell.c | |||
@@ -244,7 +244,8 @@ static void handle_request_fullscreen(struct wl_listener *listener, void *data) | |||
244 | view_set_fullscreen(view, e->fullscreen); | 244 | view_set_fullscreen(view, e->fullscreen); |
245 | 245 | ||
246 | struct sway_container *output = container_parent(view->swayc, C_OUTPUT); | 246 | struct sway_container *output = container_parent(view->swayc, C_OUTPUT); |
247 | arrange_and_commit(output); | 247 | arrange_windows(output); |
248 | transaction_commit_dirty(); | ||
248 | } | 249 | } |
249 | 250 | ||
250 | static void handle_unmap(struct wl_listener *listener, void *data) { | 251 | static void handle_unmap(struct wl_listener *listener, void *data) { |
@@ -281,10 +282,11 @@ static void handle_map(struct wl_listener *listener, void *data) { | |||
281 | if (xdg_surface->toplevel->client_pending.fullscreen) { | 282 | if (xdg_surface->toplevel->client_pending.fullscreen) { |
282 | view_set_fullscreen(view, true); | 283 | view_set_fullscreen(view, true); |
283 | struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE); | 284 | struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE); |
284 | arrange_and_commit(ws); | 285 | arrange_windows(ws); |
285 | } else { | 286 | } else { |
286 | arrange_and_commit(view->swayc->parent); | 287 | arrange_windows(view->swayc->parent); |
287 | } | 288 | } |
289 | transaction_commit_dirty(); | ||
288 | 290 | ||
289 | xdg_shell_view->commit.notify = handle_commit; | 291 | xdg_shell_view->commit.notify = handle_commit; |
290 | wl_signal_add(&xdg_surface->surface->events.commit, | 292 | wl_signal_add(&xdg_surface->surface->events.commit, |
diff --git a/sway/desktop/xdg_shell_v6.c b/sway/desktop/xdg_shell_v6.c index 88d9bb94..4d76f0a7 100644 --- a/sway/desktop/xdg_shell_v6.c +++ b/sway/desktop/xdg_shell_v6.c | |||
@@ -239,7 +239,8 @@ static void handle_request_fullscreen(struct wl_listener *listener, void *data) | |||
239 | view_set_fullscreen(view, e->fullscreen); | 239 | view_set_fullscreen(view, e->fullscreen); |
240 | 240 | ||
241 | struct sway_container *output = container_parent(view->swayc, C_OUTPUT); | 241 | struct sway_container *output = container_parent(view->swayc, C_OUTPUT); |
242 | arrange_and_commit(output); | 242 | arrange_windows(output); |
243 | transaction_commit_dirty(); | ||
243 | } | 244 | } |
244 | 245 | ||
245 | static void handle_unmap(struct wl_listener *listener, void *data) { | 246 | static void handle_unmap(struct wl_listener *listener, void *data) { |
@@ -276,10 +277,11 @@ static void handle_map(struct wl_listener *listener, void *data) { | |||
276 | if (xdg_surface->toplevel->client_pending.fullscreen) { | 277 | if (xdg_surface->toplevel->client_pending.fullscreen) { |
277 | view_set_fullscreen(view, true); | 278 | view_set_fullscreen(view, true); |
278 | struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE); | 279 | struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE); |
279 | arrange_and_commit(ws); | 280 | arrange_windows(ws); |
280 | } else { | 281 | } else { |
281 | arrange_and_commit(view->swayc->parent); | 282 | arrange_windows(view->swayc->parent); |
282 | } | 283 | } |
284 | transaction_commit_dirty(); | ||
283 | 285 | ||
284 | xdg_shell_v6_view->commit.notify = handle_commit; | 286 | xdg_shell_v6_view->commit.notify = handle_commit; |
285 | wl_signal_add(&xdg_surface->surface->events.commit, | 287 | wl_signal_add(&xdg_surface->surface->events.commit, |
diff --git a/sway/desktop/xwayland.c b/sway/desktop/xwayland.c index 460d1cc8..11516673 100644 --- a/sway/desktop/xwayland.c +++ b/sway/desktop/xwayland.c | |||
@@ -333,10 +333,11 @@ static void handle_map(struct wl_listener *listener, void *data) { | |||
333 | if (xsurface->fullscreen) { | 333 | if (xsurface->fullscreen) { |
334 | view_set_fullscreen(view, true); | 334 | view_set_fullscreen(view, true); |
335 | struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE); | 335 | struct sway_container *ws = container_parent(view->swayc, C_WORKSPACE); |
336 | arrange_and_commit(ws); | 336 | arrange_windows(ws); |
337 | } else { | 337 | } else { |
338 | arrange_and_commit(view->swayc->parent); | 338 | arrange_windows(view->swayc->parent); |
339 | } | 339 | } |
340 | transaction_commit_dirty(); | ||
340 | } | 341 | } |
341 | 342 | ||
342 | static void handle_destroy(struct wl_listener *listener, void *data) { | 343 | static void handle_destroy(struct wl_listener *listener, void *data) { |
@@ -392,7 +393,8 @@ static void handle_request_fullscreen(struct wl_listener *listener, void *data) | |||
392 | view_set_fullscreen(view, xsurface->fullscreen); | 393 | view_set_fullscreen(view, xsurface->fullscreen); |
393 | 394 | ||
394 | struct sway_container *output = container_parent(view->swayc, C_OUTPUT); | 395 | struct sway_container *output = container_parent(view->swayc, C_OUTPUT); |
395 | arrange_and_commit(output); | 396 | arrange_windows(output); |
397 | transaction_commit_dirty(); | ||
396 | } | 398 | } |
397 | 399 | ||
398 | static void handle_set_title(struct wl_listener *listener, void *data) { | 400 | static void handle_set_title(struct wl_listener *listener, void *data) { |
diff --git a/sway/server.c b/sway/server.c index 1d8eb964..8566d512 100644 --- a/sway/server.c +++ b/sway/server.c | |||
@@ -125,8 +125,7 @@ bool server_init(struct sway_server *server) { | |||
125 | if (debug != NULL && strcmp(debug, "txn_timings") == 0) { | 125 | if (debug != NULL && strcmp(debug, "txn_timings") == 0) { |
126 | server->debug_txn_timings = true; | 126 | server->debug_txn_timings = true; |
127 | } | 127 | } |
128 | server->destroying_containers = create_list(); | 128 | server->dirty_containers = create_list(); |
129 | |||
130 | server->transactions = create_list(); | 129 | server->transactions = create_list(); |
131 | 130 | ||
132 | input_manager = input_manager_create(server); | 131 | input_manager = input_manager_create(server); |
@@ -136,7 +135,7 @@ bool server_init(struct sway_server *server) { | |||
136 | void server_fini(struct sway_server *server) { | 135 | void server_fini(struct sway_server *server) { |
137 | // TODO: free sway-specific resources | 136 | // TODO: free sway-specific resources |
138 | wl_display_destroy(server->wl_display); | 137 | wl_display_destroy(server->wl_display); |
139 | list_free(server->destroying_containers); | 138 | list_free(server->dirty_containers); |
140 | list_free(server->transactions); | 139 | list_free(server->transactions); |
141 | } | 140 | } |
142 | 141 | ||
diff --git a/sway/tree/arrange.c b/sway/tree/arrange.c index bcc3ee9a..533cf71c 100644 --- a/sway/tree/arrange.c +++ b/sway/tree/arrange.c | |||
@@ -144,38 +144,22 @@ static void apply_tabbed_or_stacked_layout(struct sway_container *parent) { | |||
144 | } | 144 | } |
145 | } | 145 | } |
146 | 146 | ||
147 | /** | 147 | static void arrange_children_of(struct sway_container *parent); |
148 | * If a container has been deleted from the pending tree state, we must add it | ||
149 | * to the transaction so it can be freed afterwards. To do this, we iterate the | ||
150 | * server's destroying_containers list and add all of them. We may add more than | ||
151 | * what we need to, but this is easy and has no negative consequences. | ||
152 | */ | ||
153 | static void add_deleted_containers(struct sway_transaction *transaction) { | ||
154 | for (int i = 0; i < server.destroying_containers->length; ++i) { | ||
155 | struct sway_container *child = server.destroying_containers->items[i]; | ||
156 | transaction_add_container(transaction, child); | ||
157 | } | ||
158 | } | ||
159 | |||
160 | static void arrange_children_of(struct sway_container *parent, | ||
161 | struct sway_transaction *transaction); | ||
162 | 148 | ||
163 | static void arrange_floating(struct sway_container *floating, | 149 | static void arrange_floating(struct sway_container *floating) { |
164 | struct sway_transaction *transaction) { | ||
165 | for (int i = 0; i < floating->children->length; ++i) { | 150 | for (int i = 0; i < floating->children->length; ++i) { |
166 | struct sway_container *floater = floating->children->items[i]; | 151 | struct sway_container *floater = floating->children->items[i]; |
167 | if (floater->type == C_VIEW) { | 152 | if (floater->type == C_VIEW) { |
168 | view_autoconfigure(floater->sway_view); | 153 | view_autoconfigure(floater->sway_view); |
169 | } else { | 154 | } else { |
170 | arrange_children_of(floater, transaction); | 155 | arrange_children_of(floater); |
171 | } | 156 | } |
172 | transaction_add_container(transaction, floater); | 157 | container_set_dirty(floater); |
173 | } | 158 | } |
174 | transaction_add_container(transaction, floating); | 159 | container_set_dirty(floating); |
175 | } | 160 | } |
176 | 161 | ||
177 | static void arrange_children_of(struct sway_container *parent, | 162 | static void arrange_children_of(struct sway_container *parent) { |
178 | struct sway_transaction *transaction) { | ||
179 | if (config->reloading) { | 163 | if (config->reloading) { |
180 | return; | 164 | return; |
181 | } | 165 | } |
@@ -198,7 +182,7 @@ static void arrange_children_of(struct sway_container *parent, | |||
198 | apply_horiz_layout(parent); | 182 | apply_horiz_layout(parent); |
199 | break; | 183 | break; |
200 | case L_FLOATING: | 184 | case L_FLOATING: |
201 | arrange_floating(parent, transaction); | 185 | arrange_floating(parent); |
202 | break; | 186 | break; |
203 | } | 187 | } |
204 | 188 | ||
@@ -213,14 +197,13 @@ static void arrange_children_of(struct sway_container *parent, | |||
213 | if (child->type == C_VIEW) { | 197 | if (child->type == C_VIEW) { |
214 | view_autoconfigure(child->sway_view); | 198 | view_autoconfigure(child->sway_view); |
215 | } else { | 199 | } else { |
216 | arrange_children_of(child, transaction); | 200 | arrange_children_of(child); |
217 | } | 201 | } |
218 | transaction_add_container(transaction, child); | 202 | container_set_dirty(child); |
219 | } | 203 | } |
220 | } | 204 | } |
221 | 205 | ||
222 | static void arrange_workspace(struct sway_container *workspace, | 206 | static void arrange_workspace(struct sway_container *workspace) { |
223 | struct sway_transaction *transaction) { | ||
224 | if (config->reloading) { | 207 | if (config->reloading) { |
225 | return; | 208 | return; |
226 | } | 209 | } |
@@ -234,15 +217,14 @@ static void arrange_workspace(struct sway_container *workspace, | |||
234 | workspace->x = output->x + area->x; | 217 | workspace->x = output->x + area->x; |
235 | workspace->y = output->y + area->y; | 218 | workspace->y = output->y + area->y; |
236 | add_gaps(workspace); | 219 | add_gaps(workspace); |
237 | transaction_add_container(transaction, workspace); | 220 | container_set_dirty(workspace); |
238 | wlr_log(WLR_DEBUG, "Arranging workspace '%s' at %f, %f", workspace->name, | 221 | wlr_log(WLR_DEBUG, "Arranging workspace '%s' at %f, %f", workspace->name, |
239 | workspace->x, workspace->y); | 222 | workspace->x, workspace->y); |
240 | arrange_floating(workspace->sway_workspace->floating, transaction); | 223 | arrange_floating(workspace->sway_workspace->floating); |
241 | arrange_children_of(workspace, transaction); | 224 | arrange_children_of(workspace); |
242 | } | 225 | } |
243 | 226 | ||
244 | static void arrange_output(struct sway_container *output, | 227 | static void arrange_output(struct sway_container *output) { |
245 | struct sway_transaction *transaction) { | ||
246 | if (config->reloading) { | 228 | if (config->reloading) { |
247 | return; | 229 | return; |
248 | } | 230 | } |
@@ -253,16 +235,16 @@ static void arrange_output(struct sway_container *output, | |||
253 | output->y = output_box->y; | 235 | output->y = output_box->y; |
254 | output->width = output_box->width; | 236 | output->width = output_box->width; |
255 | output->height = output_box->height; | 237 | output->height = output_box->height; |
256 | transaction_add_container(transaction, output); | 238 | container_set_dirty(output); |
257 | wlr_log(WLR_DEBUG, "Arranging output '%s' at %f,%f", | 239 | wlr_log(WLR_DEBUG, "Arranging output '%s' at %f,%f", |
258 | output->name, output->x, output->y); | 240 | output->name, output->x, output->y); |
259 | for (int i = 0; i < output->children->length; ++i) { | 241 | for (int i = 0; i < output->children->length; ++i) { |
260 | struct sway_container *workspace = output->children->items[i]; | 242 | struct sway_container *workspace = output->children->items[i]; |
261 | arrange_workspace(workspace, transaction); | 243 | arrange_workspace(workspace); |
262 | } | 244 | } |
263 | } | 245 | } |
264 | 246 | ||
265 | static void arrange_root(struct sway_transaction *transaction) { | 247 | static void arrange_root() { |
266 | if (config->reloading) { | 248 | if (config->reloading) { |
267 | return; | 249 | return; |
268 | } | 250 | } |
@@ -274,43 +256,35 @@ static void arrange_root(struct sway_transaction *transaction) { | |||
274 | root_container.y = layout_box->y; | 256 | root_container.y = layout_box->y; |
275 | root_container.width = layout_box->width; | 257 | root_container.width = layout_box->width; |
276 | root_container.height = layout_box->height; | 258 | root_container.height = layout_box->height; |
277 | transaction_add_container(transaction, &root_container); | 259 | container_set_dirty(&root_container); |
278 | for (int i = 0; i < root_container.children->length; ++i) { | 260 | for (int i = 0; i < root_container.children->length; ++i) { |
279 | struct sway_container *output = root_container.children->items[i]; | 261 | struct sway_container *output = root_container.children->items[i]; |
280 | arrange_output(output, transaction); | 262 | arrange_output(output); |
281 | } | 263 | } |
282 | } | 264 | } |
283 | 265 | ||
284 | void arrange_windows(struct sway_container *container, | 266 | void arrange_windows(struct sway_container *container) { |
285 | struct sway_transaction *transaction) { | ||
286 | switch (container->type) { | 267 | switch (container->type) { |
287 | case C_ROOT: | 268 | case C_ROOT: |
288 | arrange_root(transaction); | 269 | arrange_root(); |
289 | break; | 270 | break; |
290 | case C_OUTPUT: | 271 | case C_OUTPUT: |
291 | arrange_output(container, transaction); | 272 | arrange_output(container); |
292 | break; | 273 | break; |
293 | case C_WORKSPACE: | 274 | case C_WORKSPACE: |
294 | arrange_workspace(container, transaction); | 275 | arrange_workspace(container); |
295 | break; | 276 | break; |
296 | case C_CONTAINER: | 277 | case C_CONTAINER: |
297 | arrange_children_of(container, transaction); | 278 | arrange_children_of(container); |
298 | transaction_add_container(transaction, container); | 279 | container_set_dirty(container); |
299 | break; | 280 | break; |
300 | case C_VIEW: | 281 | case C_VIEW: |
301 | view_autoconfigure(container->sway_view); | 282 | view_autoconfigure(container->sway_view); |
302 | transaction_add_container(transaction, container); | 283 | container_set_dirty(container); |
303 | break; | 284 | break; |
304 | case C_TYPES: | 285 | case C_TYPES: |
305 | break; | 286 | break; |
306 | } | 287 | } |
307 | add_deleted_containers(transaction); | ||
308 | } | ||
309 | |||
310 | void arrange_and_commit(struct sway_container *container) { | ||
311 | struct sway_transaction *transaction = transaction_create(); | ||
312 | arrange_windows(container, transaction); | ||
313 | transaction_commit(transaction); | ||
314 | } | 288 | } |
315 | 289 | ||
316 | void remove_gaps(struct sway_container *c) { | 290 | void remove_gaps(struct sway_container *c) { |
diff --git a/sway/tree/container.c b/sway/tree/container.c index 58852717..35f67cce 100644 --- a/sway/tree/container.c +++ b/sway/tree/container.c | |||
@@ -159,14 +159,6 @@ void container_free(struct sway_container *cont) { | |||
159 | wlr_texture_destroy(cont->title_focused_inactive); | 159 | wlr_texture_destroy(cont->title_focused_inactive); |
160 | wlr_texture_destroy(cont->title_unfocused); | 160 | wlr_texture_destroy(cont->title_unfocused); |
161 | wlr_texture_destroy(cont->title_urgent); | 161 | wlr_texture_destroy(cont->title_urgent); |
162 | |||
163 | for (int i = 0; i < server.destroying_containers->length; ++i) { | ||
164 | if (server.destroying_containers->items[i] == cont) { | ||
165 | list_del(server.destroying_containers, i); | ||
166 | break; | ||
167 | } | ||
168 | } | ||
169 | |||
170 | list_free(cont->instructions); | 162 | list_free(cont->instructions); |
171 | list_free(cont->children); | 163 | list_free(cont->children); |
172 | list_free(cont->current.children); | 164 | list_free(cont->current.children); |
@@ -325,7 +317,7 @@ static struct sway_container *container_destroy_noreaping( | |||
325 | } | 317 | } |
326 | 318 | ||
327 | con->destroying = true; | 319 | con->destroying = true; |
328 | list_add(server.destroying_containers, con); | 320 | container_set_dirty(con); |
329 | 321 | ||
330 | if (!con->parent) { | 322 | if (!con->parent) { |
331 | return NULL; | 323 | return NULL; |
@@ -1069,9 +1061,15 @@ void container_floating_move_to(struct sway_container *con, | |||
1069 | if (old_workspace != new_workspace) { | 1061 | if (old_workspace != new_workspace) { |
1070 | container_remove_child(con); | 1062 | container_remove_child(con); |
1071 | container_add_child(new_workspace->sway_workspace->floating, con); | 1063 | container_add_child(new_workspace->sway_workspace->floating, con); |
1072 | struct sway_transaction *transaction = transaction_create(); | 1064 | arrange_windows(old_workspace); |
1073 | arrange_windows(old_workspace, transaction); | 1065 | arrange_windows(new_workspace); |
1074 | arrange_windows(new_workspace, transaction); | 1066 | } |
1075 | transaction_commit(transaction); | 1067 | } |
1068 | |||
1069 | void container_set_dirty(struct sway_container *container) { | ||
1070 | if (container->dirty) { | ||
1071 | return; | ||
1076 | } | 1072 | } |
1073 | container->dirty = true; | ||
1074 | list_add(server.dirty_containers, container); | ||
1077 | } | 1075 | } |
diff --git a/sway/tree/layout.c b/sway/tree/layout.c index ba234e89..54ddb3f9 100644 --- a/sway/tree/layout.c +++ b/sway/tree/layout.c | |||
@@ -22,7 +22,8 @@ struct sway_container root_container; | |||
22 | 22 | ||
23 | static void output_layout_handle_change(struct wl_listener *listener, | 23 | static void output_layout_handle_change(struct wl_listener *listener, |
24 | void *data) { | 24 | void *data) { |
25 | arrange_and_commit(&root_container); | 25 | arrange_windows(&root_container); |
26 | transaction_commit_dirty(); | ||
26 | } | 27 | } |
27 | 28 | ||
28 | void layout_init(void) { | 29 | void layout_init(void) { |
diff --git a/sway/tree/view.c b/sway/tree/view.c index b356183c..bf380d98 100644 --- a/sway/tree/view.c +++ b/sway/tree/view.c | |||
@@ -594,11 +594,12 @@ void view_unmap(struct sway_view *view) { | |||
594 | ws->sway_workspace->fullscreen = NULL; | 594 | ws->sway_workspace->fullscreen = NULL; |
595 | container_destroy(view->swayc); | 595 | container_destroy(view->swayc); |
596 | 596 | ||
597 | arrange_and_commit(ws->parent); | 597 | arrange_windows(ws->parent); |
598 | } else { | 598 | } else { |
599 | struct sway_container *parent = container_destroy(view->swayc); | 599 | struct sway_container *parent = container_destroy(view->swayc); |
600 | arrange_and_commit(parent); | 600 | arrange_windows(parent); |
601 | } | 601 | } |
602 | transaction_commit_dirty(); | ||
602 | view->surface = NULL; | 603 | view->surface = NULL; |
603 | } | 604 | } |
604 | 605 | ||
diff --git a/sway/tree/workspace.c b/sway/tree/workspace.c index 50f9400a..2a2d834a 100644 --- a/sway/tree/workspace.c +++ b/sway/tree/workspace.c | |||
@@ -427,7 +427,7 @@ bool workspace_switch(struct sway_container *workspace) { | |||
427 | } | 427 | } |
428 | seat_set_focus(seat, next); | 428 | seat_set_focus(seat, next); |
429 | struct sway_container *output = container_parent(workspace, C_OUTPUT); | 429 | struct sway_container *output = container_parent(workspace, C_OUTPUT); |
430 | arrange_and_commit(output); | 430 | arrange_windows(output); |
431 | return true; | 431 | return true; |
432 | } | 432 | } |
433 | 433 | ||