From a9ad083e27a545afae48268d1b4117d47fe44dda Mon Sep 17 00:00:00 2001 From: Weird Constructor Date: Sat, 29 May 2021 15:22:32 +0200 Subject: [PATCH] fixed a crash bug --- src/dsp/mod.rs | 9 ++++++--- src/dsp/node_sampl.rs | 41 ++++++++++++++++++++++++++--------------- tests/common/mod.rs | 12 ++++++------ tests/node_sampl.rs | 27 +++++++++++++++++++++++++++ 4 files changed, 65 insertions(+), 24 deletions(-) diff --git a/src/dsp/mod.rs b/src/dsp/mod.rs index 498df89..c697134 100644 --- a/src/dsp/mod.rs +++ b/src/dsp/mod.rs @@ -237,6 +237,8 @@ macro_rules! d_pit { ($x: expr) => { define_exp!{n_gain d_gain 0.0, 2.0} define_exp!{n_att d_att 0.0, 1.0} +define_exp!{n_declick d_declick 0.0, 50.0} + // A note about the input-indicies: // // Atoms and Input parameters share the same global ID space @@ -278,9 +280,10 @@ macro_rules! node_list { (1 trig n_id n_id -1.0, 1.0, 0.0) (2 offs n_id n_id 0.0, 1.0, 0.0) (3 len n_id n_id 0.0, 1.0, 1.0) - {4 0 sample audio_unloaded("") 0 0} - {5 1 pmode setting(0) 0 1} - {6 2 dclick setting(0) 0 1} + (4 dcms n_declick d_declick 0.0, 1.0, 3.14) + {5 0 sample audio_unloaded("") 0 0} + {6 1 pmode setting(0) 0 1} + {7 2 dclick setting(0) 0 1} [0 sig], sin => Sin UIType::Generic UICategory::Osc (0 freq n_pit d_pit -1.0, 1.0, 440.0) diff --git a/src/dsp/node_sampl.rs b/src/dsp/node_sampl.rs index 85c2342..9c4450d 100644 --- a/src/dsp/node_sampl.rs +++ b/src/dsp/node_sampl.rs @@ -7,8 +7,6 @@ use crate::dsp::{SAtom, ProcBuf, DspNode, LedPhaseVals}; use crate::dsp::{out, at, inp, denorm}; //, inp, denorm, denorm_v, inp_dir, at}; use super::helpers::Trigger; -const RAMP_TIME_MS : f64 = 3.14; - /// A simple amplifier #[derive(Debug, Clone)] pub struct Sampl { @@ -38,6 +36,8 @@ impl Sampl { "Sampl offs\nStart position offset.\nRange: (0..1)\n"; pub const len : &'static str = "Sampl len\nLength of the sample, after the offset has been applied.\nRange: (0..1)\n"; + pub const dcms : &'static str = + "Sampl dcms\nDeclick fade time in milliseconds.\nUnsmoothed\nRange: (0..1)\n"; pub const sample : &'static str = "Sampl sample\nThe audio sample that is played back.\nRange: (-1..1)\n"; @@ -101,13 +101,15 @@ impl Sampl { let trig = inp::Sampl::trig(inputs); let offs = inp::Sampl::offs(inputs); let len = inp::Sampl::len(inputs); + let dcms = inp::Sampl::dcms(inputs); let sample_srate = sample_data[0] as f64; let sample_data = &sample_data[1..]; let sr_factor = sample_srate / self.srate; - let ramp_sample_count = ((RAMP_TIME_MS * self.srate) / 1000.0).ceil() as usize; - let ramp_inc = 1000.0 / (RAMP_TIME_MS * self.srate); + let ramp_time = denorm::Sampl::dcms(dcms, 0) as f64 * self.srate; + let ramp_sample_count = (ramp_time / 1000.0).ceil() as usize; + let ramp_inc = 1000.0 / ramp_time; let mut is_playing = self.is_playing; @@ -136,21 +138,30 @@ impl Sampl { let prev_phase = self.phase; + let sd_len = sample_data.len(); + let cur_offs = - denorm::Sampl::offs(offs, frame).abs().min(0.999999); - if prev_offs != cur_offs { - start_idx = - (sample_data.len() as f32 * cur_offs) - .floor() as usize; - prev_offs = cur_offs; - } + denorm::Sampl::offs(offs, frame).abs().min(0.999999) + as f64; + let recalc_end = + if prev_offs != cur_offs { + start_idx = + ((sd_len as f64 * cur_offs) + .floor() as usize).min(sd_len); + prev_offs = cur_offs; + true + } else { + false + }; let cur_len = - denorm::Sampl::len(len, frame).abs().min(0.999999); - if prev_len != cur_len { + denorm::Sampl::len(len, frame).abs().min(0.999999) + as f64; + if recalc_end || prev_len != cur_len { + let remain_s_len = sd_len - start_idx; end_idx_plus1 = - ((sample_data.len() - start_idx) as f32 * cur_len) - .ceil() as usize; + ((remain_s_len as f64 * cur_len) + .ceil() as usize).min(remain_s_len); prev_len = cur_len; } diff --git a/tests/common/mod.rs b/tests/common/mod.rs index 4903106..eaeba08 100644 --- a/tests/common/mod.rs +++ b/tests/common/mod.rs @@ -42,18 +42,18 @@ macro_rules! assert_f3tupl_eq { ($a:expr, $b:expr) => { if ($a.0 - $b.0).abs() > 0.0001 { panic!(r#"assertion failed: `(left.0 == right.0)` - left: `{:?}`, - right: `{:?}`"#, $a.0, $b.0) + left.0: `{:?}`, + right.0: `{:?}`"#, $a.0, $b.0) } if ($a.1 - $b.1).abs() > 0.0001 { panic!(r#"assertion failed: `(left.1 == right.1)` - left: `{:?}`, - right: `{:?}`"#, $a.1, $b.1) + left.1: `{:?}`, + right.1: `{:?}`"#, $a.1, $b.1) } if ($a.2 - $b.2).abs() > 0.0001 { panic!(r#"assertion failed: `(left.2 == right.2)` - left: `{:?}`, - right: `{:?}`"#, $a.2, $b.2) + left.2: `{:?}`, + right.2: `{:?}`"#, $a.2, $b.2) } } } diff --git a/tests/node_sampl.rs b/tests/node_sampl.rs index 5252fb5..00dc214 100644 --- a/tests/node_sampl.rs +++ b/tests/node_sampl.rs @@ -332,6 +332,33 @@ fn check_node_sampl_offs_len_zero_crash() { assert_minmax_of_rms!(rmsvec[0], (0.0, 0.0)); } +#[test] +fn check_node_sampl_offs_modulated_crash() { + let (node_conf, mut node_exec) = new_node_engine(); + let mut matrix = Matrix::new(node_conf, 3, 3); + + let sin = NodeId::Sin(0); + let smpl = NodeId::Sampl(0); + let out = NodeId::Out(0); + matrix.place(0, 0, Cell::empty(sin) + .out(None, None, sin.out("sig"))); + matrix.place(0, 1, Cell::empty(smpl) + .input(smpl.inp("offs"), None, None) + .out(None, None, smpl.out("sig"))); + matrix.place(0, 2, Cell::empty(out) + .input(out.inp("ch1"), None, None)); + matrix.sync().unwrap(); + + let sample_p = smpl.inp_param("sample").unwrap(); + let pmode_p = smpl.inp_param("pmode").unwrap(); + + matrix.set_param(sample_p, create_1sec_ramp()); + matrix.set_param(pmode_p, SAtom::setting(0)); + + let rmsvec = run_and_get_each_rms_mimax(&mut node_exec, 100.0); + assert_rmsmima!(rmsvec[0], (0.5008, 0.0, 1.0)); +} + #[test] fn check_node_sampl_declick() { let (node_conf, mut node_exec) = new_node_engine();