From 8809a9db973a2c378da0fe1d8d8e4cea928b2a6a Mon Sep 17 00:00:00 2001 From: Jean Pierre Cimalando Date: Tue, 13 Apr 2021 20:45:06 +0200 Subject: [PATCH] Pitch envelope in cents, bend_smooth linear in pitch --- src/sfizz/Voice.cpp | 50 ++++++++++++++++++++++----------------------- 1 file changed, 25 insertions(+), 25 deletions(-) diff --git a/src/sfizz/Voice.cpp b/src/sfizz/Voice.cpp index 7b414a93..26928526 100644 --- a/src/sfizz/Voice.cpp +++ b/src/sfizz/Voice.cpp @@ -268,7 +268,6 @@ struct Voice::Impl ADSREnvelope egAmplitude_; std::unique_ptr egPitch_; std::unique_ptr egFilter_; - float bendStepFactor_ { centsFactor(1) }; WavetableOscillator waveOscillators_[config::oscillatorsPerVoice]; @@ -501,9 +500,8 @@ bool Voice::startVoice(Layer* layer, int delay, const TriggerEvent& event) noexc impl.baseFrequency_ = resources.tuning.getFrequencyOfKey(impl.triggerEvent_.number); impl.sampleEnd_ = int(region.getSampleEnd(resources.midiState, resources.filePool.getOversamplingFactor())); impl.sampleSize_ = impl.sampleEnd_- impl.sourcePosition_ - 1; - impl.bendStepFactor_ = centsFactor(region.bendStep); impl.bendSmoother_.setSmoothing(region.bendSmooth, impl.sampleRate_); - impl.bendSmoother_.reset(centsFactor(region.getBendInCents(resources.midiState.getPitchBend()))); + impl.bendSmoother_.reset(region.getBendInCents(resources.midiState.getPitchBend())); resources.modMatrix.initVoice(impl.id_, region.getId(), impl.initialDelay_); impl.saveModulationTargets(®ion); @@ -1022,7 +1020,7 @@ void Voice::Impl::filterStageStereo(AudioSpan buffer) noexcept void Voice::Impl::fillWithData(AudioSpan buffer) noexcept { - const auto numSamples = buffer.getNumFrames(); + const size_t numSamples = buffer.getNumFrames(); if (numSamples == 0) return; @@ -1045,14 +1043,17 @@ void Voice::Impl::fillWithData(AudioSpan buffer) noexcept if (!jumps) return; - fill(*jumps, pitchRatio_ * speedRatio_); + absl::Span pitch = *jumps; // temporary + pitchEnvelope(pitch); + + float baseRatio = pitchRatio_ * speedRatio_; + for (size_t i = 0; i < numSamples; ++i) + (*jumps)[i] = baseRatio * centsFactor(pitch[i]); // Take the first sample if the voice just started if (age_ == 0) jumps->front() = 0.0f; - pitchEnvelope(*jumps); - jumps->front() += floatPositionOffset_; cumsum(*jumps, *jumps); sfzInterpolationCast(*jumps, *indices, *coeffs); @@ -1461,15 +1462,20 @@ void Voice::Impl::fillWithGenerator(AudioSpan buffer) noexcept absl::c_generate(leftSpan, gen); absl::c_generate(rightSpan, gen); } else { - const auto numFrames = buffer.getNumFrames(); + const size_t numFrames = buffer.getNumFrames(); auto frequencies = resources_.bufferPool.getBuffer(numFrames); if (!frequencies) return; - float keycenterFrequency = midiNoteFrequency(pitchKeycenter_); - fill(*frequencies, pitchRatio_ * keycenterFrequency); - pitchEnvelope(*frequencies); + absl::Span pitch = *frequencies; // temporary + pitchEnvelope(pitch); + + const float keycenterFrequency = midiNoteFrequency(pitchKeycenter_); + const float baseRatio = pitchRatio_ * keycenterFrequency; + + for (size_t i = 0; i < numFrames; ++i) + (*frequencies)[i] = baseRatio * centsFactor(pitch[i]); auto detuneSpan = resources_.bufferPool.getBuffer(numFrames); if (!detuneSpan) @@ -1901,34 +1907,28 @@ void Voice::Impl::switchState(State s) void Voice::Impl::pitchEnvelope(absl::Span pitchSpan) noexcept { - const auto numFrames = pitchSpan.size(); - auto bends = resources_.bufferPool.getBuffer(numFrames); - if (!bends) - return; + const size_t numFrames = pitchSpan.size(); const EventVector& events = resources_.midiState.getPitchEvents(); const auto bendLambda = [this](float bend) { - return centsFactor(region_->getBendInCents(bend)); + return region_->getBendInCents(bend); }; if (region_->bendStep > 1.0f) - pitchBendEnvelope(events, *bends, bendLambda, bendStepFactor_); + linearEnvelope(events, pitchSpan, bendLambda, region_->bendStep); else - pitchBendEnvelope(events, *bends, bendLambda); - bendSmoother_.process(*bends, *bends); - applyGain(*bends, pitchSpan); + linearEnvelope(events, pitchSpan, bendLambda); + bendSmoother_.process(pitchSpan, pitchSpan); ModMatrix& mm = resources_.modMatrix; - if (float* mod = mm.getModulation(pitchTarget_)) { - for (size_t i = 0; i < numFrames; ++i) - pitchSpan[i] *= centsFactor(mod[i]); - } + if (float* mod = mm.getModulation(pitchTarget_)) + add(absl::MakeSpan(mod, numFrames), pitchSpan); } void Voice::Impl::resetSmoothers() noexcept { - bendSmoother_.reset(1.0f); + bendSmoother_.reset(0.0f); gainSmoother_.reset(0.0f); }