2009-02-06 14 views
8

Jestem prototypowanie aplikacji Python z modułem cmd.paginacja z modułem cmd Pythona

Niektóre wiadomości do użytkownika będą dość długie i chciałbym je paginować. Pojawi się pierwszych 10 (lub numer konfigurowalny) wiadomości, a naciśnięcie klawisza SPACJA wyświetli następną stronę, aż do końca wiadomości.

Nie chcę czegoś tutaj wymyślić, czy istnieje prosty sposób na wdrożenie tej funkcji?

Odpowiedz

4

Prostą rzeczą byłoby po prostu przekierowanie skryptu przez "mniej" lub podobne polecenie w czasie wykonywania.

Oto prosta metoda, która ma w przybliżeniu to, co chcesz, ale:

def print_and_wait(some_long_message): 
    lines = some_long_message.split('\n') 
    i=0 
    while i < len(lines): 
     print '\n'.join(lines[i:i+10]) 
     raw_input("press enter to read more...") 
     i += 10 

Można również zajrzeć do korzystania przekleństwa.

+0

Dzięki, ale mniejszy przerywnik uniemożliwi interakcję, co jest celem modułu cmd. Wdrożenie rozwiązania curses daleko wykracza poza pierwszą wersję roboczą, którą chcę zbudować za pomocą modułu cmd. Jednak twoje rozwiązanie print_and_wait jest dobrym początkiem (nie działało jak jest). – Gra

3

Jak powiedział Yoni, właściwą metodą jest automatyczne drukowanie stron w obrębie uruchomionej instancji cmd. Konstruktor Cmd przyjmuje argumenty stdin i stdout. Tak proste dostarczają obiekt, który działa jak standardowe wyjście i obsługuje metodę drukowania stronicowania.

class PagingStdOut(object): 
    def write(self, buffer, lines_before_pause=40): 
     # do magic paging here... 
0

przywoławcze podprogramy można znaleźć w aktach IPythongenutils.py (patrz page lub page_dumb na prostsze). Kod jest trochę skomplikowany, ale prawdopodobnie jest nieunikniony, jeśli próbujesz być przenośny dla systemów, w tym Windows i różnych rodzajów emulatorów terminali.

+0

Dzięki, zaimplementowałem już procedury przywoławcze. Zobaczę, co przegapiłem w plikach, które wskazałeś. Obecnie działa w moim systemie operacyjnym, ale nie testowałem niczego innego, więc przenośne ulepszenia mogą być przydatne. – Gra

1

Miałem to samo pytanie. Na stronie pydoc module jest wbudowany pager. Włączyłem go w ten sposób (co uważam za hackowskie i niesatysfakcjonujące ... jestem jednak otwarty na lepsze pomysły).

Podoba mi się pomysł, że będzie on działał automatycznie, jeśli jest więcej niż x wyników i jest włączona obsługa stronicowania, którą można zaimplementować, ale nie można jej tutaj wykonać.

import cmd 
from pydoc import pager 
from cStringIO import StringIO 
import sys 

PAGER = True 
class Commander(cmd.Cmd): 
    prompt = "> " 
    def do_pager(self,line): 
     global PAGER 
     line = line + " 1" 
     tokens = line.lower().split() 
     if tokens[0] in ("on","true","t", "1"): 
      PAGER = True 
      print "# setting PAGER True" 
     elif tokens[0] in ("off","false","f","0"): 
      PAGER = False 
      print "# setting PAGER False" 
     else: 
      print "# can't set pager: don't know -> %s" % tokens[0] 

    def do_demo(self,line): 
     results = dict(a=1,b=2,c=3) 
     self.format_commandline_results(results) 

    def format_commandline_results(self,results): 
     if PAGER: 
      ofh = StringIO() 
     else: 
      ofh = sys.stdout 

     for (k,v) in sorted(results.items()): 
      print >> ofh, "%s -> %s" % (k,v) 

     if PAGER: 
      ofh.seek(0) 
      pager(ofh.read()) 

     return None 

    def do_EOF(self,line): 
     print "", 
     return True 

if __name__ == "__main__": 
    Commander().cmdloop("# try: \n> pager off \n> demo \n> pager on \n> demo \n\n")