sde1000 / python-xkbcommon

Python bindings for libxkbcommon using cffi
MIT License
19 stars 5 forks source link

Support Keymap.key_get_mods_for_level() #20

Closed sde1000 closed 6 months ago

sde1000 commented 6 months ago

xkb_keymap_key_get_mods_for_level() was introduced in libxkbcommon-1.0

sde1000 commented 6 months ago

Would it be helpful to add helper functions for dealing with xkb_mod_mask_t? Eg. to decompose it into a set of xkb_mod_index_t or a set of modifier names?

Arguably Keymap.key_get_mods_for_level() should return a suitable IntFlag type, but we would have to generate a new type for each Keymap instance because the mapping between xkb_mod_index_t and modifier name can change.

ldrahnik commented 6 months ago

I think return mask is ok then I can implement in Python something similar to:

num_mods = xkb_keymap_num_mods(keymap);

...

               for (xkb_mod_index_t mod = 0; mod < num_mods; mod++) {
                   if ((mask & (1 << mod)) == 0) {
                       continue;
                   }
                   printf("%s ", xkb_keymap_mod_get_name(keymap, mod));
               }

I tested the Python code below for masks returned by key_get_consumed_mods and it works:

        consumed_mods = keyboard_state.key_get_consumed_mods(keycode)
        if consumed_mods > 0:
            print("char: `" + char + "`, consumed mods mask: " + str(consumed_mods))
            for mod_index in range(0, keymap.num_mods()):

                if (consumed_mods & (1 << mod_index) == 0):
                    continue

                mod_name = keymap.mod_get_name(mod_index)
                print(mod_name)

Sounds better to me use cycle outside and not put cycle into this lib.