Skip to content

Commit

Permalink
Merge pull request #634 from paulfd/note-polyphony-1
Browse files Browse the repository at this point in the history
Note polyphony tweaks
  • Loading branch information
paulfd authored Feb 12, 2021
2 parents da41ed5 + 360d441 commit b782b3b
Show file tree
Hide file tree
Showing 2 changed files with 66 additions and 8 deletions.
8 changes: 2 additions & 6 deletions src/sfizz/VoiceManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -189,13 +189,9 @@ void VoiceManager::checkNotePolyphony(const Region* region, int delay, const Tri

for (Voice* voice : activeVoices_) {
const TriggerEvent& voiceTriggerEvent = voice->getTriggerEvent();
const bool skipVoice =
(triggerEvent.type == TriggerEventType::NoteOn && voice->releasedOrFree())
|| voice->isFree();
if (!skipVoice
if (!voice->releasedOrFree()
&& voice->getRegion()->group == region->group
&& voiceTriggerEvent.number == triggerEvent.number
&& voiceTriggerEvent.type == triggerEvent.type) {
&& voiceTriggerEvent.number == triggerEvent.number) {
notePolyphonyCounter += 1;
switch (region->selfMask) {
case SelfMask::mask:
Expand Down
66 changes: 64 additions & 2 deletions tests/PolyphonyT.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -439,7 +439,7 @@ TEST_CASE("[Polyphony] Note polyphony operates on release voices and sustain ped
sfz::Synth synth;
sfz::AudioBuffer<float> buffer { 2, blockSize };
synth.loadSfzString(fs::current_path() / "tests/TestFiles/polyphony.sfz", R"(
<region> key=48 sample=*silence
<region> key=48 sample=*sine
<region> key=48 note_polyphony=1 sample=*saw trigger=release ampeg_attack=1 ampeg_decay=1
)");
synth.cc(0, 64, 127);
Expand All @@ -450,9 +450,17 @@ TEST_CASE("[Polyphony] Note polyphony operates on release voices and sustain ped
synth.noteOn(4, 48, 63 );
synth.noteOff(5, 48, 0 );
REQUIRE( synth.getNumActiveVoices() == 3);
REQUIRE( synth.getVoiceView(0)->getRegion()->sampleId->filename() == "*sine");
REQUIRE( synth.getVoiceView(1)->getRegion()->sampleId->filename() == "*sine");
REQUIRE( synth.getVoiceView(2)->getRegion()->sampleId->filename() == "*sine");
synth.renderBlock(buffer);
REQUIRE( numPlayingVoices(synth) == 3 );
synth.cc(20, 64, 0);
REQUIRE( synth.getNumActiveVoices() == 6 );
REQUIRE( synth.getVoiceView(3)->getRegion()->sampleId->filename() == "*saw");
REQUIRE( synth.getVoiceView(4)->getRegion()->sampleId->filename() == "*saw");
REQUIRE( synth.getVoiceView(5)->getRegion()->sampleId->filename() == "*saw");
synth.renderBlock(buffer);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( synth.getVoiceView(0)->getTriggerEvent().value == 61_norm);
REQUIRE( synth.getVoiceView(0)->releasedOrFree());
Expand All @@ -473,7 +481,7 @@ TEST_CASE("[Polyphony] Note polyphony operates on release voices and sustain ped
sfz::Synth synth;
sfz::AudioBuffer<float> buffer { 2, blockSize };
synth.loadSfzString(fs::current_path() / "tests/TestFiles/polyphony.sfz", R"(
<region> key=48 sample=*silence
<region> key=48 sample=*sine
<region> key=48 note_polyphony=1 sample=*saw trigger=release ampeg_attack=1 ampeg_decay=1
)");
synth.cc(0, 64, 127);
Expand All @@ -484,9 +492,17 @@ TEST_CASE("[Polyphony] Note polyphony operates on release voices and sustain ped
synth.noteOn(4, 48, 61 );
synth.noteOff(5, 48, 0 );
REQUIRE( synth.getNumActiveVoices() == 3);
REQUIRE( synth.getVoiceView(0)->getRegion()->sampleId->filename() == "*sine");
REQUIRE( synth.getVoiceView(1)->getRegion()->sampleId->filename() == "*sine");
REQUIRE( synth.getVoiceView(2)->getRegion()->sampleId->filename() == "*sine");
synth.renderBlock(buffer);
REQUIRE( numPlayingVoices(synth) == 3 );
synth.cc(20, 64, 0);
REQUIRE( synth.getNumActiveVoices() == 6 );
REQUIRE( synth.getVoiceView(3)->getRegion()->sampleId->filename() == "*saw");
REQUIRE( synth.getVoiceView(4)->getRegion()->sampleId->filename() == "*saw");
REQUIRE( synth.getVoiceView(5)->getRegion()->sampleId->filename() == "*saw");
synth.renderBlock(buffer);
REQUIRE( numPlayingVoices(synth) == 3 );
REQUIRE( synth.getVoiceView(0)->getTriggerEvent().value == 63_norm);
REQUIRE( synth.getVoiceView(0)->releasedOrFree());
Expand All @@ -501,3 +517,49 @@ TEST_CASE("[Polyphony] Note polyphony operates on release voices and sustain ped
REQUIRE( synth.getVoiceView(5)->getTriggerEvent().value == 61_norm);
REQUIRE(!synth.getVoiceView(5)->releasedOrFree());
}

TEST_CASE("[Polyphony] Bi-directional choking (with polyphony)")
{
sfz::Synth synth;
sfz::AudioBuffer<float> buffer { 2, blockSize };
synth.loadSfzString(fs::current_path() / "tests/TestFiles/polyphony.sfz", R"(
<group> key=60 polyphony=1
<region> sample=kick.wav loop_mode=one_shot
<region> sample=snare.wav trigger=release
)");
synth.noteOn(0, 60, 63 );
REQUIRE( synth.getNumActiveVoices() == 1);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( getPlayingVoices(synth).front()->getRegion()->sampleId->filename() == "kick.wav" );
synth.noteOff(10, 60, 63 );
REQUIRE( synth.getNumActiveVoices() == 2);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( getPlayingVoices(synth).front()->getRegion()->sampleId->filename() == "snare.wav" );
synth.noteOn(20, 60, 63 );
REQUIRE( synth.getNumActiveVoices() == 3);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( getPlayingVoices(synth).front()->getRegion()->sampleId->filename() == "kick.wav" );
}

TEST_CASE("[Polyphony] Bi-directional choking (with note_polyphony)")
{
sfz::Synth synth;
sfz::AudioBuffer<float> buffer { 2, blockSize };
synth.loadSfzString(fs::current_path() / "tests/TestFiles/polyphony.sfz", R"(
<group> key=60 note_polyphony=1
<region> sample=kick.wav loop_mode=one_shot
<region> sample=snare.wav trigger=release
)");
synth.noteOn(0, 60, 63 );
REQUIRE( synth.getNumActiveVoices() == 1);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( getPlayingVoices(synth).front()->getRegion()->sampleId->filename() == "kick.wav" );
synth.noteOff(10, 60, 63 );
REQUIRE( synth.getNumActiveVoices() == 2);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( getPlayingVoices(synth).front()->getRegion()->sampleId->filename() == "snare.wav" );
synth.noteOn(20, 60, 63 );
REQUIRE( synth.getNumActiveVoices() == 3);
REQUIRE( numPlayingVoices(synth) == 1 );
REQUIRE( getPlayingVoices(synth).front()->getRegion()->sampleId->filename() == "kick.wav" );
}

0 comments on commit b782b3b

Please sign in to comment.