23 #define MAX_MIDI_MESSAGE_SIZE 256 // Max message size. SysEx can be up to 65536 but 256 should be fine for most usage    41 #define CABLE_NUM (0<<4)    47     MIDIMessage() : data(
new uint8_t[MAX_MIDI_MESSAGE_SIZE + 1]), length(0) {}
    49     MIDIMessage(uint8_t *buf) : data(
new uint8_t[MAX_MIDI_MESSAGE_SIZE + 1]), length(0)
    51         for (
int i = 0; i < 4; i++) {
    69         length = other.length;
    70         for (
int i = 0; i < length; i++) {
    71             data[i] = other.data[i];
    91         if (length > MAX_MIDI_MESSAGE_SIZE) {
    98         data[0] = CABLE_NUM | 0x08;
   100         for (
int i = 0; i < buf_len; i++) {
   101             data[i + 1] = buf[i];
   116         msg.data[0] = CABLE_NUM | 0x08;
   117         msg.data[1] = 0x80 | (
channel & 0x0F);
   118         msg.data[2] = key & 0x7F;
   133         msg.data[0] = CABLE_NUM | 0x09;
   134         msg.data[1] = 0x90 | (
channel & 0x0F);
   135         msg.data[2] = key & 0x7F;
   150         msg.data[0] = CABLE_NUM | 0x0A;
   151         msg.data[1] = 0xA0 | (
channel & 0x0F);
   152         msg.data[2] = key & 0x7F;
   153         msg.data[3] = pressure & 0x7F;
   167         msg.data[0] = CABLE_NUM | 0x0B;
   168         msg.data[1] = 0xB0 | (
channel & 0x0F);
   169         msg.data[2] = control & 0x7F;
   170         msg.data[3] = value & 0x7F;
   183         msg.data[0] = CABLE_NUM | 0x0C;
   184         msg.data[1] = 0xC0 | (
channel & 0x0F);
   185         msg.data[2] = program & 0x7F;
   199         msg.data[0] = CABLE_NUM | 0x0D;
   200         msg.data[1] = 0xD0 | (
channel & 0x0F);
   201         msg.data[2] = pressure & 0x7F;
   215         int p = 
pitch + 8192;    
   216         msg.data[0] = CABLE_NUM | 0x0E;
   217         msg.data[1] = 0xE0 | (
channel & 0x0F);
   218         msg.data[2] = p & 0x7F;
   219         msg.data[3] = (p >> 7) & 0x7F;
   252         PolyphonicAftertouchType,
   255         ChannelAftertouchType,
   257         ResetAllControllersType,
   270         switch ((data[1] >> 4) & 0xF) {
   276                 message_type = NoteOffType;
   283                 message_type = NoteOnType;
   290                 message_type = PolyphonicAftertouchType;
   296                 if ((data[2] & 0x7F) < 120) { 
   297                     message_type = ControlChangeType;
   298                 } 
else if ((data[2] & 0x7F) == 121) {
   299                     message_type = ResetAllControllersType;
   300                 } 
else if ((data[2] & 0x7F) == 123) {
   301                     message_type = AllNotesOffType;
   303                     message_type = ErrorType; 
   310                 message_type = ProgramChangeType;
   316                 message_type = ChannelAftertouchType;
   323                 message_type = PitchWheelType;
   327                 message_type = SysExType;
   330                 message_type = ErrorType;
   335         if (length < min_size) {
   337             message_type = ErrorType;
   350         return (data[1] & 0x0F);
   361         if ((msg_type != NoteOffType) &&
   362                 (msg_type != NoteOnType) &&
   363                 (msg_type != PolyphonicAftertouchType)) {
   367         return data[2] & 0x7F;
   378         if ((msg_type != NoteOffType) &&
   379                 (msg_type != NoteOnType)) {
   383         return data[3] & 0x7F;
   394         if ((msg_type != ControlChangeType) &&
   395                 (msg_type != ResetAllControllersType) &&
   396                 (msg_type != AllNotesOffType)) {
   400         return data[3] & 0x7F;
   411         if ((msg_type != PolyphonicAftertouchType) &&
   412                 (msg_type != ChannelAftertouchType)) {
   416         if (
type() == PolyphonicAftertouchType) {
   417             return data[3] & 0x7F;
   419             return data[2] & 0x7F;
   431         if ((msg_type != ControlChangeType) &&
   432                 (msg_type != ResetAllControllersType) &&
   433                 (msg_type != AllNotesOffType)) {
   437         return data[2] & 0x7F;
   448         if (msg_type != ProgramChangeType) {
   452         return data[2] & 0x7F;
   463         if (msg_type != PitchWheelType) {
   467         int p = ((data[3] & 0x7F) << 7) | (data[2] & 0x7F);
 MIDIMessageType type()
Read the message type. 
static MIDIMessage NoteOn(int key, int velocity=127, int channel=0)
Create a NoteOn message. 
static MIDIMessage ProgramChange(int program, int channel=0)
Create a Program Change message. 
int controller()
Read the controller number. 
static MIDIMessage NoteOff(int key, int velocity=127, int channel=0)
Create a NoteOff message. 
static MIDIMessage AllNotesOff(int channel=0)
Create an All Notes Off message. 
static MIDIMessage SysEx(uint8_t *data, int len)
Create a SysEx message. 
int pressure()
Read the aftertouch pressure. 
static MIDIMessage ControlChange(int control, int value, int channel=0)
Create a Control Change message. 
int key()
Read the key ID. 
int channel()
Read the channel number. 
static MIDIMessage ChannelAftertouch(int pressure, int channel=0)
Create a Channel Aftertouch message. 
void from_raw(uint8_t *buf, int buf_len)
Set this MIDIMessage to a raw MIDI message. 
MIDIMessage & operator=(const MIDIMessage &other)
Assignment operator. 
A MIDI message container. 
static MIDIMessage PitchWheel(int pitch=0, int channel=0)
Create a Pitch Wheel message. 
static MIDIMessage PolyphonicAftertouch(int key, int pressure, int channel=0)
Create a PolyPhonic Aftertouch message. 
int program()
Read the program number. 
int value()
Read the controller value. 
int pitch()
Read the pitch value. 
int velocity()
Read the velocity. 
MIDIMessageType
MIDI Message Types. 
MIDIMessage(const MIDIMessage &other)
Copy constructor.