diff --git a/sway/commands.c b/sway/commands.c index cb24f796..3f286c3c 100644 --- a/sway/commands.c +++ b/sway/commands.c @@ -1,3 +1,5 @@ +#include +#include #include #include #include @@ -20,17 +22,40 @@ int cmd_set(struct sway_config *config, int argc, char **argv) { } int cmd_bindsym(struct sway_config *config, int argc, char **argv) { - if (argc != 2) { + if (argc < 2) { fprintf(stderr, "Invalid bindsym command (expected 2 arguments, got %d)\n", argc); return 1; } - // TODO: parse out keybindings + argv[0] = do_var_replacement(config, argv[0]); + + struct sway_binding *binding = malloc(sizeof(struct sway_binding)); + binding->keys = create_list(); + binding->modifiers = 0; + binding->command = join_args(argv + 1, argc - 1); + + list_t *split = split_string(argv[0], "+"); + int i; + for (i = 0; i < split->length; ++i) { + // TODO: Parse modifier keys + xkb_keysym_t sym = xkb_keysym_from_name(split->items[i], XKB_KEYSYM_CASE_INSENSITIVE); + if (!sym) { + fprintf(stderr, "bindsym - unknown key '%s'\n", (char *)split->items[i]); + // Ignore for now, we need to deal with modifier keys + // return 1; + } + list_add(binding->keys, split->items[i]); + } + list_free(split); + + list_add(config->current_mode->bindings, binding); + + fprintf(stderr, "bindsym - Bound %s to command %s\n", argv[0], binding->command); return 0; } /* Keep alphabetized */ struct cmd_handler handlers[] = { - { "bindsym", cmd_bindsym } + { "bindsym", cmd_bindsym }, { "set", cmd_set } }; diff --git a/sway/config.c b/sway/config.c index 7242be8d..e98246ff 100644 --- a/sway/config.c +++ b/sway/config.c @@ -50,3 +50,31 @@ _continue: return config; } + +char *do_var_replacement(struct sway_config *config, char *str) { + // TODO: Handle escaping $ and using $ in string literals + int i; + for (i = 0; str[i]; ++i) { + if (str[i] == '$') { + // Try for match (note: this could be faster) + int j; + for (j = 0; j < config->symbols->length; ++j) { + struct sway_variable *var = config->symbols->items[j]; + if (strstr(str + i, var->name) == str + i) { + // Match, do replacement + char *new_string = malloc( + strlen(str) - + strlen(var->name) + + strlen(var->value) + 1); + strncpy(new_string, str, i); + new_string[i] = 0; + strcat(new_string, var->value); + strcat(new_string, str + i + strlen(var->name)); + free(str); + str = new_string; + } + } + } + } + return str; +} diff --git a/sway/config.h b/sway/config.h index b2475871..bcf65ec8 100644 --- a/sway/config.h +++ b/sway/config.h @@ -12,7 +12,7 @@ struct sway_variable { struct sway_binding { list_t *keys; - struct wlc_modifiers modifiers; + uint32_t modifiers; char *command; }; @@ -28,5 +28,6 @@ struct sway_config { }; struct sway_config *read_config(FILE *file); +char *do_var_replacement(struct sway_config *config, char *str); #endif diff --git a/sway/stringop.c b/sway/stringop.c index 4b05e657..bbc0bcdf 100644 --- a/sway/stringop.c +++ b/sway/stringop.c @@ -148,3 +148,19 @@ int unescape_string(char *string) { } return len; } + +char *join_args(char **argv, int argc) { + int len = 0, i; + for (i = 0; i < argc; ++i) { + len += strlen(argv[i]) + 1; + } + char *res = malloc(len); + len = 0; + for (i = 0; i < argc; ++i) { + strcpy(res + len, argv[i]); + len += strlen(argv[i]); + res[len++] = ' '; + } + res[len - 1] = '\0'; + return res; +} diff --git a/sway/stringop.h b/sway/stringop.h index 74f34ebf..a5346829 100644 --- a/sway/stringop.h +++ b/sway/stringop.h @@ -9,5 +9,6 @@ void free_flat_list(list_t *list); char *code_strchr(const char *string, char delimiter); char *code_strstr(const char *haystack, const char *needle); int unescape_string(char *string); +char *join_args(char **argv, int argc); #endif