Skip to content

Instantly share code, notes, and snippets.

@itarato
Created April 30, 2019 01:08
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save itarato/64bed88716f2cca6a1b2a59f0c9e5a98 to your computer and use it in GitHub Desktop.
Save itarato/64bed88716f2cca6a1b2a59f0c9e5a98 to your computer and use it in GitHub Desktop.
DMG Boot logo beep sound prototype.
extern crate sdl2;
use sdl2::audio::{AudioCallback, AudioSpecDesired};
use std::sync::{Arc, Mutex};
use std::time::Duration;
struct SoundPacket {
pitch: f32,
len: Option<usize>,
volume: f32,
envelope_sweep_length: usize,
restart: bool,
}
impl SoundPacket {
fn new(
pitch: f32,
len: Option<usize>,
volume: f32,
envelope_sweep_length: usize,
) -> SoundPacket {
SoundPacket {
pitch,
len,
volume,
envelope_sweep_length,
restart: true,
}
}
}
struct SquareWave {
freq: f32,
phase: f32,
pocket: Arc<Mutex<Option<SoundPacket>>>,
envelope_sweep_counter: usize,
}
impl AudioCallback for SquareWave {
type Channel = f32;
fn callback(&mut self, out: &mut [f32]) {
for x in out.iter_mut() {
let mut pocket = self.pocket.lock().unwrap();
*x = if pocket.is_some()
/* && (*pocket).as_ref().unwrap().len > 0 */
{
if (*pocket).as_ref().unwrap().restart {
(*pocket).as_mut().unwrap().restart = false;
self.envelope_sweep_counter = (*pocket).as_mut().unwrap().envelope_sweep_length;
}
let next_x = if self.phase <= 0.50 {
pocket.as_ref().unwrap().volume
} else {
-pocket.as_ref().unwrap().volume
};
let pitch = pocket.as_ref().unwrap().pitch;
self.phase = (self.phase + (pitch / self.freq)) % 1.0;
// (*pocket).as_mut().unwrap().len -= 1;
if (*pocket).as_ref().unwrap().volume > 0f32 {
if (*pocket).as_ref().unwrap().envelope_sweep_length > 0 {
if self.envelope_sweep_counter > 0 {
self.envelope_sweep_counter -= 1;
} else {
(*pocket).as_mut().unwrap().volume -= 1f32 / 16f32;
self.envelope_sweep_counter =
(*pocket).as_mut().unwrap().envelope_sweep_length;
}
}
}
next_x
} else {
0.0
};
}
}
}
fn main() -> Result<(), String> {
let sdl_context = sdl2::init()?;
let audio_subsystem = sdl_context.audio()?;
let desired_spec = AudioSpecDesired {
freq: Some(44_100),
channels: Some(1),
samples: None,
};
let pocket = Arc::new(Mutex::new(None));
let device = audio_subsystem.open_playback(None, &desired_spec, |spec| SquareWave {
freq: spec.freq as f32,
phase: 0.5,
pocket: pocket.clone(),
envelope_sweep_counter: 0usize,
})?;
device.resume();
{
let start_volume = 9f32;
let env_count = 4;
let mut pocket = pocket.lock().unwrap();
*pocket = Some(SoundPacket::new(
1048.0,
None,
start_volume / 16f32,
(22050 * env_count) / 64,
));
}
std::thread::sleep(Duration::from_millis(60));
{
let start_volume = 9f32;
let env_count = 4;
let mut pocket = pocket.lock().unwrap();
*pocket = Some(SoundPacket::new(
2080.0,
None,
start_volume / 16f32,
(22050 * env_count) / 64,
));
}
std::thread::sleep(Duration::from_millis(558));
Ok(())
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment