forked from enlightenment/terminology
store keybindings in a hash map
This commit is contained in:
parent
eab93284b7
commit
2f9532d28c
140
src/bin/keyin.c
140
src/bin/keyin.c
|
@ -18,6 +18,8 @@ struct _Keyout
|
|||
int outlen;
|
||||
};
|
||||
|
||||
static Eina_Hash *_key_bindings = NULL;
|
||||
|
||||
|
||||
|
||||
#define KEY(in, out) {in, out, sizeof(in) - 1, sizeof(out) - 1}
|
||||
|
@ -622,19 +624,43 @@ _handle_key_to_pty(Termpty *ty, const Evas_Event_Key_Down *ev,
|
|||
}
|
||||
}
|
||||
|
||||
static Key_Binding *
|
||||
key_binding_lookup(const Evas_Event_Key_Down *ev,
|
||||
Eina_Bool ctrl, Eina_Bool alt, Eina_Bool shift)
|
||||
{
|
||||
Key_Binding *kb;
|
||||
size_t len = strlen(ev->keyname);
|
||||
|
||||
if (len > UINT16_MAX) return NULL;
|
||||
|
||||
kb = alloca(sizeof(Key_Binding) + len + 1);
|
||||
if (!kb) return NULL;
|
||||
kb->ctrl = ctrl;
|
||||
kb->alt = alt;
|
||||
kb->shift = shift;
|
||||
kb->len = len;
|
||||
strncpy(kb->keyname, ev->keyname, kb->len + 1);
|
||||
|
||||
return eina_hash_find(_key_bindings, kb);
|
||||
}
|
||||
|
||||
Eina_Bool
|
||||
keyin_handle(Keys_Handler *khdl, Termpty *ty, const Evas_Event_Key_Down *ev,
|
||||
int alt, int shift, int ctrl)
|
||||
Eina_Bool ctrl, Eina_Bool alt, Eina_Bool shift)
|
||||
{
|
||||
Key_Binding *kb;
|
||||
|
||||
kb = key_binding_lookup(ev, ctrl, alt, shift);
|
||||
if (kb)
|
||||
{
|
||||
if (kb->cb(ty->obj))
|
||||
goto end;
|
||||
}
|
||||
|
||||
|
||||
if ((!alt) && (ctrl) && (!shift))
|
||||
{
|
||||
if (!strcmp(ev->key, "Prior"))
|
||||
{
|
||||
keyin_compose_seq_reset(khdl);
|
||||
evas_object_smart_callback_call(ty->obj, "prev", NULL);
|
||||
return EINA_TRUE;
|
||||
}
|
||||
else if (!strcmp(ev->key, "Next"))
|
||||
if (!strcmp(ev->key, "Next"))
|
||||
{
|
||||
keyin_compose_seq_reset(khdl);
|
||||
evas_object_smart_callback_call(ty->obj, "next", NULL);
|
||||
|
@ -877,3 +903,101 @@ keyin_handle_up(Keys_Handler *khdl, Evas_Event_Key_Up *ev)
|
|||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static Eina_Bool
|
||||
cb_term_prev(Evas_Object *term)
|
||||
{
|
||||
evas_object_smart_callback_call(term, "prev", NULL);
|
||||
return EINA_TRUE;
|
||||
}
|
||||
|
||||
static unsigned int
|
||||
key_binding_key_length(EINA_UNUSED const void *key)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
key_binding_key_cmp(const void *key1, int key1_length,
|
||||
const void *key2, int key2_length)
|
||||
{
|
||||
const Key_Binding *kb1 = key1,
|
||||
*kb2 = key2;
|
||||
|
||||
if (key1_length < key2_length)
|
||||
return -1;
|
||||
else if (key1_length > key2_length)
|
||||
return 1;
|
||||
else
|
||||
{
|
||||
unsigned int m1 = (kb1->ctrl << 2) | (kb1->alt << 1) | kb1->shift,
|
||||
m2 = (kb2->ctrl << 2) | (kb2->alt << 1) | kb2->shift;
|
||||
if (m1 < m2)
|
||||
return -1;
|
||||
else if (m1 > m2)
|
||||
return 1;
|
||||
else
|
||||
return strncmp(kb1->keyname, kb2->keyname, kb1->len);
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
key_binding_key_hash(const void *key, int key_length)
|
||||
{
|
||||
const Key_Binding *kb = key;
|
||||
int hash;
|
||||
|
||||
hash = eina_hash_djb2(key, key_length);
|
||||
hash &= 0x1fffffff;
|
||||
hash |= (kb->ctrl << 31) | (kb->alt << 30) | (kb->shift << 29);
|
||||
return hash;
|
||||
}
|
||||
|
||||
|
||||
Key_Binding *
|
||||
key_binding_new(const char *keyname,
|
||||
Eina_Bool ctrl, Eina_Bool alt, Eina_Bool shift,
|
||||
Key_Binding_Cb cb)
|
||||
{
|
||||
Key_Binding *kb;
|
||||
size_t len = strlen(keyname);
|
||||
|
||||
if (len > UINT16_MAX) return NULL;
|
||||
|
||||
kb = malloc(sizeof(Key_Binding) + len + 1);
|
||||
if (!kb) return NULL;
|
||||
kb->ctrl = ctrl;
|
||||
kb->alt = alt;
|
||||
kb->shift = shift;
|
||||
kb->len = len;
|
||||
strncpy(kb->keyname, keyname, kb->len + 1);
|
||||
kb->cb = cb;
|
||||
|
||||
return kb;
|
||||
}
|
||||
|
||||
int key_bindings_init(void)
|
||||
{
|
||||
Key_Binding *kb;
|
||||
|
||||
_key_bindings = eina_hash_new(key_binding_key_length,
|
||||
key_binding_key_cmp,
|
||||
key_binding_key_hash,
|
||||
free,
|
||||
5);
|
||||
if (!_key_bindings) return -1;
|
||||
|
||||
kb = key_binding_new("Prior", 1, 0, 0, cb_term_prev);
|
||||
if (!kb) return -1;
|
||||
if (!eina_hash_direct_add(_key_bindings, kb, kb)) return -1;
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void key_bindings_shutdown(void)
|
||||
{
|
||||
if (_key_bindings)
|
||||
eina_hash_free(_key_bindings);
|
||||
_key_bindings = NULL;
|
||||
}
|
||||
|
|
|
@ -14,9 +14,31 @@ struct _Keys_Handler
|
|||
void keyin_compose_seq_reset(Keys_Handler *khdl);
|
||||
Eina_Bool key_is_modifier(const char *key);
|
||||
Eina_Bool keyin_handle(Keys_Handler *khdl, Termpty *ty, const Evas_Event_Key_Down *ev,
|
||||
int alt, int shift, int ctrl);
|
||||
Eina_Bool ctrl, Eina_Bool alt, Eina_Bool shift);
|
||||
|
||||
void keyin_handle_up(Keys_Handler *khdl, Evas_Event_Key_Up *ev);
|
||||
|
||||
typedef struct _Key_Binding Key_Binding;
|
||||
|
||||
typedef Eina_Bool (*Key_Binding_Cb)(Evas_Object *term);
|
||||
struct _Key_Binding
|
||||
{
|
||||
uint16_t ctrl : 1;
|
||||
uint16_t alt : 1;
|
||||
uint16_t shift : 1;
|
||||
|
||||
uint16_t len;
|
||||
|
||||
Key_Binding_Cb cb;
|
||||
char keyname[];
|
||||
};
|
||||
|
||||
Key_Binding *
|
||||
key_binding_new(const char *keyname,
|
||||
Eina_Bool ctrl, Eina_Bool alt, Eina_Bool shift,
|
||||
Key_Binding_Cb cb);
|
||||
int key_bindings_init(void);
|
||||
void key_bindings_shutdown(void);
|
||||
|
||||
|
||||
#endif
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
#include "dbus.h"
|
||||
#include "app_server.h"
|
||||
#include "miniview.h"
|
||||
#include "keyin.h"
|
||||
|
||||
#if (ELM_VERSION_MAJOR == 1) && (ELM_VERSION_MINOR < 8)
|
||||
#define PANES_TOP "left"
|
||||
|
@ -2977,6 +2978,12 @@ elm_main(int argc, char **argv)
|
|||
elm_app_info_set(elm_main, "terminology", "themes/default.edj");
|
||||
|
||||
config_init();
|
||||
if (key_bindings_init() < 0)
|
||||
{
|
||||
ERR(_("Could not Initialize key bindings."));
|
||||
retval = EXIT_FAILURE;
|
||||
goto end;
|
||||
}
|
||||
|
||||
main_config = config_load("config");
|
||||
|
||||
|
@ -3373,6 +3380,7 @@ remote:
|
|||
|
||||
|
||||
config_del(main_config);
|
||||
key_bindings_shutdown();
|
||||
config_shutdown();
|
||||
eina_log_domain_unregister(_log_domain);
|
||||
_log_domain = -1;
|
||||
|
|
|
@ -1850,9 +1850,9 @@ _smart_cb_key_down(void *data, Evas *e EINA_UNUSED,
|
|||
{
|
||||
const Evas_Event_Key_Down *ev = event;
|
||||
Termio *sd = evas_object_smart_data_get(data);
|
||||
int ctrl = evas_key_modifier_is_set(ev->modifiers, "Control");
|
||||
int alt = evas_key_modifier_is_set(ev->modifiers, "Alt");
|
||||
int shift = evas_key_modifier_is_set(ev->modifiers, "Shift");
|
||||
int ctrl = evas_key_modifier_is_set(ev->modifiers, "Control");
|
||||
|
||||
EINA_SAFETY_ON_NULL_RETURN(sd);
|
||||
EINA_SAFETY_ON_NULL_RETURN(ev->key);
|
||||
|
@ -1861,7 +1861,7 @@ _smart_cb_key_down(void *data, Evas *e EINA_UNUSED,
|
|||
return;
|
||||
|
||||
|
||||
if (keyin_handle(&sd->khdl, sd->pty, ev, alt, shift, ctrl))
|
||||
if (keyin_handle(&sd->khdl, sd->pty, ev, ctrl, alt, shift))
|
||||
goto end;
|
||||
|
||||
if (sd->jump_on_keypress)
|
||||
|
|
Loading…
Reference in New Issue