gimp but for windows: a wayland compositor
git clone https://github.com/m-col/wimp
Files | Refs | Readme

-rw-r--r-- src/keybind.c


      1 #include "action.h"
      2 #include "keybind.h"
      3 #include "parse.h"
      4 #include "types.h"
      5 
      6 
      7 static struct dict mods[] = {
      8     { "shift", WLR_MODIFIER_SHIFT },
      9     { "caps", WLR_MODIFIER_CAPS },
     10     { "ctrl", WLR_MODIFIER_CTRL },
     11     { "alt", WLR_MODIFIER_ALT },
     12     { "mod2", WLR_MODIFIER_MOD2 },
     13     { "mod3", WLR_MODIFIER_MOD3 },
     14     { "logo", WLR_MODIFIER_LOGO },
     15     { "mod5", WLR_MODIFIER_MOD5 },
     16 };
     17 
     18 
     19 static struct dict mouse_keys[] = {
     20     { "motion", MOTION },
     21     { "scroll", SCROLL },
     22     { "drag1", DRAG1 },
     23     { "drag2", DRAG2 },
     24     { "drag3", DRAG3 },
     25     { "pinch", PINCH },
     26 };
     27 
     28 
     29 void free_binding(struct binding *kb) {
     30     if (kb->data)
     31 	free(kb->data);
     32     wl_list_remove(&kb->link);
     33     free(kb);
     34 }
     35 
     36 
     37 void add_binding(char *message, char *response) {
     38     char *s;
     39     if (!(s = strtok(NULL, " \t\n\r"))) {
     40 	sprintf(response, "What do you want to bind?");
     41 	return;
     42     }
     43 
     44     struct binding *kb = calloc(1, sizeof(struct binding));
     45     enum wlr_keyboard_modifier mod;
     46     bool is_mouse_binding = false;
     47 
     48     // additional modifiers
     49     kb->mods = 0;
     50     for (int i = 0; i < 8; i++) {
     51 	mod = get(mods, s);
     52 	if (mod == 0)
     53 	    break;
     54 	kb->mods |= mod;
     55 	s = strtok(NULL, " \t\n\r");
     56     }
     57 
     58     // key
     59     kb->key = xkb_keysym_from_name(s, XKB_KEYSYM_NO_FLAGS);
     60     if (kb->key == XKB_KEY_NoSymbol) {
     61 	kb->key = xkb_keysym_from_name(s, XKB_KEYSYM_CASE_INSENSITIVE);
     62     }
     63 
     64     if (kb->key == XKB_KEY_NoSymbol) {
     65 	kb->key = get(mouse_keys, s);
     66 	if (kb->key == 0) {
     67 	    sprintf(response, "No such key '%s'.", s);
     68 	    free(kb);
     69 	    return;
     70 	}
     71 	is_mouse_binding = true;
     72     }
     73 
     74     // action
     75     s = strtok(NULL, " \t\n\r");
     76     if (!s) {
     77 	sprintf(response,  "Command malformed/incomplete.");
     78 	return;
     79     }
     80     if (!get_action(s, &kb->action, strtok(NULL, "\n\r"), &kb->data, response, kb->key)) {
     81 	free(kb);
     82 	return;
     83     }
     84 
     85     struct binding *kb_existing, *tmp;
     86     struct wl_list *bindings;
     87     if (is_mouse_binding) {
     88 	bindings = &wimp.mouse_bindings;
     89     } else {
     90 	bindings = &wimp.key_bindings;
     91     }
     92     wl_list_for_each_safe(kb_existing, tmp, bindings, link) {
     93 	if (kb_existing->key == kb->key && kb_existing->mods == kb->mods) {
     94 	    free_binding(kb_existing);
     95 	}
     96     }
     97     wl_list_insert(bindings->prev, &kb->link);
     98 }
     99 
    100 
    101 void set_mod(char *message, char *response) {
    102     char *s = strtok(NULL, " \t\n\r");
    103     enum wlr_keyboard_modifier mod = get(mods, s);
    104     if (mod) {
    105         wimp.mod = mod;
    106     } else {
    107         sprintf(response, "Invalid modifier name '%s'.", s);
    108     }
    109 }
    110