from discord import option from discord.ext import commands, tasks import discord import requests from bs4 import BeautifulSoup import re import os class PalWorld(commands.Cog): def __init__(self, bot): self.bot: commands.Bot = bot # self.poll_server_population.start() palworld = discord.SlashCommandGroup("palworld", "Palworld related commands") async def get_all_pals(ctx: discord.AutocompleteContext): """ returns a list of all pals in the game, which can then be passed to the /ship command for auto complete """ import requests from bs4 import BeautifulSoup url = "https://palworld.gg/pals" response = requests.get(url).text soup = BeautifulSoup(response, "html.parser") pal_list = [] all_pals = soup.find_all("div", class_="pal") try: for pal in all_pals: name = pal.find("div", class_="name").text.split("#", 1)[0].strip() pal_list.append(name) except: pass return pal_list @palworld.command( guild_ids=None, name="paldeck", description="Looks up data about a pal", contexts={ discord.InteractionContextType.guild, discord.InteractionContextType.bot_dm, discord.InteractionContextType.private_channel, }, integration_types={ discord.IntegrationType.guild_install, discord.IntegrationType.user_install, }, ) async def pal_lookup( self, ctx: discord.ApplicationContext, pal: discord.Option( str, autocomplete=discord.utils.basic_autocomplete(get_all_pals), description="Pal to look up", ), ): pal_url = f"https://palworld.gg/pal/{pal.lower().replace(' ', '-')}" response = requests.get(pal_url) soup = BeautifulSoup(response.text, "html.parser") elements = {} # Get the pal's primary element pal_elements_div = soup.find("div", class_="elements") element_icon = "https://palworld.gg" + pal_elements_div.find("img")["src"] element_type = pal_elements_div.text elements[element_type] = element_icon primary_element = list(elements.keys())[0] # https://discordpy.readthedocs.io/en/latest/api.html?highlight=colour#discord.Colour color_lookup = { "Dark": discord.Color.dark_purple(), "Dragon": discord.Color.purple(), "DragonDark": discord.Color.dark_purple(), "Earth": discord.Color.greyple(), "Electricity": discord.Color.yellow(), "Fire": discord.Color.red(), "Leaf": discord.Color.green(), "Ice": discord.Color.blue(), "Neutral": discord.Color.lighter_grey(), "Water": discord.Color.dark_blue(), } embed = discord.Embed( description="-------", color=color_lookup[primary_element], type="rich", title=pal.capitalize(), ) embed.set_author( name=", ".join(elements.keys()), icon_url=elements[primary_element], url=pal_url, ) embed.set_thumbnail( url="https://palworld.gg" + soup.find("div", class_="image").find_next("img")["src"] ) # embed.add_field(name="Work Skills", value="-----", inline=False) # work skills skills_emojis = { "Cooling": "❄️", "Farming": "🚜", "Gathering": "🍃", "Generating Electricity": "⚡️", "Handiwork": "🤚", "Kindling": "🔥", "Deforesting": "🪵", "Medicine Production": "💉", "Mining": "⛏️", "Planting": "🌱", "Transporting": "📦", "Watering": "💦", "Oil Extracting": "🛢️", } work_suit = ( soup.find("h2", string="Work Suitability") .find_next("div", class_="items") .find_all("div", class_="active item") ) for skill in work_suit: skill_name, skill_level = skill.text.split("Lv") embed.add_field( name=skills_emojis[skill_name] + " " + skill_name, value="%s" % (int(skill_level) * "⭐️"), inline=True, ) # Partner Skill embed.add_field(name="Partner Skill", value="-----", inline=False) skill = soup.find("div", class_="passive skills") skill_name = skill.find_next("div", class_="name").text skill_description = skill.find_next("p").text embed.add_field( name=skill_name, value=skill_description, inline=False, ) # Drops embed.add_field(name="Drops", value="-----", inline=False) drops = [ x.text for x in soup.find("h2", string="Possible Drops") .find_next("table") .find_all("div", class_="name") ] for item in drops: embed.add_field( name=item, value="", inline=False, ) await ctx.defer() await ctx.send_followup(embed=embed) @palworld.command( guild_ids=None, name="elements", description="Posts an infographic about which Pal elements are weak/strong against which", contexts={ discord.InteractionContextType.guild, discord.InteractionContextType.bot_dm, discord.InteractionContextType.private_channel, }, integration_types={ discord.IntegrationType.guild_install, discord.IntegrationType.user_install, }, ) async def post_medpen_guide(self, ctx: discord.ApplicationContext): await ctx.respond( "https://img.game8.co/3822502/5ae8382d16bd390dd19f343e87680d51.png/show" ) # @tasks.loop(seconds=60) # async def poll_server_population(self): # # Wait until the bot is ready before we actually start executing code # await self.bot.wait_until_ready() # from source_rcon import SourceRcon # from loguru import logger # logger.disable("source_rcon") # rcon = SourceRcon("192.168.1.200", 25575, os.getenv("pal_rcon_pass")) # num_players = len(rcon.send_command("ShowPlayers").split("\n")[1:-1]) # # channel = self.bot.get_channel(1201389692759842816) # test server # channel = self.bot.get_channel(1199397770746925239) # if str(num_players) in channel.name.split("/")[0]: # return # await channel.edit(name="Palworlders (%s/16 online)" % num_players) def setup(bot): bot.add_cog(PalWorld(bot))