>From: Roland Eggner Add vi-style navigation keys, based on initial work by Dmitry Voytik. Users of netbooks, notebooks and other devices with keyboards lacking a dedicated number keypad will enjoy. And advanced users of vim, less, mutt, … having navigation by keys hjkl “hardwired” in their fingers will “fly” :) In global help window called by key provide a table with all current and added keybindings: | Menu navigation keys plain style vi-style | | ---------------------------------------------------------------------- | | Linewise up | | Linewise down | | Pagewise up | | Pagewise down | | First entry | | Last entry | | Enter a submenu | | Go back to parent menu | | Close a help window | | Close entry window, apply | | Close entry window, forget | | Start incremental, case-insensitive search for STRING in menu entries, | | no regex support, STRING is displayed in upper left corner | | STRING | | Remove last character | | Jump to next hit | | Jump to previous hit | | Exit menu search mode | | Search for configuration variables with or without leading CONFIG_ | | RegExpr | | Verbose search help | | ---------------------------------------------------------------------- | Intention is an easy to memorize set of keybindings resembling user interfaces of other frequently used software, not a strict clone of the historic vi user interface. In contrast to historic vi, is used for characterwise right and left movement by libreadline (bash, xfsprogs, bc, gdb, python, ruby, hunspell, mysql, sqlite, gnupg, xine-ui, parted …). Thus pagewise movement by would be weird for my fingers, so I have added , resembling e.g. thread-wise navigation in mutt message lists. To call help related to the current menu entry, currently any of the keys may be used. To solve the conflict with new navigation key , this is changed to keys . Lesser experienced users will not note, they use . And advanced users will consider, how much faster they can work, when all frequently used keys are in the middle of the keyboard. Signed-off-by: Dmitry Voytik Signed-off-by: Roland Eggner --- scripts/kconfig/nconf.c | 81 ++++++++++++++++++++++++++++++------------------ 1 files changed, 51 insertions(+), 30 deletions(-) To be applied on vanilla 3.8-rc3 diff --git a/scripts/kconfig/nconf.c b/scripts/kconfig/nconf.c --- a/scripts/kconfig/nconf.c +++ b/scripts/kconfig/nconf.c @@ -12,6 +12,8 @@ #include "nconf.h" #include +#define KEY_CONTROL(k) ((k) & 0x1f) + static const char nconf_global_help[] = N_( "Help windows\n" "------------\n" @@ -21,7 +23,7 @@ static const char nconf_global_help[] = "o A short version of the global help is available by key .\n" "\n" "o Local help: To get help related to the current menu entry, use any\n" -" of keys, or if in a data entry window then use key.\n" +" of keys, or if in a data entry window then use key.\n" "\n" "\n" "Menu entries\n" @@ -47,16 +49,16 @@ static const char nconf_global_help[] = "A trailing \"--->\" designates a submenu.\n" "\n" "\n" -"Menu navigation keys\n" +"Menu navigation keys plain style vi-style\n" "----------------------------------------------------------------------\n" -"Linewise up \n" -"Linewise down \n" -"Pagewise up \n" -"Pagewise down \n" -"First entry \n" -"Last entry \n" -"Enter a submenu \n" -"Go back to parent menu \n" +"Linewise up \n" +"Linewise down \n" +"Pagewise up \n" +"Pagewise down \n" +"First entry \n" +"Last entry \n" +"Enter a submenu \n" +"Go back to parent menu \n" "Close a help window \n" "Close entry window, apply \n" "Close entry window, forget \n" @@ -90,8 +92,8 @@ static const char nconf_global_help[] = "\n" "Text Box (Help Window)\n" "----------------------\n" -"Use movement keys as listed in\n" -"table above.\n" +"Use movement keys \n" +"as listed in table above.\n" "\n" "Press any of to exit.\n" "\n" @@ -134,9 +136,9 @@ menu_no_f_instructions[] = N_( "Submenus are designated by a trailing \"--->\".\n" "\n" "Use the following keys to navigate the menus:\n" -"Move up or down by any of keys.\n" -"To enter a submenu use any of keys.\n" -"To go back to the parent menu use any of keys.\n" +"Move up or down by any of keys.\n" +"To enter a submenu use any of keys.\n" +"To go back to the parent menu use any of keys.\n" "Pressing includes, excludes, modularizes features.\n" "Pressing cycles through the available options.\n" "To search for menu entries use key .\n" @@ -145,15 +147,15 @@ menu_no_f_instructions[] = N_( "You do not have function keys support.\n" "Use key <1> instead of , <2> instead of , etc.\n" "For verbose global help use key <1>.\n" -"For help related to the current menu entry use any of keys.\n"), +"For help related to the current menu entry use any of keys.\n"), menu_instructions[] = N_( "Legend: [*] built-in [ ] excluded module < > module capable.\n" "Submenus are designated by a trailing \"--->\".\n" "\n" "Use the following keys to navigate the menus:\n" -"Move up or down by any of keys.\n" -"To enter a submenu use any of keys.\n" -"To go back to the parent menu use any of keys.\n" +"Move up or down by any of keys.\n" +"To enter a submenu use any of keys.\n" +"To go back to the parent menu use any of keys.\n" "Pressing includes, excludes, modularizes features.\n" "Pressing cycles through the available options.\n" "To search for menu entries use key .\n" @@ -161,11 +163,11 @@ menu_instructions[] = N_( "\n" "Key <1> may be used instead of , <2> instead of , etc.\n" "For verbose global help use key .\n" -"For help related to the current menu entry use any of keys.\n"), +"For help related to the current menu entry use any of keys.\n"), radiolist_instructions[] = N_( -"Use keys to navigate this\n" +"Use keys to navigate this\n" "radiolist followed by .\n" -"For help related to the current entry use any of keys.\n" +"For help related to the current entry use any of keys.\n" "For global help use key .\n"), inputbox_instructions_int[] = N_( "Please enter a decimal value.\n" @@ -1101,24 +1103,32 @@ static void conf(struct menu *menu) break; switch (res) { case KEY_DOWN: + case 'j': menu_driver(curses_menu, REQ_DOWN_ITEM); break; case KEY_UP: + case 'k': menu_driver(curses_menu, REQ_UP_ITEM); break; case KEY_NPAGE: + case KEY_CONTROL('f'): + case KEY_CONTROL('n'): menu_driver(curses_menu, REQ_SCR_DPAGE); break; case KEY_PPAGE: + case KEY_CONTROL('b'): + case KEY_CONTROL('p'): menu_driver(curses_menu, REQ_SCR_UPAGE); break; case KEY_HOME: + case 'g': menu_driver(curses_menu, REQ_FIRST_ITEM); break; case KEY_END: + case 'G': menu_driver(curses_menu, REQ_LAST_ITEM); break; - case 'h': + case 'H': case '?': show_help((struct menu *) item_data()); break; @@ -1126,14 +1136,15 @@ static void conf(struct menu *menu) if (res == 10 || res == 27 || res == 32 || res == 'n' || res == 'y' || res == KEY_LEFT || res == KEY_RIGHT || - res == 'm') + res == 'h' || res == 'l' || res == 'm') break; refresh_all_windows(main_window); } refresh_all_windows(main_window); /* if ESC or left*/ - if (res == 27 || (menu != &rootmenu && res == KEY_LEFT)) + if (res == 27 || (menu != &rootmenu + && (res == 'h' || res == KEY_LEFT))) break; /* remember location in the menu */ @@ -1155,6 +1166,7 @@ static void conf(struct menu *menu) else if (item_is_tag('m')) conf(submenu); break; + case 'l': case KEY_RIGHT: case 10: /* ENTER WAS PRESSED */ switch (item_tag()) { @@ -1286,36 +1298,44 @@ static void conf_choice(struct menu *men break; switch (res) { case KEY_DOWN: + case 'j': menu_driver(curses_menu, REQ_DOWN_ITEM); break; case KEY_UP: + case 'k': menu_driver(curses_menu, REQ_UP_ITEM); break; case KEY_NPAGE: + case KEY_CONTROL('f'): + case KEY_CONTROL('n'): menu_driver(curses_menu, REQ_SCR_DPAGE); break; case KEY_PPAGE: + case KEY_CONTROL('b'): + case KEY_CONTROL('p'): menu_driver(curses_menu, REQ_SCR_UPAGE); break; case KEY_HOME: + case 'g': menu_driver(curses_menu, REQ_FIRST_ITEM); break; case KEY_END: + case 'G': menu_driver(curses_menu, REQ_LAST_ITEM); break; - case 'h': + case 'H': case '?': show_help((struct menu *) item_data()); break; } - if (res == 10 || res == 27 || res == ' ' || - res == KEY_LEFT){ + if (res == 10 || res == 27 || res == ' ' + || res == 'h' || res == KEY_LEFT){ break; } refresh_all_windows(main_window); } /* if ESC or left */ - if (res == 27 || res == KEY_LEFT) + if (res == 27 || res == 'h' || res == KEY_LEFT) break; child = item_data(); @@ -1324,10 +1344,11 @@ static void conf_choice(struct menu *men switch (res) { case ' ': case 10: + case 'l': case KEY_RIGHT: sym_set_tristate_value(child->sym, yes); return; - case 'h': + case 'H': case '?': show_help(child); active = child->sym; -- Roland Eggner