Add CC message processing for OSC

This commit is contained in:
Jean Pierre Cimalando 2020-12-14 19:35:21 +01:00
parent a69497e7bf
commit c81f74100b
3 changed files with 75 additions and 5 deletions

View file

@ -244,7 +244,7 @@ void Synth::Impl::clear()
resources_.midiState.reset(); resources_.midiState.reset();
resources_.filePool.clear(); resources_.filePool.clear();
resources_.filePool.setRamLoading(config::loadInRam); resources_.filePool.setRamLoading(config::loadInRam);
ccLabels_.clear(); clearCCLabels();
keyLabels_.clear(); keyLabels_.clear();
keyswitchLabels_.clear(); keyswitchLabels_.clear();
globalOpcodes_.clear(); globalOpcodes_.clear();
@ -261,9 +261,9 @@ void Synth::Impl::clear()
setDefaultHdcc(11, 1.0f); setDefaultHdcc(11, 1.0f);
// set default controller labels // set default controller labels
insertPairUniquely(ccLabels_, 7, "Volume"); setCCLabel(7, "Volume");
insertPairUniquely(ccLabels_, 10, "Pan"); setCCLabel(10, "Pan");
insertPairUniquely(ccLabels_, 11, "Expression"); setCCLabel(11, "Expression");
} }
void Synth::Impl::handleMasterOpcodes(const std::vector<Opcode>& members) void Synth::Impl::handleMasterOpcodes(const std::vector<Opcode>& members)
@ -365,7 +365,7 @@ void Synth::Impl::handleControlOpcodes(const std::vector<Opcode>& members)
break; break;
case hash("label_cc&"): case hash("label_cc&"):
if (Default::ccNumberRange.containsWithEnd(member.parameters.back())) if (Default::ccNumberRange.containsWithEnd(member.parameters.back()))
insertPairUniquely(ccLabels_, member.parameters.back(), std::string(member.value)); setCCLabel(member.parameters.back(), std::string(member.value));
break; break;
case hash("label_key&"): case hash("label_key&"):
if (member.parameters.back() <= Default::keyRange.getEnd()) { if (member.parameters.back() <= Default::keyRange.getEnd()) {
@ -1794,6 +1794,30 @@ std::bitset<config::numCCs> Synth::Impl::collectAllUsedCCs()
return used; return used;
} }
const std::string* Synth::Impl::getCCLabel(int ccNumber)
{
auto it = ccLabelsMap_.find(ccNumber);
return (it == ccLabelsMap_.end()) ? nullptr : &ccLabels_[it->second].second;
}
void Synth::Impl::setCCLabel(int ccNumber, std::string name)
{
auto it = ccLabelsMap_.find(ccNumber);
if (it != ccLabelsMap_.end())
ccLabels_[it->second].second = std::move(name);
else {
size_t index = ccLabels_.size();
ccLabels_.emplace_back(ccNumber, std::move(name));
ccLabelsMap_[ccNumber] = index;
}
}
void Synth::Impl::clearCCLabels()
{
ccLabels_.clear();
ccLabelsMap_.clear();
}
Parser& Synth::getParser() noexcept Parser& Synth::getParser() noexcept
{ {
Impl& impl = *impl_; Impl& impl = *impl_;

View file

@ -36,6 +36,47 @@ void sfz::Synth::dispatchMessage(Client& client, int delay, const char* path, co
client.receive(delay, "/hello", "", nullptr); client.receive(delay, "/hello", "", nullptr);
} break; } break;
//----------------------------------------------------------------------
MATCH("/cc/slots", "") {
uint8_t data[(config::numCCs + 7) / 8] = {};
const std::bitset<config::numCCs>& ccs = impl.currentUsedCCs_;
for (unsigned i = 0; i < config::numCCs; ++i)
data[i / 8] |= ccs.test(i) << (i % 8);
sfizz_blob_t blob { data, sizeof(data) };
client.receive<'b'>(delay, path, &blob);
} break;
MATCH("/cc&/default", "") {
if (indices[0] >= config::numCCs)
break;
client.receive<'f'>(delay, path, impl.defaultCCValues_[indices[0]]);
} break;
MATCH("/cc&/value", "") {
if (indices[0] >= config::numCCs)
break;
// Note: result value is not frame-exact
client.receive<'f'>(delay, path, impl.resources_.midiState.getCCValue(indices[0]));
} break;
MATCH("/cc&/value", "f") {
if (indices[0] >= config::numCCs)
break;
impl.resources_.midiState.ccEvent(delay, indices[0], args[0].f);
} break;
MATCH("/cc&/label", "") {
if (indices[0] >= config::numCCs)
break;
const std::string* label = impl.getCCLabel(indices[0]);
client.receive<'s'>(delay, path, label ? label->c_str() : "");
} break;
//----------------------------------------------------------------------
MATCH("/region&/delay", "") { MATCH("/region&/delay", "") {
GET_REGION_OR_BREAK(indices[0]) GET_REGION_OR_BREAK(indices[0])
client.receive<'f'>(delay, path, region.delay); client.receive<'f'>(delay, path, region.delay);

View file

@ -179,6 +179,10 @@ struct Synth::Impl final: public Parser::Listener {
std::bitset<config::numCCs> collectAllUsedCCs(); std::bitset<config::numCCs> collectAllUsedCCs();
const std::string* getCCLabel(int ccNumber);
void setCCLabel(int ccNumber, std::string name);
void clearCCLabels();
/** /**
* @brief Perform a CC event * @brief Perform a CC event
* *
@ -208,6 +212,7 @@ struct Synth::Impl final: public Parser::Listener {
// Names for the CC and notes as set by label_cc and label_key // Names for the CC and notes as set by label_cc and label_key
std::vector<CCNamePair> ccLabels_; std::vector<CCNamePair> ccLabels_;
std::map<int, size_t> ccLabelsMap_;
std::vector<NoteNamePair> keyLabels_; std::vector<NoteNamePair> keyLabels_;
std::vector<NoteNamePair> keyswitchLabels_; std::vector<NoteNamePair> keyswitchLabels_;