void MidiCommOut::Write(const MidiEvent &out) { MidiEventSimple simple; if (out.GetSimpleEvent(&simple)) { // You could use a bunch of MAKELONG(MAKEWORD(lo,hi), MAKEWORD(lo,hi)) stuff here, but // this is easier to read and likely faster. unsigned long message = simple.status | (simple.byte1 << 8) | (simple.byte2 << 16); midi_check(midiOutShortMsg(m_output_device, message)); } }
void MidiCommOut::Write(const MidiEvent &out) { MidiEventSimple simple; if (!out.GetSimpleEvent(&simple)) return; if (m_description.id == 0) { MusicDeviceMIDIEvent(m_device, simple.status, simple.byte1, simple.byte2, 0); if (out.Type() == MidiEventType_Controller) { // If we just set the data byte for some previous controller event, // "close off" changes to it. That way, if the output device doesn't // accept this (N)RPN event, it won't accidentally overwrite the last // one that it did. // NOTE: Hopefully there aren't any (N)RPN types that rely on sequentially // changing these values smoothly. That seems like a pretty special // case though. I'll cross that bridge when I come to it. // // I tried "closing" controller changes just *before* a data (N)RPN // event (in order to cut off some hypothetical previous (N)RPN event // at the last possible second), but it didn't appear to work. // NOTE: This appears to only be necessary for the DLS Synth. I suppose // I've only got a VERY limited pool of MIDI devices to work with though, // and I'm sure there are a handful of devices out there that have the // same problem. Again, I'll cross that bridge when I come to it. // Detect coarse data byte changes if (simple.byte1 == 0x06) { MusicDeviceMIDIEvent(m_device, simple.status, 0x64, 0x7F, 0); // RPN (coarse) reset MusicDeviceMIDIEvent(m_device, simple.status, 0x62, 0x7F, 0); // NRPN (coarse) reset } // Detect fine data byte changes if (simple.byte1 == 0x26) { MusicDeviceMIDIEvent(m_device, simple.status, 0x65, 0x7F, 0); // RPN (fine) reset MusicDeviceMIDIEvent(m_device, simple.status, 0x63, 0x7F, 0); // NRPN (fine) reset } } } else { const static int PacketBufferSize = 128; Byte packet_buffer[PacketBufferSize]; MIDIPacketList *packets = reinterpret_cast<MIDIPacketList*>(packet_buffer); MIDIPacket *packet = MIDIPacketListInit(packets); int messageSize = 3; if (out.Type() == MidiEventType_ProgramChange || out.Type() == MidiEventType_ChannelPressure) messageSize = 2; const static int MaxMessageSize = 3; const Byte message[MaxMessageSize] = { simple.status, simple.byte1, simple.byte2 }; packet = MIDIPacketListAdd(packets, PacketBufferSize, packet, 0, messageSize, message); MIDISend(m_port, m_endpoint, packets); } }