
Le choix par defaut ne marchait pas. darcs-hash:20071218005218-af139-a0606ebac7075654f6fc833b7e1ca97cbfd31cb9.gz
100 lines
3.7 KiB
Python
100 lines
3.7 KiB
Python
# -*- coding: utf-8 -*-
|
|
#
|
|
# interactive.py
|
|
# --------------
|
|
#
|
|
# Copyright (C) 2007 Jeremie Dimino <jeremie@dimino.org>
|
|
#
|
|
# This file is free software; you can redistribute it and/or modify
|
|
# it under the terms of the GNU General Public License as published by
|
|
# the Free Software Foundation; either version 2 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# This file is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program; if not, write to the Free Software
|
|
# Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
|
|
|
|
'''Utilitaire pour poser des questions de manières interactives
|
|
à l'utilisateur, à la manière de darcs.'''
|
|
|
|
import os, sys, tty, termios
|
|
from affich_tools import cprint
|
|
|
|
__all__ = ["getch", "ask", "Exit"]
|
|
|
|
def getch():
|
|
fd = sys.stdin.fileno()
|
|
try:
|
|
mode = termios.tcgetattr(fd)
|
|
except:
|
|
return os.read(fd, 1)
|
|
try:
|
|
tty.setraw(fd)
|
|
return os.read(fd, 1)
|
|
finally:
|
|
termios.tcsetattr(fd, termios.TCSAFLUSH, mode)
|
|
|
|
# Constantes de choix
|
|
Exit = ("q", "quitter le programme", None, lambda: sys.exit(0))
|
|
|
|
def ask(message, choices):
|
|
'''Pose une question à l'utilisateur.
|
|
choices est une liste d'élément de la forme (choix) ou (choix, doc)
|
|
ou (choix, doc, valeur) ou encore (choix, doc, valeur, operation), où:
|
|
- choix sont les lettres pour le choix, si une est en majuscule alors
|
|
ce choix est celui par défaut.
|
|
- doc est une description du choix
|
|
- valeur est la valeur renvoyée si ce choix est fait, par défaut c'est choix[0].lower()
|
|
- operation est soit une fonction, auquel cas elle est éxécutée si le choix est fait
|
|
(et le questionnement continue si elle renoie vrai),
|
|
soit un tuple sur lequel ask est éxécutée,
|
|
soit une chaîne qui est affichée'''
|
|
while True:
|
|
cprint("%s [%s], ou ? pour l'aide: " % (message, "".join([c[0] for c in choices])), "bleu", newline=False)
|
|
sys.stdout.flush()
|
|
answer = getch()
|
|
sys.stdout.write(answer+"\n")
|
|
if answer in ['\x03', '\x04']:
|
|
raise KeyboardInterrupt()
|
|
if answer == " ":
|
|
for choice in choices:
|
|
if choice[0].lower != choice[0]:
|
|
answer = choice[0][0].lower()
|
|
break
|
|
if answer == " ":
|
|
cprint("Aucun choix par défaut!")
|
|
else:
|
|
answer = answer.lower()
|
|
for choice in choices:
|
|
if answer in choice[0].lower():
|
|
answer = choice[0][0].lower()
|
|
break
|
|
if choices and answer == choice[0][0].lower():
|
|
if len(choice) <= 2:
|
|
return answer
|
|
elif len(choice) == 3:
|
|
return choice[2]
|
|
elif type(choice[3]) == tuple:
|
|
(message, choices) = choice[3]
|
|
elif type(choice[3]) == str:
|
|
print
|
|
print choice[3]
|
|
elif not choice[3]():
|
|
return choice[2]
|
|
if answer in ["h", "?"]:
|
|
print
|
|
cprint("Réponses possible:")
|
|
for choice in choices:
|
|
cprint("%s: %s" % (" ou ".join(list(choice[0])),
|
|
((len(choice) >= 2) and choice[1]) or "non documentée"))
|
|
cprint("h ou ?: afficher cette aide")
|
|
print
|
|
cprint("<Espace>: accepter le choix par défault (celui qui est en majuscule)")
|
|
print
|
|
else:
|
|
cprint("Choix invalide, essaies encore!")
|