From 3f8bee1301157e82adac9cfccb15ecf2838a4e25 Mon Sep 17 00:00:00 2001 From: Weird Constructor Date: Wed, 23 Jun 2021 05:11:24 +0200 Subject: [PATCH] fixed a bug in the delay line, that made it 1 sample off, getting incrementally worse --- src/dsp/helpers.rs | 2 +- src/dsp/node_delay.rs | 17 ++++------------- tests/node_delay.rs | 18 ++++++++++++++---- 3 files changed, 19 insertions(+), 18 deletions(-) diff --git a/src/dsp/helpers.rs b/src/dsp/helpers.rs index 1625196..2d5ac15 100644 --- a/src/dsp/helpers.rs +++ b/src/dsp/helpers.rs @@ -561,8 +561,8 @@ impl DelayBuffer { #[inline] pub fn feed(&mut self, input: f32) { - self.wr = (self.wr + 1) % self.data.len(); self.data[self.wr] = input; + self.wr = (self.wr + 1) % self.data.len(); } #[inline] diff --git a/src/dsp/node_delay.rs b/src/dsp/node_delay.rs index 4c9bdde..a73e2d6 100644 --- a/src/dsp/node_delay.rs +++ b/src/dsp/node_delay.rs @@ -21,7 +21,6 @@ macro_rules! fa_delay_mode { ($formatter: expr, $v: expr, $denorm_v: expr) => { #[derive(Debug, Clone)] pub struct Delay { buffer: Box, - fb_sample: f32, clock: TriggerSampleClock, } @@ -29,7 +28,6 @@ impl Delay { pub fn new(_nid: &NodeId) -> Self { Self { buffer: Box::new(DelayBuffer::new()), - fb_sample: 0.0, clock: TriggerSampleClock::new(), } } @@ -108,43 +106,36 @@ impl DspNode for Delay { let mix = inp::Delay::mix(inputs); let out = out::Delay::sig(outputs); - let mut fb_s = self.fb_sample; - if mode.i() == 0 { for frame in 0..ctx.nframes() { let dry = inp.read(frame); - buffer.feed(dry + fb_s * denorm::Delay::fb(fb, frame)); let out_sample = buffer.cubic_interpolate_at( denorm::Delay::time(time, frame)); + buffer.feed(dry + out_sample * denorm::Delay::fb(fb, frame)); + out.write(frame, crossfade(dry, out_sample, denorm::Delay::mix(mix, frame).clamp(0.0, 1.0))); - - fb_s = out_sample; } } else { for frame in 0..ctx.nframes() { let dry = inp.read(frame); - buffer.feed(dry + fb_s * denorm::Delay::fb(fb, frame)); let clock_samples = self.clock.next(denorm::Delay::trig(trig, frame)); - let out_sample = buffer.at(clock_samples as usize); + buffer.feed(dry + out_sample * denorm::Delay::fb(fb, frame)); + out.write(frame, crossfade(dry, out_sample, denorm::Delay::mix(mix, frame).clamp(0.0, 1.0))); - - fb_s = out_sample; } } - self.fb_sample = fb_s; - let last_frame = ctx.nframes() - 1; ctx_vals[0].set(out.read(last_frame)); } diff --git a/tests/node_delay.rs b/tests/node_delay.rs index d81b7aa..b4ae726 100644 --- a/tests/node_delay.rs +++ b/tests/node_delay.rs @@ -225,7 +225,7 @@ fn check_node_delay_fb() { let idxs_big = collect_signal_changes(&res.0[..], 50); // We expect the signal to be delayed by 20ms: - assert_eq!(idxs_big, vec![(220, 106), (441, 53)]); + assert_eq!(idxs_big, vec![(220, 106), (440, 53)]); } #[test] @@ -258,7 +258,7 @@ fn check_node_delay_fb_neg() { let idxs_big = collect_signal_changes(&res.0[..], 70); - assert_eq!(idxs_big, vec![(441, 100), (883, -100), (1325, 100)]); + assert_eq!(idxs_big, vec![(441, 100), (882, -100), (1323, 100)]); } @@ -288,9 +288,19 @@ fn check_node_delay_fb_pos() { // Emit the trigger signal: pset_n(&mut matrix, test, "trig", 1.0); - let res = run_for_ms(&mut node_exec, 40.0); + let res = run_for_ms(&mut node_exec, 100.0); let idxs_big = collect_signal_changes(&res.0[..], 70); - assert_eq!(idxs_big, vec![(441, 100), (883, 100), (1325, 100)]); + assert_eq!(idxs_big, vec![ + (441, 100), + (441 + 1 * 441, 100), + (441 + 2 * 441, 100), + (441 + 3 * 441, 100), + (441 + 4 * 441, 100), + (441 + 5 * 441, 100), + (441 + 6 * 441, 100), + (441 + 7 * 441, 100), + (441 + 8 * 441, 100), + ]); }