问题
I'm trying to programmatically modify some of the properties of my xkb keyboard mapping in X11. In the XkbClientMapRec
struct map
member of the XkbDescRec
struct, we have the following members:
typedef struct { /* Client Map */
unsigned char size_types; /* # occupied entries in types */
unsigned char num_types; /* # entries in types */
XkbKeyTypePtr types; /* vector of key types used by this keymap */
unsigned short size_syms; /* length of the syms array */
unsigned short num_syms; /* # entries in syms */
KeySym * syms; /* linear 2d tables of keysyms, 1 per key */
XkbSymMapPtr key_sym_map; /* 1 per keycode, maps keycode to syms */
unsigned char * modmap; /* 1 per keycode, real mods bound to key */
} XkbClientMapRec, *XkbClientMapPtr;
Then, we have the XkbSymMapRec struct, here:
#define XkbNumKbdGroups 4
#define XkbMaxKbdGroup (XkbNumKbdGroups-1)
typedef struct { /* map to keysyms for a single keycode */
unsigned char kt_index[XkbNumKbdGroups]; /* key type index for each group */
unsigned char group_info; /* # of groups and out of range group handling */
unsigned char width; /* max # of shift levels for key */
unsigned short offset; /* index to keysym table in syms array */
} XkbSymMapRec, *XkbSymMapPtr;
The KeySym * syms
array in the XkbClientMapRec
array is of course just an array of KeySym
s (actually, an array of 2D arrays) as defined in keysymdefs.h
.
Anyways, what I'm wondering here is how to add completely new KeySym
s to that syms
array. Basically I want to completely change the mapping for one of the key codes on my keyboard, and the KeySym that I want to equate is with isn't typically in the KeySym
s array. Reassigning a keycode to an existing and defined set of KeySym
s is easy - for example, if I wanted keycode 45 to do the same thing as keycode 63, I'd do this:
XkbDescPtr desc = XkbGetKeyboard( curr_display, XkbAllComponentsMask, XkbUseCoreKbd );
XkbSymMapRec * client_map = desc->map;
client_map->key_sym_map[ 45 ] = client_map->key_sym_map[ 23 ];
XkbMapChangesRec changes;
changes.changed = XkbKeySymsMask;
changes.first_key_sym = 45;
changes.num_key_syms = 1;
XkbChangeMap( curr_display, desc, &changes );
This works, but it isn't what I want. I want to create completely new KeySym
entries in client_map->sym
and assign client_map->key_sym_map[ 45 ]->kt_index[ 0..n ]
to those new entries. Unfortunately, this doesn't seem to be possible? The XbkMapChangesRec struct doesn't have any way of stipulating that the KeySym * syms
array has been reallocated to something larger. The best that it has is XkbKeySymsMask
which is ONLY for changes to key_sym_map
.
Any ideas?
来源:https://stackoverflow.com/questions/10661998/xkb-how-to-increase-the-number-of-keysyms-in-the-client-map-of-an-xkbdescrec-ke