::requires 'ooSQLite.cls' ::requires "rxunixsys" LIBRARY ::requires 'ncurses.cls' ::requires 'app/utils.rex' ::class AddressBookUI public ::method init expose win mainMenu return ::method initialize expose win mainMenu win = self~DrawMainPanel(0, .true) /* default colour, draw border box */ self~setupMainMenu(win) return ::METHOD DrawMainPanel use arg clrset, with_box win = .window~new() /* The first invocation must be with no arguments */ win~curs_set(0) /* Hide the cursor by default */ win~keypad(1) /* Enable function keys and arrow keys */ win~raw win~noecho win~clear win~cbreak self~SetPanelColor(win, clrset) if with_box = .true then DO win~box(0, 0) /* Draw box with default ACS characters */ win~refresh END return win ::METHOD DrawSubPanel use arg height, width, starty, startx, clrset, title, with_box new_win = .window~new(height, width, starty, startx) new_win~curs_set(0) /* Set the panel color */ self~SetPanelColor(new_win, clrset) /* Display title */ new_win~attron(new_win~A_BOLD) new_win~mvaddstr(starty-(starty-2), (width - title~length) % 2, title) new_win~attroff(new_win~A_BOLD) new_win~refresh if with_box = .true then DO new_win~box(0,0) new_win~refresh END return new_win ::METHOD SetPanelColor use arg panel, clrset panel~start_color() SELECT /* white text on blue background */ when clrset = 1 then panel~init_pair(2, panel~COLOR_WHITE, panel~COLOR_BLUE) /* white text on grey background */ when clrset = 2 then panel~init_pair(3, panel~COLOR_WHITE, panel~COLOR_GREEN) /* yellow text on red background */ when clrset = 3 then panel~init_pair(4, panel~COLOR_YELLOW, panel~COLOR_RED) /* black text on white background */ when clrset = 4 then panel~init_pair(5, panel~COLOR_BLACK, panel~COLOR_WHITE) /* black text on green background */ when clrset = 5 then panel~init_pair(6, panel~COLOR_BLACK, panel~COLOR_GREEN) /* black text on cyan background */ when clrset = 6 then panel~init_pair(7, panel~COLOR_BLACK, panel~COLOR_CYAN) /* Default to white text on black background */ OTHERWISE DO clrset=0 panel~init_pair(1, panel~COLOR_WHITE, panel~COLOR_BLACK) END END panel~bkgd(panel~color_pair(clrset+1)) panel~refresh RETURN ::method setupMainMenu expose mainMenu menuwin menu_items menu_keys selected use arg win max_y = win~lines max_x = win~cols menu_height = 21 menu_width = 40 start_y = (max_y - menu_height) % 2 start_x = (max_x - menu_width) % 2 clrset=1 title = "Rexx Address Book" with_box = .true menuwin = self~DrawSubPanel(menu_height, menu_width, start_y, start_x, clrset, title, with_box) menu_items = .array~of("[A]dd Contact", "[R]emove Contact", "[E]dit Contact", "[S]earch", "[L]ist All", "[Q]uit") menu_keys = .array~of("a", "r", "e", "s", "l", "q") /* Display menu items */ .environment~selected = 1 self~DrawMenu(menuwin, menu_items, .environment~selected, win) menuwin~refresh RETURN ::method DrawMenu expose win menu_items menu_keys selected mainwin use arg menuwin, items, selected, mainwin do i = 1 to items~items if i = .environment~selected then do menuwin~attron(menuwin~attron(menuwin~A_REVERSE)) menuwin~attron(menuwin~A_BOLD) menuwin~mvaddstr(i+3, 2, items[i]) menuwin~attroff(menuwin~A_REVERSE) menuwin~attroff(menuwin~A_BOLD) end else do menuwin~mvaddstr(i+3, 2, items[i]) end end menuwin~refresh return /** MAIN LOOP **/ ::method mainLoop expose win mainMenu menuwin selected menu_items menu_keys menuwin~refresh running = .true do while running key = win~getch old_selected = .environment~selected select when key = menuwin~KEY_UP then do if .environment~selected > 1 then .environment~selected = .environment~selected - 1 self~DrawMenu(menuwin, menu_items, .environment~selected, win) menuwin~refresh end when key = menuwin~KEY_DOWN then do if .environment~selected < menu_items~items then .environment~selected = .environment~selected + 1 self~DrawMenu(menuwin, menu_items, .environment~selected, win) menuwin~refresh end when key = D2C(81) | key = D2C(113) | key = "q" | key = C2D("q") then do menuwin~endwin .environment['STOPNOW'] = 1 RETURN end when key = D2C(10) | key = D2C(13) then do /* Enter key - numeric codes only */ menuwin~refresh self~ProcessSelection(menuwin, menu_keys[.environment~selected]) return end otherwise do if datatype(key) = 'CHAR' then do key = lower(key) pos = self~findInArray(menu_keys, key) if pos > 0 then do menuwin~mvaddstr(19 - 1, 18, "Letter selection ["||key||"]") menuwin~refresh call SysWait 0.5 self~ProcessSelection(menuwin, key) return end end end /* otherwise */ end /* select */ /* Only redraw if selection changed */ if old_selected \= .environment~selected then do self~DrawMenu(menuwin, menu_items, .environment~selected, win) end end /* do while running */ return /* Process selection */ ::METHOD ProcessSelection expose menu_items menu_keys use arg menuwin, key_char select when key_char = 'a' then do menuwin~mvaddstr(19 - 3, 5, "I would launch the ADD panel "); menuwin~refresh call SysWait 1 END when key_char = 'r' then do menuwin~mvaddstr(19 - 3, 5, "I would launch the REMOVE panel "); menuwin~refresh call SysWait 1 END when key_char = 'e' then do menuwin~mvaddstr(19 - 3, 5, "I would launch the EDIT panel "); menuwin~refresh call SysWait 1 END when key_char = 's' then do menuwin~mvaddstr(19 - 3, 5, "I would launch the SEARCH panel "); menuwin~refresh call SysWait 1 END when key_char = 'l' then do menuwin~mvaddstr(19 - 3, 5, "I would launch the LIST panel ") menuwin~refresh call SysWait 1 END when key_char = 'q' then do menuwin~mvaddstr(19 - 3, 5, "Exiting The Application... "); menuwin~refresh call SysWait 1 menuwin~endwin .environment['STOPNOW'] = 1 END otherwise nop end return ::METHOD findInArray use arg array, item do i = 1 to array~items if array[i] = item then return i end return 0 /* Not found */ ::method cleanup expose win /* Clean up ncurses */ win~endwin return