Control Surface
main
MIDI Control Surface library for Arduino
Toggle main menu visibility
Loading...
Searching...
No Matches
src
MIDI_Parsers
USBMIDI_Parser.hpp
Go to the documentation of this file.
1
#include "
MIDI_Parser.hpp
"
2
#include "
SysExBuffer.hpp
"
3
#include <
AH/Containers/Array.hpp
>
4
5
#ifdef MIDI_NUM_CABLES
6
#define USB_MIDI_NUMBER_OF_CABLES MIDI_NUM_CABLES
7
#elif defined(USB_MIDI4_SERIAL) || defined(USB_MIDI4)
8
#define USB_MIDI_NUMBER_OF_CABLES 4
9
#elif defined(USB_MIDI16_AUDIO_SERIAL) || defined(USB_MIDI16_SERIAL) || \
10
defined(USB_MIDI16)
11
// TODO: || defined(USB_EVERYTHING)
12
#define USB_MIDI_NUMBER_OF_CABLES 16
13
#elif defined(ARDUINO_ARCH_RP2040)
14
#define USB_MIDI_NUMBER_OF_CABLES 16
15
#elif !defined(ARDUINO) || defined(DOXYGEN)
16
#define USB_MIDI_NUMBER_OF_CABLES 16
17
#else
18
#define USB_MIDI_NUMBER_OF_CABLES 1
19
#endif
20
21
BEGIN_CS_NAMESPACE
22
28
class
USBMIDI_Parser
:
public
MIDI_Parser
{
29
public
:
30
using
MIDIUSBPacket_t
=
AH::Array<uint8_t, 4>
;
31
40
template
<
class
BytePuller>
41
MIDIReadEvent
pull
(BytePuller &&puller);
42
43
protected
:
45
MIDIReadEvent
feed
(
MIDIUSBPacket_t
packet);
47
MIDIReadEvent
resume
();
48
49
public
:
50
#if !IGNORE_SYSEX
52
SysExMessage
getSysExMessage
()
const
{
53
return
{
54
sysexbuffers
[
activeCable
.getRaw()].getBuffer(),
55
sysexbuffers
[
activeCable
.getRaw()].getLength(),
56
activeCable
,
57
};
58
}
59
#endif
60
61
protected
:
62
MIDIReadEvent
handleChannelMessage
(
MIDIUSBPacket_t
packet,
Cable
cable);
63
MIDIReadEvent
handleSingleByte
(
MIDIUSBPacket_t
packet,
Cable
cable);
64
MIDIReadEvent
handleSysExStartCont
(
MIDIUSBPacket_t
packet,
Cable
cable);
65
template
<u
int
8_t NumBytes>
66
MIDIReadEvent
handleSysExEnd
(
MIDIUSBPacket_t
packet,
Cable
cable);
67
MIDIReadEvent
handleSysCommon
(
MIDIUSBPacket_t
packet,
Cable
cable);
68
69
protected
:
70
#if !IGNORE_SYSEX
71
void
startSysEx
(
Cable
cable) {
sysexbuffers
[cable.
getRaw
()].start(); }
72
void
endSysEx
(
Cable
cable) {
73
sysexbuffers
[cable.
getRaw
()].end();
74
activeCable
= cable;
75
}
76
void
endSysExChunk
(
Cable
cable) {
activeCable
= cable; }
77
bool
hasSysExSpace
(
Cable
cable, uint8_t amount)
const
{
78
return
sysexbuffers
[cable.
getRaw
()].hasSpaceLeft(amount);
79
}
80
void
addSysExByte
(
Cable
cable, uint8_t data) {
81
sysexbuffers
[cable.
getRaw
()].add(data);
82
}
83
void
addSysExBytes
(
Cable
cable,
const
uint8_t *data, uint8_t len) {
84
sysexbuffers
[cable.
getRaw
()].add(data, len);
85
}
86
bool
receivingSysEx
(
Cable
cable)
const
{
87
return
sysexbuffers
[cable.
getRaw
()].isReceiving();
88
}
89
90
void
storePacket
(
MIDIUSBPacket_t
packet) {
storedPacket
= packet; }
91
bool
hasStoredPacket
()
const
{
return
storedPacket
[0] != 0x00; }
92
MIDIUSBPacket_t
popStoredPacket
() {
93
MIDIUSBPacket_t
t =
storedPacket
;
94
storedPacket
[0] = 0x00;
95
return
t;
96
}
97
98
Cable
activeCable
=
Cable_1
;
99
100
private
:
101
SysExBuffer
sysexbuffers
[
USB_MIDI_NUMBER_OF_CABLES
] = {};
102
MIDIUSBPacket_t
storedPacket
= {{ 0x00 }};
103
#endif
104
};
105
106
template
<
class
BytePuller>
107
inline
MIDIReadEvent
USBMIDI_Parser::pull
(BytePuller &&puller) {
108
// First try resuming the parser, we might have a stored packet that has to
109
// be parsed first.
110
MIDIReadEvent
evt =
resume
();
111
if
(evt !=
MIDIReadEvent::NO_MESSAGE
)
112
return
evt;
113
114
// If resumption didn't produce a message, read new packets from the input
115
// and parse them until either we get a message, or until the input runs out
116
// of new packets.
117
MIDIUSBPacket_t
midiPacket;
118
while
(puller.pull(midiPacket)) {
119
evt =
feed
(midiPacket);
120
if
(evt !=
MIDIReadEvent::NO_MESSAGE
)
121
return
evt;
122
}
123
return
MIDIReadEvent::NO_MESSAGE
;
124
}
125
126
END_CS_NAMESPACE
Array.hpp
Cable_1
constexpr Cable Cable_1
Definition
Cable.hpp:118
MIDIReadEvent
MIDIReadEvent
Values returned by the MIDI reading functions.
Definition
MIDIReadEvent.hpp:11
MIDIReadEvent::NO_MESSAGE
@ NO_MESSAGE
No new messages were received.
Definition
MIDIReadEvent.hpp:12
MIDI_Parser.hpp
END_CS_NAMESPACE
#define END_CS_NAMESPACE
Definition
Settings/NamespaceSettings.hpp:14
BEGIN_CS_NAMESPACE
#define BEGIN_CS_NAMESPACE
Definition
Settings/NamespaceSettings.hpp:11
SysExBuffer.hpp
USB_MIDI_NUMBER_OF_CABLES
#define USB_MIDI_NUMBER_OF_CABLES
Definition
USBMIDI_Parser.hpp:16
Cable
A type-safe class for MIDI USB Cable numbers.
Definition
Cable.hpp:13
Cable::getRaw
constexpr uint8_t getRaw() const
Get the cable as an integer.
Definition
Cable.hpp:29
MIDI_Parser
Base class for MIDI parsers.
Definition
MIDI_Parser.hpp:16
SysExBuffer
Helper for storing the System Exclusive messages being received by a MIDI parser.
Definition
SysExBuffer.hpp:13
USBMIDI_Parser
Parser for MIDI over USB packets.
Definition
USBMIDI_Parser.hpp:28
USBMIDI_Parser::hasSysExSpace
bool hasSysExSpace(Cable cable, uint8_t amount) const
Definition
USBMIDI_Parser.hpp:77
USBMIDI_Parser::handleSingleByte
MIDIReadEvent handleSingleByte(MIDIUSBPacket_t packet, Cable cable)
Definition
USBMIDI_Parser.cpp:131
USBMIDI_Parser::resume
MIDIReadEvent resume()
Resume the parser with the previously stored and unhandled packet.
Definition
USBMIDI_Parser.cpp:175
USBMIDI_Parser::sysexbuffers
SysExBuffer sysexbuffers[16]
Definition
USBMIDI_Parser.hpp:101
USBMIDI_Parser::handleSysExStartCont
MIDIReadEvent handleSysExStartCont(MIDIUSBPacket_t packet, Cable cable)
Definition
USBMIDI_Parser.cpp:15
USBMIDI_Parser::endSysExChunk
void endSysExChunk(Cable cable)
Definition
USBMIDI_Parser.hpp:76
USBMIDI_Parser::storePacket
void storePacket(MIDIUSBPacket_t packet)
Definition
USBMIDI_Parser.hpp:90
USBMIDI_Parser::handleSysExEnd
MIDIReadEvent handleSysExEnd(MIDIUSBPacket_t packet, Cable cable)
Definition
USBMIDI_Parser.cpp:46
USBMIDI_Parser::handleChannelMessage
MIDIReadEvent handleChannelMessage(MIDIUSBPacket_t packet, Cable cable)
Definition
USBMIDI_Parser.cpp:6
USBMIDI_Parser::startSysEx
void startSysEx(Cable cable)
Definition
USBMIDI_Parser.hpp:71
USBMIDI_Parser::receivingSysEx
bool receivingSysEx(Cable cable) const
Definition
USBMIDI_Parser.hpp:86
USBMIDI_Parser::hasStoredPacket
bool hasStoredPacket() const
Definition
USBMIDI_Parser.hpp:91
USBMIDI_Parser::storedPacket
MIDIUSBPacket_t storedPacket
Definition
USBMIDI_Parser.hpp:102
USBMIDI_Parser::popStoredPacket
MIDIUSBPacket_t popStoredPacket()
Definition
USBMIDI_Parser.hpp:92
USBMIDI_Parser::feed
MIDIReadEvent feed(MIDIUSBPacket_t packet)
Feed a new packet to the parser.
Definition
USBMIDI_Parser.cpp:139
USBMIDI_Parser::pull
MIDIReadEvent pull(BytePuller &&puller)
Parse one incoming MIDI message.
Definition
USBMIDI_Parser.hpp:107
USBMIDI_Parser::addSysExByte
void addSysExByte(Cable cable, uint8_t data)
Definition
USBMIDI_Parser.hpp:80
USBMIDI_Parser::activeCable
Cable activeCable
Definition
USBMIDI_Parser.hpp:98
USBMIDI_Parser::endSysEx
void endSysEx(Cable cable)
Definition
USBMIDI_Parser.hpp:72
USBMIDI_Parser::addSysExBytes
void addSysExBytes(Cable cable, const uint8_t *data, uint8_t len)
Definition
USBMIDI_Parser.hpp:83
USBMIDI_Parser::handleSysCommon
MIDIReadEvent handleSysCommon(MIDIUSBPacket_t packet, Cable cable)
Definition
USBMIDI_Parser.cpp:121
USBMIDI_Parser::getSysExMessage
SysExMessage getSysExMessage() const
Get the latest SysEx message.
Definition
USBMIDI_Parser.hpp:52
USBMIDI_Parser::MIDIUSBPacket_t
AH::Array< uint8_t, 4 > MIDIUSBPacket_t
Definition
USBMIDI_Parser.hpp:30
AH::Array
An array wrapper for easy copying, comparing, and iterating.
Definition
Array.hpp:32
SysExMessage
Definition
MIDI_MessageTypes.hpp:305
Generated by
1.17.0