summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/ingen/URIs.hpp1
-rw-r--r--src/URIs.cpp1
-rw-r--r--src/server/ControlBindings.cpp44
3 files changed, 39 insertions, 7 deletions
diff --git a/include/ingen/URIs.hpp b/include/ingen/URIs.hpp
index f1244ba5..c555cbf9 100644
--- a/include/ingen/URIs.hpp
+++ b/include/ingen/URIs.hpp
@@ -162,6 +162,7 @@ public:
const Quark midi_binding;
const Quark midi_controllerNumber;
const Quark midi_noteNumber;
+ const Quark midi_channel;
const Quark morph_AutoMorphPort;
const Quark morph_MorphPort;
const Quark morph_currentType;
diff --git a/src/URIs.cpp b/src/URIs.cpp
index a2ad6819..41706868 100644
--- a/src/URIs.cpp
+++ b/src/URIs.cpp
@@ -155,6 +155,7 @@ URIs::URIs(Forge& ingen_forge, URIMap* map, LilvWorld* lworld)
, midi_binding (forge, map, lworld, LV2_MIDI__binding)
, midi_controllerNumber (forge, map, lworld, LV2_MIDI__controllerNumber)
, midi_noteNumber (forge, map, lworld, LV2_MIDI__noteNumber)
+ , midi_channel (forge, map, lworld, LV2_MIDI__channel)
, morph_AutoMorphPort (forge, map, lworld, LV2_MORPH__AutoMorphPort)
, morph_MorphPort (forge, map, lworld, LV2_MORPH__MorphPort)
, morph_currentType (forge, map, lworld, LV2_MORPH__currentType)
diff --git a/src/server/ControlBindings.cpp b/src/server/ControlBindings.cpp
index aefc8608..e4f7e104 100644
--- a/src/server/ControlBindings.cpp
+++ b/src/server/ControlBindings.cpp
@@ -83,9 +83,31 @@ ControlBindings::binding_key(const Atom& binding) const
if (binding.type() == uris.atom_Object) {
const auto* obj = static_cast<const LV2_Atom_Object_Body*>(binding.get_body());
if (obj->otype == uris.midi_Bender) {
- key = Key(Type::MIDI_BENDER);
+ lv2_atom_object_body_get(binding.size(),
+ obj,
+ uris.midi_channel.urid(),
+ &num,
+ nullptr);
+ if (!num) {
+ _engine.log().rt_error("Bender binding missing channel\n");
+ } else if (num->type != uris.atom_Int) {
+ _engine.log().rt_error("Bender channel not an integer\n");
+ } else {
+ key = Key(Type::MIDI_BENDER, reinterpret_cast<LV2_Atom_Int*>(num)->body);
+ }
} else if (obj->otype == uris.midi_ChannelPressure) {
- key = Key(Type::MIDI_CHANNEL_PRESSURE);
+ lv2_atom_object_body_get(binding.size(),
+ obj,
+ uris.midi_channel.urid(),
+ &num,
+ nullptr);
+ if (!num) {
+ _engine.log().rt_error("Pressure binding missing channel\n");
+ } else if (num->type != uris.atom_Int) {
+ _engine.log().rt_error("Pressure channel not an integer\n");
+ } else {
+ key = Key(Type::MIDI_CHANNEL_PRESSURE, reinterpret_cast<LV2_Atom_Int*>(num)->body);
+ }
} else if (obj->otype == uris.midi_Controller) {
lv2_atom_object_body_get(binding.size(),
obj,
@@ -125,19 +147,23 @@ ControlBindings::midi_event_key(uint16_t, const uint8_t* buf, uint16_t& value)
switch (lv2_midi_message_type(buf)) {
case LV2_MIDI_MSG_CONTROLLER:
value = buf[2];
- return {Type::MIDI_CC, static_cast<int8_t>(buf[1])};
+ return {Type::MIDI_CC,
+ static_cast<int16_t>(((buf[0] & 0x0FU) << 8U) | buf[1])};
case LV2_MIDI_MSG_BENDER:
value = (buf[2] << 7U) + buf[1];
- return {Type::MIDI_BENDER};
+ return {Type::MIDI_BENDER, static_cast<int16_t>((buf[0] & 0x0FU))};
case LV2_MIDI_MSG_CHANNEL_PRESSURE:
value = buf[1];
- return {Type::MIDI_CHANNEL_PRESSURE};
+ return {Type::MIDI_CHANNEL_PRESSURE,
+ static_cast<int16_t>((buf[0] & 0x0FU))};
case LV2_MIDI_MSG_NOTE_ON:
value = 1;
- return {Type::MIDI_NOTE, buf[1]};
+ return {Type::MIDI_NOTE,
+ static_cast<int16_t>(((buf[0] & 0x0FU) << 8U) | buf[1])};
case LV2_MIDI_MSG_NOTE_OFF:
value = 0;
- return {Type::MIDI_NOTE, buf[1]};
+ return {Type::MIDI_NOTE,
+ static_cast<int16_t>(((buf[0] & 0x0FU) << 8U) | buf[1])};
default:
return {};
}
@@ -325,9 +351,13 @@ forge_binding(const URIs& uris,
break;
case ControlBindings::Type::MIDI_BENDER:
lv2_atom_forge_object(forge, &frame, 0, uris.midi_Bender);
+ lv2_atom_forge_key(forge, uris.midi_channel);
+ lv2_atom_forge_int(forge, value);
break;
case ControlBindings::Type::MIDI_CHANNEL_PRESSURE:
lv2_atom_forge_object(forge, &frame, 0, uris.midi_ChannelPressure);
+ lv2_atom_forge_key(forge, uris.midi_channel);
+ lv2_atom_forge_int(forge, value);
break;
case ControlBindings::Type::MIDI_NOTE:
lv2_atom_forge_object(forge, &frame, 0, uris.midi_NoteOn);