comparison data/midi/rtmidi/RtMidi.cpp @ 562:ecce042cc374

* Wire up MIDI input port (as far as printing a message when an event comes in, anyway)
author Chris Cannam
date Mon, 23 Feb 2009 17:50:17 +0000
parents 32d156c75df7
children a5e0d1068cae
comparison
equal deleted inserted replaced
561:863ad4b1f841 562:ecce042cc374
67 67
68 //*********************************************************************// 68 //*********************************************************************//
69 // Common RtMidiIn Definitions 69 // Common RtMidiIn Definitions
70 //*********************************************************************// 70 //*********************************************************************//
71 71
72 RtMidiIn :: RtMidiIn() : RtMidi() 72 RtMidiIn :: RtMidiIn(std::string name) : RtMidi()
73 { 73 {
74 this->initialize(); 74 this->initialize(name);
75 } 75 }
76 76
77 void RtMidiIn :: setCallback( RtMidiCallback callback, void *userData ) 77 void RtMidiIn :: setCallback( RtMidiCallback callback, void *userData )
78 { 78 {
79 if ( inputData_.usingCallback ) { 79 if ( inputData_.usingCallback ) {
142 142
143 //*********************************************************************// 143 //*********************************************************************//
144 // Common RtMidiOut Definitions 144 // Common RtMidiOut Definitions
145 //*********************************************************************// 145 //*********************************************************************//
146 146
147 RtMidiOut :: RtMidiOut() : RtMidi() 147 RtMidiOut :: RtMidiOut(std::string name) : RtMidi()
148 { 148 {
149 this->initialize(); 149 this->initialize(name);
150 } 150 }
151 151
152 152
153 //*********************************************************************// 153 //*********************************************************************//
154 // API: Macintosh OS-X 154 // API: Macintosh OS-X
309 } 309 }
310 packet = MIDIPacketNext(packet); 310 packet = MIDIPacketNext(packet);
311 } 311 }
312 } 312 }
313 313
314 void RtMidiIn :: initialize( void ) 314 void RtMidiIn :: initialize(std::string name)
315 { 315 {
316 // Set up our client. 316 // Set up our client.
317 MIDIClientRef client; 317 MIDIClientRef client;
318 OSStatus result = MIDIClientCreate( CFSTR("RtMidi Input Client"), NULL, NULL, &client ); 318 OSStatus result = MIDIClientCreate( CFSTR(name.c_str()), NULL, NULL, &client );
319 if ( result != noErr ) { 319 if ( result != noErr ) {
320 errorString_ = "RtMidiIn::initialize: error creating OS-X MIDI client object."; 320 errorString_ = "RtMidiIn::initialize: error creating OS-X MIDI client object.";
321 error( RtError::DRIVER_ERROR ); 321 error( RtError::DRIVER_ERROR );
322 } 322 }
323 323
477 CFRelease( nameRef ); 477 CFRelease( nameRef );
478 std::string stringName = name; 478 std::string stringName = name;
479 return stringName; 479 return stringName;
480 } 480 }
481 481
482 void RtMidiOut :: initialize( void ) 482 void RtMidiOut :: initialize(std::string name)
483 { 483 {
484 // Set up our client. 484 // Set up our client.
485 MIDIClientRef client; 485 MIDIClientRef client;
486 OSStatus result = MIDIClientCreate( CFSTR("RtMidi Output Client"), NULL, NULL, &client ); 486 OSStatus result = MIDIClientCreate( CFSTR(name.c_str()), NULL, NULL, &client );
487 if ( result != noErr ) { 487 if ( result != noErr ) {
488 errorString_ = "RtMidiOut::initialize: error creating OS-X MIDI client object."; 488 errorString_ = "RtMidiOut::initialize: error creating OS-X MIDI client object.";
489 error( RtError::DRIVER_ERROR ); 489 error( RtError::DRIVER_ERROR );
490 } 490 }
491 491
811 snd_midi_event_free( apiData->coder ); 811 snd_midi_event_free( apiData->coder );
812 apiData->coder = 0; 812 apiData->coder = 0;
813 return 0; 813 return 0;
814 } 814 }
815 815
816 void RtMidiIn :: initialize( void ) 816 void RtMidiIn :: initialize(std::string name)
817 { 817 {
818 // Set up the ALSA sequencer client. 818 // Set up the ALSA sequencer client.
819 snd_seq_t *seq; 819 snd_seq_t *seq;
820 int result = snd_seq_open(&seq, "default", SND_SEQ_OPEN_DUPLEX, SND_SEQ_NONBLOCK); 820 int result = snd_seq_open(&seq, "default", SND_SEQ_OPEN_DUPLEX, SND_SEQ_NONBLOCK);
821 if ( result < 0 ) { 821 if ( result < 0 ) {
822 errorString_ = "RtMidiIn::initialize: error creating ALSA sequencer input client object."; 822 errorString_ = "RtMidiIn::initialize: error creating ALSA sequencer input client object.";
823 error( RtError::DRIVER_ERROR ); 823 error( RtError::DRIVER_ERROR );
824 } 824 }
825 825
826 // Set client name. 826 // Set client name.
827 snd_seq_set_client_name(seq, "RtMidi Input Client"); 827 snd_seq_set_client_name(seq, name.c_str());
828 828
829 // Save our api-specific connection information. 829 // Save our api-specific connection information.
830 AlsaMidiData *data = (AlsaMidiData *) new AlsaMidiData; 830 AlsaMidiData *data = (AlsaMidiData *) new AlsaMidiData;
831 data->seq = seq; 831 data->seq = seq;
832 data->vport = -1; 832 data->vport = -1;
883 if (nSrc < 1) { 883 if (nSrc < 1) {
884 errorString_ = "RtMidiIn::openPort: no MIDI input sources found!"; 884 errorString_ = "RtMidiIn::openPort: no MIDI input sources found!";
885 error( RtError::NO_DEVICES_FOUND ); 885 error( RtError::NO_DEVICES_FOUND );
886 } 886 }
887 887
888 snd_seq_port_info_t *pinfo; 888 snd_seq_port_info_t *pinfo;
889 snd_seq_port_info_alloca( &pinfo ); 889 snd_seq_port_info_alloca( &pinfo );
890 std::ostringstream ost; 890 std::ostringstream ost;
891 AlsaMidiData *data = static_cast<AlsaMidiData *> (apiData_); 891 AlsaMidiData *data = static_cast<AlsaMidiData *> (apiData_);
892 if ( portInfo( data->seq, pinfo, SND_SEQ_PORT_CAP_READ|SND_SEQ_PORT_CAP_SUBS_READ, (int) portNumber ) == 0 ) { 892 if ( portInfo( data->seq, pinfo, SND_SEQ_PORT_CAP_READ|SND_SEQ_PORT_CAP_SUBS_READ, (int) portNumber ) == 0 ) {
893 ost << "RtMidiIn::openPort: the 'portNumber' argument (" << portNumber << ") is invalid."; 893 ost << "RtMidiIn::openPort: the 'portNumber' argument (" << portNumber << ") is invalid.";
894 errorString_ = ost.str(); 894 errorString_ = ost.str();
895 error( RtError::INVALID_PARAMETER ); 895 error( RtError::INVALID_PARAMETER );
896 } 896 }
897 897
898 char name[20];
899 sprintf(name, "Input %d", portNumber + 1);
898 900
899 snd_seq_addr_t sender, receiver; 901 snd_seq_addr_t sender, receiver;
900 sender.client = snd_seq_port_info_get_client( pinfo ); 902 sender.client = snd_seq_port_info_get_client( pinfo );
901 sender.port = snd_seq_port_info_get_port( pinfo ); 903 sender.port = snd_seq_port_info_get_port( pinfo );
902 receiver.client = snd_seq_client_id( data->seq ); 904 receiver.client = snd_seq_client_id( data->seq );
911 SND_SEQ_PORT_TYPE_APPLICATION ); 913 SND_SEQ_PORT_TYPE_APPLICATION );
912 snd_seq_port_info_set_midi_channels(pinfo, 16); 914 snd_seq_port_info_set_midi_channels(pinfo, 16);
913 snd_seq_port_info_set_timestamping(pinfo, 1); 915 snd_seq_port_info_set_timestamping(pinfo, 1);
914 snd_seq_port_info_set_timestamp_real(pinfo, 1); 916 snd_seq_port_info_set_timestamp_real(pinfo, 1);
915 snd_seq_port_info_set_timestamp_queue(pinfo, data->queue_id); 917 snd_seq_port_info_set_timestamp_queue(pinfo, data->queue_id);
916 snd_seq_port_info_set_name(pinfo, "RtMidi Input"); 918 snd_seq_port_info_set_name(pinfo, name);
917 data->vport = snd_seq_create_port(data->seq, pinfo); 919 data->vport = snd_seq_create_port(data->seq, pinfo);
918 920
919 if ( data->vport < 0 ) { 921 if ( data->vport < 0 ) {
920 errorString_ = "RtMidiIn::openPort: ALSA error creating input port."; 922 errorString_ = "RtMidiIn::openPort: ALSA error creating input port.";
921 error( RtError::DRIVER_ERROR ); 923 error( RtError::DRIVER_ERROR );
1093 errorString_ = "RtMidiOut::getPortName: error looking for port name!"; 1095 errorString_ = "RtMidiOut::getPortName: error looking for port name!";
1094 error( RtError::INVALID_PARAMETER ); 1096 error( RtError::INVALID_PARAMETER );
1095 return 0; 1097 return 0;
1096 } 1098 }
1097 1099
1098 void RtMidiOut :: initialize( void ) 1100 void RtMidiOut :: initialize(std::string name)
1099 { 1101 {
1100 // Set up the ALSA sequencer client. 1102 // Set up the ALSA sequencer client.
1101 snd_seq_t *seq; 1103 snd_seq_t *seq;
1102 int result = snd_seq_open(&seq, "default", SND_SEQ_OPEN_OUTPUT, 0); 1104 int result = snd_seq_open(&seq, "default", SND_SEQ_OPEN_OUTPUT, 0);
1103 if ( result < 0 ) { 1105 if ( result < 0 ) {
1104 errorString_ = "RtMidiOut::initialize: error creating ALSA sequencer client object."; 1106 errorString_ = "RtMidiOut::initialize: error creating ALSA sequencer client object.";
1105 error( RtError::DRIVER_ERROR ); 1107 error( RtError::DRIVER_ERROR );
1106 } 1108 }
1107 1109
1108 // Set client name. 1110 // Set client name.
1109 snd_seq_set_client_name(seq, "RtMidi Output Client"); 1111 snd_seq_set_client_name(seq, name.c_str());
1110 1112
1111 // Save our api-specific connection information. 1113 // Save our api-specific connection information.
1112 AlsaMidiData *data = (AlsaMidiData *) new AlsaMidiData; 1114 AlsaMidiData *data = (AlsaMidiData *) new AlsaMidiData;
1113 data->seq = seq; 1115 data->seq = seq;
1114 data->vport = -1; 1116 data->vport = -1;
1143 if (nSrc < 1) { 1145 if (nSrc < 1) {
1144 errorString_ = "RtMidiOut::openPort: no MIDI output sources found!"; 1146 errorString_ = "RtMidiOut::openPort: no MIDI output sources found!";
1145 error( RtError::NO_DEVICES_FOUND ); 1147 error( RtError::NO_DEVICES_FOUND );
1146 } 1148 }
1147 1149
1148 snd_seq_port_info_t *pinfo; 1150 snd_seq_port_info_t *pinfo;
1149 snd_seq_port_info_alloca( &pinfo ); 1151 snd_seq_port_info_alloca( &pinfo );
1150 std::ostringstream ost; 1152 std::ostringstream ost;
1151 AlsaMidiData *data = static_cast<AlsaMidiData *> (apiData_); 1153 AlsaMidiData *data = static_cast<AlsaMidiData *> (apiData_);
1152 if ( portInfo( data->seq, pinfo, SND_SEQ_PORT_CAP_WRITE|SND_SEQ_PORT_CAP_SUBS_WRITE, (int) portNumber ) == 0 ) { 1154 if ( portInfo( data->seq, pinfo, SND_SEQ_PORT_CAP_WRITE|SND_SEQ_PORT_CAP_SUBS_WRITE, (int) portNumber ) == 0 ) {
1153 ost << "RtMidiOut::openPort: the 'portNumber' argument (" << portNumber << ") is invalid."; 1155 ost << "RtMidiOut::openPort: the 'portNumber' argument (" << portNumber << ") is invalid.";
1154 errorString_ = ost.str(); 1156 errorString_ = ost.str();
1158 snd_seq_addr_t sender, receiver; 1160 snd_seq_addr_t sender, receiver;
1159 receiver.client = snd_seq_port_info_get_client( pinfo ); 1161 receiver.client = snd_seq_port_info_get_client( pinfo );
1160 receiver.port = snd_seq_port_info_get_port( pinfo ); 1162 receiver.port = snd_seq_port_info_get_port( pinfo );
1161 sender.client = snd_seq_client_id( data->seq ); 1163 sender.client = snd_seq_client_id( data->seq );
1162 1164
1165 char name[20];
1166 sprintf(name, "Output %d", portNumber + 1);
1167
1163 if ( data->vport < 0 ) { 1168 if ( data->vport < 0 ) {
1164 data->vport = snd_seq_create_simple_port( data->seq, "RtMidi Output", 1169 data->vport = snd_seq_create_simple_port( data->seq, name,
1165 SND_SEQ_PORT_CAP_READ|SND_SEQ_PORT_CAP_SUBS_READ, 1170 SND_SEQ_PORT_CAP_READ|SND_SEQ_PORT_CAP_SUBS_READ,
1166 SND_SEQ_PORT_TYPE_MIDI_GENERIC ); 1171 SND_SEQ_PORT_TYPE_MIDI_GENERIC );
1167 if ( data->vport < 0 ) { 1172 if ( data->vport < 0 ) {
1168 errorString_ = "RtMidiOut::openPort: ALSA error creating output port."; 1173 errorString_ = "RtMidiOut::openPort: ALSA error creating output port.";
1169 error( RtError::DRIVER_ERROR ); 1174 error( RtError::DRIVER_ERROR );
1421 } 1426 }
1422 1427
1423 return 0; 1428 return 0;
1424 } 1429 }
1425 1430
1426 void RtMidiIn :: initialize( void ) 1431 void RtMidiIn :: initialize(std::string name)
1427 { 1432 {
1428 // Initialize the Irix MIDI system. At the moment, we will not 1433 // Initialize the Irix MIDI system. At the moment, we will not
1429 // worry about a return value of zero (ports) because there is a 1434 // worry about a return value of zero (ports) because there is a
1430 // chance the user could plug something in after instantiation. 1435 // chance the user could plug something in after instantiation.
1431 int nPorts = mdInit(); 1436 int nPorts = mdInit();
1562 1567
1563 std::string stringName = std::string( mdGetName( portNumber ) ); 1568 std::string stringName = std::string( mdGetName( portNumber ) );
1564 return stringName; 1569 return stringName;
1565 } 1570 }
1566 1571
1567 void RtMidiOut :: initialize( void ) 1572 void RtMidiOut :: initialize(std::string name)
1568 { 1573 {
1569 // Initialize the Irix MIDI system. At the moment, we will not 1574 // Initialize the Irix MIDI system. At the moment, we will not
1570 // worry about a return value of zero (ports) because there is a 1575 // worry about a return value of zero (ports) because there is a
1571 // chance the user could plug something in after instantiation. 1576 // chance the user could plug something in after instantiation.
1572 int nPorts = mdInit(); 1577 int nPorts = mdInit();
1787 // this here allows our code to work for sysex messages which are 1792 // this here allows our code to work for sysex messages which are
1788 // segmented across multiple buffers. 1793 // segmented across multiple buffers.
1789 apiData->message.bytes.clear(); 1794 apiData->message.bytes.clear();
1790 } 1795 }
1791 1796
1792 void RtMidiIn :: initialize( void ) 1797 void RtMidiIn :: initialize(std::string name)
1793 { 1798 {
1794 // We'll issue a warning here if no devices are available but not 1799 // We'll issue a warning here if no devices are available but not
1795 // throw an error since the user can plugin something later. 1800 // throw an error since the user can plugin something later.
1796 unsigned int nDevices = midiInGetNumDevs(); 1801 unsigned int nDevices = midiInGetNumDevs();
1797 if ( nDevices == 0 ) { 1802 if ( nDevices == 0 ) {
1968 1973
1969 std::string stringName( nameString ); 1974 std::string stringName( nameString );
1970 return stringName; 1975 return stringName;
1971 } 1976 }
1972 1977
1973 void RtMidiOut :: initialize( void ) 1978 void RtMidiOut :: initialize(std::string name)
1974 { 1979 {
1975 // We'll issue a warning here if no devices are available but not 1980 // We'll issue a warning here if no devices are available but not
1976 // throw an error since the user can plug something in later. 1981 // throw an error since the user can plug something in later.
1977 unsigned int nDevices = midiOutGetNumDevs(); 1982 unsigned int nDevices = midiOutGetNumDevs();
1978 if ( nDevices == 0 ) { 1983 if ( nDevices == 0 ) {