From e73db927c17866793293868d915bf0e37a906737 Mon Sep 17 00:00:00 2001 From: Parker Date: Thu, 28 Nov 2024 00:41:33 -0600 Subject: Create `create_embed` template to replace `discord.Embed()` - Auto-set color to BOT_COLOR - Set footer to timestamp (overridden is timestamp is passed) - Optional thumbnail --- code/cogs/skip.py | 40 +++++++++++++++++----------------------- 1 file changed, 17 insertions(+), 23 deletions(-) (limited to 'code/cogs/skip.py') diff --git a/code/cogs/skip.py b/code/cogs/skip.py index c35a203..46a767f 100644 --- a/code/cogs/skip.py +++ b/code/cogs/skip.py @@ -5,7 +5,7 @@ from discord.ext import commands from cogs.music import Music import asyncio -from utils.config import BOT_COLOR +from utils.config import create_embed from utils.custom_sources import LoadError @@ -22,22 +22,25 @@ class Skip(commands.Cog): "Skips the song that is currently playing" player = self.bot.lavalink.player_manager.get(interaction.guild.id) - embed = discord.Embed(color=BOT_COLOR) - if number != 1: if number < 1: - embed.title = "Invalid Number" - embed.description = "The number option cannot be less than 1" + embed = create_embed( + title="Invalid Number", + description="The number option cannot be less than 1", + ) return await interaction.response.send_message( embed=embed, ephemeral=True ) elif number > len(player.queue): - embed.title = "Number too Large" - embed.description = ( - "The number you entered is larger than the number of songs" - " in queue. If you want to stop playing music entirely," - " try the command." + embed = create_embed( + title="Number too Large", + description=( + "The number you entered is larger than the number of" + " songs in queue. If you want to stop playing music" + " entirely, try the " + " command." + ), ) return await interaction.response.send_message( embed=embed, ephemeral=True @@ -53,14 +56,13 @@ class Skip(commands.Cog): # If the song is on repeat, catch the IndexError and get the current song # Otherwise, pass if player.loop == 1: - embed = discord.Embed( + embed = create_embed( title="Song on Repeat", description=( "There is nothing in queue, but the current song is on" " repeat. Use to stop" " playing music." ), - color=BOT_COLOR, ) return await interaction.response.send_message( embed=embed, ephemeral=True @@ -77,34 +79,26 @@ class Skip(commands.Cog): await player.skip() if not player.current: - embed = discord.Embed( + embed = create_embed( title="End of Queue", description=( "All songs in queue have been played. Thank you for using" f" me :wave:\n\nIssued by: {interaction.user.mention}" ), - color=BOT_COLOR, ) return await interaction.response.send_message(embed=embed) # It takes a sec for the new track to be grabbed and played # So just wait a sec before sending the message await asyncio.sleep(0.5) - embed = discord.Embed( + embed = create_embed( title="Track Skipped", description=( f"**Now Playing: [{next_song.title}]({next_song.uri})** by" f" {next_song.author}\n\nQueued by:" f" {next_song.requester.mention}" ), - color=BOT_COLOR, - ) - embed.set_thumbnail(url=next_song.artwork_url) - embed.set_footer( - text=datetime.datetime.now(datetime.timezone.utc).strftime( - "%Y-%m-%d %H:%M:%S" - ) - + " UTC" + thumbnail=next_song.artwork_url, ) await interaction.response.send_message(embed=embed) -- cgit v1.2.3-70-g09d2 From 33493b7b4ec72636d73910cff93a9b3a3c863a2f Mon Sep 17 00:00:00 2001 From: Parker Date: Fri, 29 Nov 2024 00:24:18 -0600 Subject: Continue skipping tracks on LoadError --- code/cogs/skip.py | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) (limited to 'code/cogs/skip.py') diff --git a/code/cogs/skip.py b/code/cogs/skip.py index 46a767f..eb4bf51 100644 --- a/code/cogs/skip.py +++ b/code/cogs/skip.py @@ -70,13 +70,13 @@ class Skip(commands.Cog): else: pass - # Sometimes when a playlist/album of custom source tracks are loaded, one is not able to be found - # so, when a user attempts to skip to that track, we get a LoadError. In this case, just pass it. - try: - await player.skip() - except LoadError: - pass - await player.skip() + # Skip current track, continue skipping on LoadError + while True: + try: + await player.skip() + break + except LoadError: + continue if not player.current: embed = create_embed( -- cgit v1.2.3-70-g09d2 From 4e8030eca4b1f4028268683ccfc7b481b1608dde Mon Sep 17 00:00:00 2001 From: Parker Date: Fri, 29 Nov 2024 01:36:06 -0600 Subject: Largely embed wording changes + other small tweaks + combine pause commands --- code/cogs/autoplay.py | 30 ++++++++----------- code/cogs/bug.py | 8 +++-- code/cogs/help.py | 18 +++++------ code/cogs/lyrics.py | 5 ++-- code/cogs/news.py | 32 +++++--------------- code/cogs/nowplaying.py | 2 +- code/cogs/pause.py | 43 +++++++++++++++++++-------- code/cogs/play.py | 25 +++++++++++----- code/cogs/remove.py | 19 ++++++++---- code/cogs/resume.py | 33 -------------------- code/cogs/skip.py | 15 ++++------ code/cogs/stop.py | 4 +-- code/utils/command_tree.py | 17 ----------- code/utils/source_helpers/spotify/playlist.py | 2 +- 14 files changed, 109 insertions(+), 144 deletions(-) delete mode 100644 code/cogs/resume.py (limited to 'code/cogs/skip.py') diff --git a/code/cogs/autoplay.py b/code/cogs/autoplay.py index 5c2ec29..6c815b9 100644 --- a/code/cogs/autoplay.py +++ b/code/cogs/autoplay.py @@ -19,16 +19,15 @@ class Autoplay(commands.Cog): async def autoplay( self, interaction: discord.Interaction, toggle: Literal["ON", "OFF"] ): - "Keep the music playing forever with music suggestions from OpenAI" + "Keep music playing 24/7 with AI-generated song recommendations" if toggle == "OFF": self.bot.autoplay.remove(interaction.guild.id) embed = create_embed( title="Autoplay Off", description=( - "Autoplay has been turned off. I will no longer" - " automatically add new songs to the queue based on AI" - " recommendations." + "Autoplay has been turned off. Song recommendations will" + " no longer be added to the queue." ), ) return await interaction.response.send_message(embed=embed) @@ -40,8 +39,8 @@ class Autoplay(commands.Cog): title="Autoplay Already Enabled", description=( "Autoplay is already enabled. If you would like to turn it" - " off, choose the `OFF` option in the" - " command." + " off, run and choose the" + " `OFF` option." ), ) return await interaction.response.send_message( @@ -54,9 +53,8 @@ class Autoplay(commands.Cog): embed = create_embed( title="Not Enough Context", description=( - "You must have at least 5 songs in the queue so that I can" - " get a good understanding of what music I should continue" - " to play. Add some more music to the queue, then try" + "Autoplay requires at least 5 songs in the queue in order" + " to generate recommendations. Please add more and try" " again." ), ) @@ -84,9 +82,9 @@ class Autoplay(commands.Cog): embed = create_embed( title=":infinity: Autoplay Enabled :infinity:", description=( - "I have added a few similar songs to the queue and will" - " continue to do so once the queue gets low again. Now" - " just sit back and enjoy the music!\n\nEnabled by:" + "Recommendations have been generated and added to the" + " queue. Autoplay will automatically search for more" + " songs whenever the queue gets low.\n\nEnabled by:" f" {interaction.user.mention}" ), ) @@ -96,11 +94,9 @@ class Autoplay(commands.Cog): embed = create_embed( title="Autoplay Error", description=( - "Autoplay is an experimental feature, meaning sometimes it" - " doesn't work as expected. I had an error when attempting" - " to get similar songs for you, please try running the" - " command again. If the issue persists, fill out a bug" - " report with the command." + "Unable to get AI recommendations at this time. Please try" + " again. If issues continue, please fill out a bug report" + " with ." ), ) await interaction.edit_original_response(embed=embed) diff --git a/code/cogs/bug.py b/code/cogs/bug.py index fecf5e6..aec51b6 100644 --- a/code/cogs/bug.py +++ b/code/cogs/bug.py @@ -15,7 +15,9 @@ class BugReport(discord.ui.Modal, title="Report a bug"): placeholder="EX: itsmefreddy01...", ) command = discord.ui.TextInput( - label="Command with error", placeholder="EX: skip...", required=True + label="Command with error", + placeholder="EX: autoplay, skip...", + required=True, ) report = discord.ui.TextInput( label="A detailed report of the bug", @@ -27,8 +29,8 @@ class BugReport(discord.ui.Modal, title="Report a bug"): async def on_submit(self, interaction: discord.Interaction): await interaction.response.send_message( - f"Thanks for your bug report. We will get back to you as soon as" - f" possible", + f"Thanks for your bug report. We will work on resolving the" + f" issue as soon as possible.", ephemeral=True, ) channel = self.bot.get_channel(BUG_CHANNEL_ID) diff --git a/code/cogs/help.py b/code/cogs/help.py index ea54058..2475564 100644 --- a/code/cogs/help.py +++ b/code/cogs/help.py @@ -169,18 +169,18 @@ class Help(commands.Cog): embed = discord.Embed( title=f":musical_note: Help :musical_note:", description=( - "**Check out recent news and updates about the bot with" - " the command!\n\u200b**" + "**Check out recent updates with the" + " command!\n\u200b**" ), color=BOT_COLOR, ) embed.add_field( - name="**Use Me**", + name="**Get Started**", value=( - "> To get started, use the " - " command and enter the name or link to the song of your" - " choice." + "> Start playing music with the" + " command. Enter the name or" + " link of the song you want to play." ), inline=False, ) @@ -195,9 +195,9 @@ class Help(commands.Cog): embed.add_field( name="**Help for Specific Commands**", value=( - "> If you want more information on how to use a specific" - " command, use the command and" - " include the specific command." + "> To get information on a specific command, use" + " and include the command" + " name." ), inline=False, ) diff --git a/code/cogs/lyrics.py b/code/cogs/lyrics.py index 6e3a1d3..8c47457 100644 --- a/code/cogs/lyrics.py +++ b/code/cogs/lyrics.py @@ -65,8 +65,9 @@ class Lyrics(commands.Cog): f" {player.current.author}" ), description=( - "Song lyrics are too long to display on Discord. [Click" - f" here to view the lyrics on Genius]({song.url})." + "The lyrics for this song are too long to display on" + " Discord. [Click here to view the lyrics on" + f" Genius]({song.url})." ), thumbnail=player.current.artwork_url, ) diff --git a/code/cogs/news.py b/code/cogs/news.py index 434d8b3..35aeb04 100644 --- a/code/cogs/news.py +++ b/code/cogs/news.py @@ -13,7 +13,7 @@ class News(commands.Cog): async def news(self, interaction: discord.Interaction): "Get recent news and updates about the bot" embed = discord.Embed( - title="Recent News :newspaper2:", + title="Recent News and Updates", description=( "View recent code commits" " [here](https://github.com/packetparker/guava/commits)\n\u200b" @@ -22,30 +22,12 @@ class News(commands.Cog): ) embed.add_field( - name="**Lyrics!**", - value=( - "> You can now get lyrics for the song that is currently" - " playing. Just use the `/lyrics` command! Some songs may not" - " have lyrics available, but the bot will do its best to find" - " them." - ), - ) - - embed.add_field( - name="**Apple Music Support!**", - value=( - "> After some trial and error, you can now play music through" - " Apple Music links. Just paste the link and the bot will do" - " the rest!" - ), - ) - - embed.add_field( - name="**Autoplay Update**", - value=( - "> Autoplay is now much more stable after a revamp of the" - " previous system. If you experienced short outages recently," - " this was due to the update. Thank you for your patience!" + name="**Limited YouTube Support**", + description=( + "Support for YouTube links and searches has been added. This" + " is currently in a testing phase and is not guaranteed to" + " work. If you encounter any issues, please submit a but" + " report." ), inline=False, ) diff --git a/code/cogs/nowplaying.py b/code/cogs/nowplaying.py index 1f29c3c..71f0d75 100644 --- a/code/cogs/nowplaying.py +++ b/code/cogs/nowplaying.py @@ -15,7 +15,7 @@ class NowPlaying(commands.Cog): @app_commands.command() @app_commands.check(Music.create_player) async def np(self, interaction: discord.Interaction): - "Show what song is currently playing" + "See what song is currently playing" player = self.bot.lavalink.player_manager.get(interaction.guild.id) time_in = str(datetime.timedelta(milliseconds=player.position))[:-7] diff --git a/code/cogs/pause.py b/code/cogs/pause.py index fb55aa4..eb3b508 100644 --- a/code/cogs/pause.py +++ b/code/cogs/pause.py @@ -1,5 +1,6 @@ import discord import datetime +from typing import Literal from discord import app_commands from discord.ext import commands from cogs.music import Music @@ -12,21 +13,39 @@ class Pause(commands.Cog): self.bot = bot @app_commands.command() + @app_commands.describe(pause="TRUE to pause, FALSE to unpause") @app_commands.check(Music.create_player) - async def pause(self, interaction: discord.Interaction): - "Pauses the song that is currently playing" + async def pause( + self, interaction: discord.Interaction, pause: Literal["TRUE", "FALSE"] + ): + "Pause or unpause the current song" player = self.bot.lavalink.player_manager.get(interaction.guild.id) - await player.set_pause(pause=True) - embed = create_embed( - title=f"Music Now Paused ⏸️", - description=( - f"**[{player.current.title}]({player.current.uri})**\n\nQueued" - f" by: {player.current.requester.mention}" - ), - thumbnail=player.current.artwork_url, - ) - await interaction.response.send_message(embed=embed) + if pause: + await player.set_pause(pause=True) + embed = create_embed( + title=f"Music Paused ⏸️", + description=( + f"**[{player.current.title}]({player.current.uri})** by" + f" {player.current.author}\n\nQueued by:" + f" {player.current.requester.mention}" + ), + thumbnail=player.current.artwork_url, + ) + return await interaction.response.send_message(embed=embed) + + else: + await player.set_pause(pause=False) + embed = create_embed( + title=f"Music Unpaused ▶️", + description=( + f"**[{player.current.title}]({player.current.uri})** by" + f" {player.current.author}\n\nQueued by:" + f" {player.current.requester.mention}" + ), + thumbnail=player.current.artwork_url, + ) + return await interaction.response.send_message(embed=embed) async def setup(bot): diff --git a/code/cogs/play.py b/code/cogs/play.py index ec32c06..56e3344 100644 --- a/code/cogs/play.py +++ b/code/cogs/play.py @@ -91,7 +91,7 @@ class Play(commands.Cog): # Create the embed if the results are a playlist if results.load_type == LoadType.PLAYLIST: embed = create_embed( - title="Songs Queued!", + title="Songs Queued", description=( f"**{results.playlist_info.name}**\n" f"` {len(results.tracks)} ` tracks\n\n" @@ -104,7 +104,7 @@ class Play(commands.Cog): # Remove all but first track (most relevant result) results.tracks = results.tracks[:1] embed = create_embed( - title="Song Queued!", + title="Song Queued", description=( f"**{results.tracks[0].title}** by" f" **{results.tracks[0].author}**\n\nQueued by:" @@ -119,9 +119,9 @@ class Play(commands.Cog): embed = create_embed( title="Nothing Found", description=( - "I was not able to find or load any songs for that query." - " Please try again and fill out a bug report with" - " if this continues to happen." + "No songs were found for that query. Please try again and" + " fill out a bug report with if" + " this continues to happen." ), ) return await interaction.response.send_message( @@ -143,9 +143,20 @@ class Play(commands.Cog): try: await results.tracks[0].load(player.node) # If it fails, remove it from the queue and alert the user - except LoadError: + except LoadError as e: player.queue.remove(results.tracks[0]) - raise LoadError + embed = create_embed( + title="Load Error", + description=( + "Apple Music and Spotify do not allow direct" + " playing from their websites, and I was unable to" + " load a track on a supported platform. Please try" + " again." + ), + ) + return await interaction.response.send_message( + embed=embed, ephemeral=True + ) # Join the voice channel if not already connected if not interaction.guild.voice_client: diff --git a/code/cogs/remove.py b/code/cogs/remove.py index bba07a4..82e5848 100644 --- a/code/cogs/remove.py +++ b/code/cogs/remove.py @@ -23,12 +23,20 @@ class Remove(commands.Cog): title="Nothing Queued", description="There are no songs in the queue to remove.", ) - return await interaction.response.send_message(embed=embed) + return await interaction.response.send_message( + embed=embed, ephemeral=True + ) if number > len(player.queue) or number < 1: + embed = create_embed( + title="Number Out of Range", + description=( + "The number you entered is outside of the allowed range." + " Please try again with a valid song number." + ), + ) return await interaction.response.send_message( - "Number out of range - please try again!", - ephemeral=True, + embed=embed, ephemeral=True ) index = number - 1 @@ -40,9 +48,8 @@ class Remove(commands.Cog): embed = create_embed( title="Song Removed from Queue", description=( - "**Song Removed -" - f" [{removed_title}]({removed_url})**\n\nIssued by:" - f" {interaction.user.mention}" + f"**[{removed_title}]({removed_url})** has been unqueued.\n\n" + f"Issued by: {interaction.user.mention}" ), thumbnail=removed_artwork, ) diff --git a/code/cogs/resume.py b/code/cogs/resume.py deleted file mode 100644 index 6297404..0000000 --- a/code/cogs/resume.py +++ /dev/null @@ -1,33 +0,0 @@ -import discord -import datetime -from discord import app_commands -from discord.ext import commands -from cogs.music import Music - -from utils.config import create_embed - - -class Resume(commands.Cog): - def __init__(self, bot): - self.bot = bot - - @app_commands.command() - @app_commands.check(Music.create_player) - async def resume(self, interaction: discord.Interaction): - "Resumes the paused song" - player = self.bot.lavalink.player_manager.get(interaction.guild.id) - - await player.set_pause(pause=False) - embed = create_embed( - title=f"Music Now Resumed ⏯️", - description=( - f"**[{player.current.title}]({player.current.uri})**\n\nQueued" - f" by: {player.current.requester.mention}" - ), - thumbnail=player.current.artwork_url, - ) - await interaction.response.send_message(embed=embed) - - -async def setup(bot): - await bot.add_cog(Resume(bot)) diff --git a/code/cogs/skip.py b/code/cogs/skip.py index eb4bf51..a228444 100644 --- a/code/cogs/skip.py +++ b/code/cogs/skip.py @@ -75,15 +75,16 @@ class Skip(commands.Cog): try: await player.skip() break - except LoadError: + except LoadError as e: continue if not player.current: embed = create_embed( title="End of Queue", description=( - "All songs in queue have been played. Thank you for using" - f" me :wave:\n\nIssued by: {interaction.user.mention}" + "I have left the voice channel as all songs in the queue" + " have been played.\n\n" + f"Issued by: {interaction.user.mention}" ), ) return await interaction.response.send_message(embed=embed) @@ -92,13 +93,9 @@ class Skip(commands.Cog): # So just wait a sec before sending the message await asyncio.sleep(0.5) embed = create_embed( - title="Track Skipped", - description=( - f"**Now Playing: [{next_song.title}]({next_song.uri})** by" - f" {next_song.author}\n\nQueued by:" - f" {next_song.requester.mention}" + title=( + f"{'Track Skipped' if number == 1 else f'{number} Tracks Skipped'}" ), - thumbnail=next_song.artwork_url, ) await interaction.response.send_message(embed=embed) diff --git a/code/cogs/stop.py b/code/cogs/stop.py index 5d1f148..9f4810e 100644 --- a/code/cogs/stop.py +++ b/code/cogs/stop.py @@ -28,8 +28,8 @@ class Stop(commands.Cog): embed = create_embed( title="Queue Cleared and Music Stopped", description=( - "Thank you for using me :wave:\n\nIssued by:" - f" {interaction.user.mention}" + f"Thank you for using {self.bot.me.mention}\n\n" + f"Issued by: {interaction.user.mention}" ), ) await interaction.response.send_message(embed=embed) diff --git a/code/utils/command_tree.py b/code/utils/command_tree.py index 03ecfe4..afdbd2c 100644 --- a/code/utils/command_tree.py +++ b/code/utils/command_tree.py @@ -69,22 +69,5 @@ class Tree(app_commands.CommandTree): except discord.errors.InteractionResponded: await interaction.followup.send(embed=embed, ephemeral=True) - elif (error, LoadError): - embed = create_embed( - title="Load Error", - description=( - "Apple Music and Spotify do not allow direct playing from" - " their websites, and I was unable to load a track on a" - " valid source. Please try again." - ), - ) - # Only send the error if the interaction is still valid - try: - await interaction.response.send_message( - embed=embed, ephemeral=True - ) - except discord.errors.InteractionResponded: - pass - else: raise error diff --git a/code/utils/source_helpers/spotify/playlist.py b/code/utils/source_helpers/spotify/playlist.py index c7313a4..7ca9c6a 100644 --- a/code/utils/source_helpers/spotify/playlist.py +++ b/code/utils/source_helpers/spotify/playlist.py @@ -15,7 +15,7 @@ async def load( """ Get the playlist info from the Spotify API """ - playlist_id = query.split("/playlist/")[1].split("?si=")[0] + playlist_id = query.split("/playlist/")[1] try: # Get the playlist info -- cgit v1.2.3-70-g09d2 From 00bf7880be8e9bae5ba3bcabe6fa9a1ea220db86 Mon Sep 17 00:00:00 2001 From: Parker Date: Sat, 30 Nov 2024 00:22:27 -0600 Subject: Update success message embed --- code/cogs/skip.py | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'code/cogs/skip.py') diff --git a/code/cogs/skip.py b/code/cogs/skip.py index a228444..d1f1dfb 100644 --- a/code/cogs/skip.py +++ b/code/cogs/skip.py @@ -96,6 +96,12 @@ class Skip(commands.Cog): title=( f"{'Track Skipped' if number == 1 else f'{number} Tracks Skipped'}" ), + description=( + f"**[{player.current.title}]({player.current.uri})**" + f" by **{player.current.author}** is now playing\n\n" + f"Issued by: {interaction.user.mention}" + ), + thumbnail=player.current.artwork_url, ) await interaction.response.send_message(embed=embed) -- cgit v1.2.3-70-g09d2 From 9f7c2860787a9312f1fedac69eb69f19ad52b363 Mon Sep 17 00:00:00 2001 From: Parker Date: Sun, 1 Dec 2024 01:48:53 -0600 Subject: Tidy up unused variable/old logic --- code/cogs/skip.py | 35 +++++++++++++++-------------------- 1 file changed, 15 insertions(+), 20 deletions(-) (limited to 'code/cogs/skip.py') diff --git a/code/cogs/skip.py b/code/cogs/skip.py index d1f1dfb..7bed931 100644 --- a/code/cogs/skip.py +++ b/code/cogs/skip.py @@ -49,26 +49,21 @@ class Skip(commands.Cog): for i in range(number - 2, -1, -1): player.queue.pop(i) - # If there is a next song, get it - try: - next_song = player.queue[0] - except IndexError: - # If the song is on repeat, catch the IndexError and get the current song - # Otherwise, pass - if player.loop == 1: - embed = create_embed( - title="Song on Repeat", - description=( - "There is nothing in queue, but the current song is on" - " repeat. Use to stop" - " playing music." - ), - ) - return await interaction.response.send_message( - embed=embed, ephemeral=True - ) - else: - pass + # If the queue is empty, but the current song is on repeat + if player.loop == 1 and not player.queue: + embed = create_embed( + title="Song on Repeat", + description=( + "There is nothing in queue, but the current song is on" + " repeat. Use to stop" + " playing music." + ), + ) + return await interaction.response.send_message( + embed=embed, ephemeral=True + ) + else: + pass # Skip current track, continue skipping on LoadError while True: -- cgit v1.2.3-70-g09d2