Пример #1
0
    async def overall_stats(self, ctx, mode):
        """Show the number of wins of red/blue."""
        archive = get_game(ctx).archive[mode]
        wins = [0, 0, 0]
        yDlist, yRlist, yBlist = [], [], []
        for _, winner, _ in archive.values():
            wins[0] += winner == 0
            wins[1] += winner == 1
            wins[2] += winner == 2
            yDlist.append(wins[0])
            yRlist.append(wins[1])
            yBlist.append(wins[2])

        total = sum(wins)

        x = np.arange(total)
        plt.clf()
        plt.plot(x, yDlist)
        plt.plot(x, yRlist)
        plt.plot(x, yBlist)
        plt.title(f'Teams wins Graph')
        plt.xlabel("Number of games")
        plt.legend(['Draw', 'Red', 'Blue'], loc='upper left')
        plt.savefig(fname='plot')
        await ctx.send(file=discord.File('plot.png'))
        os.remove('plot.png')
Пример #2
0
    async def setpickmode(self, ctx, mode, new_mode):
        """Set the pickmode to the new_mode set

        new mode:
            0: random teams
            1: balanced teams
            2: random cap, picks 1-1 1-1
            3: best cap, picks 1-1 1-1
            4: random cap, picks 1-2 2-1
            5: best cap, picks 1-2 2-1
        """
        game = get_game(ctx)
        new_mode = int(new_mode)
        if split_with_numbers(mode)[1] == 't':
            await ctx.send("Can't set a pickmode for team vs team")
            return
        if new_mode not in range(6):
            await ctx.send("Wrong new_mode given, read help pickmode")
            return
        pickmodes = [
            "random teams", "balanced random", "random cap (1-1)",
            "best cap (1-1)", "random cap (1-2 2-1)", "best cap (1-2 2-1)"
        ]
        game.queues[mode].mode = new_mode
        if len(game.queues[mode].modes) <= 4:  # backward compatibility
            game.queues[mode].modes.append(game.queues[mode].modes[2])
            game.queues[mode].modes.append(game.queues[mode].modes[3])
        game.queues[mode].pick_function = game.queues[mode].modes[new_mode]
        await ctx.send(f"Pickmode changed to {pickmodes[new_mode]} !")
Пример #3
0
    async def add_mode(self, ctx, mode):
        """Add a mode to the game modes.

        Example: !add_mode 4s
        Will add the mode solo 4vs4 into the available modes, a channel will be
        created and the leaderboard will now have a 4s key.
        Can be used only in init channel by a Elo Admin role having user."""
        splitted = split_with_numbers(mode)
        if len(splitted) == 2:
            num, vsmode = splitted

            if num.isdigit() and int(num) > 0 and vsmode in ("s", "t"):
                if get_game(ctx).add_mode(mode):
                    guild = ctx.message.guild
                    await create_mode_discord(num, {
                        "s": "Solo elo",
                        "t": "Teams elo"
                    }[vsmode], ctx)
                    if not discord.utils.get(guild.roles,
                                             name=f"{num}vs{num} Elo Player"):

                        await guild.create_role(
                            name=f"{num}vs{num} Elo Player",
                            colour=discord.Colour(random.randint(0, 0xFFFFFF)))
                        await ctx.send(f"{num}vs{num} Elo Player role created")
                    return

        await ctx.send(embed=Embed(color=0x000000,
                                   description="Couldn't add the game mode."))
Пример #4
0
    async def most(self,
                   ctx,
                   mode,
                   mention="",
                   order_key="games",
                   with_or_vs="with"):
        """Show who you played the most with.

        Example: !most losses @Anddy with
        Will show the leaderboard of the people with who you lost the most.
        order_key must € [games, draws, wins, losses]
        is the key the table will be ordered by."""
        game = get_game(ctx)

        player = await get_player_by_mention(ctx, mode, mention) if mention\
            else await get_player_by_id(ctx, mode, ctx.author.id)

        if order_key not in ("games", "draws", "wins", "losses"):
            raise commands.errors.BadArgument(order_key)
        if with_or_vs not in ("with", "vs"):
            raise commands.errors.BadArgument(with_or_vs)

        # most_played_with = build_most_played_with(game, mode, name)
        msg = await ctx.send(embed=most_stat_embed(
            game, mode, player, order_key, with_or_vs=with_or_vs))
        await add_scroll(msg)
Пример #5
0
    async def setallstats(self, ctx, mode, name, *stats):
        """Set the stats to the player in the specific mode.
        Let any stat to -1 to not let it change.
        In order:
            [elo, wins, losses, nb_matches, wlr, most_wins_in_a_row,
            most_losses_in_a_row, current_win_streak,
            current_lose_streak]
            The wlr will anyway be calculated at the end.
        """
        player = get_game(ctx).leaderboards[mode][int(name[3: -1])]
        stats_name = Player.STATS[1: -2]
        if len(stats) > len(stats_name):
            await ctx.send("Too much arguments ! I'll cancel in case you messed up")
            return

        for i, stat in enumerate(stats):
            try:
                stat = int(stat)
                if stat >= 0:
                    setattr(player, stats_name[i], stat)
            except ValueError:
                await ctx.send(f"Wrong format for {stats_name[i]}.")

        player.wlr = player.wins / player.losses if player.losses != 0 else 0
        await ctx.send("Worked!")
Пример #6
0
    async def join_with(self, ctx, *mentions):
        """Join the queue with your own team.

        Example in 4vs4:
        !jw @player1 @player2 @player3
        """
        game = get_game(ctx)
        mode = get_channel_mode(ctx)
        queue = game.queues[mode]
        nb_players = int(split_with_numbers(mode)[0])
        players = {await get_player_by_id(ctx, mode, ctx.author.id)} |\
            {await get_player_by_mention(ctx, mode, m) for m in mentions}
        if nb_players != len(players):
            await send_error(
                ctx,
                f"You joined with {len(players)} player(s) but you need exactly {nb_players}"
            )
            raise PassException()

        embed = Embed(title=f"Invitations for {mode} from {ctx.author.display_name}",
            description="To join with your team, everyone involved have to confirm by clicking on 👍.\n"
                "To deny, click on the 👎.")\
            .add_field(name=f"Captain", value=ctx.author.mention)

        for i in range(len(mentions)):
            embed.add_field(name=f"Player n°{i + 1}", value=mentions[i])

        msg = await ctx.send(embed=embed)
        await msg.add_reaction("👍")
        await msg.add_reaction("👎")
Пример #7
0
    async def graph(self, ctx, mode, mention="", stat_key="elo"):
        """Show the graph of previous elo points.

        This doesn't count the boosts due to double xp or win streaks.
        Name MUST be given if you want to make a graph based on the wlr.
        """
        game = get_game(ctx)
        player = await get_player_by_mention(ctx, mode, mention) if mention\
            else await get_player_by_id(ctx, mode, ctx.author.id)
        values = list(game.archive[mode].values())
        yList = []
        if stat_key == "elo":
            values.reverse()
            yList = self.build_elo_graph(values, player)
        elif stat_key == "wlr":
            yList = self.build_wlr_graph(values, player)

        xList = [x for x in range(len(yList))]

        # xList.sort()
        x = np.array(xList)
        y = np.array(yList)
        arr = np.vstack((x, y))
        plt.clf()
        plt.plot(arr[0], arr[1])
        plt.title(f'{player.name}\'s {stat_key} Graph')
        plt.xlabel("Number of games")
        plt.ylabel(f"{stat_key} points")
        plt.savefig(fname='plot')
        await ctx.send(file=discord.File('plot.png'))
        os.remove('plot.png')
Пример #8
0
    async def add_rank(self, ctx, mode, name, image_url, from_points,
                       to_points):
        """Add a rank and set this rank to everyone having required points.

        mode is the N in NvsN.
        name is the name of the rank. Must be in " "
        from_points is the points required to have this rank.
        to_points is the max points of this rank.
        """
        game = get_game(ctx)
        from_points = int(from_points)
        to_points = int(to_points)
        if to_points < from_points:
            await ctx.send("To points must be greater than from points")
            return
        if not is_url_image(image_url):
            await ctx.send("The url doesn't lead to an image. (png jpg jpeg)")
            return
        if name in game.ranks[mode]:
            await ctx.send(
                "The rank couldn't be added, maybe it already exists.")
            return

        game.ranks[mode][name] = Rank(mode, name, image_url, from_points,
                                      to_points)
        await ctx.send("The rank was added and the players got updated.")
Пример #9
0
 async def force_remove(self, ctx, mention):
     """Remove the player from the current queue."""
     mode = get_channel_mode(ctx)
     player = await get_player_by_mention(ctx, mode, mention)
     game = get_game(ctx)
     queue = game.queues[mode]
     await ctx.send(embed=Embed(color=0x00FF00,
         description=queue.remove_player(player)))
Пример #10
0
    async def ban(self, ctx, mention, timeUnity, *reason):
        """Bans the player for a certain time.

        Example:
        !ban @Anddy 2h code very badly
        unity must be in s, m, h, d (secs, mins, hours, days).

        """

        id = await get_id(ctx, mention)
        time = split_with_numbers(timeUnity)
        unity = ""
        if len(time) == 2:
            time, unity = time
        total_sec = await get_total_sec(ctx, time, unity)
        get_game(ctx).ban_player(id, total_sec, ' '.join(reason))
        await ctx.send(embed=Embed(color=0x00FF00,
            description=f"{mention} has been banned ! Check !bans"))
Пример #11
0
    async def canceled(self, ctx, mode):
        """Display every canceled games of a specific mode.

        Example: !cl 2
        Will show every canceled games in 2vs2.
        """
        game = get_game(ctx)
        msg = await ctx.send(embed=game.canceled(mode))
        await add_scroll(msg)
Пример #12
0
    async def undecided(self, ctx, mode):
        """Display every undecided games.

        Example: !undecided 2
        Will show every undecided games in 2vs2, with the format below.
        id: [id], Red team: [player1, player2], Blue team: [player3, player4]."""
        game = get_game(ctx)
        msg = await ctx.send(embed=game.undecided(mode))
        await add_scroll(msg)
Пример #13
0
    async def uncancel(self, ctx, mode, id_game):
        """Uncancel the game given in arg.

        Example: !uncancel 1 3
        will uncancel the game with the id 3 in the mode 1vs1.
        """
        game = get_game(ctx)
        await ctx.send(embed=Embed(
            color=0x00FF00, description=game.uncancel(mode, int(id_game))))
Пример #14
0
    async def archived(self, ctx, mode):
        """Display every games of a specific mode.

        Example: !archived 2
        Will show every games in 2vs2, with the format below.
        id: [id], Winner: Team Red/Blue, Red team: [player1, player2],
        Blue team: [player3, player4]."""
        game = get_game(ctx)
        msg = await ctx.send(embed=game.archived(mode))
        await add_scroll(msg)
Пример #15
0
    def predicate(ctx):
        args = ctx.message.content.split(' ')
        if len(args) < 2:
            raise commands.errors.BadArgument("The mode argument is missing.")
        if args[1] not in get_game(ctx).available_modes:
            raise commands.errors.BadArgument(
                f"The mode is incorrect, you wrote {args[1]}\n"
                f"But it must be in {str(get_game(ctx).available_modes)}")

        return True
Пример #16
0
    async def queue(self, ctx):
        """Show the current queue.

        When using it on a channel in Modes category, the user will see the
        current queue with everyone's Elo.
        Can't be used outside Modes category.
        """
        game = get_game(ctx)
        mode = get_channel_mode(ctx)
        await ctx.send(
            embed=Embed(color=0x00FF00, description=str(game.queues[mode])))
Пример #17
0
    async def undo(self, ctx, mode, id_game):
        """Undo a game.

        Example: !undo 1 7
        in the mode 1vs1, in the 7th game.
        This will reset the ranking updates of this match.
        The game will be in undecided.
        """
        game = get_game(ctx)
        await ctx.send(embed=Embed(color=0x00FF00,
                                   description=game.undo(mode, int(id_game))))
Пример #18
0
    async def setfavpos(self, ctx, *args):
        """The arguments will now be in the list that players can pick as position.

        example:
        !setfavpos gk dm am st
        will allow the players to use
        !pos st gk am dm
        """
        game = get_game(ctx)
        setattr(game, "available_positions", list(args))
        await ctx.send(
            f"The available_positions are now {game.available_positions}")
Пример #19
0
    async def rank(self, ctx, mode, name):
        """Show the rank of the name."""
        ranks = get_game(ctx).ranks[mode]
        if name not in ranks:
            await ctx.send(embed=Embed(
                color=0x000000,
                description="Couldn't find the rank with that name."))
            return

        await ctx.send(embed=Embed(color=0x00FF00,
                                   description=str(ranks[name])).set_thumbnail(
                                       url=ranks[name].url))
Пример #20
0
    async def rename(self, ctx, new_name=""):
        """Will rename the user in every leaderboards.

        With no argument, the user will have his name resetted.
        Only usable in #register
        """
        game = get_game(ctx)
        if not new_name:
            new_name = ctx.author.nick if ctx.author.nick is not None else ctx.author.name
        for mode in game.leaderboards:
            if ctx.author.id in game.leaderboards[mode]:
                game.leaderboards[mode][ctx.author.id].name = new_name
        await ctx.send(f"You have been renamed to {new_name}")
Пример #21
0
 async def leave_with(self, ctx):
     game = get_game(ctx)
     mode = get_channel_mode(ctx)
     queue = game.queues[mode]
     player = await get_player_by_id(ctx, mode, ctx.author.id)
     if player in queue.players:
         # The queue is full after the second team gets added so they can't leave anyway
         queue.players = queue.players[queue.max_queue // 2:]
         await ctx.send(embed=Embed(
             color=0x00FF00,
             description="Your team was removed from the queue."))
         return
     await send_error(ctx, "You are not in the queue.")
Пример #22
0
    async def force_quit(self, ctx, mention):
        """Delete the seized user from the registered players.

        Example: !force_quit @Anddy
        The command is the same than quit_elo except that the user has to make
        someone else quit the Elo.
        Can't be undone."""
        game = get_game(ctx)
        id = await get_id(ctx, mention)
        game.erase_player_from_queues(id)
        game.erase_player_from_leaderboards(id)

        await ctx.send(embed=Embed(color=0x00FF00,
            description=f'{mention} has been removed from the rankings'))
Пример #23
0
    async def remove_non_server_players(self, ctx):
        """Remove people that aren't in the server anymore."""
        game = get_game(ctx)
        guild = self.bot.get_guild(ctx.guild.id)
        start = sum(len(v) for mode, v in game.leaderboards.items())
        for mode in game.available_modes:
            game.leaderboards[mode] = {
                id: player for id, player in game.leaderboards[mode].items()
                if guild.get_member(id) is not None
            }
        end = sum(len(v) for mode, v in game.leaderboards.items())

        await ctx.send(embed=Embed(color=0x00FF00,
            description=f"You kicked {start - end} members from the leaderboards"))
Пример #24
0
    async def leaderboard(self, ctx, mode, stat_key="elo"):
        """Show current leaderboard.

        Example: !lb 1 wins
        Will show the leaderboard of the mode 1vs1 based on the wins.
        [mode] can be any mode in !modes.
        [stats key] can be any stat in !info. e.g:
        name, elo, wins, losses, nb_matches, wlr
        most_wins_in_a_row, most_losses_in_a_row.
        By default, if the stats key is missing, the bot will show the elo lb.
        """
        game = get_game(ctx)
        msg = await ctx.send(embed=game.leaderboard(mode, stat_key, 1))
        await add_scroll(msg)
Пример #25
0
    async def leave(self, ctx):
        """Remove the player from the queue.

        As opposite to the !join, the leave will remove the player from the
        queue if he was in.
        Can't be used outside Modes category.
        The user needs to be in the queue for using this command.
        The user can't leave a queue after it went full."""
        game = get_game(ctx)
        mode = get_channel_mode(ctx)
        player = await get_player_by_id(ctx, mode, ctx.author.id)
        await ctx.send(
            embed=Embed(color=0x00FF00,
                        description=game.queues[mode].remove_player(player)))
Пример #26
0
    async def history(self, ctx, mode, mention=""):
        """Show every matches the user played in.

        Example: !h 1 @Anddy
        With no argument, the !info will show the user's stats.
        With a player_name as argument, if the player exists, this will show
        is stats in the seized mode.
        Can be used only in info_chat channel.
        """
        game = get_game(ctx)
        player = await get_player_by_mention(ctx, mode, mention) if mention\
            else await get_player_by_id(ctx, mode, ctx.author.id)

        msg = await ctx.send(embed=game.history(mode, player))
        await add_scroll(msg)
Пример #27
0
 async def register_all(self, ctx):
     """Register to every available modes in one command."""
     game = get_game(ctx)
     name = ctx.author.id
     for mode in game.leaderboards:
         if name not in game.leaderboards[mode]:
             game.leaderboards[mode][name] = Player(ctx.author.name,
                                                    ctx.author.id)
         num = int(split_with_numbers(mode)[0])
         role = discord.utils.get(ctx.guild.roles,
                                  name=f"{num}vs{num} Elo Player")
         await ctx.author.add_roles(role)
     await ctx.send(embed=Embed(
         color=0x00FF00,
         description=f"<@{name}> has been registered for every mode."))
Пример #28
0
    async def quit_elo(self, ctx):
        """Delete the user from the registered players.

        The user will lose all of his data after the command.
        Can be used only in Bye channel.
        Can't be undone."""
        game = get_game(ctx)
        id = ctx.author.id

        game.erase_player_from_queues(id)
        game.erase_player_from_leaderboards(id)

        await ctx.send(embed=Embed(
            color=0x00FF00,
            description=f'<@{id}> has been removed from the rankings'))
Пример #29
0
 async def clear_queue(self, ctx):
     """Clear the current queue."""
     game = get_game(ctx)
     mode = get_channel_mode(ctx)
     last_id = game.queues[mode].game_id
     if not game.queues[mode].has_queue_been_full:
         for player in game.queues[mode].players:
             if player in TIMEOUTS:
                 TIMEOUTS[player].cancel()
                 TIMEOUTS.pop(player, None)
         game.queues[mode] = Queue(
             2 * int(split_with_numbers(mode)[0]), game.queues[mode].mode,
             game.queues[mode].mapmode, last_id)
     await ctx.send(embed=Embed(color=0x00FF00,
                                description="The queue is now empty"))
Пример #30
0
    async def cancel(self, ctx, mode, id_game):
        """Cancel the game given in arg.

        Example: !cancel 1 3
        will cancel the game with the id 3 in the mode 1vs1.
        """
        game = get_game(ctx)
        if game.cancel(mode, int(id_game)):
            await ctx.send(embed=Embed(
                color=0x00FF00,
                description=f"The game {id_game} has been canceled"))
        else:
            await ctx.send(embed=Embed(
                color=0x000000,
                description=
                f"Couldn't find the game {id_game} in the current games."))