1
Fork 0
mirror of https://github.com/RYGhub/royalnet.git synced 2024-11-27 13:34:28 +00:00

Create queue command

This commit is contained in:
Steffo 2019-06-02 18:19:53 +02:00
parent a512da0058
commit 956cdb5ac0
7 changed files with 116 additions and 5 deletions

View file

@ -47,6 +47,18 @@ class PlayMode:
"""Delete all :py:class:`royalnet.audio.RoyalPCMAudio` contained inside this PlayMode."""
raise NotImplementedError()
def queue_preview(self) -> typing.List[RoyalPCMAudio]:
"""Display all the videos in the PlayMode as a list, if possible.
To be used with `queue` commands, for example.
Raises:
NotImplementedError: If a preview can't be generated.
Returns:
A list of videos contained in the queue."""
raise NotImplementedError()
class Playlist(PlayMode):
"""A video list. :py:class:`royalnet.audio.RoyalPCMAudio` played are removed from the list."""
@ -85,6 +97,9 @@ class Playlist(PlayMode):
while self.list:
self.list.pop(0).delete()
def queue_preview(self) -> typing.List[RoyalPCMAudio]:
return self.list
class Pool(PlayMode):
"""A :py:class:`royalnet.audio.RoyalPCMAudio` pool. :py:class:`royalnet.audio.RoyalPCMAudio` are selected in random order and are not repeated until every song has been played at least once."""
@ -126,3 +141,8 @@ class Pool(PlayMode):
item.delete()
self.pool = None
self._pool_copy = None
def queue_preview(self) -> typing.List[RoyalPCMAudio]:
preview_pool = self.pool.copy()
random.shuffle(preview_pool)
return preview_pool

View file

@ -26,9 +26,11 @@ from .videochannel import VideochannelCommand
from .missing import MissingCommand
from .cv import CvCommand
from .pause import PauseCommand
from .queue import QueueCommand
__all__ = ["NullCommand", "PingCommand", "ShipCommand", "SmecdsCommand", "CiaoruoziCommand", "ColorCommand",
"SyncCommand", "DiarioCommand", "RageCommand", "DateparserCommand", "AuthorCommand", "ReminderCommand",
"KvactiveCommand", "KvCommand", "KvrollCommand", "VideoinfoCommand", "SummonCommand", "PlayCommand",
"SkipCommand", "PlaymodeCommand", "VideochannelCommand", "MissingCommand", "CvCommand", "PauseCommand"]
"SkipCommand", "PlaymodeCommand", "VideochannelCommand", "MissingCommand", "CvCommand", "PauseCommand",
"QueueCommand"]

View file

@ -10,6 +10,7 @@ if typing.TYPE_CHECKING:
class PauseNH(NetworkHandler):
message_type = "music_pause"
# noinspection PyProtectedMember
@classmethod
async def discord(cls, bot: "DiscordBot", data: dict):
# Find the matching guild
@ -23,7 +24,7 @@ class PauseNH(NetworkHandler):
guild = list(bot.music_data)[0]
# Set the currently playing source as ended
voice_client: discord.VoiceClient = bot.client.find_voice_client_by_guild(guild)
if not voice_client.is_playing():
if not (voice_client.is_playing() or voice_client.is_paused()):
raise NoneFoundError("Nothing to pause")
# Toggle pause
resume = voice_client._player.is_paused()

View file

@ -0,0 +1,76 @@
import typing
import pickle
from ..network import Request, ResponseSuccess
from ..utils import Command, Call, NetworkHandler, numberemojiformat
from ..error import TooManyFoundError, NoneFoundError
if typing.TYPE_CHECKING:
from ..bots import DiscordBot
class QueueNH(NetworkHandler):
message_type = "music_queue"
@classmethod
async def discord(cls, bot: "DiscordBot", data: dict):
# Find the matching guild
if data["guild_name"]:
guild = bot.client.find_guild_by_name(data["guild_name"])
else:
if len(bot.music_data) == 0:
raise NoneFoundError("No voice clients active")
if len(bot.music_data) > 1:
raise TooManyFoundError("Multiple guilds found")
guild = list(bot.music_data)[0]
# Check if the guild has a PlayMode
playmode = bot.music_data.get(guild)
if not playmode:
return ResponseSuccess({
"type": None
})
try:
queue = playmode.queue_preview()
except NotImplementedError:
return ResponseSuccess({
"type": playmode.__class__.__name__
})
return ResponseSuccess({
"type": playmode.__class__.__name__,
"queue":
{
"strings": [str(element.rpf.info) for element in queue],
"pickled_embeds": str(pickle.dumps([element.rpf.info.to_discord_embed() for element in queue]))
}
})
class QueueCommand(Command):
command_name = "queue"
command_description = "Visualizza un'anteprima della coda di riproduzione attuale."
command_syntax = "[ [guild] ]"
network_handlers = [QueueNH]
@classmethod
async def common(cls, call: Call):
guild, = call.args.match(r"(?:\[(.+)])?")
data = await call.net_request(Request("music_queue", {"guild_name": guild}), "discord")
if data["type"] is None:
await call.reply(" Non c'è nessuna coda di riproduzione attiva al momento.")
return
elif "queue" not in data:
await call.reply(f" La coda di riproduzione attuale ([c]{data['type']}[/c]) non permette l'anteprima.")
return
if data["type"] == "Playlist":
message = f" Questa [c]Playlist[/c] contiene {len(data['queue'])} elementi, e i prossimi saranno:\n"
elif data["type"] == "Pool":
message = f" Questo [c]Pool[/c] contiene {len(data['queue'])} elementi, tra cui:\n"
else:
message = f" Il PlayMode attuale, [c]{data['type']}[/c], contiene {len(data['queue'])} elementi:\n"
if call.interface_name == "discord":
await call.reply(message)
for embed in pickle.loads(eval(data["queue"]["pickled_embeds"]))[:5]:
await call.channel.send(embed=embed)
else:
message += numberemojiformat(data["queue"]["strings"])
await call.reply(message)

View file

@ -20,7 +20,7 @@ log.setLevel(logging.WARNING)
commands = [PingCommand, ShipCommand, SmecdsCommand, ColorCommand, CiaoruoziCommand, DebugCreateCommand, SyncCommand,
AuthorCommand, DiarioCommand, RageCommand, DateparserCommand, ReminderCommand, KvactiveCommand, KvCommand,
KvrollCommand, VideoinfoCommand, SummonCommand, PlayCommand, SkipCommand, PlaymodeCommand,
VideochannelCommand, CvCommand, PauseCommand]
VideochannelCommand, CvCommand, PauseCommand, QueueCommand]
address, port = "127.0.0.1", 1234

View file

@ -9,7 +9,7 @@ from .safeformat import safeformat
from .classdictjanitor import cdj
from .sleepuntil import sleep_until
from .networkhandler import NetworkHandler
from .formatters import andformat, plusformat, fileformat, ytdldateformat
from .formatters import andformat, plusformat, fileformat, ytdldateformat, numberemojiformat
__all__ = ["asyncify", "Call", "Command", "safeformat", "cdj", "sleep_until", "plusformat", "CommandArgs",
"NetworkHandler", "andformat", "plusformat", "fileformat", "ytdldateformat"]
"NetworkHandler", "andformat", "plusformat", "fileformat", "ytdldateformat", "numberemojiformat"]

View file

@ -58,3 +58,15 @@ def ytdldateformat(string: typing.Optional[str], separator: str = "-") -> str:
if string is None:
return ""
return f"{string[0:4]}{separator}{string[4:6]}{separator}{string[6:8]}"
def numberemojiformat(l: typing.List[str]) -> str:
number_emojis = ["1", "2", "3", "4", "5", "6", "7", "8", "9", "🔟"]
extra_emoji = "*️⃣"
result = ""
for index, element in enumerate(l):
try:
result += f"{number_emojis[index]} {element}\n"
except IndexError:
result += f"{extra_emoji} {element}\n"
return result