Форум сайта python.su
0
Привет!
Написал простой тестовый примерчик и не могу понять, почему не работает ф-я up_down(inc)
И, если кто-нибудь подскажет как более правильно написать менюшку, по которой можно будет передвигать с помощью стрелок (так что бы строки подсвечивались), буду благодарен)
#!/usr/bin/python3 # -*- coding: utf-8 -*- import curses def init_curses(): stdscr = curses.initscr() curses.noecho() curses.cbreak() stdscr.keypad(1) curses.start_color() curses.init_pair(1, curses.COLOR_YELLOW, curses.COLOR_BLACK) stdscr.bkgd(curses.color_pair(1)) stdscr.refresh() return stdscr def show_menu(stdscr): stdscr.clear() stdscr.box() stdscr.addstr(1,1, '1') stdscr.addstr(2,1, '2') stdscr.addstr(3,1, '3') stdscr.addstr(4,1, 'Q:Exit') stdscr.refresh() def up_down(inc): stdscr.clear() stdscr.box() if inc == 1: stdscr.addstr(10,1, 'key_up') elif inc == -1: stdscr.addstr(11,1, 'key_down') stdscr.refresh() stdscr = init_curses() while True: show_menu(stdscr) c = stdscr.getch() if c == ord('q') or c == ord('Q'): break elif c == curses.KEY_UP: up_down(1) elif c == curses.KEY_DOWN: up_down(-1) curses.nocbreak() stdscr.keypad(0) curses.echo() curses.endwin()
Отредактировано __sirroko (Апрель 11, 2013 01:20:49)
Офлайн
0
Доброго времени суток!
Снова возникли сложности с curses. Но на этот раз разобраться самостоятельно не получается 
Строки, на которых программа завершается с ошибкой, отмечены комментариями.
Код постарался прокомментировать. Главным образом интересуют функции show_processes, up_down и последние 5 строк из __init__, т.к. баг притаился где-то там…
Ошибка: addstr() returned ERR
Код:
#!/usr/bin/python3 # -*- coding: utf-8 -*- import curses # import psutil # требует дополнительной установки class stdscr: processes_list = ['31111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11111','11112'] def __init__(self): self.win = curses.initscr() curses.noecho() curses.cbreak() curses.curs_set(0) # убираем курсор self.win.keypad(1) self.win.refresh() curses.start_color() # header curses.init_pair(1, curses.COLOR_BLACK, curses.COLOR_BLUE) # processes # не под курсором curses.init_pair(2, curses.COLOR_BLACK, curses.COLOR_WHITE) # под курсором curses.init_pair(3, curses.COLOR_WHITE, curses.COLOR_BLUE) # menubar curses.init_pair(4, curses.COLOR_BLACK, curses.COLOR_BLUE) self.w_header = curses.newwin(1, curses.COLS, 0, 0) self.w_header.bkgd(curses.color_pair(1)) self.w_processes = curses.newwin(curses.LINES - 2, curses.COLS, 1, 0) self.w_processes.bkgd(curses.color_pair(2)) self.w_menubar = curses.newwin(1, curses.COLS, curses.LINES - 1, 0) self.w_menubar.bkgd(curses.color_pair(4)) # корректный вывод текста на экран self.start_line = 0 # смещение начально строки (на случай добавления рамки) self.cur_index = 0 # индекс текущего элемента в списке processes_list # выделение области списка processes_list, которая в текущий момент выводится на экран self.min_index = 0 self.max_row = curses.LINES - 2 # максимальное кол-во строк, умещающееся в текущее окно def show_header(self): self.w_header.clear() self.w_header.addstr(0, 0, 'header') self.w_header.refresh() def show_processes(self): self.w_processes.clear() # в цилке выводится только опредленная область списка (границы min_index, min_index + max_row) for i in range(self.min_index, self.min_index + self.max_row): if i == len(self.processes_list): break if i == self.cur_index: # ругается на эти строки self.win.addstr(i - self.min_index + self.max_row, 1, self.processes_list[i], curses.color_pair(2)) else: # ругается на эти строки self.win.addstr(i - self.min_index + self.max_row, 1, self.processes_list[i]) self.w_processes.refresh() def show_menubar(self): self.w_menubar.clear() self.w_menubar.addstr(0, 0, 'menubar') self.w_menubar.refresh() # шагательный механизм def up_down(self, inc): tmp = self.cur_index + inc # новый индекс в списке, на который мы попадаем после key_up, key_down if tmp >= 0 and tmp < len(self.processes_list): # если мы достигаем крайних элементов, выведенных на экран, то смещаем область просмотра в списке if tmp < (self.min_index) or tmp >= (self.min_index + self.max_row): self.min_index += inc self.cur_index = tmp self.show_processes() def main_loop(self): self.show_header() self.show_processes() self.show_menubar() while True: key = self.win.getch() if key == ord('q') or key == ord('Q'): break elif key == curses.KEY_DOWN: self.up_down(1) elif key == curses.KEY_UP: self.up_down(-1) def restore_screen(self): self.win.keypad(0) curses.nocbreak() curses.echo() curses.endwin() class task_manager: def __init__(self): pass def kill_process(self): pass def refresh_processes(self): pass def main(): try: scr = stdscr() scr.main_loop() except Exception as err: scr.win.clear() scr.win.addstr(1, 1, str(err)) scr.win.refresh() scr.win.getch() finally: scr.restore_screen() if __name__ == '__main__': main()

Отредактировано __sirroko (Апрель 11, 2013 01:29:47)
Офлайн
0
Кажется, я сам с собой тут общаюсь…
Но да ладно, ошибку я все-таки нашел)
Если кому-нибудь интересно, то, на всякий случай, выкладываю код правильной функции show_processes:
def show_processes(self): self.w_processes.clear() # в цилке выводится только опредленная область списка (границы min_index, min_index + max_row) for i in range(self.min_index, self.min_index + self.max_row): if i == len(self.processes_list): break if i == self.cur_index: # ругаЛся на эти строки # не win, а w_processes, и + self.max_row не нужно было прибавлять # оно давало больше смещение, и текст писался в несуществующую строку self.w_processes.addstr(i - self.min_index, 1, self.processes_list[i], curses.color_pair(3)) else: # ругаЛся на эти строки self.w_processes.addstr(i - self.min_index, 1, self.processes_list[i]) self.w_processes.refresh()
Отредактировано __sirroko (Апрель 11, 2013 20:00:51)
Офлайн