Untitled

 avatar
unknown
python
a year ago
11 kB
8
Indexable
import discord
from discord.ext import commands
import asyncio
import random

intents = discord.Intents.all()
bot = commands.Bot(command_prefix='/', intents=intents)

# Global variables to store queue and player data
queues = {}
players_in_queue = {}
players_in_match = {}
players = {}

# Function to initialize player data
def initialize_player(player_id, player_name):
    if player_id not in players:
        players[player_id] = {
            'name': player_name,
            'elo': 1000,  # Initial ELO, adjust as needed
            'winning_streak': 0,
            'team': None  # Initialize team as None
        }

# Function to calculate ELO changes
def calculate_elo_change(winning_streak):
    elo_change = 10
    if winning_streak >= 3:
        elo_change += 2
    return elo_change

@bot.command()
async def report(ctx, result: str):
    print("Report command invoked")
    print("Result:", result)
    if result.lower() not in ['w', 'l']:
        await ctx.send("Invalid report. Use `/report w` for win or `/report l` for loss.")
        return
    
    # Check if the player is in a match
    match_found = False
    for guild_id, data in queues.items():
        if ctx.author.id in [player.id for player in data['players']]:
            match_found = True
            break
    
    if not match_found:
        await ctx.send("You are not in a match.")
        return

    print("Match found. Guild ID:", guild_id)
    print("Match data:", queues[guild_id])

    # Check if the player has already reported for the current match
    if ctx.author.id in players_in_match[guild_id]['reported']:
        await ctx.send("You have already reported for this match.")
        return

    print("Player has not reported yet")

    # Get the player's team
    match_data = queues[guild_id]
    player_data = players.get(ctx.author.id)
    if player_data and 'team' in player_data:
        team = player_data['team']
    else:
        await ctx.send("You are not assigned to a team.")
        return
    
    # Find opponent's team
    opponent_team = None
    for player in match_data['players']:
        if players[player.id]['team'] != team:
            opponent_team = player
            break  # Move the break statement inside the loop

    # Calculate ELO changes
    elo_change = 0  # Initialize elo change

    if result.lower() == 'w':
        elo_change += 20  # Add 20 ELO for winning
        players[ctx.author.id]['winning_streak'] += 1
        # Deduct ELO from opponent only if the player reported a win
        players[opponent_team.id]['elo'] -= 15  # Deduct 15 ELO for opponent losing
        winner_team = team
    else:
        elo_change -= 15  # Deduct 15 ELO for losing
        players[ctx.author.id]['winning_streak'] = 0
        # Add ELO to opponent only if the player reported a loss
        players[opponent_team.id]['elo'] += 20  # Add 20 ELO for opponent winning
        winner_team = opponent_team['team']

    # Check if the player's winning streak is >= 3
    if players[ctx.author.id]['winning_streak'] >= 3:
        elo_change += 25  # Add 25 extra ELO for winning streak

    # Update ELO for the player
    players[ctx.author.id]['elo'] += elo_change

    # Mark the player as reported for this match
    players_in_match[guild_id]['reported'].append(ctx.author.id)

    print("Player reported for the match")

    # Check if all players have reported for this match
    if len(players_in_match[guild_id]['reported']) == len(match_data['players']):
        # Report the match and perform cleanup
        print("All players reported. Reporting match...")
        await report_match(ctx, guild_id, winner_team)


async def handle_queue(guild_id, ctx):
    # Create a lobby voice channel in the category
    queue_data = queues[guild_id]
    queue_code = queue_data['queue_code']
    category = discord.utils.get(ctx.guild.channels, type=discord.ChannelType.category)
    voice_category = await ctx.guild.create_category(name=f'{queue_code})', overwrites={}, reason="Creating a category for game channels")
    lobby_vc = await voice_category.create_voice_channel(name='Lobby')
    queue_data['voice_channels'].append(lobby_vc)

    print("Lobby created")

    # Initialize reported list for the match
    players_in_match[guild_id] = {'reported': [], 'voice_channels': queue_data['voice_channels']}

    # Announce that both players need to join the lobby before proceeding
    embed_message = discord.Embed(title="Lobby", description="Both players need to join the lobby voice chat to proceed.", color=0xff0000)
    await ctx.send(embed=embed_message)

    # Wait for both players to join the lobby
    while True:
        # Check if both players have joined the lobby
        if all(member.voice and member.voice.channel == lobby_vc for member in queue_data['players']):
            break
        await asyncio.sleep(5)  # Wait for 5 seconds before checking again

    print("Both players joined the lobby")

    # Split players into two teams randomly
    random.shuffle(queue_data['players'])
    team1 = queue_data['players'][:len(queue_data['players']) // 2]
    team2 = queue_data['players'][len(queue_data['players']) // 2:]

    # Set team attribute for each player
    for player in team1:
        player_data = players.get(player.id)
        if player_data:
            player_data['team'] = 'Team 1'
            # Remove player from the queue
            del players_in_queue[player.id]
    for player in team2:
        player_data = players.get(player.id)
        if player_data:
            player_data['team'] = 'Team 2'
            # Remove player from the queue
            del players_in_queue[player.id]

    # Create team voice channels
    team1_vc = await voice_category.create_voice_channel(name='Team 1')
    team2_vc = await voice_category.create_voice_channel(name='Team 2')

    print("Team voice channels created")

    # Assign teams to players and move them to respective team voice channels
    for player in team1:
        player_data = players.get(player.id)
        if player_data:
            print(f"Checking if {player.name} is connected to voice chat...")
            if player.voice:  # Check if the player is connected to a voice channel
                try:
                    print(f"{player.name} is connected to voice chat. Moving to Team 1 VC")
                    await player.move_to(team1_vc)
                    print(f"{player.name} moved to Team 1 VC")
                except Exception as e:
                    print(f"Error moving {player.name} to Team 1 VC: {e}")
            else:
                print(f"{player.name} is not connected to voice chat.")
    for player in team2:
        player_data = players.get(player.id)
        if player_data:
            print(f"Checking if {player.name} is connected to voice chat...")
            if player.voice:  # Check if the player is connected to a voice channel
                try:
                    print(f"{player.name} is connected to voice chat. Moving to Team 2 VC")
                    await player.move_to(team2_vc)
                    print(f"{player.name} moved to Team 2 VC")
                except Exception as e:
                    print(f"Error moving {player.name} to Team 2 VC: {e}")
            else:
                print(f"{player.name} is not connected to voice chat.")

    print("Players moved to team voice channels")

    # Delete the lobby channel
    await lobby_vc.delete()

    print("Lobby channel deleted")

    # Send teams message with queue code
    embed = discord.Embed(title=f"Teams Created (Queue Code: {queue_code})",
                          description="Teams have been moved to their the voice channels according to your team.",
                          color=0xff8000)
    embed.add_field(name="Team 1", value=", ".join([player.name for player in team1]), inline=False)
    embed.add_field(name="Team 2", value=", ".join([player.name for player in team2]), inline=False)
    await ctx.send(embed=embed)


# Command to view player's ELO
@bot.command()
async def elo(ctx):
    initialize_player(ctx.author.id, ctx.author.name)
    await ctx.send(f"Your ELO: {players[ctx.author.id]['elo']}")

# Command to join queue
@bot.command()
async def j(ctx):
    # Check if the player is already in a match
    if ctx.author.id in players_in_match:
        await ctx.send("You are already in a match.")
        return

    # Check if the player is already in a queue
    if ctx.author.id in players_in_queue:
        await ctx.send("You are already in a queue.")
        return

    # Check if there is an existing queue for the guild
    guild_id = ctx.guild.id
    if guild_id not in queues or len(queues[guild_id]['players']) >= 2:
        # Create a new queue
        queue_code = ''.join(random.choices('ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789', k=6))
        queues[guild_id] = {
            'players': [ctx.author],
            'voice_channels': [],
            'queue_code': queue_code
        }
        players_in_queue[ctx.author.id] = guild_id
        # Initialize player's data
        initialize_player(ctx.author.id, ctx.author.name)
    else:
        # Add the player to the existing queue
        queues[guild_id]['players'].append(ctx.author)
        players_in_queue[ctx.author.id] = guild_id
        # Initialize player's data if not already initialized
        initialize_player(ctx.author.id, ctx.author.name)

    # Send embed message confirming the player has joined the queue
    embed = discord.Embed(title="Queue Joined", description=f"{ctx.author.mention} has joined the queue.", color=0x00ff00)
    await ctx.send(embed=embed)

    # List members currently in the queue with the queue code
    queue_code = queues[guild_id]['queue_code']
    player_list = "\n".join([f"{member.mention}" for member in queues[guild_id]['players']])
    embed = discord.Embed(title=f"Current Queue (Queue Code: {queue_code})", description=player_list, color=0x0000ff)
    await ctx.send(embed=embed)

    # Check if the queue has reached its capacity (2 players)
    if len(queues[guild_id]['players']) == 2:
        await handle_queue(guild_id, ctx)


async def report_match(ctx, guild_id, winner_team):
    print("Match Message")
    # Remove players from the queue
    del queues[guild_id]

    # Delete team voice channels with error handling
    for voice_channel in players_in_match[guild_id]['voice_channels']:
        try:
            await voice_channel.delete()
        except discord.Forbidden:
            print(f"Bot does not have permission to delete voice channel: {voice_channel.name}")
        except discord.HTTPException as e:
            print(f"An error occurred while deleting voice channel {voice_channel.name}: {e}")

    # Send match report message
    embed = discord.Embed(title="Match Report",
                          description=f"{ctx.author.mention} has reported the scores. Winner: {winner_team}. If this is incorrect, please open a support ticket.",
                          color=0xff0000)
    await ctx.send(embed=embed)

    # Clear match data
    del players_in_match[guild_id]

bot.run('')
Editor is loading...
Leave a Comment