use dasp_graph::{Buffer, Input};
use rtrb::Producer;
use crate::node::{AudioNode, ProcessContext};
pub struct RtrbSink {
producer: Producer<f32>,
channels: usize,
}
impl RtrbSink {
pub fn new(producer: Producer<f32>, channels: usize) -> Self {
Self {
producer,
channels: channels.max(1),
}
}
pub fn mono(producer: Producer<f32>) -> Self {
Self::new(producer, 1)
}
pub fn stereo(producer: Producer<f32>) -> Self {
Self::new(producer, 2)
}
#[inline]
pub fn available(&self) -> usize {
self.producer.slots()
}
}
impl AudioNode for RtrbSink {
type Message = ();
fn process(
&mut self,
_ctx: &ProcessContext,
_messages: impl Iterator<Item = ()>,
inputs: &[Input],
_outputs: &mut [Buffer],
) {
if inputs.is_empty() {
return;
}
let input = &inputs[0];
let buffers = input.buffers();
if buffers.is_empty() {
return;
}
let buffer_len = buffers[0].len();
let samples_needed = buffer_len * self.channels;
if self.producer.slots() < samples_needed {
return;
}
for i in 0..buffer_len {
for ch in 0..self.channels {
let src_ch = ch.min(buffers.len() - 1);
let _ = self.producer.push(buffers[src_ch][i]);
}
}
}
#[inline]
fn num_inputs(&self) -> usize { 1 }
#[inline]
fn num_outputs(&self) -> usize { 0 }
}