diff options
-rw-r--r-- | include/config.h | 13 | ||||
-rw-r--r-- | sway/commands.c | 42 | ||||
-rw-r--r-- | sway/config.c | 27 |
3 files changed, 81 insertions, 1 deletions
diff --git a/include/config.h b/include/config.h index a8370532..0fc8202c 100644 --- a/include/config.h +++ b/include/config.h | |||
@@ -27,6 +27,14 @@ struct sway_binding { | |||
27 | }; | 27 | }; |
28 | 28 | ||
29 | /** | 29 | /** |
30 | * A mouse binding and an associated command. | ||
31 | */ | ||
32 | struct sway_mouse_binding { | ||
33 | uint32_t button; | ||
34 | char *command; | ||
35 | }; | ||
36 | |||
37 | /** | ||
30 | * A "mode" of keybindings created via the `mode` command. | 38 | * A "mode" of keybindings created via the `mode` command. |
31 | */ | 39 | */ |
32 | struct sway_mode { | 40 | struct sway_mode { |
@@ -81,6 +89,7 @@ struct bar_config { | |||
81 | char *id; | 89 | char *id; |
82 | uint32_t modifier; | 90 | uint32_t modifier; |
83 | enum desktop_shell_panel_position position; | 91 | enum desktop_shell_panel_position position; |
92 | list_t *bindings; | ||
84 | char *status_command; | 93 | char *status_command; |
85 | char *font; | 94 | char *font; |
86 | int bar_height; | 95 | int bar_height; |
@@ -163,6 +172,10 @@ int sway_binding_cmp(const void *a, const void *b); | |||
163 | int sway_binding_cmp_keys(const void *a, const void *b); | 172 | int sway_binding_cmp_keys(const void *a, const void *b); |
164 | void free_sway_binding(struct sway_binding *sb); | 173 | void free_sway_binding(struct sway_binding *sb); |
165 | 174 | ||
175 | int sway_mouse_binding_cmp(const void *a, const void *b); | ||
176 | int sway_mouse_binding_cmp_buttons(const void *a, const void *b); | ||
177 | void free_sway_mouse_binding(struct sway_mouse_binding *smb); | ||
178 | |||
166 | /** | 179 | /** |
167 | * Global config singleton. | 180 | * Global config singleton. |
168 | */ | 181 | */ |
diff --git a/sway/commands.c b/sway/commands.c index aa4cb89e..053f40fc 100644 --- a/sway/commands.c +++ b/sway/commands.c | |||
@@ -65,6 +65,7 @@ static sway_cmd cmd_sticky; | |||
65 | static sway_cmd cmd_workspace; | 65 | static sway_cmd cmd_workspace; |
66 | static sway_cmd cmd_ws_auto_back_and_forth; | 66 | static sway_cmd cmd_ws_auto_back_and_forth; |
67 | 67 | ||
68 | static sway_cmd bar_cmd_bindsym; | ||
68 | static sway_cmd bar_cmd_mode; | 69 | static sway_cmd bar_cmd_mode; |
69 | static sway_cmd bar_cmd_hidden_state; | 70 | static sway_cmd bar_cmd_hidden_state; |
70 | static sway_cmd bar_cmd_id; | 71 | static sway_cmd bar_cmd_id; |
@@ -1132,6 +1133,7 @@ static struct cmd_results *cmd_bar(int argc, char **argv) { | |||
1132 | bar->hidden_state = strdup(config->bar.hidden_state); | 1133 | bar->hidden_state = strdup(config->bar.hidden_state); |
1133 | bar->modifier = config->bar.modifier; | 1134 | bar->modifier = config->bar.modifier; |
1134 | bar->position = config->bar.position; | 1135 | bar->position = config->bar.position; |
1136 | bar->bindings = create_list(); | ||
1135 | bar->status_command = strdup(config->bar.status_command); | 1137 | bar->status_command = strdup(config->bar.status_command); |
1136 | bar->font = strdup(config->bar.font); | 1138 | bar->font = strdup(config->bar.font); |
1137 | bar->bar_height = config->bar.bar_height; | 1139 | bar->bar_height = config->bar.bar_height; |
@@ -1539,6 +1541,44 @@ static struct cmd_handler handlers[] = { | |||
1539 | { "workspace_auto_back_and_forth", cmd_ws_auto_back_and_forth }, | 1541 | { "workspace_auto_back_and_forth", cmd_ws_auto_back_and_forth }, |
1540 | }; | 1542 | }; |
1541 | 1543 | ||
1544 | static struct cmd_results *bar_cmd_bindsym(int argc, char **argv) { | ||
1545 | struct cmd_results *error = NULL; | ||
1546 | if ((error = checkarg(argc, "bindsym", EXPECTED_MORE_THAN, 1))) { | ||
1547 | return error; | ||
1548 | } else if (!config->reading) { | ||
1549 | return cmd_results_new(CMD_FAILURE, "bindsym", "Can only be used in config file."); | ||
1550 | } | ||
1551 | |||
1552 | if (!config->current_bar) { | ||
1553 | return cmd_results_new(CMD_FAILURE, "bindsym", "No bar defined."); | ||
1554 | } | ||
1555 | |||
1556 | if (strlen(argv[1]) != 7) { | ||
1557 | return cmd_results_new(CMD_INVALID, "bindsym", "Invalid mouse binding %s", argv[1]); | ||
1558 | } | ||
1559 | uint32_t numbutton = (uint32_t)atoi(argv[1] + 6); | ||
1560 | if (numbutton < 1 || numbutton > 5 || strncmp(argv[1], "button", 6) != 0) { | ||
1561 | return cmd_results_new(CMD_INVALID, "bindsym", "Invalid mouse binding %s", argv[1]); | ||
1562 | } | ||
1563 | struct sway_mouse_binding *binding = malloc(sizeof(struct sway_mouse_binding)); | ||
1564 | binding->button = numbutton; | ||
1565 | binding->command = join_args(argv + 1, argc - 1); | ||
1566 | |||
1567 | struct bar_config *bar = config->current_bar; | ||
1568 | int i = list_seq_find(bar->bindings, sway_mouse_binding_cmp_buttons, binding); | ||
1569 | if (i > -1) { | ||
1570 | sway_log(L_DEBUG, "bindsym - '%s' for swaybar already exists, overwriting", argv[0]); | ||
1571 | struct sway_mouse_binding *dup = bar->bindings->items[i]; | ||
1572 | free_sway_mouse_binding(dup); | ||
1573 | list_del(bar->bindings, i); | ||
1574 | } | ||
1575 | list_add(bar->bindings, binding); | ||
1576 | list_sort(bar->bindings, sway_mouse_binding_cmp); | ||
1577 | |||
1578 | sway_log(L_DEBUG, "bindsym - Bound %s to command %s when clicking swaybar", argv[0], binding->command); | ||
1579 | return cmd_results_new(CMD_SUCCESS, NULL, NULL); | ||
1580 | } | ||
1581 | |||
1542 | static struct cmd_results *bar_cmd_hidden_state(int argc, char **argv) { | 1582 | static struct cmd_results *bar_cmd_hidden_state(int argc, char **argv) { |
1543 | struct cmd_results *error = NULL; | 1583 | struct cmd_results *error = NULL; |
1544 | if ((error = checkarg(argc, "hidden_state", EXPECTED_EQUAL_TO, 1))) { | 1584 | if ((error = checkarg(argc, "hidden_state", EXPECTED_EQUAL_TO, 1))) { |
@@ -1723,7 +1763,7 @@ static struct cmd_results *bar_cmd_workspace_buttons(int argc, char **argv) { | |||
1723 | 1763 | ||
1724 | static struct cmd_handler bar_handlers[] = { | 1764 | static struct cmd_handler bar_handlers[] = { |
1725 | { "binding_mode_indicator", NULL }, | 1765 | { "binding_mode_indicator", NULL }, |
1726 | { "bindsym", NULL }, | 1766 | { "bindsym", bar_cmd_bindsym }, |
1727 | { "colors", NULL }, | 1767 | { "colors", NULL }, |
1728 | { "font", NULL }, | 1768 | { "font", NULL }, |
1729 | { "hidden_state", bar_cmd_hidden_state }, | 1769 | { "hidden_state", bar_cmd_hidden_state }, |
diff --git a/sway/config.c b/sway/config.c index 2a1f0310..2c2cc025 100644 --- a/sway/config.c +++ b/sway/config.c | |||
@@ -519,3 +519,30 @@ void free_sway_binding(struct sway_binding *binding) { | |||
519 | } | 519 | } |
520 | free(binding); | 520 | free(binding); |
521 | } | 521 | } |
522 | |||
523 | int sway_mouse_binding_cmp_buttons(const void *a, const void *b) { | ||
524 | const struct sway_mouse_binding *binda = a, *bindb = b; | ||
525 | if (binda->button > bindb->button) { | ||
526 | return 1; | ||
527 | } | ||
528 | if (binda->button < bindb->button) { | ||
529 | return -1; | ||
530 | } | ||
531 | return 0; | ||
532 | } | ||
533 | |||
534 | int sway_mouse_binding_cmp(const void *a, const void *b) { | ||
535 | int cmp = 0; | ||
536 | if ((cmp = sway_binding_cmp_keys(a, b)) != 0) { | ||
537 | return cmp; | ||
538 | } | ||
539 | const struct sway_mouse_binding *binda = a, *bindb = b; | ||
540 | return lenient_strcmp(binda->command, bindb->command); | ||
541 | } | ||
542 | |||
543 | void free_sway_mouse_binding(struct sway_mouse_binding *binding) { | ||
544 | if (binding->command) { | ||
545 | free(binding->command); | ||
546 | } | ||
547 | free(binding); | ||
548 | } | ||