Merge pull request #621 from jpcima/xruns

Fix a variety of xrun situations
This commit is contained in:
JP Cimalando 2021-02-02 14:18:22 +01:00 committed by GitHub
commit 86e7e6fbcc
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 33 additions and 15 deletions

View file

@ -139,6 +139,17 @@ namespace config {
*/ */
static constexpr float overflowVoiceMultiplier { 1.5f }; static constexpr float overflowVoiceMultiplier { 1.5f };
static_assert(overflowVoiceMultiplier >= 1.0f, "This needs to add voices"); static_assert(overflowVoiceMultiplier >= 1.0f, "This needs to add voices");
/**
* @brief Calculate the effective voice number for the polyphony setting,
* accounting for the overflow factor.
*/
inline constexpr int calculateActualVoices(int polyphony)
{
return
(int(polyphony * config::overflowVoiceMultiplier) < int(config::maxVoices)) ?
int(polyphony * config::overflowVoiceMultiplier) : int(config::maxVoices);
}
} // namespace config } // namespace config
} // namespace sfz } // namespace sfz

View file

@ -1,9 +1,13 @@
#include "PolyphonyGroup.h" #include "PolyphonyGroup.h"
sfz::PolyphonyGroup::PolyphonyGroup()
{
voices.reserve(config::maxVoices);
}
void sfz::PolyphonyGroup::setPolyphonyLimit(unsigned limit) noexcept void sfz::PolyphonyGroup::setPolyphonyLimit(unsigned limit) noexcept
{ {
polyphonyLimit = limit; polyphonyLimit = limit;
voices.reserve(limit);
} }
void sfz::PolyphonyGroup::registerVoice(Voice* voice) noexcept void sfz::PolyphonyGroup::registerVoice(Voice* voice) noexcept

View file

@ -16,6 +16,8 @@ namespace sfz
{ {
class PolyphonyGroup { class PolyphonyGroup {
public: public:
PolyphonyGroup();
/** /**
* @brief Set the polyphony limit for this polyphony group. * @brief Set the polyphony limit for this polyphony group.
* *

View file

@ -1,9 +1,16 @@
#include "RegionSet.h" #include "RegionSet.h"
sfz::RegionSet::RegionSet(RegionSet* parentSet, OpcodeScope level)
: parent(parentSet), level(level)
{
voices.reserve(config::maxVoices);
if (parentSet != nullptr)
parentSet->addSubset(this);
}
void sfz::RegionSet::setPolyphonyLimit(unsigned limit) noexcept void sfz::RegionSet::setPolyphonyLimit(unsigned limit) noexcept
{ {
polyphonyLimit = limit; polyphonyLimit = limit;
voices.reserve(limit);
} }
void sfz::RegionSet::addRegion(Region* region) noexcept void sfz::RegionSet::addRegion(Region* region) noexcept

View file

@ -18,12 +18,7 @@ namespace sfz
class RegionSet { class RegionSet {
public: public:
RegionSet() = delete; RegionSet() = delete;
RegionSet(RegionSet* parentSet, OpcodeScope level) RegionSet(RegionSet* parentSet, OpcodeScope level);
: parent(parentSet), level(level)
{
if (parentSet != nullptr)
parentSet->addSubset(this);
}
/** /**
* @brief Set the polyphony limit for the set * @brief Set the polyphony limit for the set
* *

View file

@ -1645,7 +1645,7 @@ void Voice::Impl::pitchEnvelope(absl::Span<float> pitchSpan) noexcept
if (!bends) if (!bends)
return; return;
const auto events = resources_.midiState.getPitchEvents(); const EventVector& events = resources_.midiState.getPitchEvents();
const auto bendLambda = [this](float bend) { const auto bendLambda = [this](float bend) {
return centsFactor(region_->getBendInCents(bend)); return centsFactor(region_->getBendInCents(bend));
}; };

View file

@ -159,15 +159,14 @@ Voice* VoiceManager::findFreeVoice() noexcept
void VoiceManager::requireNumVoices(int numVoices, Resources& resources) void VoiceManager::requireNumVoices(int numVoices, Resources& resources)
{ {
numActualVoices_ =
static_cast<int>(config::overflowVoiceMultiplier * numVoices);
numRequiredVoices_ = numVoices; numRequiredVoices_ = numVoices;
const int numEffectiveVoices = getNumEffectiveVoices();
clear(); clear();
list_.reserve(numActualVoices_); list_.reserve(numEffectiveVoices);
activeVoices_.reserve(numActualVoices_); activeVoices_.reserve(numEffectiveVoices);
for (int i = 0; i < numActualVoices_; ++i) { for (int i = 0; i < numEffectiveVoices; ++i) {
list_.emplace_back(i, resources); list_.emplace_back(i, resources);
Voice& lastVoice = list_.back(); Voice& lastVoice = list_.back();
lastVoice.setStateListener(this); lastVoice.setStateListener(this);

View file

@ -133,7 +133,7 @@ struct VoiceManager final : public Voice::StateListener
private: private:
int numRequiredVoices_ { config::numVoices }; int numRequiredVoices_ { config::numVoices };
int numActualVoices_ { static_cast<int>(config::numVoices * config::overflowVoiceMultiplier) }; int getNumEffectiveVoices() const noexcept { return config::calculateActualVoices(numRequiredVoices_); }
std::vector<Voice> list_; std::vector<Voice> list_;
std::vector<Voice*> activeVoices_; std::vector<Voice*> activeVoices_;
// These are the `group=` groups where you can off voices // These are the `group=` groups where you can off voices