tuned the BowStri oscillator
This commit is contained in:
parent
24ea58eda0
commit
ed1f9f7f4a
1 changed files with 74 additions and 8 deletions
|
@ -60,7 +60,7 @@ impl BowedString {
|
||||||
self.string_filter =
|
self.string_filter =
|
||||||
FixedOnePole::new(
|
FixedOnePole::new(
|
||||||
0.75 - (0.2 * (22050.0 / sample_rate)),
|
0.75 - (0.2 * (22050.0 / sample_rate)),
|
||||||
0.95);
|
0.9);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn reset(&mut self) {
|
pub fn reset(&mut self) {
|
||||||
|
@ -78,25 +78,33 @@ impl BowedString {
|
||||||
freq: f32, bow_velocity: f32, bow_force: f32, pos: f32
|
freq: f32, bow_velocity: f32, bow_force: f32, pos: f32
|
||||||
) -> f32
|
) -> f32
|
||||||
{
|
{
|
||||||
|
// baseDelay_ = Stk::sampleRate() / frequency - 4.0;
|
||||||
|
// if ( baseDelay_ <= 0.0 ) baseDelay_ = 0.3;
|
||||||
|
// bridgeDelay_.setDelay( baseDelay_ * betaRatio_ ); // bow to bridge length
|
||||||
|
// neckDelay_.setDelay( baseDelay_ * (1.0 - betaRatio_) ); // bow to nut (finger) length
|
||||||
|
|
||||||
let total_l = self.srate / freq.max(20.0);
|
let total_l = self.srate / freq.max(20.0);
|
||||||
|
let total_l = if total_l <= 0.0 { 0.3 } else { total_l };
|
||||||
let bow_position = ((pos + 1.0) / 2.0).clamp(0.01, 0.99);
|
let bow_position = ((pos + 1.0) / 2.0).clamp(0.01, 0.99);
|
||||||
|
|
||||||
let bow_nut_l = total_l * (1.0 - bow_position);
|
let bow_nut_l = total_l * (1.0 - bow_position);
|
||||||
let bow_bridge_l = total_l * bow_position;
|
let bow_bridge_l = total_l * bow_position;
|
||||||
|
|
||||||
let nut = -self.nut_to_bow.linear_interpolate_at_s(bow_nut_l);
|
let nut = -self.nut_to_bow.cubic_interpolate_at_s(bow_nut_l);
|
||||||
let brid = self.bow_to_bridge.linear_interpolate_at_s(bow_bridge_l);
|
let brid = self.bow_to_bridge.cubic_interpolate_at_s(bow_bridge_l);
|
||||||
let bridge = -self.string_filter.process(brid);
|
let bridge = -self.string_filter.process(brid);
|
||||||
|
|
||||||
let dv = bow_velocity - (nut + bridge);
|
let dv = 0.25 * bow_velocity - (nut + bridge);
|
||||||
|
|
||||||
let phat =
|
let phat =
|
||||||
((dv + 0.001) * bow_force + 0.75)
|
((dv + 0.001) * bow_force + 0.75)
|
||||||
|
.abs()
|
||||||
.powf(-4.0)
|
.powf(-4.0)
|
||||||
.clamp(0.0, 0.98);
|
.clamp(0.01, 0.98);
|
||||||
|
let phat = phat * dv;
|
||||||
|
|
||||||
self.bow_to_bridge.feed(nut + phat*dv);
|
self.bow_to_bridge.feed(nut + phat);
|
||||||
self.nut_to_bow.feed(bridge + phat*dv);
|
self.nut_to_bow.feed(bridge + phat);
|
||||||
|
|
||||||
let mut output = bridge;
|
let mut output = bridge;
|
||||||
for f in self.body_filters.iter_mut() {
|
for f in self.body_filters.iter_mut() {
|
||||||
|
@ -107,6 +115,44 @@ impl BowedString {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// maxVelocity_ = 0.25;
|
||||||
|
//
|
||||||
|
// StkFloat bowVelocity = maxVelocity_ * adsr_.tick();
|
||||||
|
// StkFloat bridgeReflection = -stringFilter_.tick( bridgeDelay_.lastOut() );
|
||||||
|
// StkFloat nutReflection = -neckDelay_.lastOut();
|
||||||
|
// StkFloat stringVelocity = bridgeReflection + nutReflection;
|
||||||
|
// StkFloat deltaV = bowVelocity - stringVelocity; // Differential velocity
|
||||||
|
//
|
||||||
|
// StkFloat newVelocity = 0.0;
|
||||||
|
// if ( bowDown_ )
|
||||||
|
// newVelocity = deltaV * bowTable_.tick( deltaV ); // Non-Linear bow function
|
||||||
|
// | // The input represents differential string vs. bow velocity.
|
||||||
|
// |
|
||||||
|
// | StkFloat sample = deltaV + 0.001; // add bias to input
|
||||||
|
// | sample *= 3.0; // then scale it
|
||||||
|
// | lastFrame_[0] = fabs( (double) sample ) + 0.75;
|
||||||
|
// | lastFrame_[0] = pow( lastFrame_[0], (StkFloat) -4.0 );
|
||||||
|
// |
|
||||||
|
// | // Set minimum threshold
|
||||||
|
// | if ( lastFrame_[0] < minOutput_ ) lastFrame_[0] = minOutput_;
|
||||||
|
// |
|
||||||
|
// | // Set maximum threshold
|
||||||
|
// | if ( lastFrame_[0] > maxOutput_ ) lastFrame_[0] = maxOutput_;
|
||||||
|
// |
|
||||||
|
// | return lastFrame_[0];
|
||||||
|
//
|
||||||
|
// neckDelay_.tick( bridgeReflection + newVelocity); // Do string propagations
|
||||||
|
// bridgeDelay_.tick(nutReflection + newVelocity);
|
||||||
|
//
|
||||||
|
// lastFrame_[0] = 0.1248
|
||||||
|
// * bodyFilters_[5].tick(
|
||||||
|
// bodyFilters_[4].tick(
|
||||||
|
// bodyFilters_[3].tick(
|
||||||
|
// bodyFilters_[2].tick(
|
||||||
|
// bodyFilters_[1].tick(
|
||||||
|
// bodyFilters_[0].tick(
|
||||||
|
// bridgeDelay_.lastOut()))))));
|
||||||
|
|
||||||
/// A sine oscillator
|
/// A sine oscillator
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct BowStri {
|
pub struct BowStri {
|
||||||
|
@ -148,6 +194,13 @@ This is an oscillator that simulates a bowed string.
|
||||||
pub const HELP : &'static str =
|
pub const HELP : &'static str =
|
||||||
r#"BowStri - A Bowed String Oscillator
|
r#"BowStri - A Bowed String Oscillator
|
||||||
|
|
||||||
|
This is an oscillator that simulates a bowed string.
|
||||||
|
It's a bit wonky, so play around with the parameters and see what
|
||||||
|
works and what doesn't. It plays find in the area from ~55Hz up to
|
||||||
|
~1760Hz, beyond that it might not produce a sound.
|
||||||
|
|
||||||
|
I can recommend to apply an envelope to the 'vel' parameter,
|
||||||
|
which is basically the bow's velocity.
|
||||||
"#;
|
"#;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -178,7 +231,20 @@ impl DspNode for BowStri {
|
||||||
|
|
||||||
let mut last_val = 0.0;
|
let mut last_val = 0.0;
|
||||||
for frame in 0..ctx.nframes() {
|
for frame in 0..ctx.nframes() {
|
||||||
let freq = denorm_offs::BowStri::freq(freq, det.read(frame), frame);
|
// The BowStri oscillator is usually off by ~30 cent per octave,
|
||||||
|
// that makes it off by 1 semitone at about 1760Hz and off by ~30
|
||||||
|
// at 440 Hz.
|
||||||
|
// Calculate some tune correction here based on the
|
||||||
|
// normalized value (-0.2 is 110Hz, 0.0 is 440Hz, ...):
|
||||||
|
let tune_correction =
|
||||||
|
(freq.read(frame).clamp(-0.2, 1.0) + 0.2)
|
||||||
|
* 10.0 * 0.0012;
|
||||||
|
|
||||||
|
let freq =
|
||||||
|
denorm_offs::BowStri::freq(
|
||||||
|
freq,
|
||||||
|
tune_correction + det.read(frame),
|
||||||
|
frame);
|
||||||
|
|
||||||
let out =
|
let out =
|
||||||
self.bstr.process(
|
self.bstr.process(
|
||||||
|
|
Loading…
Reference in a new issue