Imported from archive.
[mudpy.git] / lib / muff / muffmenu.py
1 """Menu objects for the MUFF Engine"""
2
3 # Copyright (c) 2005 mudpy, Jeremy Stanley <fungi@yuggoth.org>, all rights reserved.
4 # Licensed per terms in the LICENSE file distributed with this software.
5
6 # muff uses menu data stored in ini-style files supported by ConfigParser
7 import ConfigParser
8
9 # os.listdir is needed to get a file listing from a config directory
10 import os
11
12 # re.match is used to find menu options based on the choice_ prefix
13 import re
14
15 # hack to load all modules in the muff package
16 import muff
17 for module in muff.__all__:
18         exec("import " + module)
19
20 # see if the menupath can be retrieved from muffconf
21 try:
22         if muffconf.config_data.get("files", "menus"): pass
23
24 # otherwise, reload muffconf
25 except AttributeError:
26         reload(muffconf)
27
28 # build a list of files in the menus directory
29 menu_files = []
30 menu_path = muffconf.config_data.get("files", "menus")
31 for each_file in os.listdir(menu_path):
32         menu_files.append(menu_path + "/" + each_file)
33
34 # read the menu files
35 menu_data = ConfigParser.SafeConfigParser()
36 menu_data.read(menu_files)
37
38 def get_default(user):
39         """Return the default choice for a menu."""
40         return menu_data.get(user.state, "default")
41
42 def get_menu(user):
43         """Show the correct menu text to a user."""
44
45         # the menu hasn't been shown yet since the user's last input
46         if not user.menu_seen:
47
48                 # echo is currently on for the user, so don't add an extra eol
49                 if user.echoing:
50                         spacer = ""
51
52                 # echo is currently off for the user, so add an extra eol
53                 else:
54                         spacer = "$(eol)"
55
56                 # if the user has echo on and the menu specifies it should be
57                 # turned off, send: iac + will + echo + null
58                 try:
59                         if menu_data.get(user.state, "echo") == "off" and user.echoing:
60                                 echo = chr(255) + chr(251) + chr(1) + chr(0)
61                                 user.echoing = False
62                         else:
63                                 echo = ""
64
65                 # if echo is not set to off in the menu and the user curently
66                 # has echo off, send: iac + wont + echo + null
67                 except:
68                         if not user.echoing:
69                                 echo = chr(255) + chr(252) + chr(1) + chr(0)
70                                 user.echoing = True
71                         else:
72                                 echo = ""
73
74                 # and error condition was raised by the handler
75                 if user.error:
76
77                         # try to get an error message matching the condition
78                         # and current state
79                         try:
80                                 description = "$(red)" + menu_data.get(user.state, "error_" + user.error) + "$(nrm)$(eol)$(eol)"
81
82                         # otherwise, use a generic one
83                         except:
84                                 description = "$(red)That is not a valid choice...$(nrm)$(eol)$(eol)"
85
86                         # now clear the error condition
87                         user.error = ""
88
89                 # there was no error condition raised by the handler
90                 else:
91
92                         # try to get a menu description for the current state
93                         try:
94                                 description = menu_data.get(user.state, "description") + "$(eol)$(eol)"
95
96                         # otherwise, leave it blank
97                         except:
98                                 description = ""
99
100                 # try to get menu choices for the current state
101                 try:
102
103                         # build a dict of choice:meaning
104                         choices = {}
105                         for option in menu_data.options(user.state):
106                                 if re.match("choice_", option):
107                                         choices[option.split("_")[1]] = menu_data.get(user.state, option)
108
109                         # make a sorted list of choices
110                         choice_keys = choices.keys()
111                         choice_keys.sort()
112
113                         # concatenate them all into a list for display
114                         choicestring = ""
115                         for choice in choice_keys:
116                                 choicestring += "   [$(red)" + choice + "$(nrm)]  " + choices[choice] + "$(eol)"
117
118                         # throw in an additional blank line after the choices,
119                         # if there were any
120                         if choicestring:
121                                 choicestring += "$(eol)"
122
123                 # there were no choices, so leave them blank
124                 except:
125                         choicestring = ""
126
127                 # try to get a prompt, if it was defined
128                 try:
129                         prompt = menu_data.get(user.state, "prompt") + " "
130
131                 # otherwise, leave it blank
132                 except:
133                         prompt = ""
134
135                 # throw in the default choice, if it exists
136                 try:
137                         default = "[$(red)" + menu_data.get(user.state, "default") + "$(nrm)] "
138
139                 # otherwise, leave it blank
140                 except:
141                         default = ""
142
143                 # echo is on, so don't display a message about it
144                 if user.echoing:
145                         echoing = ""
146
147                 # echo is off, so let the user know
148                 else:
149                         echoing = "(won't echo) "
150
151                 # assemble and send the various strings defined above
152                 user.send(echo + spacer + description + choicestring + prompt + default + echoing, "")
153
154                 # flag that the menu has now been displayed
155                 user.menu_seen = True
156