mirror of
https://github.com/italicsjenga/agb.git
synced 2024-12-23 08:11:33 +11:00
Don't force a pointless lifetime on the tracker
This commit is contained in:
parent
a6fca49f7b
commit
71a7b6431c
|
@ -20,7 +20,7 @@ static SWICTH_TOGGLES: &[&[u8]] = &[include_wav!("sfx/switch_toggle1.wav")];
|
||||||
|
|
||||||
pub struct Sfx<'a> {
|
pub struct Sfx<'a> {
|
||||||
mixer: &'a mut Mixer<'a>,
|
mixer: &'a mut Mixer<'a>,
|
||||||
tracker: Tracker<Mixer<'a>>,
|
tracker: Tracker,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> Sfx<'a> {
|
impl<'a> Sfx<'a> {
|
||||||
|
|
|
@ -95,9 +95,9 @@ pub mod __private {
|
||||||
pub use agb_tracker_interop::Track;
|
pub use agb_tracker_interop::Track;
|
||||||
|
|
||||||
/// Stores the required state in order to play tracker music.
|
/// Stores the required state in order to play tracker music.
|
||||||
pub struct Tracker<M: Mixer> {
|
pub struct TrackerInner<TChannelId> {
|
||||||
track: &'static Track,
|
track: &'static Track,
|
||||||
channels: Vec<TrackerChannel<M>>,
|
channels: Vec<TrackerChannel<TChannelId>>,
|
||||||
envelopes: Vec<Option<EnvelopeState>>,
|
envelopes: Vec<Option<EnvelopeState>>,
|
||||||
|
|
||||||
frame: Num<u32, 8>,
|
frame: Num<u32, 8>,
|
||||||
|
@ -110,8 +110,8 @@ pub struct Tracker<M: Mixer> {
|
||||||
current_pattern: usize,
|
current_pattern: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
struct TrackerChannel<M: Mixer> {
|
struct TrackerChannel<TChannelId> {
|
||||||
channel_id: Option<M::ChannelId>,
|
channel_id: Option<TChannelId>,
|
||||||
original_speed: Num<u32, 16>,
|
original_speed: Num<u32, 16>,
|
||||||
base_speed: Num<u32, 16>,
|
base_speed: Num<u32, 16>,
|
||||||
volume: Num<i32, 8>,
|
volume: Num<i32, 8>,
|
||||||
|
@ -132,7 +132,7 @@ struct GlobalSettings {
|
||||||
volume: Num<i32, 8>,
|
volume: Num<i32, 8>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<M: Mixer> Tracker<M> {
|
impl<TChannelId> TrackerInner<TChannelId> {
|
||||||
/// Create a new tracker playing a specified track. See the [example](crate#example) for how to use the tracker.
|
/// Create a new tracker playing a specified track. See the [example](crate#example) for how to use the tracker.
|
||||||
pub fn new(track: &'static Track) -> Self {
|
pub fn new(track: &'static Track) -> Self {
|
||||||
let mut channels = Vec::new();
|
let mut channels = Vec::new();
|
||||||
|
@ -165,7 +165,7 @@ impl<M: Mixer> Tracker<M> {
|
||||||
|
|
||||||
/// Call this once per frame before calling [`mixer.frame`](agb::sound::mixer::Mixer::frame()).
|
/// Call this once per frame before calling [`mixer.frame`](agb::sound::mixer::Mixer::frame()).
|
||||||
/// See the [example](crate#example) for how to use the tracker.
|
/// See the [example](crate#example) for how to use the tracker.
|
||||||
pub fn step(&mut self, mixer: &mut M) {
|
pub fn step<M: Mixer<ChannelId = TChannelId>>(&mut self, mixer: &mut M) {
|
||||||
if !self.increment_frame() {
|
if !self.increment_frame() {
|
||||||
self.update_envelopes(mixer);
|
self.update_envelopes(mixer);
|
||||||
return;
|
return;
|
||||||
|
@ -215,7 +215,7 @@ impl<M: Mixer> Tracker<M> {
|
||||||
self.update_envelopes(mixer);
|
self.update_envelopes(mixer);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_envelopes(&mut self, mixer: &mut M) {
|
fn update_envelopes<M: Mixer<ChannelId = TChannelId>>(&mut self, mixer: &mut M) {
|
||||||
for (channel, envelope_state_option) in self.channels.iter_mut().zip(&mut self.envelopes) {
|
for (channel, envelope_state_option) in self.channels.iter_mut().zip(&mut self.envelopes) {
|
||||||
if let Some(envelope_state) = envelope_state_option {
|
if let Some(envelope_state) = envelope_state_option {
|
||||||
let envelope = &self.track.envelopes[envelope_state.envelope_id];
|
let envelope = &self.track.envelopes[envelope_state.envelope_id];
|
||||||
|
@ -288,8 +288,13 @@ impl<M: Mixer> Tracker<M> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<M: Mixer> TrackerChannel<M> {
|
impl<TChannelId> TrackerChannel<TChannelId> {
|
||||||
fn play_sound(&mut self, mixer: &mut M, sample: &Sample, global_settings: &GlobalSettings) {
|
fn play_sound<M: Mixer<ChannelId = TChannelId>>(
|
||||||
|
&mut self,
|
||||||
|
mixer: &mut M,
|
||||||
|
sample: &Sample,
|
||||||
|
global_settings: &GlobalSettings,
|
||||||
|
) {
|
||||||
if let Some(channel) = self
|
if let Some(channel) = self
|
||||||
.channel_id
|
.channel_id
|
||||||
.take()
|
.take()
|
||||||
|
@ -316,7 +321,7 @@ impl<M: Mixer> TrackerChannel<M> {
|
||||||
self.volume = sample.volume.change_base();
|
self.volume = sample.volume.change_base();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_speed(&mut self, mixer: &mut M, speed: Num<u32, 8>) {
|
fn set_speed<M: Mixer<ChannelId = TChannelId>>(&mut self, mixer: &mut M, speed: Num<u32, 8>) {
|
||||||
if let Some(channel) = self
|
if let Some(channel) = self
|
||||||
.channel_id
|
.channel_id
|
||||||
.as_ref()
|
.as_ref()
|
||||||
|
@ -331,7 +336,7 @@ impl<M: Mixer> TrackerChannel<M> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn apply_effect(
|
fn apply_effect<M: Mixer<ChannelId = TChannelId>>(
|
||||||
&mut self,
|
&mut self,
|
||||||
mixer: &mut M,
|
mixer: &mut M,
|
||||||
effect: &PatternEffect,
|
effect: &PatternEffect,
|
||||||
|
@ -473,7 +478,7 @@ impl<M: Mixer> TrackerChannel<M> {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[must_use]
|
#[must_use]
|
||||||
fn update_volume_envelope(
|
fn update_volume_envelope<M: Mixer<ChannelId = TChannelId>>(
|
||||||
&mut self,
|
&mut self,
|
||||||
mixer: &mut M,
|
mixer: &mut M,
|
||||||
envelope_state: &EnvelopeState,
|
envelope_state: &EnvelopeState,
|
||||||
|
@ -504,7 +509,7 @@ impl<M: Mixer> TrackerChannel<M> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<M: Mixer> Default for TrackerChannel<M> {
|
impl<TChannelId> Default for TrackerChannel<TChannelId> {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self {
|
Self {
|
||||||
channel_id: None,
|
channel_id: None,
|
||||||
|
@ -578,3 +583,7 @@ impl<'gba> Mixer for agb::sound::mixer::Mixer<'gba> {
|
||||||
self.play_sound(channel)
|
self.play_sound(channel)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(feature = "agb")]
|
||||||
|
/// The type to use if you're using agb-tracker with agb
|
||||||
|
pub type Tracker = TrackerInner<agb::sound::mixer::ChannelId>;
|
||||||
|
|
|
@ -18,7 +18,7 @@ fn main() -> Result<(), Box<dyn Error>> {
|
||||||
let track = Box::leak::<'static>(Box::new(agb_xm_core::parse_module(&module)));
|
let track = Box::leak::<'static>(Box::new(agb_xm_core::parse_module(&module)));
|
||||||
|
|
||||||
let mut mixer = Mixer::new();
|
let mut mixer = Mixer::new();
|
||||||
let mut tracker = agb_tracker::Tracker::new(track);
|
let mut tracker = agb_tracker::TrackerInner::new(track);
|
||||||
|
|
||||||
let host = cpal::default_host();
|
let host = cpal::default_host();
|
||||||
let device = host
|
let device = host
|
||||||
|
|
Loading…
Reference in a new issue