async def getCards(ch): C[ch]["black"] = [] C[ch]["white"] = [] async with aiosqlite.connect('packs.db') as db: async def getPack(pack): async with db.execute( 'select card from cards where pack=? and black=1', (pack, )) as cursor: b = await cursor.fetchall() async with db.execute( 'select card from cards where pack=? and black=0', (pack, )) as cursor: w = await cursor.fetchall() return b, w for p in C[ch]["packs"]: if p == "base": cards = await getPack( 'base') if C[ch]['lang'] == 'English' else await getPack( languages[C[ch]['lang']]) C[ch]["black"] += [x[0] for x in cards[0]] C[ch]["white"] += [x[0] for x in cards[1]] elif p in packs or p in thirdparty: cards = await getPack(p) C[ch]["black"] += [x[0] for x in cards[0]] C[ch]["white"] += [x[0] for x in cards[1]] else: b, w = api.get_deck_blacks_json(p), api.get_deck_whites_json(p) C[ch]["black"] += ['_'.join(c["text"]) for c in b] C[ch]["white"] += [''.join(c["text"]) for c in w]
async def removePack(self, ch, s): """Given a pack name, try to remove that pack.""" s = s.strip() # CardCast try: if s in config.C[ch]['packs']: b, w = api.get_deck_blacks_json(s), api.get_deck_whites_json(s) config.C[ch]['black'] = [x for x in config.C[ch]['black'] if x not in ['_'.join(c['text']) for c in b]] config.C[ch]['white'] = [x for x in config.C[ch]['white'] if x not in [''.join(c['text']) for c in w]] config.C[ch]['packs'].remove(s) await self.client.send_message(ch, s + ' removed!') except: pass s = s.lower() for p in config.packs: if p in s and p in config.C[ch]['packs']: config.C[ch]['black'] = [x for x in config.C[ch]['black'] if x not in eval('config.black_'+p)] config.C[ch]['white'] = [x for x in config.C[ch]['white'] if x not in eval('config.white_'+p)] config.C[ch]['packs'].remove(p) await self.client.send_message(ch, config.packs[p] + ' removed!') for p in config.thirdparty: if p in s and p in config.C[ch]['packs']: config.C[ch]['black'] = [x for x in config.C[ch]['black'] if x not in eval('config.black_'+p)] config.C[ch]['white'] = [x for x in config.C[ch]['white'] if x not in eval('config.white_'+p)] config.C[ch]['packs'].remove(p) await self.client.send_message(ch, config.thirdparty[p] + ' removed!') # remove red, green, and blue expansions if s == 'rgb': await self.removePack(ch, 'redgreenblue') # remove base pack if 'base' in s and 'base' in config.C[ch]['packs']: config.C[ch]['black'] = [x for x in config.C[ch]['black'] if x not in config.black] config.C[ch]['white'] = [x for x in config.C[ch]['white'] if x not in config.white] config.C[ch]['packs'].remove('base') await self.client.send_message(ch, 'Base Cards Against Humanity removed!') # remove all packs if len(config.C[ch]['black']) * len(config.C[ch]['white']) == 0 or s == 'all': if config.C[ch]['lang'] == 'English': config.C[ch]['black'] = list(config.black) config.C[ch]['white'] = list(config.white) else: config.C[ch]['black'] = list(eval('config.black_'+config.languages[config.C[ch]['lang']])) config.C[ch]['white'] = list(eval('config.white_'+config.languages[config.C[ch]['lang']])) config.C[ch]['packs'] = ['base'] await self.client.send_message(ch, 'No cards left. Reverting to base pack') await self.edit_start_msg(ch)
def main(): parser = OptionParser(version='%prog ' + __version__, usage="%prog [options]") parser.add_option('-t', '--task', default=None, help='[REQUIRED] Valid tasks are [deckslist, deckinfo, cards, blacks, whites]') parser.add_option('-d', '--deck', default=None, help='The deck ID. REQUIRED for deckinfo, cards, blacks, and whites tasks, ignored otherwise.') parser.add_option('-a', '--author', default=None, help='A user name to search for. Used with the deckslist task, otherwise ignored.') parser.add_option('-c', '--category', default=None, help='A category to search for. Used with the deckslist task, otherwise ignored.') parser.add_option('-s', '--search', default=None, help='Keywords to search for. Used with the deckslist task, otherwise ignored.') parser.add_option('-n', '--num-results', default=constants.DECK_LIST_REQ_MAX_RESULTS, help='The number of results to return with the deckslist task. [default: %default]') parser.add_option('-o', '--offset', default=0, help='The number of decks to offset the result window returned by the deckslist task. [default: %default]') options, args = parser.parse_args() if not options.task: parser.print_help() exit(1) if not options.task in ['deckslist', 'deckinfo', 'cards', 'blacks', 'whites']: print('Invalid task specified: %s' % options.task) parser.print_help() exit(2) if options.task in ['deckinfo', 'cards', 'blacks', 'whites']: if not options.deck: print('Task %s requires a deck ID to be specified using the -d option.' % options.task) parser.print_help() exit(3) if options.task == 'deckinfo': print(api.get_deck_info_json(options.deck)) elif options.task == 'cards': print(api.get_deck_cards_json(options.deck)) elif options.task == 'blacks': print(api.get_deck_blacks_json(options.deck)) elif options.task == 'whites': print(api.get_deck_whites_json(options.deck)) else: print(api.get_deck_list_json(search=options.search, author=options.author, category=options.category, limit=options.num_results, offset=options.offset))
async def addPack(self, ch, s): """Given a pack name, try to add that pack.""" s = s.strip() success = total = added = 0 # CardCast try: if s not in config.C[ch]['packs']: b, w = api.get_deck_blacks_json(s), api.get_deck_whites_json(s) config.C[ch]['black'] += ['_'.join(c['text']) for c in b] config.C[ch]['white'] += [''.join(c['text']) for c in w] config.C[ch]['packs'].append(s) success += 1 total += 1 else: added += 1 total += 1 except: pass s = s.lower() # add all official packs if s == 'all': await self.addPack(ch, ''.join(x for x in config.packs)) return # add all third party packs if s == '3rdparty' or s == 'thirdparty': await self.addPack(ch, ''.join(x for x in config.thirdparty)) return # add the red, green, and blue expansions if s == 'rgb': await self.addPack(ch, 'redbluegreen') return for p in config.packs: if p == 'cats' and s.count('cats') == s.count('cats2'): continue if p in s: total += 1 if p not in config.C[ch]['packs']: config.C[ch]['black'] += list(eval('config.black_' + p)) config.C[ch]['white'] += list(eval('config.white_' + p)) config.C[ch]['packs'].append(p) success += 1 else: added += 1 for p in config.thirdparty: if p in s: total += 1 if p not in config.C[ch]['packs']: config.C[ch]['black'] += list(eval('config.black_' + p)) config.C[ch]['white'] += list(eval('config.white_' + p)) config.C[ch]['packs'].append(p) success += 1 else: added += 1 if total: msg = 'Successfully added ' + str(success) + ' out of ' + str( total) + (' packs' if total > 1 else ' pack') if added: msg += '\n' + str(added) + (' packs' if added > 1 else ' pack') + ' already added' await self.client.send_message(ch, msg) await self.edit_start_msg(ch)
async def on_message(self, message): #if (time.time() / 3600) - last_update > 1: # await self.client.change_presence(game=discord.Game(name='on '+'_'*4+' servers. ' + str(len(client.servers))+'.')) # config.last_update = time.time() / 3600 msg = message.content.lower() ch = message.channel au = message.author c = config.pre[ch.id] if ch.id in config.pre else 'c' # ignore own messages if au.id == '429024440060215296': return # fill in blank cards if self.shard == 0: if ch.is_private: # check for c!p or c!play if len(msg) > 3 and msg[:3] == c + '!p': await self.client.send_message( au, 'Please play your card(s) in the corresponding channel and not as a private message.' ) return found = False if au in config.P: # check that user has a blank card for c in config.P[ au]: # check all channels that user is in if config.C[c]['started'] and au in config.C[c][ 'players']: # check that user is currently playing i = config.C[c]['players'].index(au) if '' in config.C[c]['hands'][ i]: # check that player has a blank found = True j = config.C[c]['hands'][i].index('') config.C[c][ 'hands'][i][j] = message.content.replace( '*', '\*').replace('_', '\_').replace( '~', '\~').replace('`', '\`') await self.sendHand(c, i) break if not found: edited_msg = message.content.replace('*', '\*').replace( '_', '\_').replace('~', '\~').replace('`', '\`') for i in range(1, self.num_shards): async with aiosqlite.connect( 'messages{0}.db'.format(i)) as conn: C = await conn.cursor() await C.execute( """insert into Messages values (?, ?)""", (au.id, edited_msg)) await conn.commit() return # ignore irrelevant messages if not (len(msg) > 2 and msg[:2] == c + '!'): return if ch not in config.C: config.C[ch] = {} await config.initChannel(ch) # warning if len( msg ) > 9 and msg[:9] == c + '!warning' and au.id == '252249185112293376': for x in config.C: if config.C[x]['started']: await self.client.send_message(x, message.content[9:]) # check number of ongoing games if msg == c + '!ongoing' and au.id == '252249185112293376': nC = 0 for x in config.C: if config.C[x]['started']: nC += 1 await self.client.send_message(ch, str(nC)) # save state if (msg == c + '!save' or msg == c + '!savestate') and au.id == '252249185112293376': self.save_state() # changelog if msg == c + '!whatsnew' or msg == c + '!update' or msg == c + '!updates': s = info.changelog await self.client.send_message(ch, s[:s.index('**9/27')]) # commands list if msg == c + '!commands' or msg == c + '!command': await self.client.send_message(ch, info.commands) # support server if msg == c + '!support' or msg == c + '!server' or msg == c + '!supp': await self.client.send_message(ch, 'https://discord.gg/qGjRSYQ') # FAQ if msg == c + '!faq': await self.client.send_message(ch, 'https://goo.gl/p9j2ve') # invite link if msg == c + '!invite': await self.client.send_message( ch, 'Use this link to invite the bot to your own server:\n<https://discordapp.com/api/oauth2/authorize?client_id=429024440060215296&permissions=134294592&scope=bot>' ) # vote link if msg == c + '!vote': await self.client.send_message( ch, 'Use this link to vote for the bot on discordbots.org:\n<https://discordbots.org/bot/429024440060215296/vote>' ) # shard if msg == c + '!shard': await self.client.send_message(ch, str(self.shard)) # custom prefix setting if len(msg ) == 10 and msg[:9] == c + '!prefix ' and 'a' <= msg[9] <= 'z': await self.client.send_message( ch, 'Command prefix set to `' + msg[9] + '`!') config.pre[ch.id] = msg[9] with open('prefix.txt', 'a') as f: f.write(ch.id + ' ' + msg[9] + '\n') if not config.C[ch]['started']: # language change for l in config.languages: if msg == c + '!language ' + l.lower(): if config.C[ch]['lang'] != l: config.C[ch]['lang'] = l config.C[ch]['black'] = list( eval('config.black_' + config.languages[l])) config.C[ch]['white'] = list( eval('config.white_' + config.languages[l])) await self.client.send_message( ch, 'Language changed to ' + l + '.') await self.edit_start_msg(ch) if msg == c + '!help': await self.client.send_message(ch, ( "Use `{0}!start` to start a game of Cards Against Humanity, or `{0}!cancel` to cancel an existing one.\n" "Use `{0}!commands` to bring up a list of available commands.\n" "For a list of frequently asked questions and general directions, use `{0}!faq`." ).format(c)) elif msg == c + '!language english': if config.C[ch]['lang'] != 'English': config.C[ch]['lang'] = 'English' config.C[ch]['black'] = config.black config.C[ch]['white'] = config.white await self.client.send_message( ch, 'Language changed to English.') await self.edit_start_msg(ch) elif msg == c + '!start': if not config.C[ch]['playerMenu']: config.C[ch]['playerMenu'] = True config.C[ch]['players'].append(au) s = await self.get_start_msg(ch) config.C[ch]['msg'] = await self.client.send_message(ch, s) output = str(len( config.C[ch]['players'])) + '/20 Players: ' output += ', '.join(usr.display_name for usr in config.C[ch]['players']) await self.client.send_message(ch, output) elif 2 <= len(config.C[ch]['players']) <= 20: config.C[ch]['playerMenu'] = False config.C[ch]['nPlayers'] = len(config.C[ch]['players']) await self.start_(ch) await self.client.send_message( ch, 'Game is starting!\n' + ' '.join(usr.mention for usr in config.C[ch]['players'])) config.C[ch]['msg'] = None await self.displayMid(ch) elif len(msg) > 8 and msg[:8] == c + '!setwin': try: n = int(msg[8:].strip()) if n > 0: config.C[ch]['win'] = n await self.client.send_message( ch, 'Number of points needed to win has been set to ' + str(n) + '.') await self.edit_start_msg(ch) except: pass elif len(msg) > 7 and msg[:7] == c + '!timer': try: n = int(msg[7:].strip()) if n >= 15: config.C[ch]['timer'] = n await self.client.send_message( ch, 'Idle timer set to ' + str(n) + ' seconds.') await self.edit_start_msg(ch) elif n == 0: config.C[ch]['timer'] = n await self.client.send_message( ch, 'Idle timer is now disabled.') await self.edit_start_msg(ch) else: await self.client.send_message( ch, 'Please choose a minimum of 15 seconds.') except: pass elif len(msg) > 10 and msg[:10] == c + '!settimer': try: n = int(msg[10:].strip()) if n >= 15: config.C[ch]['timer'] = n await self.client.send_message( ch, 'Idle timer set to " + str(n) + " seconds.') await self.edit_start_msg(ch) elif n == 0: config.C[ch]['timer'] = n await self.client.send_message( ch, 'Idle timer is now disabled.') await self.edit_start_msg(ch) else: await self.client.send_message( ch, 'Please choose a minimum of 15 seconds.') except: pass elif len(msg) > 10 and msg[:10] == c + '!setblank': try: n = int(msg[10:].strip()) if 0 <= n <= 30: config.C[ch]['blanks'] = n await self.client.send_message( ch, 'Number of blanks has been set to ' + str(n) + '.') await self.edit_start_msg(ch) except: pass elif msg == c + '!packs': output = ( "**List of available packs:**\n" "(pack code followed by name of pack, then number of black and white cards)\n" "----------\n") for p in config.packs: output += '**'+p+'** - ' + config.packs[p] \ + ' (' + str(len(eval('config.black_'+p))) + '/' + str(len(eval('config.white_'+p))) + ')\n' await self.client.send_message(ch, output) output = '\nThird party packs:\n' for p in config.thirdparty: output += '**'+p+'** - ' + config.thirdparty[p] \ + ' (' + str(len(eval('config.black_'+p))) + '/' + str(len(eval('config.white_'+p))) + ')\n' output += ( "\nUse `{0}!add <code>` to add a pack, or use `{0}!add all` to add all available packs.\n" "(Note: this will only add official CAH packs; use `{0}!add thirdparty` to add all third party packs.)\n" "Use `{0}!contents <code>` to see what cards are in a specific pack." ).format(c) await self.client.send_message(ch, output) elif len(msg) > 10 and msg[:10] == c + '!contents': pk = message.content[10:].strip() # check for CardCast packs try: b, w = api.get_deck_blacks_json( pk), api.get_deck_whites_json(pk) deck_b = ['_'.join(c['text']) for c in b] deck_w = [''.join(c['text']) for c in w] output = '**Cards in ' + api.get_deck_info_json( pk)['name'] + '** (code: ' + pk + ')**:**\n\n' output += '**Black cards:** (' + str(len(deck_b)) + ')\n' for c in deck_b: output += '- ' + c + '\n' if len(output) > 1500: await self.client.send_message( ch, output.replace('_', '\_' * 3)) output = '' output += '\n**White cards:** (' + str(len(deck_w)) + ')\n' for c in deck_w: output += '- ' + c + '\n' if len(output) > 1500: await self.client.send_message( ch, output.replace('_', '\_' * 3)) output = '' await self.client.send_message( ch, output.replace('_', '\_' * 3)) return except: pass # check built-in packs pk = pk.lower() if pk in config.packs or pk in config.thirdparty: output = '' if pk in config.packs: output = '**Cards in ' + config.packs[pk] + ':**\n\n' elif pk in config.thirdparty: output = '**Cards in ' + config.thirdparty[ pk] + ':**\n\n' output += '**Black cards:** (' + str( len(eval('config.black_' + pk))) + ')\n' for c in eval('config.black_' + pk): output += '- ' + c + '\n' if len(output) > 1500: await self.client.send_message( ch, output.replace('_', '\_' * 3)) output = '' output += '\n**White cards:** (' + str( len(eval('config.white_' + pk))) + ')\n' for c in eval('config.white_' + pk): output += '- ' + c + '\n' if len(output) > 1500: await self.client.send_message( ch, output.replace('_', '\_' * 3)) output = '' await self.client.send_message( ch, output.replace('_', '\_' * 3)) elif msg == c + '!cancel': if config.C[ch]['playerMenu']: config.C[ch]['playerMenu'] = False config.C[ch]['players'] = [] await self.client.send_message(ch, 'Game cancelled!') if config.C[ch]['playerMenu']: curr = len(config.C[ch]['players']) if msg == c + '!join': if au not in config.C[ch]['players']: config.C[ch]['players'].append(au) elif msg == c + '!leave': if au in config.C[ch]['players']: config.C[ch]['players'].remove(au) if curr != len(config.C[ch]['players']): output = str(len( config.C[ch]['players'])) + '/20 Players: ' output += ', '.join(usr.display_name for usr in config.C[ch]['players']) await self.client.send_message(ch, output) if len(msg) > 6 and msg[:6] == c + '!add ' and config.C[ch][ 'lang'] == 'English': await self.addPack(ch, message.content[6:]) if len(msg) > 9 and msg[:9] == c + '!remove ' and config.C[ch][ 'lang'] == 'English': await self.removePack(ch, message.content[9:]) elif len(msg) > 5 and msg[:5] == c + '!rm ' and config.C[ch][ 'lang'] == 'English': await self.removePack(ch, message.content[5:]) else: if msg == c + '!help': await self.client.send_message(ch, ( "To play white cards, use `{0}!play` followed by the letters next to the cards you want to play. " "For example, `{0}!play b` would play card B, and `{0}!play df` would play cards D and F.\n" "If you're the czar, react with the letter of your choice once everyone has played their cards.\n" "To reset an ongoing game, use `{0}!reset`.\n" "To leave an ongoing game, use `{0}!leave` or `{0}!quit`.\n" "To join an ongoing game, use `{0}!join`.\n" "To kick an AFK player, use `{0}!kick <player>`." ).format(c)) # player commands if au in config.C[ch]['players']: if msg == c + '!display': config.C[ch]['msg'] = None await self.displayMid(ch) return elif msg == c + '!leave' or msg == c + '!quit': if not config.done(ch): await self.removePlayer(ch, au) else: await self.client.send_message( ch, 'Please wait for the czar to pick a card before leaving.' ) elif len(msg) > 7 and msg[:7] == c + '!kick ': mt = message.content[7:].strip() # player to kick if mt == au.mention: await self.client.send_message( ch, 'You cannot kick yourself. To leave the game, use `' + c + '!leave`.') else: for i in range(len(config.C[ch]['players'])): p = config.C[ch]['players'][i] if mt == p.mention: if not config.C[ch]['played'][i]: config.C[ch]['kick'][config.C[ch][ 'players'].index(au)] = p.mention cnt = config.C[ch]['kick'].count(p.mention) await self.client.send_message(ch, au.mention + ' has voted to kick ' + p.mention + '. ' \ + str(cnt) + '/' + str(config.C[ch]['nPlayers']-1) + ' votes needed') if cnt == config.C[ch]['nPlayers'] - 1: await self.client.send_message( ch, p.mention + ' has been kicked from the game.') await self.removePlayer(ch, p, kick=True) else: await self.client.send_message( ch, 'This player has already played and cannot be kicked.' ) break elif msg == c + '!reset': await config.reset(ch) await self.client.send_message(ch, 'Game reset!') return else: if msg == c + '!join': if not config.done(ch): await self.addPlayer(ch, au) else: await self.client.send_message( ch, 'Please wait for the czar to pick an answer before joining.' ) # playing cards if len(msg) > 6 and msg[:6] == c + '!play': await self.play(ch, au, msg[6:]) try: await self.client.delete_message(message) except: pass elif len(msg) > 4 and msg[:4] == c + '!p ': await self.play(ch, au, msg[4:]) try: await self.client.delete_message(message) except: pass # admin override if au.id == '252249185112293376' or au.permissions_in( ch).administrator: if msg == c + '!display': config.C[ch]['msg'] = None await self.displayMid(ch) elif msg == c + '!reset': await config.reset(ch) await self.client.send_message(ch, 'Game reset!')
def main(): parser = OptionParser(version='%prog ' + __version__, usage="%prog [options]") parser.add_option( '-t', '--task', default=None, help= '[REQUIRED] Valid tasks are [deckslist, deckinfo, cards, blacks, whites]' ) parser.add_option( '-d', '--deck', default=None, help= 'The deck ID. REQUIRED for deckinfo, cards, blacks, and whites tasks, ignored otherwise.' ) parser.add_option( '-a', '--author', default=None, help= 'A user name to search for. Used with the deckslist task, otherwise ignored.' ) parser.add_option( '-c', '--category', default=None, help= 'A category to search for. Used with the deckslist task, otherwise ignored.' ) parser.add_option( '-s', '--search', default=None, help= 'Keywords to search for. Used with the deckslist task, otherwise ignored.' ) parser.add_option( '-n', '--num-results', default=constants.DECK_LIST_REQ_MAX_RESULTS, help= 'The number of results to return with the deckslist task. [default: %default]' ) parser.add_option( '-o', '--offset', default=0, help= 'The number of decks to offset the result window returned by the deckslist task. [default: %default]' ) options, args = parser.parse_args() if not options.task: parser.print_help() exit(1) if not options.task in [ 'deckslist', 'deckinfo', 'cards', 'blacks', 'whites' ]: print('Invalid task specified: %s' % options.task) parser.print_help() exit(2) if options.task in ['deckinfo', 'cards', 'blacks', 'whites']: if not options.deck: print( 'Task %s requires a deck ID to be specified using the -d option.' % options.task) parser.print_help() exit(3) if options.task == 'deckinfo': print(api.get_deck_info_json(options.deck)) elif options.task == 'cards': print(api.get_deck_cards_json(options.deck)) elif options.task == 'blacks': print(api.get_deck_blacks_json(options.deck)) elif options.task == 'whites': print(api.get_deck_whites_json(options.deck)) else: print( api.get_deck_list_json(search=options.search, author=options.author, category=options.category, limit=options.num_results, offset=options.offset))
async def on_message(self, message): #if (time.time() / 3600) - last_update > 1: # await self.client.change_presence(game=discord.Game(name='on '+'_'*4+' servers. ' + str(len(client.guilds))+'.')) # config.last_update = time.time() / 3600 msg = message.content.lower() ch = message.channel au = message.author c = config.pre[ch.id] if ch.id in config.pre else 'c' # ignore own messages if au.id == 429024440060215296: return # fill in blank cards if isinstance(ch, discord.abc.PrivateChannel): # check for c!p or c!play if msg.startswith(c + '!p'): await au.send( 'Please play your card(s) in the corresponding channel and not as a private message.' ) return # iterate through all users with blank cards for p in config.P: if p.id == au.id: for c in config.P[p]: if config.C[c]['started'] and au in config.C[c][ 'players']: # check that user is currently playing i = config.C[c]['players'].index(au) if '' in config.C[c]['hands'][ i]: # check that player has a blank j = config.C[c]['hands'][i].index('') config.C[c][ 'hands'][i][j] = message.content.replace( '*', '\*').replace('_', '\_').replace( '~', '\~').replace('`', '\`') await self.sendHand(c, i) break return # ignore irrelevant messages if not msg.startswith(c + '!'): return if ch not in config.C: config.C[ch] = {} await config.initChannel(ch) # warning if msg.startswith(c + '!warning') and au.id == 252249185112293376: for x in config.C: if config.C[x]['started']: await x.send(message.content[9:]) # check number of ongoing games if msg == c + '!ongoing' and (au.id == 252249185112293376 or au.id == 413516816137322506): nC = 0 for x in config.C: if config.C[x]['started']: nC += 1 await ch.send(str(nC)) # save state if (msg == c + '!save' or msg == c + '!savestate') and au.id == 252249185112293376: self.save_state() # number of servers if msg == c + '!servers' and (au.id == 252249185112293376 or au.id == 413516816137322506): await ch.send(str(len(self.client.guilds))) # # eval # if message.content.startswith(c+'!eval') and au.id == 252249185112293376: # try: # print(eval(message.content[6:].strip())) # await ch.send(str(eval(message.content[6:].strip()))) # except: # pass # changelog if msg == c + '!whatsnew' or msg == c + '!update' or msg == c + '!updates': s = info.changelog await ch.send(s[:s.index('**9/27')]) # commands list if msg == c + '!commands' or msg == c + '!command': await ch.send(info.commands) # support server if msg == c + '!support' or msg == c + '!server' or msg == c + '!supp': await ch.send('https://discord.gg/qGjRSYQ') # FAQ if msg == c + '!faq': await ch.send('https://goo.gl/p9j2ve') # invite link if msg == c + '!invite': await ch.send( 'Use this link to invite the bot to your own server:\n<https://discordapp.com/api/oauth2/authorize?client_id=429024440060215296&permissions=134294592&scope=bot>' ) # vote link if msg == c + '!vote': await ch.send( 'Use this link to vote for the bot on discordbots.org:\n<https://discordbots.org/bot/429024440060215296/vote>' ) # donation links if msg == c + '!donate': await ch.send( 'Help support the bot:\n<http://buymeacoffee.com/sourmongoose>\n<https://paypal.me/sourmongoose>' ) # custom prefix setting if len(msg ) == 10 and msg[:9] == c + '!prefix ' and 'a' <= msg[9] <= 'z': await ch.send('Command prefix set to `' + msg[9] + '`!') config.pre[ch.id] = msg[9] with open('prefix.txt', 'a') as f: f.write(str(ch.id) + ' ' + msg[9] + '\n') if not config.C[ch]['started']: # language change for l in config.languages: if msg == c + '!language ' + l.lower(): if config.C[ch]['lang'] != l: config.C[ch]['lang'] = l await ch.send('Language changed to ' + l + '.') await self.edit_start_msg(ch) if msg == c + '!help': await ch.send(( "Use `{0}!start` to start a game of Cards Against Humanity, or `{0}!cancel` to cancel an existing one.\n" "Use `{0}!commands` to bring up a list of available commands.\n" "For a list of frequently asked questions and general directions, use `{0}!faq`." ).format(c)) elif msg == c + '!language english': if config.C[ch]['lang'] != 'English': config.C[ch]['lang'] = 'English' await ch.send('Language changed to English.') await self.edit_start_msg(ch) elif msg == c + '!start': if not config.C[ch]['playerMenu']: config.C[ch]['playerMenu'] = True config.C[ch]['players'].append(au) s = await self.get_start_msg(ch) config.C[ch]['msg'] = await ch.send(s) output = str(len( config.C[ch]['players'])) + '/20 Players: ' output += ', '.join(usr.display_name for usr in config.C[ch]['players']) await ch.send(output) elif 2 <= len(config.C[ch]['players']) <= 20: config.C[ch]['playerMenu'] = False config.C[ch]['nPlayers'] = len(config.C[ch]['players']) await self.start_(ch) await ch.send('Game is starting!\n' + ' '.join(usr.mention for usr in config.C[ch]['players'])) config.C[ch]['msg'] = None await self.displayMid(ch) elif msg.startswith(c + '!setwin'): try: n = int(msg[8:].strip()) if n > 0: config.C[ch]['win'] = n await ch.send( f'Number of points needed to win has been set to {n}.' ) await self.edit_start_msg(ch) except: pass elif msg.startswith(c + '!timer') or msg.startswith(c + '!settimer'): #await ch.send('Idle timer is currently disabled.') try: n = int(msg[msg.index('timer') + 5:].strip()) if n >= 15: config.C[ch]['timer'] = n await ch.send(f'Idle timer set to {n} seconds.') await self.edit_start_msg(ch) elif n == 0: config.C[ch]['timer'] = n await ch.send('Idle timer is now disabled.') await self.edit_start_msg(ch) else: await ch.send('Please choose a minimum of 15 seconds.') except: pass elif msg.startswith(c + '!blank') or msg.startswith(c + '!setblank'): #await ch.send('Blank cards are currently disabled.') try: n = int(msg[msg.index('blank') + 5:].strip()) if 0 <= n <= 30: config.C[ch]['blanks'] = n await ch.send(f'Number of blanks has been set to {n}.') await self.edit_start_msg(ch) elif n > 30: await ch.send('Please choose a maximum of 30 cards.') except: pass elif msg == c + '!packs': output = ( "**List of available packs:**\n" "(pack code followed by name of pack, then number of black and white cards)\n" "----------\n") for p in config.packs: cnt = await config.getCount(p) output += f'**{p}** - {config.packs[p]} ({cnt[0]}/{cnt[1]})\n' await ch.send(output) output = '\nThird party packs:\n' for p in config.thirdparty: cnt = await config.getCount(p) output += f'**{p}** - {config.thirdparty[p]} ({cnt[0]}/{cnt[1]})\n' output += ( "\nUse `{0}!add <code>` to add a pack, or use `{0}!add all` to add all available packs.\n" "(Note: this will only add official CAH packs; use `{0}!add thirdparty` to add all third party packs.)\n" "Use `{0}!contents <code>` to see what cards are in a specific pack." ).format(c) await ch.send(output) elif msg.startswith(c + '!contents'): pk = message.content[10:].strip() # check for CardCast packs try: b, w = api.get_deck_blacks_json( pk), api.get_deck_whites_json(pk) deck_b = ['_'.join(c['text']) for c in b] deck_w = [''.join(c['text']) for c in w] output = '**Cards in ' + api.get_deck_info_json( pk)['name'] + '** (code: ' + pk + ')**:**\n\n' output += '**Black cards:** (' + str(len(deck_b)) + ')\n' for c in deck_b: output += '- ' + c + '\n' if len(output) > 1500: await ch.send(output.replace('_', '\_' * 3)) output = '' output += '\n**White cards:** (' + str(len(deck_w)) + ')\n' for c in deck_w: output += '- ' + c + '\n' if len(output) > 1500: await ch.send(output.replace('_', '\_' * 3)) output = '' await ch.send(output.replace('_', '\_' * 3)) return except: pass # check built-in packs pk = pk.lower() if pk in config.packs or pk in config.thirdparty: output = '' if pk in config.packs: output = '**Cards in ' + config.packs[pk] + ':**\n\n' elif pk in config.thirdparty: output = '**Cards in ' + config.thirdparty[ pk] + ':**\n\n' cnt = await config.getCount(pk) cards = await config.getPack(pk) output += f'**Black cards:** ({cnt[0]})\n' for card in cards[0]: output += '- ' + card[0] + '\n' if len(output) > 1500: await ch.send(output.replace('_', '\_' * 3)) output = '' output += f'\n**White cards:** ({cnt[1]})\n' for card in cards[1]: output += '- ' + card[0] + '\n' if len(output) > 1500: await ch.send(output.replace('_', '\_' * 3)) output = '' await ch.send(output.replace('_', '\_' * 3)) elif msg == c + '!cancel': if config.C[ch]['playerMenu']: config.C[ch]['playerMenu'] = False config.C[ch]['players'] = [] await ch.send('Game cancelled!') if config.C[ch]['playerMenu']: curr = len(config.C[ch]['players']) if msg == c + '!join': if au not in config.C[ch]['players']: config.C[ch]['players'].append(au) elif msg == c + '!leave': if au in config.C[ch]['players']: config.C[ch]['players'].remove(au) if curr != len(config.C[ch]['players']): output = str(len( config.C[ch]['players'])) + '/20 Players: ' output += ', '.join(usr.display_name for usr in config.C[ch]['players']) await ch.send(output) if len(msg) > 6 and msg[:6] == c + '!add ' and config.C[ch][ 'lang'] == 'English': await self.addPack(ch, message.content[6:]) if len(msg) > 9 and msg[:9] == c + '!remove ' and config.C[ch][ 'lang'] == 'English': await self.removePack(ch, message.content[9:]) elif len(msg) > 5 and msg[:5] == c + '!rm ' and config.C[ch][ 'lang'] == 'English': await self.removePack(ch, message.content[5:]) else: if msg == c + '!join' or (len(msg) > 6 and msg[:6] == c + '!add '): await ch.send( 'Use `c!start` to start a game before joining or adding packs.' ) else: if msg == c + '!help': await ch.send(( "To play white cards, use `{0}!play` followed by the letters next to the cards you want to play. " "For example, `{0}!play b` would play card B, and `{0}!play df` would play cards D and F.\n" "If you're the czar, react with the letter of your choice once everyone has played their cards.\n" "To reset an ongoing game, use `{0}!reset`.\n" "To leave an ongoing game, use `{0}!leave` or `{0}!quit`.\n" "To join an ongoing game, use `{0}!join`.\n" "To kick an AFK player, use `{0}!kick <player>`.\n" "To re-display the scoreboard, use `{0}!display`." ).format(c)) # player commands if au in config.C[ch]['players']: if msg == c + '!display': config.C[ch]['msg'] = None await self.displayMid(ch) return elif msg == c + '!leave' or msg == c + '!quit': if not config.done(ch): await self.removePlayer(ch, au) else: await ch.send( 'Please wait for the czar to pick a card before leaving.' ) elif msg.startswith(c + '!kick'): mt = message.content[6:].strip() # player to kick if mt == au.mention: await ch.send( 'You cannot kick yourself. To leave the game, use `' + c + '!leave`.') else: for i in range(len(config.C[ch]['players'])): p = config.C[ch]['players'][i] if mt == p.mention: if not config.C[ch]['played'][i]: config.C[ch]['kick'][config.C[ch][ 'players'].index(au)] = p.mention cnt = config.C[ch]['kick'].count(p.mention) await ch.send(au.mention + ' has voted to kick ' + p.mention + '. ' \ + str(cnt) + '/' + str(config.C[ch]['nPlayers']-1) + ' votes needed') if cnt == config.C[ch]['nPlayers'] - 1: await ch.send( p.mention + ' has been kicked from the game.') await self.removePlayer(ch, p, kick=True) else: await ch.send( 'This player has already played and cannot be kicked.' ) break elif msg == c + '!reset': await config.reset(ch) await ch.send('Game reset!') return else: if msg == c + '!join': if not config.done(ch): await self.addPlayer(ch, au) else: await ch.send( 'Please wait for the czar to pick an answer before joining.' ) # playing cards if msg.startswith('c!play'): await self.play(ch, au, msg[6:]) try: await message.delete() except: pass elif msg.startswith(c + '!p '): await self.play(ch, au, msg[4:]) try: await message.delete() except: pass # admin override if au.id == 252249185112293376 or au.permissions_in( ch).administrator: if msg == c + '!display': config.C[ch]['msg'] = None await self.displayMid(ch) elif msg == c + '!reset': await config.reset(ch) await ch.send('Game reset!')