diff options
author | Drew DeVault <sir@cmpwn.com> | 2018-09-22 19:51:02 -0500 |
---|---|---|
committer | GitHub <noreply@github.com> | 2018-09-22 19:51:02 -0500 |
commit | 68395f34f686aa1901077505405775ba5bafe6ee (patch) | |
tree | 0c3a2cff652b212830efb9d674c1b8d6d305bcac | |
parent | Merge pull request #2690 from ianyfan/commands (diff) | |
parent | Allow running commands on containers without focusing them (diff) | |
download | sway-68395f34f686aa1901077505405775ba5bafe6ee.tar.gz sway-68395f34f686aa1901077505405775ba5bafe6ee.tar.zst sway-68395f34f686aa1901077505405775ba5bafe6ee.zip |
Merge pull request #2688 from RyanDwyer/exec-commands-without-focus
Allow running commands on containers without focusing them
-rw-r--r-- | include/sway/commands.h | 9 | ||||
-rw-r--r-- | sway/commands.c | 16 | ||||
-rw-r--r-- | sway/commands/bind.c | 2 | ||||
-rw-r--r-- | sway/desktop/xdg_shell.c | 2 | ||||
-rw-r--r-- | sway/desktop/xdg_shell_v6.c | 2 | ||||
-rw-r--r-- | sway/desktop/xwayland.c | 2 | ||||
-rw-r--r-- | sway/ipc-server.c | 2 | ||||
-rw-r--r-- | sway/main.c | 2 | ||||
-rw-r--r-- | sway/tree/view.c | 10 |
9 files changed, 28 insertions, 19 deletions
diff --git a/include/sway/commands.h b/include/sway/commands.h index 226cf932..1654eb48 100644 --- a/include/sway/commands.h +++ b/include/sway/commands.h | |||
@@ -4,6 +4,8 @@ | |||
4 | #include <wlr/util/edges.h> | 4 | #include <wlr/util/edges.h> |
5 | #include "config.h" | 5 | #include "config.h" |
6 | 6 | ||
7 | struct sway_container; | ||
8 | |||
7 | typedef struct cmd_results *sway_cmd(int argc, char **argv); | 9 | typedef struct cmd_results *sway_cmd(int argc, char **argv); |
8 | 10 | ||
9 | struct cmd_handler { | 11 | struct cmd_handler { |
@@ -50,8 +52,13 @@ struct cmd_handler *find_handler(char *line, struct cmd_handler *cmd_handlers, | |||
50 | int handlers_size); | 52 | int handlers_size); |
51 | /** | 53 | /** |
52 | * Parse and executes a command. | 54 | * Parse and executes a command. |
55 | * | ||
56 | * If the command string contains criteria then the command will be executed on | ||
57 | * all matching containers. Otherwise, it'll run on the `con` container. If | ||
58 | * `con` is NULL then it'll run on the currently focused container. | ||
53 | */ | 59 | */ |
54 | struct cmd_results *execute_command(char *command, struct sway_seat *seat); | 60 | struct cmd_results *execute_command(char *command, struct sway_seat *seat, |
61 | struct sway_container *con); | ||
55 | /** | 62 | /** |
56 | * Parse and handles a command during config file loading. | 63 | * Parse and handles a command during config file loading. |
57 | * | 64 | * |
diff --git a/sway/commands.c b/sway/commands.c index 07169f1e..5b61f73a 100644 --- a/sway/commands.c +++ b/sway/commands.c | |||
@@ -237,7 +237,8 @@ static void set_config_node(struct sway_node *node) { | |||
237 | } | 237 | } |
238 | } | 238 | } |
239 | 239 | ||
240 | struct cmd_results *execute_command(char *_exec, struct sway_seat *seat) { | 240 | struct cmd_results *execute_command(char *_exec, struct sway_seat *seat, |
241 | struct sway_container *con) { | ||
241 | // Even though this function will process multiple commands we will only | 242 | // Even though this function will process multiple commands we will only |
242 | // return the last error, if any (for now). (Since we have access to an | 243 | // return the last error, if any (for now). (Since we have access to an |
243 | // error string we could e.g. concatenate all errors there.) | 244 | // error string we could e.g. concatenate all errors there.) |
@@ -256,6 +257,15 @@ struct cmd_results *execute_command(char *_exec, struct sway_seat *seat) { | |||
256 | } | 257 | } |
257 | } | 258 | } |
258 | 259 | ||
260 | // This is the container or workspace which this command will run on. | ||
261 | // Ignored if the command string contains criteria. | ||
262 | struct sway_node *node; | ||
263 | if (con) { | ||
264 | node = &con->node; | ||
265 | } else { | ||
266 | node = seat_get_focus_inactive(seat, &root->node); | ||
267 | } | ||
268 | |||
259 | config->handler_context.seat = seat; | 269 | config->handler_context.seat = seat; |
260 | 270 | ||
261 | head = exec; | 271 | head = exec; |
@@ -318,9 +328,7 @@ struct cmd_results *execute_command(char *_exec, struct sway_seat *seat) { | |||
318 | } | 328 | } |
319 | 329 | ||
320 | if (!config->handler_context.using_criteria) { | 330 | if (!config->handler_context.using_criteria) { |
321 | // without criteria, the command acts upon the focused | 331 | set_config_node(node); |
322 | // container | ||
323 | set_config_node(seat_get_focus_inactive(seat, &root->node)); | ||
324 | struct cmd_results *res = handler->handle(argc-1, argv+1); | 332 | struct cmd_results *res = handler->handle(argc-1, argv+1); |
325 | if (res->status != CMD_SUCCESS) { | 333 | if (res->status != CMD_SUCCESS) { |
326 | free_argv(argc, argv); | 334 | free_argv(argc, argv); |
diff --git a/sway/commands/bind.c b/sway/commands/bind.c index 047018e0..820c2a6a 100644 --- a/sway/commands/bind.c +++ b/sway/commands/bind.c | |||
@@ -321,7 +321,7 @@ void seat_execute_command(struct sway_seat *seat, struct sway_binding *binding) | |||
321 | } | 321 | } |
322 | 322 | ||
323 | config->handler_context.seat = seat; | 323 | config->handler_context.seat = seat; |
324 | struct cmd_results *results = execute_command(binding->command, NULL); | 324 | struct cmd_results *results = execute_command(binding->command, NULL, NULL); |
325 | if (results->status == CMD_SUCCESS) { | 325 | if (results->status == CMD_SUCCESS) { |
326 | ipc_event_binding(binding_copy); | 326 | ipc_event_binding(binding_copy); |
327 | } else { | 327 | } else { |
diff --git a/sway/desktop/xdg_shell.c b/sway/desktop/xdg_shell.c index 00448be7..6d1ccdd7 100644 --- a/sway/desktop/xdg_shell.c +++ b/sway/desktop/xdg_shell.c | |||
@@ -401,7 +401,7 @@ static void handle_map(struct wl_listener *listener, void *data) { | |||
401 | } else { | 401 | } else { |
402 | if (view->container->parent) { | 402 | if (view->container->parent) { |
403 | arrange_container(view->container->parent); | 403 | arrange_container(view->container->parent); |
404 | } else { | 404 | } else if (view->container->workspace) { |
405 | arrange_workspace(view->container->workspace); | 405 | arrange_workspace(view->container->workspace); |
406 | } | 406 | } |
407 | } | 407 | } |
diff --git a/sway/desktop/xdg_shell_v6.c b/sway/desktop/xdg_shell_v6.c index d2c9a68b..95ca396c 100644 --- a/sway/desktop/xdg_shell_v6.c +++ b/sway/desktop/xdg_shell_v6.c | |||
@@ -398,7 +398,7 @@ static void handle_map(struct wl_listener *listener, void *data) { | |||
398 | } else { | 398 | } else { |
399 | if (view->container->parent) { | 399 | if (view->container->parent) { |
400 | arrange_container(view->container->parent); | 400 | arrange_container(view->container->parent); |
401 | } else { | 401 | } else if (view->container->workspace) { |
402 | arrange_workspace(view->container->workspace); | 402 | arrange_workspace(view->container->workspace); |
403 | } | 403 | } |
404 | } | 404 | } |
diff --git a/sway/desktop/xwayland.c b/sway/desktop/xwayland.c index 3619f202..a12ac854 100644 --- a/sway/desktop/xwayland.c +++ b/sway/desktop/xwayland.c | |||
@@ -394,7 +394,7 @@ static void handle_map(struct wl_listener *listener, void *data) { | |||
394 | } else { | 394 | } else { |
395 | if (view->container->parent) { | 395 | if (view->container->parent) { |
396 | arrange_container(view->container->parent); | 396 | arrange_container(view->container->parent); |
397 | } else { | 397 | } else if (view->container->workspace) { |
398 | arrange_workspace(view->container->workspace); | 398 | arrange_workspace(view->container->workspace); |
399 | } | 399 | } |
400 | } | 400 | } |
diff --git a/sway/ipc-server.c b/sway/ipc-server.c index 8ae265f6..99959c97 100644 --- a/sway/ipc-server.c +++ b/sway/ipc-server.c | |||
@@ -580,7 +580,7 @@ void ipc_client_handle_command(struct ipc_client *client) { | |||
580 | switch (client->current_command) { | 580 | switch (client->current_command) { |
581 | case IPC_COMMAND: | 581 | case IPC_COMMAND: |
582 | { | 582 | { |
583 | struct cmd_results *results = execute_command(buf, NULL); | 583 | struct cmd_results *results = execute_command(buf, NULL, NULL); |
584 | transaction_commit_dirty(); | 584 | transaction_commit_dirty(); |
585 | char *json = cmd_results_to_json(results); | 585 | char *json = cmd_results_to_json(results); |
586 | int length = strlen(json); | 586 | int length = strlen(json); |
diff --git a/sway/main.c b/sway/main.c index 3d7cd158..990f5f3a 100644 --- a/sway/main.c +++ b/sway/main.c | |||
@@ -429,7 +429,7 @@ int main(int argc, char **argv) { | |||
429 | wlr_log(WLR_DEBUG, "Running deferred commands"); | 429 | wlr_log(WLR_DEBUG, "Running deferred commands"); |
430 | while (config->cmd_queue->length) { | 430 | while (config->cmd_queue->length) { |
431 | char *line = config->cmd_queue->items[0]; | 431 | char *line = config->cmd_queue->items[0]; |
432 | struct cmd_results *res = execute_command(line, NULL); | 432 | struct cmd_results *res = execute_command(line, NULL, NULL); |
433 | if (res->status != CMD_SUCCESS) { | 433 | if (res->status != CMD_SUCCESS) { |
434 | wlr_log(WLR_ERROR, "Error on line '%s': %s", line, res->error); | 434 | wlr_log(WLR_ERROR, "Error on line '%s': %s", line, res->error); |
435 | } | 435 | } |
diff --git a/sway/tree/view.c b/sway/tree/view.c index f61f5c84..e370443c 100644 --- a/sway/tree/view.c +++ b/sway/tree/view.c | |||
@@ -391,8 +391,6 @@ static bool view_has_executed_criteria(struct sway_view *view, | |||
391 | } | 391 | } |
392 | 392 | ||
393 | void view_execute_criteria(struct sway_view *view) { | 393 | void view_execute_criteria(struct sway_view *view) { |
394 | struct sway_seat *seat = input_manager_current_seat(input_manager); | ||
395 | struct sway_node *prior_focus = seat_get_focus(seat); | ||
396 | list_t *criterias = criteria_for_view(view, CT_COMMAND); | 394 | list_t *criterias = criteria_for_view(view, CT_COMMAND); |
397 | for (int i = 0; i < criterias->length; i++) { | 395 | for (int i = 0; i < criterias->length; i++) { |
398 | struct criteria *criteria = criterias->items[i]; | 396 | struct criteria *criteria = criterias->items[i]; |
@@ -403,16 +401,12 @@ void view_execute_criteria(struct sway_view *view) { | |||
403 | } | 401 | } |
404 | wlr_log(WLR_DEBUG, "for_window '%s' matches view %p, cmd: '%s'", | 402 | wlr_log(WLR_DEBUG, "for_window '%s' matches view %p, cmd: '%s'", |
405 | criteria->raw, view, criteria->cmdlist); | 403 | criteria->raw, view, criteria->cmdlist); |
406 | seat_set_focus_container(seat, view->container); | ||
407 | list_add(view->executed_criteria, criteria); | 404 | list_add(view->executed_criteria, criteria); |
408 | struct cmd_results *res = execute_command(criteria->cmdlist, NULL); | 405 | struct cmd_results *res = execute_command( |
409 | if (res->status != CMD_SUCCESS) { | 406 | criteria->cmdlist, NULL, view->container); |
410 | wlr_log(WLR_ERROR, "Command '%s' failed: %s", res->input, res->error); | ||
411 | } | ||
412 | free_cmd_results(res); | 407 | free_cmd_results(res); |
413 | } | 408 | } |
414 | list_free(criterias); | 409 | list_free(criterias); |
415 | seat_set_focus(seat, prior_focus); | ||
416 | } | 410 | } |
417 | 411 | ||
418 | static struct sway_workspace *select_workspace(struct sway_view *view) { | 412 | static struct sway_workspace *select_workspace(struct sway_view *view) { |