Implement queue
This commit is contained in:
parent
eb56c024cd
commit
07618676db
4 changed files with 306 additions and 13 deletions
198
src/commands.rs
198
src/commands.rs
|
@ -1,6 +1,5 @@
|
|||
use anyhow::{Context, Result};
|
||||
use poise::serenity_prelude::{EmbedMessageBuilding, MessageBuilder};
|
||||
use songbird::create_player;
|
||||
use tracing::{debug, log::warn};
|
||||
|
||||
use crate::{personality, CommandContext, Error};
|
||||
|
@ -116,10 +115,86 @@ pub async fn play(
|
|||
|
||||
response.edit(ctx, |r| r.content(msg.build())).await?;
|
||||
|
||||
let (audio, track_handle) = create_player(source);
|
||||
let mut currently_playing = ctx.data().currently_playing.lock();
|
||||
*currently_playing = Some(track_handle);
|
||||
handler.play_only(audio);
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
if !queue.is_empty() {
|
||||
let _ = queue.stop();
|
||||
}
|
||||
queue.add_next(source, &mut handler);
|
||||
queue.resume()?;
|
||||
} else {
|
||||
ctx.say("Neither of us are in a voice channel, silly.")
|
||||
.await?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[poise::command(slash_command)]
|
||||
pub async fn queue(
|
||||
ctx: CommandContext<'_>,
|
||||
#[description = "The URL of the song to play"] url: Option<String>,
|
||||
) -> Result<(), Error> {
|
||||
let Some(url) = url else {
|
||||
ctx.say("You need to give me a URL to play!").await?;
|
||||
return Ok(());
|
||||
};
|
||||
|
||||
let Some(guild) = ctx.guild() else {
|
||||
ctx.say("You're not in a server, silly.").await?;
|
||||
return Ok(());
|
||||
};
|
||||
|
||||
let manager = songbird::get(ctx.serenity_context())
|
||||
.await
|
||||
.context("Expected a songbird manager")?
|
||||
.clone();
|
||||
|
||||
if manager.get(guild.id).is_none() {
|
||||
let Some(Some(channel_id)) = guild.voice_states.get(&ctx.author().id).map(|vs| vs.channel_id) else {
|
||||
ctx.say("Neither of us are in a voice channel, silly.").await?;
|
||||
return Ok(());
|
||||
};
|
||||
let _handler = manager.join(guild.id, channel_id).await;
|
||||
}
|
||||
|
||||
if let Some(handler_lock) = manager.get(guild.id) {
|
||||
let mut msg = MessageBuilder::new();
|
||||
msg.push_line(String::from(personality::get_random_loading_message()))
|
||||
.push_named_link(
|
||||
"",
|
||||
"https://media.giphy.com/media/H1dxi6xdh4NGQCZSvz/giphy.gif",
|
||||
);
|
||||
let response = ctx.send(|r| r.content(msg.build())).await?;
|
||||
|
||||
let mut handler = handler_lock.lock().await;
|
||||
|
||||
debug!("Trying to play: {}", url);
|
||||
let source = songbird::ytdl(&url).await?;
|
||||
debug!("Playing: {:?}", source.metadata);
|
||||
let title = source
|
||||
.metadata
|
||||
.title
|
||||
.clone()
|
||||
.unwrap_or(String::from("This video"));
|
||||
|
||||
let mut msg = MessageBuilder::new();
|
||||
|
||||
// Optional sassy commentary!
|
||||
match personality::get_sassy_commentary(&title).await {
|
||||
Ok(commentary) => {
|
||||
msg.push_line(&commentary).push_line("");
|
||||
}
|
||||
Err(e) => {
|
||||
warn!("Failed to get sassy commentary for \"{title}\": {e}");
|
||||
}
|
||||
};
|
||||
|
||||
msg.push_bold("Queued: ").push_named_link(title, url);
|
||||
|
||||
response.edit(ctx, |r| r.content(msg.build())).await?;
|
||||
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
queue.add_to_end(source, &mut handler);
|
||||
} else {
|
||||
ctx.say("Neither of us are in a voice channel, silly.")
|
||||
.await?;
|
||||
|
@ -140,12 +215,10 @@ pub async fn stop(ctx: CommandContext<'_>) -> Result<(), Error> {
|
|||
.context("Expected a songbird manager")?
|
||||
.clone();
|
||||
|
||||
if let Some(handler_lock) = manager.get(guild.id) {
|
||||
let mut handler = handler_lock.lock().await;
|
||||
handler.stop();
|
||||
if manager.get(guild.id).is_some() {
|
||||
{
|
||||
let mut currently_playing = ctx.data().currently_playing.lock();
|
||||
*currently_playing = None;
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
queue.stop()?;
|
||||
}
|
||||
ctx.say("Alright, I guess I'll stop.").await?;
|
||||
} else {
|
||||
|
@ -155,3 +228,108 @@ pub async fn stop(ctx: CommandContext<'_>) -> Result<(), Error> {
|
|||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[poise::command(slash_command)]
|
||||
pub async fn skip(ctx: CommandContext<'_>) -> Result<(), Error> {
|
||||
let Some(guild) = ctx.guild() else {
|
||||
ctx.say("You're not in a server, silly.").await?;
|
||||
return Ok(());
|
||||
};
|
||||
|
||||
let manager = songbird::get(ctx.serenity_context())
|
||||
.await
|
||||
.context("Expected a songbird manager")?
|
||||
.clone();
|
||||
|
||||
if manager.get(guild.id).is_some() {
|
||||
{
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
let _ = queue.stop();
|
||||
queue.resume()?;
|
||||
}
|
||||
ctx.say("Skipping!").await?;
|
||||
} else {
|
||||
ctx.say("I'm not even in a channel to begin with. Silly.")
|
||||
.await?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[poise::command(slash_command)]
|
||||
pub async fn pause(ctx: CommandContext<'_>) -> Result<(), Error> {
|
||||
let Some(guild) = ctx.guild() else {
|
||||
ctx.say("You're not in a server, silly.").await?;
|
||||
return Ok(());
|
||||
};
|
||||
|
||||
let manager = songbird::get(ctx.serenity_context())
|
||||
.await
|
||||
.context("Expected a songbird manager")?
|
||||
.clone();
|
||||
|
||||
if manager.get(guild.id).is_some() {
|
||||
{
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
queue.pause()?;
|
||||
}
|
||||
ctx.say("Pausing!").await?;
|
||||
} else {
|
||||
ctx.say("I'm not even in a channel to begin with. Silly.")
|
||||
.await?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[poise::command(slash_command)]
|
||||
pub async fn resume(ctx: CommandContext<'_>) -> Result<(), Error> {
|
||||
let Some(guild) = ctx.guild() else {
|
||||
ctx.say("You're not in a server, silly.").await?;
|
||||
return Ok(());
|
||||
};
|
||||
|
||||
let manager = songbird::get(ctx.serenity_context())
|
||||
.await
|
||||
.context("Expected a songbird manager")?
|
||||
.clone();
|
||||
|
||||
if manager.get(guild.id).is_some() {
|
||||
{
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
queue.resume()?;
|
||||
}
|
||||
ctx.say("Resuming!").await?;
|
||||
} else {
|
||||
ctx.say("I'm not even in a channel to begin with. Silly.")
|
||||
.await?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[poise::command(slash_command)]
|
||||
pub async fn clear(ctx: CommandContext<'_>) -> Result<(), Error> {
|
||||
let Some(guild) = ctx.guild() else {
|
||||
ctx.say("You're not in a server, silly.").await?;
|
||||
return Ok(());
|
||||
};
|
||||
|
||||
let manager = songbird::get(ctx.serenity_context())
|
||||
.await
|
||||
.context("Expected a songbird manager")?
|
||||
.clone();
|
||||
|
||||
if manager.get(guild.id).is_some() {
|
||||
{
|
||||
let mut queue = ctx.data().queue.lock();
|
||||
queue.clear();
|
||||
}
|
||||
ctx.say("Cleared the queue!").await?;
|
||||
} else {
|
||||
ctx.say("I'm not even in a channel to begin with. Silly.")
|
||||
.await?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue