Im making a music bot but i get
AttributeError: 'Player' object has no attribute 'ctx'
when i do >>play some music when another music is playing (supposed to be for queue)
full error
Bot Online
Node <8d0e8f15e4723f72> is ready
Ignoring exception in on_wavelink_track_end
Traceback (most recent call last):
File "/home/catiganvien3/.local/lib/python3.9/site-packages/discord/client.py", line 343, in _run_event
await coro(*args, **kwargs)
File "/home/catiganvien3/scripts/WaveLinkBot/main.py", line 28, in on_wavelink_track_end
ctx = player.ctx
AttributeError: 'Player' object has no attribute 'ctx'
Full code is
import wavelink
import discord
from discord.ext import commands
import asyncio
import os
bot = commands.Bot(command_prefix='>>')
#bot.event
async def on_ready():
print('Bot Online')
bot.loop.create_task(node_connect())
#bot.event
async def on_wavelink_node_ready(node: wavelink.Node):
print(f'Node <{node.identifier}> is ready')
async def node_connect():
await bot.wait_until_ready()
await wavelink.NodePool.create_node(bot=bot, host='ash-01.thermalhosting.com', port=2008, password='ASH-01')
#bot.event
async def on_wavelink_track_end(player: wavelink.Player, track: wavelink.Track, reason):
ctx = player.ctx
vc: player = ctx.voice_client
if vc.loop:
return await vc.play(track)
try:
next_song = vc.queue.get()
await vc.play(next_song)
embed = discord.Embed(
title="Now playing", description=f'Song name: **{next_song.title}**\nSong author: **{next_song.author}**')
await ctx.send(embed=embed)
except:
# An exception when after the track end, the queue is now empty. If you dont do this, it will get error.
await vc.stop()
#bot.command()
async def play(ctx: commands.Context, *, search: wavelink.YouTubeTrack):
if not ctx.voice_client:
vc: wavelink.Player = await ctx.author.voice.channel.connect(cls=wavelink.Player)
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
song_name = search.title
song_author = search.author
if song_author == None:
song_author = 'Unknown'
# embed = discord.Embed(title="Added to queue", description=f'Song name: **{song_name}**\nSong author: **{song_author}**')
# await vc.play(search)
# await ctx.send(embed=embed)
if vc.queue.is_empty and vc.is_playing:
await vc.play(search)
embed = discord.Embed(title="Playing", description=f'Song name: **{song_name}**\nSong author: **{song_author}**')
return await ctx.send(embed=embed)
else:
await vc.queue.put_wait(search)
embed = discord.Embed(title="Added to queue", description=f'Song name: **{song_name}**\nSong author: **{song_author}**')
return await ctx.send(embed=embed)
vc.ctx = ctx
setattr(vc, "loop", False)
#bot.command()
async def pause(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send('Im not playing any music!')
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
await vc.pause()
await ctx.send(f'Paused!')
#bot.command()
async def resume(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send('Im not playing any music!')
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
await vc.resume()
await ctx.send(f'Resumed!')
#bot.command()
async def stop(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send('Im not playing any music!')
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
await vc.stop()
await ctx.send(f'Stopped!')
#bot.command()
async def disconnect(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send('Im not playing any music!')
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
await vc.disconnect()
await ctx.send('Bye!')
#bot.command()
async def loop(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send('Im not playing any music!')
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
try:
vc.loop = True
except Exception:
setattr(vc, "loop", False)
if vc.loop:
return await ctx.send('Loop is now enabled!')
else:
vc.loop = False
return await ctx.send('Loop is now disabled')
#bot.command()
async def queue(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send('Im not playing any music!')
elif not getattr(ctx.author.voice, 'channel', None):
await ctx.send(f'Connect to a voice channel to use this command!')
else:
vc: wavelink.Player = ctx.voice_client
if vc.queue.is_empty:
return await ctx.send('Queue is empty!')
embed = discord.Embed(title="Queue")
queue = vc.queue.copy()
song_count = 0
for song in queue:
song_count += 1
embed.add_field(name=f"Song number {song_count}", value=f"{song.title}")
return await ctx.send(embed=embed)
bot.run('secret')
If I'm right, it should be a version issue. There is nothing wrong with your code.
I didn't have this troble until I re-installed wavelink, so I do prefer it's a version issue, I don't know which version has this ctx value, but if I find the correct version I'll answer you!
EDIT
The version has player.ctx is 1.2.5, I am not sure if 1.3.0 still has the player.ctx but I do prefere 1.2.5 because it's a more stable version (for me).
To install
python3 -m pip install wavelink==1.2.5, python -m pip install wavelink==1.2.5
or
py -m pip install wavelink==1.2.5, depends on your machine. You could also try version 1.2.3
IMPORTANT
It could be also that the bot stayed too long in the call and wavelink can't get the ctx out of it.
Related
import asyncio
import json
import os
import random
from pathlib import Path
import discord
import requests
import youtube_dl
from discord.ext import commands
from discord.utils import get
from dotenv import load_dotenv
from youtubesearchpython import SearchVideos
from pytube import YouTube
load_dotenv()
TOKEN = os.getenv('DISCORD_TOKEN')
PREFIX = os.getenv('DISCORD_PREFIX')
YOUTUBE_KEY = os.getenv('YOUTUBE_API1')
OWNER_ID = os.getenv('OWNER_ID')
CACHE_SIZE = os.getenv('CACHE_SIZE')
intents = discord.Intents.default()
intents.message_content = True
bot = commands.Bot(command_prefix=PREFIX,intents=intents)
is_playing = True
is_skipping = False
is_recommended = False
is_bot_locked = False
is_repeat_mode = False
playlist = []
loop = asyncio.get_event_loop()
current_playing_song = ""
current_song_data = []
is_pinging = True
async def autoplay(ctx):
global is_skipping, current_playing_song, current_song_data
while is_playing:
if playlist:
voice = get(bot.voice_clients, guild=ctx.guild)
current_song_data = playlist.pop()
current_playing_song = current_song_data[0]
await ctx.channel.send('Now playing ' + current_song_data[1])
with youtube_dl.YoutubeDL({}) as ydl:
video = ydl.extract_info(current_song_data[1], download=False)
await bot.change_presence(activity=discord.Streaming(name=video['title'], url=current_song_data[1]))
voice.play(discord.FFmpegPCMAudio(f'audio_cache/{current_song_data[0]}.webm'))
while voice.is_playing() or voice.is_paused():
if is_skipping:
is_skipping = False
voice.stop()
break
else:
await asyncio.sleep(.5)
else:
if is_repeat_mode:
playlist.append(current_song_data)
elif is_recommended:
video_id = current_playing_song if current_playing_song else get_random_song()[-1]
await get_recommended_song(ctx, video_id)
else:
audio = get_random_song()
await download_file(ctx.channel, audio[0], audio[1])
#bot.event
async def on_ready():
print(f'{bot.user} has connected to Discord!')
#bot.command(pass_context=True, name='ping', help='Ping your bot')
async def ping(ctx):
global is_pinging
await ctx.send(f'Latency is {round(bot.latency * 100)}ms')
#bot.command(pass_context=True, name='summon', help='Connect the bot to voice channel')
async def summon(ctx):
global is_playing
if not await check_if_user_connected(ctx):
return
voice = get(bot.voice_clients, guild=ctx.guild)
if voice:
await ctx.channel.send('Bot is already connected to voice channel')
return
is_playing = True
channel = ctx.author.voice.channel
await channel.connect()
loop.create_task(autoplay(ctx))
await ctx.channel.send(
f"Connected to {channel}, Playing in {'Recommendation' if is_recommended else 'Auto Playlist'} mode.")
#bot.command(pass_context=True, aliases=['p', 'play'], help='play music')
async def play_music(ctx, *, arg):
voice = await get_bot_voice(ctx)
if not voice:
return
await search_video(ctx.channel, arg)
#bot.command(pass_context=True, aliases=['s', 'skip'], help='Skip music')
async def skip_music(ctx):
global is_skipping
voice = await get_bot_voice(ctx)
if not voice:
return
if is_playing:
await ctx.channel.send('Skipping the song')
is_skipping = True
else:
await ctx.channel.send('Nothing is playing')
#bot.command(pass_context=True, name='disconnect', help='Disconnect the bot')
async def disconnect(ctx):
global is_playing
voice = await get_bot_voice(ctx)
if not voice:
return
is_playing = False
await ctx.channel.send('Bye Bye')
await voice.disconnect()
#bot.command(pass_context=True, aliases=['sw', 'switch'], help='Switch play mode')
async def switch_mode(ctx):
global is_recommended
is_recommended = not is_recommended
await ctx.channel.send(f"Autoplay mode changed to {'Recommended' if is_recommended else 'Autoplaylist'}")
#bot.command(pass_context=True, name='lock', help='Lock the bot')
async def lock(ctx):
global is_bot_locked
if str(ctx.author.id) == str(OWNER_ID):
is_bot_locked = True
#bot.command(pass_context=True, name='unlock', help='Unlock the bot')
async def unlock(ctx):
global is_bot_locked
if str(ctx.author.id) == str(OWNER_ID):
is_bot_locked = False
#bot.command(pass_context=True, name='pause', help='Pause music')
async def pause(ctx):
voice = await get_bot_voice(ctx)
if not voice:
return
if voice.is_playing():
voice.pause()
await ctx.channel.send('Paused')
else:
await ctx.channel.send('Nothing is playing')
#bot.command(pass_context=True, name='resume', help='Resume music')
async def resume(ctx):
voice = await get_bot_voice(ctx)
if not voice:
return
if voice.is_paused():
voice.resume()
await ctx.channel.send('Resuming the song')
else:
await ctx.channel.send('Nothing is playing')
#bot.command(pass_context=True, name='save', help='Save music to Autoplaylist')
async def save(ctx):
voice = await get_bot_voice(ctx)
if not voice:
return
song = f"https://www.youtube.com/watch?v={current_playing_song}\n"
if song in list(open('autoplaylist.txt')):
await ctx.channel.send('This song is already in Autoplaylist')
else:
open('autoplaylist.txt', 'a').write(song)
await ctx.channel.send('Song is added to Autoplaylist')
#bot.event
async def on_voice_state_update(member, before, after):
if before.channel is None and after.channel is not None and str(member.id) == str('756835280714989620'):
await member.move_to(None)
#bot.command(pass_context=True, name='remove', help='Remove music from Autoplaylist')
async def remove(ctx):
voice = await get_bot_voice(ctx)
if not voice:
return
song = f"https://www.youtube.com/watch?v={current_playing_song}\n"
songs = list(open('autoplaylist.txt'))
if song in songs:
songs.remove(song)
open('autoplaylist.txt', 'w').write("".join(songs))
await ctx.channel.send('Song is removed from Autoplaylist')
else:
await ctx.channel.send('This Song is not in Autoplaylist')
#bot.command(pass_context=True, name='repeat', help='Toggle repeat mode')
async def repeat(ctx):
global is_repeat_mode
if is_repeat_mode:
is_repeat_mode = False
await ctx.channel.send('Repeat mode OFF')
else:
is_repeat_mode = True
await ctx.channel.send('Repeat mode ON')
async def check_if_user_connected(ctx):
connected = ctx.author.voice
if not connected:
await ctx.channel.send('You are not connected to any voice channel')
return False
return True
async def get_bot_voice(ctx):
if is_bot_locked and str(ctx.author.id) != str(OWNER_ID):
await ctx.channel.send('Bot is Locked, Ask an admin to unlock')
return None
connected = ctx.author.voice
if not connected:
await ctx.channel.send('You are not connected to any voice channel')
return None
voice = get(bot.voice_clients, guild=ctx.guild)
if not voice:
await ctx.channel.send('Bot is not connected to any voice channel, Please summon the bot first.')
return None
return voice
async def search_video(channel, search):
search = SearchVideos(search, offset=1, mode="list", max_results=1)
if len(search.result()) != 1:
await channel.send('Unable to find any Video')
else:
await channel.send('Added to stack ' + search.result()[0][3])
await download_file(channel, search.result()[0][2], search.result()[0][1])
async def download_file(channel, url, key):
file_path = f'audio_cache/{key}.webm'
if Path(file_path).is_file():
playlist.append([key, url])
return
try:
clear_cache()
yt = YouTube(url)
yt.streams.filter(only_audio=True).first().download(output_path='audio_cache', filename=f'{key}.webm')
playlist.append([key, url])
except Exception as e:
await channel.send(str(e))
def clear_cache():
try:
path, v, files = next(os.walk("audio_cache"))
if len(files) > int(CACHE_SIZE):
song = random.choice(files)
for music in playlist:
if song.strip('.webm') == music[0]:
return
os.remove(f"{path}/{song}")
except Exception as e:
print(e)
async def get_recommended_song(ctx, key):
global YOUTUBE_KEY
audio = get_random_song()
url = f"https://www.googleapis.com/youtube/v3/search?part=snippet&relatedToVideoId=" \
f"{key}&type=video&key={YOUTUBE_KEY}"
response = requests.get(url)
if response.ok:
songs = json.loads(response.content)['items']
if len(songs) > 1:
songs.pop(0)
video_id = random.choice(songs)['id']['videoId']
audio = [f"https://www.youtube.com/watch?v={video_id}", video_id]
else:
if YOUTUBE_KEY is os.getenv('YOUTUBE_API1'):
YOUTUBE_KEY = os.getenv('YOUTUBE_API2')
else:
YOUTUBE_KEY = os.getenv('YOUTUBE_API1')
await download_file(ctx.channel, audio[0], audio[1])
def get_random_song():
song = random.choice(list(open('autoplaylist.txt'))).strip('\n')
return [song, song.split("=")[-1]]
bot.run(TOKEN)
Task was destroyed but it is pending!
task: <Task pending name='Task-21' coro=<autoplay() running at c:\Users\S1ncer3ly\Desktop\DiscordMusicBot-main\main.py:38>>
C:\Users\S1ncer3ly\AppData\Local\Programs\Python\Python311\Lib\asyncio\base_events.py:675: RuntimeWarning: coroutine 'autoplay' was never awaited
Im totally new into this thankyou
change the line loop.create_task(autoplay(ctx)) to await autoplay(ctx)
I am Making a Music discord bot and I have been trying to make it loop and queue songs.
But when I try to queue a song it just starts playing it instead of queuing it and shows this error in the console:
Ignoring exception in on_wavelink_track_end Traceback (most recent call last): File "C:\Users\Name\AppData\Local\Programs\Python\Python310\lib\site-packages\nextcord\client.py", line 415, in _run_event
await coro(*args, **kwargs) File "C:\PC Code\Python Code Files\Discord Bot\Next cord\Fish Bot Complex - NextCord.py", line 32, in on_wavelink_track_end
next_song = vc.queue.get() File "C:\Users\Name\AppData\Local\Programs\Python\Python310\lib\site-packages\wavelink\queue.py", line 212, in get
raise QueueEmpty("No items in the queue.") wavelink.errors.QueueEmpty: No items in the queue.
As well as it telling me to join the VC it's in even though I already am in the same VC
Here is my code:
#bot.event
async def on_wavelink_track_end(player: wavelink.Player, track: wavelink.Track, reason):
ctx = player.ctx
vc: player = ctx.voice_client
if vc.loop:
return await vc.play(track)
next_song = vc.queue.get()
await vc.play(next_song)
await ctx.send(f"Now playing: {next_song.title}")
#bot.command(aliases=['P', 'play', 'p' ], name = 'Play', description = "Plays the music you want!")
#commands.has_role("DJ")
async def Play(ctx: commands.Context, *, search: wavelink.YouTubeTrack):
await ctx.send("Attempting to play. (Note: This is a beta bot so things may not work as intended)")
if not ctx.voice_client:
vc: wavelink.Player = await ctx.author.voice.channel.connect(cls=wavelink.Player)
elif not getattr(ctx.author.voice, "channel", None):
return await ctx.send("You need to join a VC to play music.")
else:
vc: wavelink.Player = ctx.voice_client
if vc.queue.is_empty and vc.is_playing:
await vc.play(search)
await ctx.send(f"Now Playing: {search.title}")
else:
await vc.queue.put_wait(search)
await ctx.send(f"Added `{search.title}` to the queue")
vc.ctx = ctx
setattr(vc, "loop", False)
print("Playing a song")
#bot.command(aliases=['L', 'l', 'loop' ], name = 'Loop', description = "Loops the playing music!")
#commands.has_role("DJ")
async def Loop(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send("You don't seen to be playing any music... (Note: This is a beta bot so things may not work as intended)")
elif not ctx.author.voice:
return await ctx.send("You need to join a VC to play music.")
elif not ctx.author.voice == ctx.me.voice:
return await ctx.send("You must be in the same VC as me.")
else:
vc: wavelink.Player = ctx.voice_client
try:
vc.loop ^= True
except Exception:
setattr(vc, "loop", False)
if vc.loop:
return await ctx.send("Loop has been Enabled.")
else:
return await ctx.send("Loop has been Disabled.")
#bot.command(aliases=['Q', 'q', 'queue' ], name = 'Queue', description = "Queues a song.")
#commands.has_role("DJ")
async def Queue(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send("You don't seen to be playing any music... (Note: This is a beta bot so things may not work as intended)")
elif not ctx.author.voice:
return await ctx.send("You need to join a VC to play music.")
elif not ctx.author.voice == ctx.me.voice:
return await ctx.send("You must be in the same VC as me.")
else:
vc: wavelink.Player = ctx.voice_client
if vc.queue.is_empty:
return await ctx.send("The queue is now empty.")
em = nextcord.Embed(title="Queue")
queue = vc.queue.copy()
song_count = 0
for song in queue:
song_count += 1
em.add_field(name=f"Song Number {song_count}", value=f"`{song.title}`")
return await ctx.send(embed=em)
I'm not sure on what the issue is any help is appreciated.
On your code
if vc.queue.is_empty and vc.is_playing:
await vc.play(search)
await ctx.send(f"Now Playing: {search.title}")
else:
await vc.queue.put_wait(search)
await ctx.send(f"Added `{search.title}` to the queue")
you need to change
if vc.queue.is_empty and vc.is_playing:
to
if vc.queue.is_empty and not vc.is_playing:
I am having troubles gettimg my commands to work, it keeps telling me that they do not exist when they clearly do. I've been stumped on this for hours and can't figure out why its not working. I've tried doing commands.command() instead of #commands.command(), but no luck, i tried explicitly defining the name of the command #commands.command(name="play") but still no luck
import youtube_dl
import pafy
import discord
from discord.ext import commands
intents = discord.Intents.default()
intents.members = True
bot = commands.Bot(command_prefix="!", intents=intents)
#bot.event
async def on_ready():
print(f"{bot.user.name} is ready.")
bot.run("....")
class Player(commands.Cog):
def __init__(self, bot):
self.bot = bot
self.song_queue = {}
self.setup()
def setup(self):
for guild in self.bot.guilds:
self.song_queue[guild.id] = []
async def check_queue(self, ctx):
if len(self.song_queue[ctx.guild.id]) > 0:
await self.play_song(ctx, self.song_queue[ctx.guild.id][0])
self.song_queue[ctx.guild.id].pop(0)
async def search_song(self, amount, song, get_url=False):
info = await self.bot.loop.run_in_executor(None, lambda: youtube_dl.YoutubeDL({"format" : "bestaudio", "quiet" : True}).extract_info(f"ytsearch{amount}:{song}", download=False, ie_key="YoutubeSearch"))
if len(info["entries"]) == 0: return None
return [entry["webpage_url"] for entry in info["entries"]] if get_url else info
async def play_song(self, ctx, song):
url = pafy.new(song).getbestaudio().url
ctx.voice_client.play(discord.PCMVolumeTransformer(discord.FFmpegPCMAudio(url)), after=lambda error: self.bot.loop.create_task(self.check_queue(ctx)))
ctx.voice_client.source.volume = 0.5
#commands.command()
async def join(self, ctx):
if ctx.author.voice is None:
return await ctx.send("You are not connected to a voice channel, please connect to the channel you want the bot to join.")
if ctx.voice_client is not None:
await ctx.voice_client.disconnect()
await ctx.author.voice.channel.connect()
#commands.command()
async def leave(self, ctx):
if ctx.voice_client is not None:
return await ctx.voice_client.disconnect()
await ctx.send("I am not connected to a voice channel.")
#commands.command(name="play")
async def play(self, ctx, *, song=None):
if song is None:
return await ctx.send("You must include a song to play.")
if ctx.voice_client is None:
return await ctx.send("I must be in a voice channel to play a song.")
# handle song where song isn't url
if not ("youtube.com/watch?" in song or "https://youtu.be/" in song):
await ctx.send("Searching for song, this may take a few seconds.")
result = await self.search_song(1, song, get_url=True)
if result is None:
return await ctx.send("Sorry, I could not find the given song, try using my search command.")
song = result[0]
if ctx.voice_client.source is not None:
queue_len = len(self.song_queue[ctx.guild.id])
if queue_len < 10:
self.song_queue[ctx.guild.id].append(song)
return await ctx.send(f"I am currently playing a song, this song has been added to the queue at position: {queue_len+1}.")
else:
return await ctx.send("Sorry, I can only queue up to 10 songs, please wait for the current song to finish.")
await self.play_song(ctx, song)
await ctx.send(f"Now playing: {song}")
#commands.command()
async def search(self, ctx, *, song=None):
if song is None: return await ctx.send("You forgot to include a song to search for.")
await ctx.send("Searching for song, this may take a few seconds.")
info = await self.search_song(5, song)
embed = discord.Embed(title=f"Results for '{song}':", description="*You can use these URL's to play an exact song if the one you want isn't the first result.*\n", colour=discord.Colour.red())
amount = 0
for entry in info["entries"]:
embed.description += f"[{entry['title']}]({entry['webpage_url']})\n"
amount += 1
embed.set_footer(text=f"Displaying the first {amount} results.")
await ctx.send(embed=embed)
#commands.command()
async def queue(self, ctx): # display the current guilds queue
if len(self.song_queue[ctx.guild.id]) == 0:
return await ctx.send("There are currently no songs in the queue.")
embed = discord.Embed(title="Song Queue", description="", colour=discord.Colour.dark_gold())
i = 1
for url in self.song_queue[ctx.guild.id]:
embed.description += f"{i}) {url}\n"
i += 1
embed.set_footer(text="Thanks for using me!")
await ctx.send(embed=embed)
#commands.command()
async def skip(self, ctx):
if ctx.voice_client is None:
return await ctx.send("I am not playing any song.")
if ctx.author.voice is None:
return await ctx.send("You are not connected to any voice channel.")
if ctx.author.voice.channel.id != ctx.voice_client.channel.id:
return await ctx.send("I am not currently playing any songs for you.")
poll = discord.Embed(title=f"Vote to Skip Song by - {ctx.author.name}#{ctx.author.discriminator}", description="**80% of the voice channel must vote to skip for it to pass.**", colour=discord.Colour.blue())
poll.add_field(name="Skip", value=":white_check_mark:")
poll.add_field(name="Stay", value=":no_entry_sign:")
poll.set_footer(text="Voting ends in 15 seconds.")
poll_msg = await ctx.send(embed=poll) # only returns temporary message, we need to get the cached message to get the reactions
poll_id = poll_msg.id
await poll_msg.add_reaction(u"\u2705") # yes
await poll_msg.add_reaction(u"\U0001F6AB") # no
await asyncio.sleep(15) # 15 seconds to vote
poll_msg = await ctx.channel.fetch_message(poll_id)
votes = {u"\u2705": 0, u"\U0001F6AB": 0}
reacted = []
for reaction in poll_msg.reactions:
if reaction.emoji in [u"\u2705", u"\U0001F6AB"]:
async for user in reaction.users():
if user.voice.channel.id == ctx.voice_client.channel.id and user.id not in reacted and not user.bot:
votes[reaction.emoji] += 1
reacted.append(user.id)
skip = False
if votes[u"\u2705"] > 0:
if votes[u"\U0001F6AB"] == 0 or votes[u"\u2705"] / (votes[u"\u2705"] + votes[u"\U0001F6AB"]) > 0.79: # 80% or higher
skip = True
embed = discord.Embed(title="Skip Successful", description="***Voting to skip the current song was succesful, skipping now.***", colour=discord.Colour.green())
if not skip:
embed = discord.Embed(title="Skip Failed", description="*Voting to skip the current song has failed.*\n\n**Voting failed, the vote requires at least 80% of the members to skip.**", colour=discord.Colour.red())
embed.set_footer(text="Voting has ended.")
await poll_msg.clear_reactions()
await poll_msg.edit(embed=embed)
if skip:
ctx.voice_client.stop()
#commands.command()
async def pause(self, ctx):
if ctx.voice_client.is_paused():
return await ctx.send("I am already paused.")
ctx.voice_client.pause()
await ctx.send("The current song has been paused.")
#commands.command()
async def resume(self, ctx):
if ctx.voice_client is None:
return await ctx.send("I am not connected to a voice channel.")
if not ctx.voice_client.is_paused():
return await ctx.send("I am already playing a song.")
ctx.voice_client.resume()
await ctx.send("The current song has been resumed.")
async def setup():
await bot.wait_until_ready()
bot.add_cog(Player(bot))
bot.loop.create_task(setup())
You can try replacing :
async def setup():
await bot.wait_until_ready()
bot.add_cog(Player(bot))
bot.loop.create_task(setup())
With just :
bot.add_cog(Player(bot))
Moreover, put you run statement after all setup operations, so you have :
# Cog declaration
bot.add_cog(Player(bot))
bot.run('....')
run() should be executed as last function because it starts bot and it runs until you stop bot.
And all code which you have after run() is executed after you stop bot.
bot.loop.create_task(setup())
bot.run(TOKEN)
#commands.command()
Write this down where you wrote it down.
#bot.command()
Because:
bot = commands.Bot(command_prefix="!", intents=intents)
Since you have assigned a "bot" variable here, the name of the variable is added first, and then the "command" is added.
How would I get a my bot to use /tts in a vc?
Here is the code that I have so far. It is a loop of one word and I want to use tts in the voice channel I am in.
#client.command()
async def start(ctx):
global start_channel
start_channel = ctx.channel.id
reminder.start()
await ctx.send('Bot has Started')
#tasks.loop(minutes=10)
async def reminder():
channel = client.get_channel(int(start_channel))
await channel.send('/tts Honk!')
#client.command()
async def stop(ctx):
reminder.cancel()
await ctx.send('Bot has stopped')
#client.command()
async def join(ctx):
if ctx.author.voice is None:
await ctx.send("You're not in a voice channel")
voice_channel = ctx.author.voice.channel
if ctx.voice_client is None:
await voice_channel.connect()
else:
await ctx.voice_channel.move_to(voice_channel)
add tts as = True to allow it use tts commands through discord
#tasks.loop(minutes=10)
async def reminder():
channel = client.get_channel(int(start_channel))
await channel.send('Honk!', tts=True)
#bot.event
async def on_wavelink_track_end(player:wavelink.Player, track: wavelink.Track, reason):
ctx = player.ctx
vc : player = ctx.voice_client
if vc.loop:
return await vc.play(track)
next_song= vc.queue.get()
await vc.play(next_song)
await ctx.send(f"Playing: {next_song.title} rn :)")
#bot.command()
async def play(ctx: commands.Context,*, search: wavelink.YouTubeTrack):
if not ctx.voice_client:
vc: wavelink.Player = await ctx.author.voice.channel.connect(cls=wavelink.Player)
elif not ctx.author.voice:
return await ctx.send("Pweasee join a VC <3")
elif not ctx.author.voice != ctx.me.voice:
return await ctx.send("Pwease be in the same VC <3")
else:
vc : wavelink.Player= ctx.voice_client
if vc.queue.is_empty:
await vc.play(search)
await ctx.send(f"Playing: {search.title} rn :)")
else:
await vc.queue.put_wait(search)
await ctx.send(f"Added {search.title} to the queue <3")
vc.ctx = ctx
setattr(vc,"loop",False)
#bot.command()
async def queue(ctx: commands.Context):
if not ctx.voice_client:
return await ctx.send("Pweasee let me join a VC <3")
elif not ctx.author.voice:
return await ctx.send("Pweasee join a VC <3")
elif not ctx.author.voice != ctx.me.voice:
return await ctx.send("Pwease be in the same VC <3")
else:
vc: wavelink.Player = ctx.voice_client
if vc.queue.is_empty:
return await ctx.send("queue is empty :(")
What this should do:
add a song to the queue , and play when the previous song finishes
What bug i get:
Upon adding a song, ignores the queue system and just plays it
I get this error in console:
Ignoring exception in on_wavelink_track_end
wavelink.errors.QueueEmpty: No items in the queue.