Implement MIDI sending to VST from UI
This commit is contained in:
parent
82f579bf0a
commit
1e6cdd841b
4 changed files with 66 additions and 5 deletions
|
|
@ -176,10 +176,20 @@ void SfizzVstEditor::uiEndSend(EditId id)
|
||||||
getController()->endEdit(pid);
|
getController()->endEdit(pid);
|
||||||
}
|
}
|
||||||
|
|
||||||
void SfizzVstEditor::uiSendMIDI(const uint8_t* msg, uint32_t len)
|
void SfizzVstEditor::uiSendMIDI(const uint8_t* data, uint32_t len)
|
||||||
{
|
{
|
||||||
// TODO send MIDI...
|
SfizzVstController* ctl = getController();
|
||||||
|
|
||||||
|
Steinberg::OPtr<Vst::IMessage> msg { ctl->allocateMessage() };
|
||||||
|
if (!msg) {
|
||||||
|
fprintf(stderr, "[Sfizz] UI could not allocate message\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
msg->setMessageID("MidiMessage");
|
||||||
|
Vst::IAttributeList* attr = msg->getAttributes();
|
||||||
|
attr->setBinary("Data", data, len);
|
||||||
|
ctl->sendMessage(msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
///
|
///
|
||||||
|
|
|
||||||
|
|
@ -40,7 +40,7 @@ protected:
|
||||||
void uiSendValue(EditId id, const EditValue& v) override;
|
void uiSendValue(EditId id, const EditValue& v) override;
|
||||||
void uiBeginSend(EditId id) override;
|
void uiBeginSend(EditId id) override;
|
||||||
void uiEndSend(EditId id) override;
|
void uiEndSend(EditId id) override;
|
||||||
void uiSendMIDI(const uint8_t* msg, uint32_t len) override;
|
void uiSendMIDI(const uint8_t* data, uint32_t len) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void loadSfzFile(const std::string& filePath);
|
void loadSfzFile(const std::string& filePath);
|
||||||
|
|
|
||||||
|
|
@ -22,8 +22,10 @@ static const char defaultSfzText[] =
|
||||||
"<region>sample=*sine" "\n"
|
"<region>sample=*sine" "\n"
|
||||||
"ampeg_attack=0.02 ampeg_release=0.1" "\n";
|
"ampeg_attack=0.02 ampeg_release=0.1" "\n";
|
||||||
|
|
||||||
|
enum { kMidiEventMaximumSize = 4 };
|
||||||
|
|
||||||
SfizzVstProcessor::SfizzVstProcessor()
|
SfizzVstProcessor::SfizzVstProcessor()
|
||||||
: _fifoToWorker(64 * 1024)
|
: _fifoToWorker(64 * 1024), _fifoMidiFromUi(64 * 1024)
|
||||||
{
|
{
|
||||||
setControllerClass(SfizzVstController::cid);
|
setControllerClass(SfizzVstController::cid);
|
||||||
}
|
}
|
||||||
|
|
@ -181,6 +183,8 @@ tresult PLUGIN_API SfizzVstProcessor::process(Vst::ProcessData& data)
|
||||||
else
|
else
|
||||||
synth.disableFreeWheeling();
|
synth.disableFreeWheeling();
|
||||||
|
|
||||||
|
processMidiFromUi();
|
||||||
|
|
||||||
if (Vst::IParameterChanges* pc = data.inputParameterChanges)
|
if (Vst::IParameterChanges* pc = data.inputParameterChanges)
|
||||||
processControllerChanges(*pc);
|
processControllerChanges(*pc);
|
||||||
|
|
||||||
|
|
@ -373,6 +377,40 @@ void SfizzVstProcessor::processEvents(Vst::IEventList& events)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SfizzVstProcessor::processMidiFromUi()
|
||||||
|
{
|
||||||
|
sfz::Sfizz& synth = *_synth;
|
||||||
|
|
||||||
|
for (uint32 size = 0; _fifoMidiFromUi.peek(size) &&
|
||||||
|
_fifoMidiFromUi.size_used() >= sizeof(size) + size; ) {
|
||||||
|
_fifoMidiFromUi.discard(sizeof(size));
|
||||||
|
|
||||||
|
if (size > kMidiEventMaximumSize) {
|
||||||
|
_fifoMidiFromUi.discard(size);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t data[kMidiEventMaximumSize] = {};
|
||||||
|
_fifoMidiFromUi.get(data, size);
|
||||||
|
|
||||||
|
// interpret the MIDI message
|
||||||
|
switch (data[0] & 0xf0) {
|
||||||
|
case 0x80:
|
||||||
|
synth.noteOff(0, data[1] & 0x7f, data[2] & 0x7f);
|
||||||
|
break;
|
||||||
|
case 0x90:
|
||||||
|
synth.noteOn(0, data[1] & 0x7f, data[2] & 0x7f);
|
||||||
|
break;
|
||||||
|
case 0xb0:
|
||||||
|
synth.cc(0, data[1] & 0x7f, data[2] & 0x7f);
|
||||||
|
break;
|
||||||
|
case 0xe0:
|
||||||
|
synth.pitchWheel(0, (data[2] << 7) + data[1] - 8192);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int SfizzVstProcessor::convertVelocityFromFloat(float x)
|
int SfizzVstProcessor::convertVelocityFromFloat(float x)
|
||||||
{
|
{
|
||||||
return std::min(127, std::max(0, (int)(x * 127.0f)));
|
return std::min(127, std::max(0, (int)(x * 127.0f)));
|
||||||
|
|
@ -425,6 +463,17 @@ tresult PLUGIN_API SfizzVstProcessor::notify(Vst::IMessage* message)
|
||||||
reply->getAttributes()->setBinary("File", _state.scalaFile.data(), _state.scalaFile.size());
|
reply->getAttributes()->setBinary("File", _state.scalaFile.data(), _state.scalaFile.size());
|
||||||
sendMessage(reply);
|
sendMessage(reply);
|
||||||
}
|
}
|
||||||
|
else if (!std::strcmp(id, "MidiMessage")) {
|
||||||
|
const void* data = nullptr;
|
||||||
|
uint32 size = 0;
|
||||||
|
result = attr->getBinary("Data", data, size);
|
||||||
|
if (size < kMidiEventMaximumSize) {
|
||||||
|
if (_fifoMidiFromUi.size_free() >= sizeof(size) + size) {
|
||||||
|
_fifoMidiFromUi.put(size);
|
||||||
|
_fifoMidiFromUi.put(reinterpret_cast<const uint8_t*>(data), size);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -35,6 +35,7 @@ public:
|
||||||
void processParameterChanges(Vst::IParameterChanges& pc);
|
void processParameterChanges(Vst::IParameterChanges& pc);
|
||||||
void processControllerChanges(Vst::IParameterChanges& pc);
|
void processControllerChanges(Vst::IParameterChanges& pc);
|
||||||
void processEvents(Vst::IEventList& events);
|
void processEvents(Vst::IEventList& events);
|
||||||
|
void processMidiFromUi();
|
||||||
static int convertVelocityFromFloat(float x);
|
static int convertVelocityFromFloat(float x);
|
||||||
|
|
||||||
tresult PLUGIN_API notify(Vst::IMessage* message) override;
|
tresult PLUGIN_API notify(Vst::IMessage* message) override;
|
||||||
|
|
@ -58,6 +59,7 @@ private:
|
||||||
volatile bool _workRunning = false;
|
volatile bool _workRunning = false;
|
||||||
Ring_Buffer _fifoToWorker;
|
Ring_Buffer _fifoToWorker;
|
||||||
RTSemaphore _semaToWorker;
|
RTSemaphore _semaToWorker;
|
||||||
|
Ring_Buffer _fifoMidiFromUi;
|
||||||
std::mutex _processMutex;
|
std::mutex _processMutex;
|
||||||
|
|
||||||
// file modification periodic checker
|
// file modification periodic checker
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue