This is MidiControl.m in view mode; [Download] [Up]
/* Generated by Interface Builder */ #import "MidiControl.h" @implementation MidiControl + new { self = [super new]; // super is the generic Object class, in our case pitch = .75; velocity = .75; return self; // Don't forget this! Otherwise big mess. } - setPitch:sender { pitch = [sender floatValue]; return self; } - setVelocity:sender { velocity = [sender floatValue]; return self; } - setMapping:sender { mapping = [[sender selectedCell] tag]; return self; } - (int) getSizeOfQueue { u_int size,max; if(running == 0) return(-1); midi_output_queue_size(dev_port,&size,&max); // This function returns the current number of pending MIDI messages. // Along with the maximum size of the midiOutput queue (setup below) // Henon uses it to wait for the Midi output queue to flush before // calculating more points... return(size); } - start:sender { static int firstStart = 0; if(firstStart == 0) { firstStart = 1; [self init]; // setup the midiDriver, if not already done } running = [sender intValue]; if(running ==0) { timer_stop(timer_port,owner_port); // Stops the timer! midi_clear_queue(xmit_port); // And clear the queue! } else { time = 0; } return self; } - send:(float)x:(float)y:(float)speed { float x_aux,y_aux; speed *= 200; time += speed; switch(mapping) // Two different mappings... { case 0 : x_aux = (x+1.5)/3. ; y_aux = (y+.5); break; case 1 : x_aux = (y+.5) ; y_aux = (x+1.5)/3.; break; } if(running == 0) return self; midi_data[0].quanta = (int) (time); // Time value at which to play it midi_data[0].ndata = 3; // Number of midi words (3) midi_data[0].data[0] = MIDI_NOTEON; midi_data[0].data[1] = (char) (128. * pitch * x_aux); midi_data[0].data[2] = (char) (128. * velocity * y_aux); midi_data[1].quanta = (int) (time + 500); midi_data[1].ndata = 3; midi_data[1].data[0] = MIDI_NOTEOFF; midi_data[1].data[1] = (char) (128. * pitch * x_aux); midi_data[1].data[2] = (char) 0; // Start the timer (if not already done) and send the midi data. They are // cooked (see /usr/include/midi/midi_types.h). timer_start(timer_port,owner_port); k_err = midi_send_cooked_data(xmit_port,midi_data,2,TRUE); if (k_err != KERN_SUCCESS) { midi_error("Midi didn't send event! ", k_err); exit(1); } } // Init initializes the Midi Driver to setup a midi ouput. The successive calls // are pretty general in the Mach OS (almost the same for the DSP/Sound driver. -init { // First, get the port corresponding to midi0 (midi0 = serial port A) k_err = netname_look_up(name_server_port,"","midi0", &dev_port); if (k_err != KERN_SUCCESS) { midi_error("netname lookup failure ", k_err); exit(1); } else printf("Look up done ...\n"); // Create a port (owner port) associated with the current task k_err = port_allocate(task_self(), &owner_port); if (k_err != KERN_SUCCESS) { midi_error("Cannot allocate owner port ", k_err); exit(1); } temp_port = owner_port; // Grab the midi port (dev_port); k_err = midi_set_owner(dev_port,owner_port,&temp_port); if (k_err != KERN_SUCCESS) { midi_error("Midi Ownership refused! ", k_err); exit(1); } else printf("Midi ownership acquired ...\n"); // Retrieve the transmit port of the midi device. k_err = midi_get_xmit(dev_port,owner_port,&xmit_port); if (k_err != KERN_SUCCESS) { midi_error("Midi Transmit port refused ", k_err); exit(1); } else printf("Midi transmit port acquired ...\n"); // Setup the midi protocol (including the size of the output queue.) k_err = midi_set_proto(xmit_port,MIDI_PROTO_COOKED,0,MIDI_PROTO_SYNC_SYS,10,2,1000); if (k_err != KERN_SUCCESS) { midi_error("Midi proto refused ", k_err); exit(1); } else printf("Midi Protocol set ...\n"); // Retriev the out timer port. k_err = midi_get_out_timer_port(dev_port,&timer_port); if (k_err != KERN_SUCCESS) { midi_error("Midi timer port refused ", k_err); exit(1); } else printf("Midi Timer port acquired ...\n"); return self; // AND THAT'S IT!!!!! } @end
These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.