From f32c0c98dc6a54d8affcfd7eff48c6f5310f8584 Mon Sep 17 00:00:00 2001 From: probonopd Date: Sat, 3 Dec 2022 01:00:45 -0500 Subject: [PATCH] Allow MIDI notes to be used as navigation buttons for MiniDexed (#368) * First implementation of NoteOn/NoteOff MIDI UI buttons * First implementation of NoteOn/NoteOff MIDI UI buttons Co-authored-by: diyelectromusic <68612569+diyelectromusic@users.noreply.github.com> --- src/config.cpp | 6 ++++++ src/config.h | 2 ++ src/mididevice.cpp | 6 ++++-- src/minidexed.ini | 3 +++ src/uibuttons.cpp | 44 ++++++++++++++++++++++++++++++++++--------- src/uibuttons.h | 5 +++-- src/userinterface.cpp | 9 +++++---- src/userinterface.h | 4 ++-- 8 files changed, 60 insertions(+), 19 deletions(-) diff --git a/src/config.cpp b/src/config.cpp index df3ebd7..1143476 100644 --- a/src/config.cpp +++ b/src/config.cpp @@ -105,6 +105,7 @@ void CConfig::Load (void) m_nLongPressTimeout = m_Properties.GetNumber ("LongPressTimeout", 600); m_nMIDIButtonCh = m_Properties.GetNumber ("MIDIButtonCh", 0); + m_nMIDIButtonNotes = m_Properties.GetNumber ("MIDIButtonNotes", 0); m_nMIDIButtonPrev = m_Properties.GetNumber ("MIDIButtonPrev", 0); m_nMIDIButtonNext = m_Properties.GetNumber ("MIDIButtonNext", 0); m_nMIDIButtonBack = m_Properties.GetNumber ("MIDIButtonBack", 0); @@ -310,6 +311,11 @@ unsigned CConfig::GetMIDIButtonCh (void) const return m_nMIDIButtonCh; } +unsigned CConfig::GetMIDIButtonNotes (void) const +{ + return m_nMIDIButtonNotes; +} + unsigned CConfig::GetMIDIButtonPrev (void) const { return m_nMIDIButtonPrev; diff --git a/src/config.h b/src/config.h index 649bdf4..be75100 100644 --- a/src/config.h +++ b/src/config.h @@ -119,6 +119,7 @@ public: // MIDI Button Navigation unsigned GetMIDIButtonCh (void) const; + unsigned GetMIDIButtonNotes (void) const; unsigned GetMIDIButtonPrev (void) const; unsigned GetMIDIButtonNext (void) const; unsigned GetMIDIButtonBack (void) const; @@ -187,6 +188,7 @@ private: unsigned m_nLongPressTimeout; unsigned m_nMIDIButtonCh; + unsigned m_nMIDIButtonNotes; unsigned m_nMIDIButtonPrev; unsigned m_nMIDIButtonNext; unsigned m_nMIDIButtonBack; diff --git a/src/mididevice.cpp b/src/mididevice.cpp index 012dc72..898c187 100644 --- a/src/mididevice.cpp +++ b/src/mididevice.cpp @@ -187,11 +187,13 @@ void CMIDIDevice::MIDIMessageHandler (const u8 *pMessage, size_t nLength, unsign switch (ucType) { case MIDI_CONTROL_CHANGE: + case MIDI_NOTE_OFF: + case MIDI_NOTE_ON: if (nLength < 3) { - break; + break; } - m_pUI->UIMIDICCHandler (ucChannel, pMessage[1], pMessage[2]); + m_pUI->UIMIDICmdHandler (ucChannel, ucStatus & 0xF0, pMessage[1], pMessage[2]); break; } diff --git a/src/minidexed.ini b/src/minidexed.ini index 7917fe7..9025423 100644 --- a/src/minidexed.ini +++ b/src/minidexed.ini @@ -62,7 +62,10 @@ LongPressTimeout=400 # Specify MIDI CC to act as a button # NB: Off < 64 < ON # CC channel: 0=OFF; 1-16 MIDI Ch; >16 Omni +# If MIDIButtonNotes>0 then treat MIDIButton +# numbers as MIDI Note numbers note CC numbers. MIDIButtonCh=0 +MIDIButtonNotes=1 MIDIButtonPrev=00 MIDIButtonNext=02 MIDIButtonBack=03 diff --git a/src/uibuttons.cpp b/src/uibuttons.cpp index 8f2599a..e3e64f8 100644 --- a/src/uibuttons.cpp +++ b/src/uibuttons.cpp @@ -264,7 +264,7 @@ CUIButtons::CUIButtons ( unsigned selectPin, const char *selectAction, unsigned homePin, const char *homeAction, unsigned doubleClickTimeout, unsigned longPressTimeout, - unsigned prevMidi, unsigned nextMidi, unsigned backMidi, unsigned selectMidi, unsigned homeMidi + unsigned notesMidi, unsigned prevMidi, unsigned nextMidi, unsigned backMidi, unsigned selectMidi, unsigned homeMidi ) : m_doubleClickTimeout(doubleClickTimeout), m_longPressTimeout(longPressTimeout), @@ -278,6 +278,7 @@ CUIButtons::CUIButtons ( m_selectAction(CUIButton::triggerTypeFromString(selectAction)), m_homePin(homePin), m_homeAction(CUIButton::triggerTypeFromString(homeAction)), + m_notesMidi(notesMidi), m_prevMidi(ccToMidiPin(prevMidi)), m_nextMidi(ccToMidiPin(nextMidi)), m_backMidi(ccToMidiPin(backMidi)), @@ -444,7 +445,7 @@ void CUIButtons::Update (void) for (unsigned i=0; i 0) { +// LOGDBG("BtnMIDICmdHandler (notes): %x %x %x)", nMidiCmd, nMidiData1, nMidiData2); + // Using MIDI Note messages for MIDI buttons + unsigned midiPin = ccToMidiPin(nMidiData1); + for (unsigned i=0; iGetButtonActionHome (), m_pConfig->GetDoubleClickTimeout (), m_pConfig->GetLongPressTimeout (), + m_pConfig->GetMIDIButtonNotes (), m_pConfig->GetMIDIButtonPrev (), m_pConfig->GetMIDIButtonNext (), m_pConfig->GetMIDIButtonBack (), @@ -129,7 +130,7 @@ bool CUserInterface::Initialize (void) } m_pUIButtons->RegisterEventHandler (UIButtonsEventStub, this); - UISetMIDICCChannel (m_pConfig->GetMIDIButtonCh ()); + UISetMIDIButtonChannel (m_pConfig->GetMIDIButtonCh ()); LOGDBG ("Button User Interface initialized"); @@ -330,7 +331,7 @@ void CUserInterface::UIButtonsEventStub (CUIButton::BtnEvent Event, void *pParam pThis->UIButtonsEventHandler (Event); } -void CUserInterface::UIMIDICCHandler (unsigned nMidiCh, unsigned nMidiCC, unsigned nMidiData) +void CUserInterface::UIMIDICmdHandler (unsigned nMidiCh, unsigned nMidiCmd, unsigned nMidiData1, unsigned nMidiData2) { if (m_nMIDIButtonCh == CMIDIDevice::Disabled) { @@ -345,11 +346,11 @@ void CUserInterface::UIMIDICCHandler (unsigned nMidiCh, unsigned nMidiCC, unsign if (m_pUIButtons) { - m_pUIButtons->BtnMIDICCHandler (nMidiCC, nMidiData); + m_pUIButtons->BtnMIDICmdHandler (nMidiCmd, nMidiData1, nMidiData2); } } -void CUserInterface::UISetMIDICCChannel (unsigned uCh) +void CUserInterface::UISetMIDIButtonChannel (unsigned uCh) { // Mirrors the logic in Performance Config for handling MIDI channel configuration if (uCh == 0) diff --git a/src/userinterface.h b/src/userinterface.h index 3a2d27d..5de2846 100644 --- a/src/userinterface.h +++ b/src/userinterface.h @@ -53,7 +53,7 @@ public: bool bArrowDown, bool bArrowUp); // To be called from the MIDI device on reception of a MIDI CC message - void UIMIDICCHandler (unsigned nMidiCh, unsigned nMidiCC, unsigned nMidiData); + void UIMIDICmdHandler (unsigned nMidiCh, unsigned nMidiCmd, unsigned nMidiData1, unsigned nMidiData2); private: void LCDWrite (const char *pString); // Print to optional HD44780 display @@ -62,7 +62,7 @@ private: static void EncoderEventStub (CKY040::TEvent Event, void *pParam); void UIButtonsEventHandler (CUIButton::BtnEvent Event); static void UIButtonsEventStub (CUIButton::BtnEvent Event, void *pParam); - void UISetMIDICCChannel (unsigned uCh); + void UISetMIDIButtonChannel (unsigned uCh); private: CMiniDexed *m_pMiniDexed;