audio input and fft
All checks were successful
Build legacy Nix package on Ubuntu / build (push) Successful in 4m17s

This commit is contained in:
2025-01-12 17:52:47 +01:00
parent 33907234fd
commit 86dfbd21f4
6 changed files with 1336 additions and 12 deletions

View File

@ -1,3 +1,67 @@
fn main() {
println!("Hello, world!");
use std::{thread::sleep, time::Duration};
use color_eyre::eyre::bail;
use cpal::{
traits::{DeviceTrait, HostTrait, StreamTrait},
BufferSize, HostId, SupportedBufferSize,
};
use log::{debug, error, info, trace};
use rustfft::{num_complex::Complex, FftPlanner};
fn main() -> color_eyre::Result<()> {
env_logger::init();
debug!("Starting");
let mut hosts = cpal::platform::available_hosts();
hosts.sort_unstable_by_key(|host| match host {
HostId::Jack => 0,
HostId::Alsa => 1,
});
let host_id = hosts[0];
info!("Selected {host_id:?} audio backend");
let host = cpal::platform::host_from_id(host_id)?;
let Some(device) = host.default_input_device() else {
error!("Unable to get default input device for {host_id:?}");
bail!("Unable to get default input device")
};
debug!("Got default input device {:?}", device.name());
let default_config = device.default_input_config()?;
trace!("Default config {:?}", default_config);
let mut config = default_config.config();
let buffer_size =
if let SupportedBufferSize::Range { min, max: _ } = default_config.buffer_size() {
*min
} else {
1024
};
config.buffer_size = BufferSize::Fixed(buffer_size);
config.channels = 1;
debug!("Using config {config:?}");
let mut planner = FftPlanner::<f32>::new();
let fft = planner.plan_fft_forward(buffer_size as usize);
let mut fft_data = vec![Complex::new(0.0, 0.0); buffer_size as usize];
let mut fft_scratch = vec![Complex::new(0.0, 0.0); buffer_size as usize];
let stream = device.build_input_stream(
&config,
move |data: &[f32], _| {
for i in 0..data.len() {
fft_data[i] = Complex::new(data[i], 0.0);
}
fft.process_with_scratch(&mut fft_data[..], &mut fft_scratch[..]);
},
|err| {
error!("input stream error: {err}");
},
None,
)?;
stream.play()?;
loop {
sleep(Duration::from_secs(1));
}
}