15257cf54a5810105bc4a75703a06740d756d8e8landley/* 25257cf54a5810105bc4a75703a06740d756d8e8landley * menubox.c -- implements the menu box 35257cf54a5810105bc4a75703a06740d756d8e8landley * 45257cf54a5810105bc4a75703a06740d756d8e8landley * ORIGINAL AUTHOR: Savio Lam (lam836@cs.cuhk.hk) 55257cf54a5810105bc4a75703a06740d756d8e8landley * MODIFIED FOR LINUX KERNEL CONFIG BY: William Roadcap (roadcapw@cfw.com) 65257cf54a5810105bc4a75703a06740d756d8e8landley * 75257cf54a5810105bc4a75703a06740d756d8e8landley * This program is free software; you can redistribute it and/or 85257cf54a5810105bc4a75703a06740d756d8e8landley * modify it under the terms of the GNU General Public License 95257cf54a5810105bc4a75703a06740d756d8e8landley * as published by the Free Software Foundation; either version 2 105257cf54a5810105bc4a75703a06740d756d8e8landley * of the License, or (at your option) any later version. 115257cf54a5810105bc4a75703a06740d756d8e8landley * 125257cf54a5810105bc4a75703a06740d756d8e8landley * This program is distributed in the hope that it will be useful, 135257cf54a5810105bc4a75703a06740d756d8e8landley * but WITHOUT ANY WARRANTY; without even the implied warranty of 145257cf54a5810105bc4a75703a06740d756d8e8landley * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 155257cf54a5810105bc4a75703a06740d756d8e8landley * GNU General Public License for more details. 165257cf54a5810105bc4a75703a06740d756d8e8landley * 175257cf54a5810105bc4a75703a06740d756d8e8landley * You should have received a copy of the GNU General Public License 185257cf54a5810105bc4a75703a06740d756d8e8landley * along with this program; if not, write to the Free Software 195257cf54a5810105bc4a75703a06740d756d8e8landley * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 205257cf54a5810105bc4a75703a06740d756d8e8landley */ 215257cf54a5810105bc4a75703a06740d756d8e8landley 225257cf54a5810105bc4a75703a06740d756d8e8landley/* 235257cf54a5810105bc4a75703a06740d756d8e8landley * Changes by Clifford Wolf (god@clifford.at) 245257cf54a5810105bc4a75703a06740d756d8e8landley * 255257cf54a5810105bc4a75703a06740d756d8e8landley * [ 1998-06-13 ] 265257cf54a5810105bc4a75703a06740d756d8e8landley * 275257cf54a5810105bc4a75703a06740d756d8e8landley * *) A bugfix for the Page-Down problem 285257cf54a5810105bc4a75703a06740d756d8e8landley * 295257cf54a5810105bc4a75703a06740d756d8e8landley * *) Formerly when I used Page Down and Page Up, the cursor would be set 305257cf54a5810105bc4a75703a06740d756d8e8landley * to the first position in the menu box. Now lxdialog is a bit 315257cf54a5810105bc4a75703a06740d756d8e8landley * smarter and works more like other menu systems (just have a look at 325257cf54a5810105bc4a75703a06740d756d8e8landley * it). 335257cf54a5810105bc4a75703a06740d756d8e8landley * 345257cf54a5810105bc4a75703a06740d756d8e8landley * *) Formerly if I selected something my scrolling would be broken because 355257cf54a5810105bc4a75703a06740d756d8e8landley * lxdialog is re-invoked by the Menuconfig shell script, can't 365257cf54a5810105bc4a75703a06740d756d8e8landley * remember the last scrolling position, and just sets it so that the 375257cf54a5810105bc4a75703a06740d756d8e8landley * cursor is at the bottom of the box. Now it writes the temporary file 385257cf54a5810105bc4a75703a06740d756d8e8landley * lxdialog.scrltmp which contains this information. The file is 395257cf54a5810105bc4a75703a06740d756d8e8landley * deleted by lxdialog if the user leaves a submenu or enters a new 405257cf54a5810105bc4a75703a06740d756d8e8landley * one, but it would be nice if Menuconfig could make another "rm -f" 415257cf54a5810105bc4a75703a06740d756d8e8landley * just to be sure. Just try it out - you will recognise a difference! 425257cf54a5810105bc4a75703a06740d756d8e8landley * 435257cf54a5810105bc4a75703a06740d756d8e8landley * [ 1998-06-14 ] 445257cf54a5810105bc4a75703a06740d756d8e8landley * 455257cf54a5810105bc4a75703a06740d756d8e8landley * *) Now lxdialog is crash-safe against broken "lxdialog.scrltmp" files 465257cf54a5810105bc4a75703a06740d756d8e8landley * and menus change their size on the fly. 475257cf54a5810105bc4a75703a06740d756d8e8landley * 485257cf54a5810105bc4a75703a06740d756d8e8landley * *) If for some reason the last scrolling position is not saved by 495257cf54a5810105bc4a75703a06740d756d8e8landley * lxdialog, it sets the scrolling so that the selected item is in the 505257cf54a5810105bc4a75703a06740d756d8e8landley * middle of the menu box, not at the bottom. 515257cf54a5810105bc4a75703a06740d756d8e8landley * 525257cf54a5810105bc4a75703a06740d756d8e8landley * 02 January 1999, Michael Elizabeth Chastain (mec@shout.net) 535257cf54a5810105bc4a75703a06740d756d8e8landley * Reset 'scroll' to 0 if the value from lxdialog.scrltmp is bogus. 545257cf54a5810105bc4a75703a06740d756d8e8landley * This fixes a bug in Menuconfig where using ' ' to descend into menus 555257cf54a5810105bc4a75703a06740d756d8e8landley * would leave mis-synchronized lxdialog.scrltmp files lying around, 565257cf54a5810105bc4a75703a06740d756d8e8landley * fscanf would read in 'scroll', and eventually that value would get used. 575257cf54a5810105bc4a75703a06740d756d8e8landley */ 585257cf54a5810105bc4a75703a06740d756d8e8landley 595257cf54a5810105bc4a75703a06740d756d8e8landley#include "dialog.h" 605257cf54a5810105bc4a75703a06740d756d8e8landley 615257cf54a5810105bc4a75703a06740d756d8e8landleystatic int menu_width, item_x; 625257cf54a5810105bc4a75703a06740d756d8e8landley 635257cf54a5810105bc4a75703a06740d756d8e8landley/* 645257cf54a5810105bc4a75703a06740d756d8e8landley * Print menu item 655257cf54a5810105bc4a75703a06740d756d8e8landley */ 665257cf54a5810105bc4a75703a06740d756d8e8landleystatic void do_print_item(WINDOW * win, const char *item, int line_y, 675257cf54a5810105bc4a75703a06740d756d8e8landley int selected, int hotkey) 685257cf54a5810105bc4a75703a06740d756d8e8landley{ 695257cf54a5810105bc4a75703a06740d756d8e8landley int j; 705257cf54a5810105bc4a75703a06740d756d8e8landley char *menu_item = malloc(menu_width + 1); 715257cf54a5810105bc4a75703a06740d756d8e8landley 725257cf54a5810105bc4a75703a06740d756d8e8landley strncpy(menu_item, item, menu_width - item_x); 735257cf54a5810105bc4a75703a06740d756d8e8landley menu_item[menu_width - item_x] = '\0'; 745257cf54a5810105bc4a75703a06740d756d8e8landley j = first_alpha(menu_item, "YyNnMmHh"); 755257cf54a5810105bc4a75703a06740d756d8e8landley 765257cf54a5810105bc4a75703a06740d756d8e8landley /* Clear 'residue' of last item */ 775257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, dlg.menubox.atr); 785257cf54a5810105bc4a75703a06740d756d8e8landley wmove(win, line_y, 0); 795257cf54a5810105bc4a75703a06740d756d8e8landley#if OLD_NCURSES 805257cf54a5810105bc4a75703a06740d756d8e8landley { 815257cf54a5810105bc4a75703a06740d756d8e8landley int i; 825257cf54a5810105bc4a75703a06740d756d8e8landley for (i = 0; i < menu_width; i++) 835257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ' '); 845257cf54a5810105bc4a75703a06740d756d8e8landley } 855257cf54a5810105bc4a75703a06740d756d8e8landley#else 865257cf54a5810105bc4a75703a06740d756d8e8landley wclrtoeol(win); 875257cf54a5810105bc4a75703a06740d756d8e8landley#endif 885257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, selected ? dlg.item_selected.atr : dlg.item.atr); 895257cf54a5810105bc4a75703a06740d756d8e8landley mvwaddstr(win, line_y, item_x, menu_item); 905257cf54a5810105bc4a75703a06740d756d8e8landley if (hotkey) { 915257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, selected ? dlg.tag_key_selected.atr 925257cf54a5810105bc4a75703a06740d756d8e8landley : dlg.tag_key.atr); 935257cf54a5810105bc4a75703a06740d756d8e8landley mvwaddch(win, line_y, item_x + j, menu_item[j]); 945257cf54a5810105bc4a75703a06740d756d8e8landley } 955257cf54a5810105bc4a75703a06740d756d8e8landley if (selected) { 965257cf54a5810105bc4a75703a06740d756d8e8landley wmove(win, line_y, item_x + 1); 975257cf54a5810105bc4a75703a06740d756d8e8landley } 985257cf54a5810105bc4a75703a06740d756d8e8landley free(menu_item); 995257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(win); 1005257cf54a5810105bc4a75703a06740d756d8e8landley} 1015257cf54a5810105bc4a75703a06740d756d8e8landley 1025257cf54a5810105bc4a75703a06740d756d8e8landley#define print_item(index, choice, selected) \ 1035257cf54a5810105bc4a75703a06740d756d8e8landleydo { \ 1045257cf54a5810105bc4a75703a06740d756d8e8landley item_set(index); \ 1055257cf54a5810105bc4a75703a06740d756d8e8landley do_print_item(menu, item_str(), choice, selected, !item_is_tag(':')); \ 1065257cf54a5810105bc4a75703a06740d756d8e8landley} while (0) 1075257cf54a5810105bc4a75703a06740d756d8e8landley 1085257cf54a5810105bc4a75703a06740d756d8e8landley/* 1095257cf54a5810105bc4a75703a06740d756d8e8landley * Print the scroll indicators. 1105257cf54a5810105bc4a75703a06740d756d8e8landley */ 1115257cf54a5810105bc4a75703a06740d756d8e8landleystatic void print_arrows(WINDOW * win, int item_no, int scroll, int y, int x, 1125257cf54a5810105bc4a75703a06740d756d8e8landley int height) 1135257cf54a5810105bc4a75703a06740d756d8e8landley{ 1145257cf54a5810105bc4a75703a06740d756d8e8landley int cur_y, cur_x; 1155257cf54a5810105bc4a75703a06740d756d8e8landley 1165257cf54a5810105bc4a75703a06740d756d8e8landley getyx(win, cur_y, cur_x); 1175257cf54a5810105bc4a75703a06740d756d8e8landley 1185257cf54a5810105bc4a75703a06740d756d8e8landley wmove(win, y, x); 1195257cf54a5810105bc4a75703a06740d756d8e8landley 1205257cf54a5810105bc4a75703a06740d756d8e8landley if (scroll > 0) { 1215257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, dlg.uarrow.atr); 1225257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_UARROW); 1235257cf54a5810105bc4a75703a06740d756d8e8landley waddstr(win, "(-)"); 1245257cf54a5810105bc4a75703a06740d756d8e8landley } else { 1255257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, dlg.menubox.atr); 1265257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1275257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1285257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1295257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1305257cf54a5810105bc4a75703a06740d756d8e8landley } 1315257cf54a5810105bc4a75703a06740d756d8e8landley 1325257cf54a5810105bc4a75703a06740d756d8e8landley y = y + height + 1; 1335257cf54a5810105bc4a75703a06740d756d8e8landley wmove(win, y, x); 1345257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(win); 1355257cf54a5810105bc4a75703a06740d756d8e8landley 1365257cf54a5810105bc4a75703a06740d756d8e8landley if ((height < item_no) && (scroll + height < item_no)) { 1375257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, dlg.darrow.atr); 1385257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_DARROW); 1395257cf54a5810105bc4a75703a06740d756d8e8landley waddstr(win, "(+)"); 1405257cf54a5810105bc4a75703a06740d756d8e8landley } else { 1415257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(win, dlg.menubox_border.atr); 1425257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1435257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1445257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1455257cf54a5810105bc4a75703a06740d756d8e8landley waddch(win, ACS_HLINE); 1465257cf54a5810105bc4a75703a06740d756d8e8landley } 1475257cf54a5810105bc4a75703a06740d756d8e8landley 1485257cf54a5810105bc4a75703a06740d756d8e8landley wmove(win, cur_y, cur_x); 1495257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(win); 1505257cf54a5810105bc4a75703a06740d756d8e8landley} 1515257cf54a5810105bc4a75703a06740d756d8e8landley 1525257cf54a5810105bc4a75703a06740d756d8e8landley/* 1535257cf54a5810105bc4a75703a06740d756d8e8landley * Display the termination buttons. 1545257cf54a5810105bc4a75703a06740d756d8e8landley */ 1555257cf54a5810105bc4a75703a06740d756d8e8landleystatic void print_buttons(WINDOW * win, int height, int width, int selected) 1565257cf54a5810105bc4a75703a06740d756d8e8landley{ 1575257cf54a5810105bc4a75703a06740d756d8e8landley int x = width / 2 - 16; 1585257cf54a5810105bc4a75703a06740d756d8e8landley int y = height - 2; 1595257cf54a5810105bc4a75703a06740d756d8e8landley 1605257cf54a5810105bc4a75703a06740d756d8e8landley print_button(win, "Select", y, x, selected == 0); 1615257cf54a5810105bc4a75703a06740d756d8e8landley print_button(win, " Exit ", y, x + 12, selected == 1); 1625257cf54a5810105bc4a75703a06740d756d8e8landley print_button(win, " Help ", y, x + 24, selected == 2); 1635257cf54a5810105bc4a75703a06740d756d8e8landley 1645257cf54a5810105bc4a75703a06740d756d8e8landley wmove(win, y, x + 1 + 12 * selected); 1655257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(win); 1665257cf54a5810105bc4a75703a06740d756d8e8landley} 1675257cf54a5810105bc4a75703a06740d756d8e8landley 1685257cf54a5810105bc4a75703a06740d756d8e8landley/* scroll up n lines (n may be negative) */ 1695257cf54a5810105bc4a75703a06740d756d8e8landleystatic void do_scroll(WINDOW *win, int *scroll, int n) 1705257cf54a5810105bc4a75703a06740d756d8e8landley{ 1715257cf54a5810105bc4a75703a06740d756d8e8landley /* Scroll menu up */ 1725257cf54a5810105bc4a75703a06740d756d8e8landley scrollok(win, TRUE); 1735257cf54a5810105bc4a75703a06740d756d8e8landley wscrl(win, n); 1745257cf54a5810105bc4a75703a06740d756d8e8landley scrollok(win, FALSE); 1755257cf54a5810105bc4a75703a06740d756d8e8landley *scroll = *scroll + n; 1765257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(win); 1775257cf54a5810105bc4a75703a06740d756d8e8landley} 1785257cf54a5810105bc4a75703a06740d756d8e8landley 1795257cf54a5810105bc4a75703a06740d756d8e8landley/* 1805257cf54a5810105bc4a75703a06740d756d8e8landley * Display a menu for choosing among a number of options 1815257cf54a5810105bc4a75703a06740d756d8e8landley */ 1825257cf54a5810105bc4a75703a06740d756d8e8landleyint dialog_menu(const char *title, const char *prompt, 1835257cf54a5810105bc4a75703a06740d756d8e8landley const void *selected, int *s_scroll) 1845257cf54a5810105bc4a75703a06740d756d8e8landley{ 1855257cf54a5810105bc4a75703a06740d756d8e8landley int i, j, x, y, box_x, box_y; 1865257cf54a5810105bc4a75703a06740d756d8e8landley int height, width, menu_height; 1875257cf54a5810105bc4a75703a06740d756d8e8landley int key = 0, button = 0, scroll = 0, choice = 0; 1885257cf54a5810105bc4a75703a06740d756d8e8landley int first_item = 0, max_choice; 1895257cf54a5810105bc4a75703a06740d756d8e8landley WINDOW *dialog, *menu; 1905257cf54a5810105bc4a75703a06740d756d8e8landley 1915257cf54a5810105bc4a75703a06740d756d8e8landleydo_resize: 1925257cf54a5810105bc4a75703a06740d756d8e8landley height = getmaxy(stdscr); 1935257cf54a5810105bc4a75703a06740d756d8e8landley width = getmaxx(stdscr); 1945257cf54a5810105bc4a75703a06740d756d8e8landley if (height < 15 || width < 65) 1955257cf54a5810105bc4a75703a06740d756d8e8landley return -ERRDISPLAYTOOSMALL; 1965257cf54a5810105bc4a75703a06740d756d8e8landley 1975257cf54a5810105bc4a75703a06740d756d8e8landley height -= 4; 1985257cf54a5810105bc4a75703a06740d756d8e8landley width -= 5; 1995257cf54a5810105bc4a75703a06740d756d8e8landley menu_height = height - 10; 2005257cf54a5810105bc4a75703a06740d756d8e8landley 2015257cf54a5810105bc4a75703a06740d756d8e8landley max_choice = MIN(menu_height, item_count()); 2025257cf54a5810105bc4a75703a06740d756d8e8landley 2035257cf54a5810105bc4a75703a06740d756d8e8landley /* center dialog box on screen */ 2045257cf54a5810105bc4a75703a06740d756d8e8landley x = (COLS - width) / 2; 2055257cf54a5810105bc4a75703a06740d756d8e8landley y = (LINES - height) / 2; 2065257cf54a5810105bc4a75703a06740d756d8e8landley 2075257cf54a5810105bc4a75703a06740d756d8e8landley draw_shadow(stdscr, y, x, height, width); 2085257cf54a5810105bc4a75703a06740d756d8e8landley 2095257cf54a5810105bc4a75703a06740d756d8e8landley dialog = newwin(height, width, y, x); 2105257cf54a5810105bc4a75703a06740d756d8e8landley keypad(dialog, TRUE); 2115257cf54a5810105bc4a75703a06740d756d8e8landley 2125257cf54a5810105bc4a75703a06740d756d8e8landley draw_box(dialog, 0, 0, height, width, 2135257cf54a5810105bc4a75703a06740d756d8e8landley dlg.dialog.atr, dlg.border.atr); 2145257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(dialog, dlg.border.atr); 2155257cf54a5810105bc4a75703a06740d756d8e8landley mvwaddch(dialog, height - 3, 0, ACS_LTEE); 2165257cf54a5810105bc4a75703a06740d756d8e8landley for (i = 0; i < width - 2; i++) 2175257cf54a5810105bc4a75703a06740d756d8e8landley waddch(dialog, ACS_HLINE); 2185257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(dialog, dlg.dialog.atr); 2195257cf54a5810105bc4a75703a06740d756d8e8landley wbkgdset(dialog, dlg.dialog.atr & A_COLOR); 2205257cf54a5810105bc4a75703a06740d756d8e8landley waddch(dialog, ACS_RTEE); 2215257cf54a5810105bc4a75703a06740d756d8e8landley 2225257cf54a5810105bc4a75703a06740d756d8e8landley print_title(dialog, title, width); 2235257cf54a5810105bc4a75703a06740d756d8e8landley 2245257cf54a5810105bc4a75703a06740d756d8e8landley wattrset(dialog, dlg.dialog.atr); 2255257cf54a5810105bc4a75703a06740d756d8e8landley print_autowrap(dialog, prompt, width - 2, 1, 3); 2265257cf54a5810105bc4a75703a06740d756d8e8landley 2275257cf54a5810105bc4a75703a06740d756d8e8landley menu_width = width - 6; 2285257cf54a5810105bc4a75703a06740d756d8e8landley box_y = height - menu_height - 5; 2295257cf54a5810105bc4a75703a06740d756d8e8landley box_x = (width - menu_width) / 2 - 1; 2305257cf54a5810105bc4a75703a06740d756d8e8landley 2315257cf54a5810105bc4a75703a06740d756d8e8landley /* create new window for the menu */ 2325257cf54a5810105bc4a75703a06740d756d8e8landley menu = subwin(dialog, menu_height, menu_width, 2335257cf54a5810105bc4a75703a06740d756d8e8landley y + box_y + 1, x + box_x + 1); 2345257cf54a5810105bc4a75703a06740d756d8e8landley keypad(menu, TRUE); 2355257cf54a5810105bc4a75703a06740d756d8e8landley 2365257cf54a5810105bc4a75703a06740d756d8e8landley /* draw a box around the menu items */ 2375257cf54a5810105bc4a75703a06740d756d8e8landley draw_box(dialog, box_y, box_x, menu_height + 2, menu_width + 2, 2385257cf54a5810105bc4a75703a06740d756d8e8landley dlg.menubox_border.atr, dlg.menubox.atr); 2395257cf54a5810105bc4a75703a06740d756d8e8landley 2405257cf54a5810105bc4a75703a06740d756d8e8landley if (menu_width >= 80) 2415257cf54a5810105bc4a75703a06740d756d8e8landley item_x = (menu_width - 70) / 2; 2425257cf54a5810105bc4a75703a06740d756d8e8landley else 2435257cf54a5810105bc4a75703a06740d756d8e8landley item_x = 4; 2445257cf54a5810105bc4a75703a06740d756d8e8landley 2455257cf54a5810105bc4a75703a06740d756d8e8landley /* Set choice to default item */ 2465257cf54a5810105bc4a75703a06740d756d8e8landley item_foreach() 2475257cf54a5810105bc4a75703a06740d756d8e8landley if (selected && (selected == item_data())) 2485257cf54a5810105bc4a75703a06740d756d8e8landley choice = item_n(); 2495257cf54a5810105bc4a75703a06740d756d8e8landley /* get the saved scroll info */ 2505257cf54a5810105bc4a75703a06740d756d8e8landley scroll = *s_scroll; 2515257cf54a5810105bc4a75703a06740d756d8e8landley if ((scroll <= choice) && (scroll + max_choice > choice) && 2525257cf54a5810105bc4a75703a06740d756d8e8landley (scroll >= 0) && (scroll + max_choice <= item_count())) { 2535257cf54a5810105bc4a75703a06740d756d8e8landley first_item = scroll; 2545257cf54a5810105bc4a75703a06740d756d8e8landley choice = choice - scroll; 2555257cf54a5810105bc4a75703a06740d756d8e8landley } else { 2565257cf54a5810105bc4a75703a06740d756d8e8landley scroll = 0; 2575257cf54a5810105bc4a75703a06740d756d8e8landley } 2585257cf54a5810105bc4a75703a06740d756d8e8landley if ((choice >= max_choice)) { 2595257cf54a5810105bc4a75703a06740d756d8e8landley if (choice >= item_count() - max_choice / 2) 2605257cf54a5810105bc4a75703a06740d756d8e8landley scroll = first_item = item_count() - max_choice; 2615257cf54a5810105bc4a75703a06740d756d8e8landley else 2625257cf54a5810105bc4a75703a06740d756d8e8landley scroll = first_item = choice - max_choice / 2; 2635257cf54a5810105bc4a75703a06740d756d8e8landley choice = choice - scroll; 2645257cf54a5810105bc4a75703a06740d756d8e8landley } 2655257cf54a5810105bc4a75703a06740d756d8e8landley 2665257cf54a5810105bc4a75703a06740d756d8e8landley /* Print the menu */ 2675257cf54a5810105bc4a75703a06740d756d8e8landley for (i = 0; i < max_choice; i++) { 2685257cf54a5810105bc4a75703a06740d756d8e8landley print_item(first_item + i, i, i == choice); 2695257cf54a5810105bc4a75703a06740d756d8e8landley } 2705257cf54a5810105bc4a75703a06740d756d8e8landley 2715257cf54a5810105bc4a75703a06740d756d8e8landley wnoutrefresh(menu); 2725257cf54a5810105bc4a75703a06740d756d8e8landley 2735257cf54a5810105bc4a75703a06740d756d8e8landley print_arrows(dialog, item_count(), scroll, 2745257cf54a5810105bc4a75703a06740d756d8e8landley box_y, box_x + item_x + 1, menu_height); 2755257cf54a5810105bc4a75703a06740d756d8e8landley 2765257cf54a5810105bc4a75703a06740d756d8e8landley print_buttons(dialog, height, width, 0); 2775257cf54a5810105bc4a75703a06740d756d8e8landley wmove(menu, choice, item_x + 1); 2785257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(menu); 2795257cf54a5810105bc4a75703a06740d756d8e8landley 2805257cf54a5810105bc4a75703a06740d756d8e8landley while (key != KEY_ESC) { 2815257cf54a5810105bc4a75703a06740d756d8e8landley key = wgetch(menu); 2825257cf54a5810105bc4a75703a06740d756d8e8landley 2835257cf54a5810105bc4a75703a06740d756d8e8landley if (key < 256 && isalpha(key)) 2845257cf54a5810105bc4a75703a06740d756d8e8landley key = tolower(key); 2855257cf54a5810105bc4a75703a06740d756d8e8landley 2865257cf54a5810105bc4a75703a06740d756d8e8landley if (strchr("ynmh", key)) 2875257cf54a5810105bc4a75703a06740d756d8e8landley i = max_choice; 2885257cf54a5810105bc4a75703a06740d756d8e8landley else { 2895257cf54a5810105bc4a75703a06740d756d8e8landley for (i = choice + 1; i < max_choice; i++) { 2905257cf54a5810105bc4a75703a06740d756d8e8landley item_set(scroll + i); 2915257cf54a5810105bc4a75703a06740d756d8e8landley j = first_alpha(item_str(), "YyNnMmHh"); 2925257cf54a5810105bc4a75703a06740d756d8e8landley if (key == tolower(item_str()[j])) 2935257cf54a5810105bc4a75703a06740d756d8e8landley break; 2945257cf54a5810105bc4a75703a06740d756d8e8landley } 2955257cf54a5810105bc4a75703a06740d756d8e8landley if (i == max_choice) 2965257cf54a5810105bc4a75703a06740d756d8e8landley for (i = 0; i < max_choice; i++) { 2975257cf54a5810105bc4a75703a06740d756d8e8landley item_set(scroll + i); 2985257cf54a5810105bc4a75703a06740d756d8e8landley j = first_alpha(item_str(), "YyNnMmHh"); 2995257cf54a5810105bc4a75703a06740d756d8e8landley if (key == tolower(item_str()[j])) 3005257cf54a5810105bc4a75703a06740d756d8e8landley break; 3015257cf54a5810105bc4a75703a06740d756d8e8landley } 3025257cf54a5810105bc4a75703a06740d756d8e8landley } 3035257cf54a5810105bc4a75703a06740d756d8e8landley 3045257cf54a5810105bc4a75703a06740d756d8e8landley if (i < max_choice || 3055257cf54a5810105bc4a75703a06740d756d8e8landley key == KEY_UP || key == KEY_DOWN || 3065257cf54a5810105bc4a75703a06740d756d8e8landley key == '-' || key == '+' || 3075257cf54a5810105bc4a75703a06740d756d8e8landley key == KEY_PPAGE || key == KEY_NPAGE) { 3085257cf54a5810105bc4a75703a06740d756d8e8landley /* Remove highligt of current item */ 3095257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll + choice, choice, FALSE); 3105257cf54a5810105bc4a75703a06740d756d8e8landley 3115257cf54a5810105bc4a75703a06740d756d8e8landley if (key == KEY_UP || key == '-') { 3125257cf54a5810105bc4a75703a06740d756d8e8landley if (choice < 2 && scroll) { 3135257cf54a5810105bc4a75703a06740d756d8e8landley /* Scroll menu down */ 3145257cf54a5810105bc4a75703a06740d756d8e8landley do_scroll(menu, &scroll, -1); 3155257cf54a5810105bc4a75703a06740d756d8e8landley 3165257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll, 0, FALSE); 3175257cf54a5810105bc4a75703a06740d756d8e8landley } else 3185257cf54a5810105bc4a75703a06740d756d8e8landley choice = MAX(choice - 1, 0); 3195257cf54a5810105bc4a75703a06740d756d8e8landley 3205257cf54a5810105bc4a75703a06740d756d8e8landley } else if (key == KEY_DOWN || key == '+') { 3215257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll+choice, choice, FALSE); 3225257cf54a5810105bc4a75703a06740d756d8e8landley 3235257cf54a5810105bc4a75703a06740d756d8e8landley if ((choice > max_choice - 3) && 3245257cf54a5810105bc4a75703a06740d756d8e8landley (scroll + max_choice < item_count())) { 3255257cf54a5810105bc4a75703a06740d756d8e8landley /* Scroll menu up */ 3265257cf54a5810105bc4a75703a06740d756d8e8landley do_scroll(menu, &scroll, 1); 3275257cf54a5810105bc4a75703a06740d756d8e8landley 3285257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll+max_choice - 1, 3295257cf54a5810105bc4a75703a06740d756d8e8landley max_choice - 1, FALSE); 3305257cf54a5810105bc4a75703a06740d756d8e8landley } else 3315257cf54a5810105bc4a75703a06740d756d8e8landley choice = MIN(choice + 1, max_choice - 1); 3325257cf54a5810105bc4a75703a06740d756d8e8landley 3335257cf54a5810105bc4a75703a06740d756d8e8landley } else if (key == KEY_PPAGE) { 3345257cf54a5810105bc4a75703a06740d756d8e8landley scrollok(menu, TRUE); 3355257cf54a5810105bc4a75703a06740d756d8e8landley for (i = 0; (i < max_choice); i++) { 3365257cf54a5810105bc4a75703a06740d756d8e8landley if (scroll > 0) { 3375257cf54a5810105bc4a75703a06740d756d8e8landley do_scroll(menu, &scroll, -1); 3385257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll, 0, FALSE); 3395257cf54a5810105bc4a75703a06740d756d8e8landley } else { 3405257cf54a5810105bc4a75703a06740d756d8e8landley if (choice > 0) 3415257cf54a5810105bc4a75703a06740d756d8e8landley choice--; 3425257cf54a5810105bc4a75703a06740d756d8e8landley } 3435257cf54a5810105bc4a75703a06740d756d8e8landley } 3445257cf54a5810105bc4a75703a06740d756d8e8landley 3455257cf54a5810105bc4a75703a06740d756d8e8landley } else if (key == KEY_NPAGE) { 3465257cf54a5810105bc4a75703a06740d756d8e8landley for (i = 0; (i < max_choice); i++) { 3475257cf54a5810105bc4a75703a06740d756d8e8landley if (scroll + max_choice < item_count()) { 3485257cf54a5810105bc4a75703a06740d756d8e8landley do_scroll(menu, &scroll, 1); 3495257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll+max_choice-1, 3505257cf54a5810105bc4a75703a06740d756d8e8landley max_choice - 1, FALSE); 3515257cf54a5810105bc4a75703a06740d756d8e8landley } else { 3525257cf54a5810105bc4a75703a06740d756d8e8landley if (choice + 1 < max_choice) 3535257cf54a5810105bc4a75703a06740d756d8e8landley choice++; 3545257cf54a5810105bc4a75703a06740d756d8e8landley } 3555257cf54a5810105bc4a75703a06740d756d8e8landley } 3565257cf54a5810105bc4a75703a06740d756d8e8landley } else 3575257cf54a5810105bc4a75703a06740d756d8e8landley choice = i; 3585257cf54a5810105bc4a75703a06740d756d8e8landley 3595257cf54a5810105bc4a75703a06740d756d8e8landley print_item(scroll + choice, choice, TRUE); 3605257cf54a5810105bc4a75703a06740d756d8e8landley 3615257cf54a5810105bc4a75703a06740d756d8e8landley print_arrows(dialog, item_count(), scroll, 3625257cf54a5810105bc4a75703a06740d756d8e8landley box_y, box_x + item_x + 1, menu_height); 3635257cf54a5810105bc4a75703a06740d756d8e8landley 3645257cf54a5810105bc4a75703a06740d756d8e8landley wnoutrefresh(dialog); 3655257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(menu); 3665257cf54a5810105bc4a75703a06740d756d8e8landley 3675257cf54a5810105bc4a75703a06740d756d8e8landley continue; /* wait for another key press */ 3685257cf54a5810105bc4a75703a06740d756d8e8landley } 3695257cf54a5810105bc4a75703a06740d756d8e8landley 3705257cf54a5810105bc4a75703a06740d756d8e8landley switch (key) { 3715257cf54a5810105bc4a75703a06740d756d8e8landley case KEY_LEFT: 3725257cf54a5810105bc4a75703a06740d756d8e8landley case TAB: 3735257cf54a5810105bc4a75703a06740d756d8e8landley case KEY_RIGHT: 3745257cf54a5810105bc4a75703a06740d756d8e8landley button = ((key == KEY_LEFT ? --button : ++button) < 0) 3755257cf54a5810105bc4a75703a06740d756d8e8landley ? 2 : (button > 2 ? 0 : button); 3765257cf54a5810105bc4a75703a06740d756d8e8landley 3775257cf54a5810105bc4a75703a06740d756d8e8landley print_buttons(dialog, height, width, button); 3785257cf54a5810105bc4a75703a06740d756d8e8landley wrefresh(menu); 3795257cf54a5810105bc4a75703a06740d756d8e8landley break; 3805257cf54a5810105bc4a75703a06740d756d8e8landley case ' ': 3815257cf54a5810105bc4a75703a06740d756d8e8landley case 's': 3825257cf54a5810105bc4a75703a06740d756d8e8landley case 'y': 3835257cf54a5810105bc4a75703a06740d756d8e8landley case 'n': 3845257cf54a5810105bc4a75703a06740d756d8e8landley case 'm': 3855257cf54a5810105bc4a75703a06740d756d8e8landley case '/': 3865257cf54a5810105bc4a75703a06740d756d8e8landley /* save scroll info */ 3875257cf54a5810105bc4a75703a06740d756d8e8landley *s_scroll = scroll; 3885257cf54a5810105bc4a75703a06740d756d8e8landley delwin(menu); 3895257cf54a5810105bc4a75703a06740d756d8e8landley delwin(dialog); 3905257cf54a5810105bc4a75703a06740d756d8e8landley item_set(scroll + choice); 3915257cf54a5810105bc4a75703a06740d756d8e8landley item_set_selected(1); 3925257cf54a5810105bc4a75703a06740d756d8e8landley switch (key) { 3935257cf54a5810105bc4a75703a06740d756d8e8landley case 's': 3945257cf54a5810105bc4a75703a06740d756d8e8landley return 3; 3955257cf54a5810105bc4a75703a06740d756d8e8landley case 'y': 3965257cf54a5810105bc4a75703a06740d756d8e8landley return 3; 3975257cf54a5810105bc4a75703a06740d756d8e8landley case 'n': 3985257cf54a5810105bc4a75703a06740d756d8e8landley return 4; 3995257cf54a5810105bc4a75703a06740d756d8e8landley case 'm': 4005257cf54a5810105bc4a75703a06740d756d8e8landley return 5; 4015257cf54a5810105bc4a75703a06740d756d8e8landley case ' ': 4025257cf54a5810105bc4a75703a06740d756d8e8landley return 6; 4035257cf54a5810105bc4a75703a06740d756d8e8landley case '/': 4045257cf54a5810105bc4a75703a06740d756d8e8landley return 7; 4055257cf54a5810105bc4a75703a06740d756d8e8landley } 4065257cf54a5810105bc4a75703a06740d756d8e8landley return 0; 4075257cf54a5810105bc4a75703a06740d756d8e8landley case 'h': 4085257cf54a5810105bc4a75703a06740d756d8e8landley case '?': 4095257cf54a5810105bc4a75703a06740d756d8e8landley button = 2; 4105257cf54a5810105bc4a75703a06740d756d8e8landley case '\n': 4115257cf54a5810105bc4a75703a06740d756d8e8landley *s_scroll = scroll; 4125257cf54a5810105bc4a75703a06740d756d8e8landley delwin(menu); 4135257cf54a5810105bc4a75703a06740d756d8e8landley delwin(dialog); 4145257cf54a5810105bc4a75703a06740d756d8e8landley item_set(scroll + choice); 4155257cf54a5810105bc4a75703a06740d756d8e8landley item_set_selected(1); 4165257cf54a5810105bc4a75703a06740d756d8e8landley return button; 4175257cf54a5810105bc4a75703a06740d756d8e8landley case 'e': 4185257cf54a5810105bc4a75703a06740d756d8e8landley case 'x': 4195257cf54a5810105bc4a75703a06740d756d8e8landley key = KEY_ESC; 4205257cf54a5810105bc4a75703a06740d756d8e8landley break; 4215257cf54a5810105bc4a75703a06740d756d8e8landley case KEY_ESC: 4225257cf54a5810105bc4a75703a06740d756d8e8landley key = on_key_esc(menu); 4235257cf54a5810105bc4a75703a06740d756d8e8landley break; 4245257cf54a5810105bc4a75703a06740d756d8e8landley case KEY_RESIZE: 4255257cf54a5810105bc4a75703a06740d756d8e8landley on_key_resize(); 4265257cf54a5810105bc4a75703a06740d756d8e8landley delwin(menu); 4275257cf54a5810105bc4a75703a06740d756d8e8landley delwin(dialog); 4285257cf54a5810105bc4a75703a06740d756d8e8landley goto do_resize; 4295257cf54a5810105bc4a75703a06740d756d8e8landley } 4305257cf54a5810105bc4a75703a06740d756d8e8landley } 4315257cf54a5810105bc4a75703a06740d756d8e8landley delwin(menu); 4325257cf54a5810105bc4a75703a06740d756d8e8landley delwin(dialog); 4335257cf54a5810105bc4a75703a06740d756d8e8landley return key; /* ESC pressed */ 4345257cf54a5810105bc4a75703a06740d756d8e8landley} 435