Extend the usage function and add descriptions for commands

User-facing help text is now kept in a dictionary where command tuples
map to help entries. This greatly simplifies maintenance should more
commands be added in the future.

Additionally, every command now has a short description that serves to
give players a quick overview of its functionality.
This commit is contained in:
Wolfgang Müller 2019-08-26 20:09:10 +02:00
parent 221b740bce
commit 2f8fb69dbf
1 changed files with 39 additions and 47 deletions

View File

@ -1,5 +1,6 @@
import threading
import time
from collections import namedtuple
import channel
@ -13,6 +14,8 @@ irc_chan = None
game_channel = None
HelpEntry = namedtuple('HelpEntry', ['synopsis', 'desc', 'is_sub'])
def chunk(l, n):
assert 0 < n
chunked = []
@ -122,6 +125,33 @@ def send_event(event):
game_channel.send(event)
def usage(command):
entries = {
('status',) : HelpEntry('!status', 'Show the game status.', False),
('ready',) : HelpEntry('!ready', 'Mark yourself as ready.', False),
('unready',) : HelpEntry('!unready', 'Mark yourself as not ready.', False),
('kill',) : HelpEntry('!kill', 'Stop the game.', False),
('leave',) : HelpEntry('!leave', 'Leave the game.', False),
('players',) : HelpEntry('!players', 'Show a list of players.', False),
('cards',) : HelpEntry('!cards', 'Show the cards in your hand.', False),
('origins',) : HelpEntry('!origins', 'Show the cardcast codes of the decks containing the cards that can be picked currently.', False),
('redeal',) : HelpEntry('!redeal', 'Remove all cards from your hand and redeal.', False),
('start',) : HelpEntry('!start [<preset>]', 'Start a game with the specified preset. If no preset is given, use "default". Available presets are: default, empty, offtopia, offtopia-random', False),
('join',) : HelpEntry('!join [<message>]', 'Join the game with the specified message.', False),
('kick',) : HelpEntry('!kick <nick>', 'Kick the specified player from the game.', False),
('card',) : HelpEntry('[!card] <number[,number,...]> ...', 'Pick the specified cards. If multiple numbers are specified for a single pick, play one of them at random.', False),
('jape',) : HelpEntry('[!jape] <number[,number,...]> ...', 'See !card.', False),
('deck',) : HelpEntry('!deck add | remove | list', 'Manage decks.', True),
('bot',) : HelpEntry('!bot add | remove', 'Manage bots.', True),
('limit',) : HelpEntry('!limit [<number> [<type>]]', 'Show or adjust the win limit. Type can be "r" for rounds and "p" for points.', False),
('help',) : HelpEntry('!help [command [subcommand]]', 'Show a synopsis and description for the specified command.', False),
('deck', 'add') : HelpEntry('!deck add <code> | random', 'Add the deck with the specified cardcast code (or pick one randomly).', False),
('deck', 'remove') : HelpEntry('!deck remove <code>', 'Remove the deck with the specified cardcast code.', False),
('deck', 'list') : HelpEntry('!deck list', 'List selected decks.', False),
('bot', 'add') : HelpEntry('!bot add <type> [<name>]', 'Add a bot of the specified type and name. If the name is omitted, name the bot after its type.', False),
('bot', 'remove') : HelpEntry('!bot remove <name>', 'Remove the specified bot.', False),
}
if type(command) == str:
command = [command]
@ -130,55 +160,17 @@ def usage(command):
command[0] = command[0][1:]
if len(command) == 0:
return '!status !start !ready !unready !kill !join !leave !players !kick !deck !limit !card !cards !origins !redeal !help'
elif len(command) == 1:
if command[0] in ('status', 'ready', 'unready', 'kill', 'join', 'leave', 'players', 'cards', 'origins', 'redeal'):
return 'Usage: !%s' % (command[0])
elif command[0] == 'start':
return 'Usage: !start [<preset>]'
elif command[0] == 'join':
return 'Usage: !join [<message>]'
elif command[0] == 'kick':
return 'Usage: !kick <nick>'
elif command[0] == 'card':
return 'Usage: [!card] <number[,number,...]> ...'
elif command[0] == 'jape':
return 'Usage: [!jape] <number[,number,...]> ...'
elif command[0] == 'deck':
return 'Subcommands: !deck add | remove | list'
elif command[0] == 'bot':
return 'Subcommands: !bot add | remove'
elif command[0] == 'limit':
return 'Usage: !limit [<number> [<type>]]'
elif command[0] == 'help':
return 'Usage: !help [command [subcommmand]]'
else:
return 'No such command !%s' % (command[0])
elif len(command) == 2:
if command[0] == 'deck':
if command[1] == 'add':
return 'Usage: !deck add <code> | random'
elif command[1] == 'remove':
return 'Usage: !deck remove <code>'
elif command[1] == 'list':
return 'Usage: !deck list'
else:
return 'No such subcommand !%s %s' % (command[0], command[1])
elif command[0] == 'bot':
if command[1] == 'add':
return 'Usage: !bot add <type> [<name>]'
elif command[1] == 'remove':
return 'Usage: !bot remove <name>'
else:
return 'No such subcommand !%s %s' % (command[0], command[1])
else:
return 'No such subcommand !%s %s' % (command[0], command[1])
else:
return ' '.join(sorted(set('!' + cmd[0] for cmd in entries.keys())))
elif len(command) > 2:
return 'Uh, how did we get %i args?' % len(command)
key = tuple(command)
if key in entries:
e = entries[key]
return '%s: %s %s' % ('Subcommands' if e.is_sub else 'Usage', e.synopsis, e.desc)
else:
return 'No such command !%s' % ' '.join(command)
def parse_command(message, nick, irc):
def send(m):
global irc_chan