aboutsummaryrefslogtreecommitdiff
path: root/src/voice/audio.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/voice/audio.rs')
-rw-r--r--src/voice/audio.rs84
1 files changed, 83 insertions, 1 deletions
diff --git a/src/voice/audio.rs b/src/voice/audio.rs
index 8a001d1..cb60f57 100644
--- a/src/voice/audio.rs
+++ b/src/voice/audio.rs
@@ -1,5 +1,6 @@
use parking_lot::Mutex;
use std::sync::Arc;
+use std::time::Duration;
pub const HEADER_LEN: usize = 12;
pub const SAMPLE_RATE: u32 = 48_000;
@@ -36,12 +37,63 @@ pub enum AudioType {
/// Control object for audio playback.
///
/// Accessed by both commands and the playback code -- as such, access is
-/// always guarded.
+/// always guarded. In particular, you should expect to receive
+/// a [`LockedAudio`] when calling [`Handler::play_returning`] or
+/// [`Handler::play_only`].
+///
+/// # Example
+///
+/// ```rust,ignore
+/// use serenity::voice::{Handler, LockedAudio, ffmpeg};
+///
+/// let handler: Handler = /* ... */;
+/// let source = ffmpeg("../audio/my-favourite-song.mp3")?;
+/// let safe_audio: LockedAudio = handler.play_only();
+/// {
+/// let audio_lock = safe_audio_control.clone();
+/// let mut audio = audio_lock.lock();
+///
+/// audio.volume(0.5);
+/// }
+/// ```
+///
+/// [`LockedAudio`]: type.LockedAudio.html
+/// [`Handler::play_only`]: struct.Handler.html#method.play_only
+/// [`Handler::play_returning`]: struct.Handler.html#method.play_returning
pub struct Audio {
+
+ /// Whether or not this sound is currently playing.
+ ///
+ /// Can be controlled with [`play`] or [`pause`]
+ /// if chaining is desired.
+ ///
+ /// [`play`]: #method.play
+ /// [`pause`]: #method.pause
pub playing: bool,
+
+ /// The desired volume for playback.
+ ///
+ /// Sensible values fall between `0.0` and `1.0`.
+ /// Can be controlled with [`volume`] if chaining is desired.
+ ///
+ /// [`volume`]: #method.volume
pub volume: f32,
+
+ /// Whether or not the sound has finished, or reached the end of its stream.
+ ///
+ /// ***Read-only*** for now.
pub finished: bool,
+
+ /// Underlying data access object.
+ ///
+ /// *Calling code is not expected to use this.*
pub source: Box<AudioSource>,
+
+ /// The current position for playback.
+ ///
+ /// Consider the position fields **read-only** for now.
+ pub position: Duration,
+ pub position_modified: bool,
}
impl Audio {
@@ -51,26 +103,56 @@ impl Audio {
volume: 1.0,
finished: false,
source,
+ position: Duration::new(0, 0),
+ position_modified: false,
}
}
+ /// Sets [`playing`] to `true` in a manner that allows method chaining.
+ ///
+ /// [`playing`]: #structfield.playing
pub fn play(&mut self) -> &mut Self {
self.playing = true;
self
}
+ /// Sets [`playing`] to `false` in a manner that allows method chaining.
+ ///
+ /// [`playing`]: #structfield.playing
pub fn pause(&mut self) -> &mut Self {
self.playing = false;
self
}
+ /// Sets [`volume`] in a manner that allows method chaining.
+ ///
+ /// [`volume`]: #structfield.volume
pub fn volume(&mut self, volume: f32) -> &mut Self {
self.volume = volume;
self
}
+
+ /// Change the position in the stream for subsequent playback.
+ ///
+ /// Currently a No-op.
+ pub fn position(&mut self, position: Duration) -> &mut Self {
+ self.position = position;
+ self.position_modified = true;
+
+ self
+ }
+
+ /// Steps playback location forward by one frame.
+ ///
+ /// *Used internally*, although in future this might affect seek position.
+ pub(crate) fn step_frame(&mut self) {
+ self.position += Duration::from_millis(20);
+ self.position_modified = false;
+ }
+
}
/// Threadsafe form of an instance of the [`Audio`] struct, locked behind a