ultra-keyboard-controlled-menus
This commit is contained in:
parent
43fded6a10
commit
dcdc325f5c
4 changed files with 88 additions and 0 deletions
|
@ -1147,6 +1147,19 @@ static void event_handle_dockapp(ObDockApp *app, XEvent *e)
|
|||
}
|
||||
}
|
||||
|
||||
ObMenuFrame* find_active_menu()
|
||||
{
|
||||
GList *it;
|
||||
ObMenuFrame *f;
|
||||
|
||||
for (it = menu_frame_visible; it; it = g_list_next(it)) {
|
||||
f = it->data;
|
||||
if (f->selected)
|
||||
break;
|
||||
}
|
||||
return it ? it->data : NULL;
|
||||
}
|
||||
|
||||
static void event_handle_menu(XEvent *ev)
|
||||
{
|
||||
ObMenuFrame *f;
|
||||
|
@ -1173,5 +1186,30 @@ static void event_handle_menu(XEvent *ev)
|
|||
menu_frame_select(f, e);
|
||||
}
|
||||
break;
|
||||
case KeyPress:
|
||||
if (ev->xkey.keycode == ob_keycode(OB_KEY_ESCAPE))
|
||||
menu_frame_hide_all();
|
||||
else if (ev->xkey.keycode == ob_keycode(OB_KEY_RETURN)) {
|
||||
ObMenuFrame *f;
|
||||
if ((f = find_active_menu()))
|
||||
menu_entry_frame_execute(f->selected,
|
||||
!(ev->xkey.state & ControlMask));
|
||||
} else if (ev->xkey.keycode == ob_keycode(OB_KEY_LEFT)) {
|
||||
ObMenuFrame *f;
|
||||
if ((f = find_active_menu()) && f->parent)
|
||||
menu_frame_select(f, NULL);
|
||||
} else if (ev->xkey.keycode == ob_keycode(OB_KEY_RIGHT)) {
|
||||
ObMenuFrame *f;
|
||||
if ((f = find_active_menu()) && f->child && f->child->entries)
|
||||
menu_frame_select(f->child, f->child->entries->data);
|
||||
} else if (ev->xkey.keycode == ob_keycode(OB_KEY_UP)) {
|
||||
ObMenuFrame *f;
|
||||
if ((f = find_active_menu()))
|
||||
menu_frame_select_previous(f);
|
||||
} else if (ev->xkey.keycode == ob_keycode(OB_KEY_DOWN)) {
|
||||
ObMenuFrame *f;
|
||||
if ((f = find_active_menu()))
|
||||
menu_frame_select_next(f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -215,6 +215,8 @@ void menu_show(gchar *name, gint x, gint y, ObClient *client)
|
|||
frame = menu_frame_new(self, client);
|
||||
menu_frame_move(frame, x, y);
|
||||
menu_frame_show(frame, NULL);
|
||||
if (frame->entries)
|
||||
menu_frame_select_next(frame);
|
||||
}
|
||||
|
||||
static ObMenuEntry* menu_entry_new(ObMenu *menu, ObMenuEntryType type, gint id)
|
||||
|
|
|
@ -627,3 +627,49 @@ void menu_entry_frame_execute(ObMenuEntryFrame *self, gboolean hide)
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
void menu_frame_select_previous(ObMenuFrame *self)
|
||||
{
|
||||
GList *it = NULL, *start;
|
||||
|
||||
if (self->entries) {
|
||||
start = it = g_list_find(self->entries, self->selected);
|
||||
while (TRUE) {
|
||||
ObMenuEntryFrame *e;
|
||||
|
||||
it = it ? g_list_previous(it) : g_list_last(self->entries);
|
||||
if (it == start)
|
||||
break;
|
||||
|
||||
if (it) {
|
||||
e = it->data;
|
||||
if (e->entry->type != OB_MENU_ENTRY_TYPE_SEPARATOR)
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
menu_frame_select(self, it ? it->data : NULL);
|
||||
}
|
||||
|
||||
void menu_frame_select_next(ObMenuFrame *self)
|
||||
{
|
||||
GList *it = NULL, *start;
|
||||
|
||||
if (self->entries) {
|
||||
start = it = g_list_find(self->entries, self->selected);
|
||||
while (TRUE) {
|
||||
ObMenuEntryFrame *e;
|
||||
|
||||
it = it ? g_list_next(it) : self->entries;
|
||||
if (it == start)
|
||||
break;
|
||||
|
||||
if (it) {
|
||||
e = it->data;
|
||||
if (e->entry->type != OB_MENU_ENTRY_TYPE_SEPARATOR)
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
menu_frame_select(self, it ? it->data : NULL);
|
||||
}
|
||||
|
|
|
@ -88,6 +88,8 @@ void menu_frame_hide_all();
|
|||
void menu_frame_hide_all_client(struct _ObClient *client);
|
||||
|
||||
void menu_frame_select(ObMenuFrame *self, ObMenuEntryFrame *entry);
|
||||
void menu_frame_select_previous(ObMenuFrame *self);
|
||||
void menu_frame_select_next(ObMenuFrame *self);
|
||||
|
||||
ObMenuFrame* menu_frame_under(gint x, gint y);
|
||||
ObMenuEntryFrame* menu_entry_frame_under(gint x, gint y);
|
||||
|
|
Loading…
Reference in a new issue