chena1@ese.essex.ac.uk (Chengodan A) (10/21/89)
***************
A.Chengodan,
ESE,
Essex University,
Colchester,CO4 3SQ,
Essex, UK.
21/10/89.
Hi,
I have got more problems to solve with MIDI.
I'm trying to interface an IBM-AT with a keyboard
via MIDI. Now I`m not sure the actual DATA structure
I need to use on READING THE MIDI MESSAGES; especially
the timing information of each MIDI MESSAGES
i.e:
In storing the MIDI MESSAGE ( key on/off ..), how do I
include the time field indicating when each note/event
( key on/off ..) has occurred (relatively/ ??). This is to
make sure the MIDI MESSAGES are sent at a right time on
playback.
How to incorporate this timing in the MIDI
MESSAGE structure?
So far I could only think of these, using:
(1). hardware: Reading a Real-Time clock
with high resolution.
or
A special timer set after each
key is pressed and reset it as
it's released. ( not sure this is
that simple when 16 keys are
pressed simultaneously ....)
(2). software: Reading a computers Real-Time
clock and calculate the time
interval between each event.
( this might eat-up a lot of
CPU's time and miss reading
the incoming data..).
The structure which I think suitable
in C is:
struc MIDIMSG
{
int status; /* 8 bit integer */
int data; /* to make a full */
int speed; /* use of memory */
int time;
};
(3). SYSTEM REAL-TIME MESSAGES:
Using the System Real-Time MIDI Messages
which provide a TIMING-CLOCK at a rate of
24 beats per quarter notes.
If I could use this, what sort of calculations
or steps I should take to make it work?
I hope to get some comments and ideas of how I can go around
solving this problem. I wish you will be able to send some Email for me.
Thank You Very Much.
***************
***************
Email: chena1@ese.essex.ac.uk.
***************
maverick@oak.Berkeley.EDU (Vance Maverick) (10/22/89)
I failed sending mail, so I'll post this as a followup. > I`m not sure the actual DATA structure > I need to use on READING THE MIDI MESSAGES; especially > the timing information of each MIDI MESSAGES > In storing the MIDI MESSAGE ( key on/off ..), how do I > include the time field indicating when each note/event > ( key on/off ..) has occurred (relatively/ ??). This is to > make sure the MIDI MESSAGES are sent at a right time on > playback. For notes I recommend a structure like this: typedef struct { long time; /* Attack time from start of track */ unsigned int length; /* Length in same time units */ char pitch, /* MIDI information: pitch 0-127 */ channel, /* channel 0-15 (low nibble of status) */ velocity, /* Attack velocity (from note-on) */ release; /* Release velocity (from note-off) */ } note; (Assuming long = 32 bits, int = 16, char = 8.) In writing a MIDI sequencer three years ago, my partner and I committed ourselves early on to a track format where ons and offs were stored separately. This became a real pain when we started implementing edit operations. Also, I think you want to store the time as absolute, i.e. from the start of the track, rather than with respect to the previous note: again, the advantage becomes most apparent with edit operations. For timing on the PC, there are a couple of options. The Roland MPU interface and its clones will do timing for you, in 120ths of a quarter note (and other resolutions); this is quite adequate for a sequencer. If you don't have one, or don't want to deal with the eccentricities of the MPU command set and timing scheme, you can do the timing yourself with the PC's system timer. You'll need to speed up the timer, divert the interrupt to a handler of your own, and call the old handler at the right (old) speed. This is not "hard", but tricky to get right. I don't have the demo
scott@bbxsda.UUCP (Scott Amspoker) (10/24/89)
In article <2211@servax0.essex.ac.uk> chena1@ese.UUCP (Chengodan A) writes: >Hi, > I have got more problems to solve with MIDI. >I'm trying to interface an IBM-AT with a keyboard >via MIDI. Now I`m not sure the actual DATA structure >I need to use on READING THE MIDI MESSAGES; especially >the timing information of each MIDI MESSAGES >[...] Here are a couple of suggestions based on what I have done with my own software: Use one of the programmable interval timers on your PC. They can be set to interrupt at ranges from 2 microseconds to many milliseconds. Make your timer interrupt handle increment a tick counter in memory. This will be your "clock". I use a Yamaha C1 which has an additional timer just for music applications. Your midi receive interrupt handler should remember the current clock upon receiving a status byte (or implied running status). When the entire midi message had been recieved it is then stuffed (along with the clock value) into a quick and dirty circular queue (don't spend too much time in the interrupt routine). A higher level routine may retrieve these time-stamped messages at its leasure and place them into a more complex and permanent data structure. (Be sure to disable interrupts when setting/retrieving the clock value as well as when accessing the circular queue). My recieve interrupt handler is also responsible for echoing incoming MIDI messages to the appropriate output port. There are several ways to handle playback of MIDI data. It depends on how you chose to represent your "tracks" in memory. If absolute timing accuracy is important (as it is for me) than you can prepare a "dispatch" queue containing data indicating time delays between the MIDI messages. Your clock tick interrupt may then take the responsibility of dispatching the data precisely on schedule (including the timely dispatch of MIDI sync messages). Once again, keep it simple. Don't spend too much time in an interrupt handler. Your higher level logic can take all the time it wants preparing output data, updating the screen, etc. as long as it doesn't allow the dispatch queue to become empty. The actual MIDI output ports are also interrupt driven. If the port is busy then place output data in a queue so that the output interrupt handler can take care of it when it's ready. This is a rather oversimplified description of one of *many* ways of doing things. I hope it gave you some ideas. -- Scott Amspoker Basis International, Albuquerque, NM (505) 345-5232 unmvax.cs.unm.edu!bbx!bbxsda!scott
scott@bbxsda.UUCP (Scott Amspoker) (10/24/89)
In article <18642@pasteur.Berkeley.EDU> maverick@oak.Berkeley.EDU (Vance Maverick) writes: >[about designing a sequencer] >For notes I recommend a structure like this: > >typedef struct { > long time; /* Attack time from start of track */ > unsigned int length; /* Length in same time units */ > char pitch, /* MIDI information: pitch 0-127 */ > channel, /* channel 0-15 (low nibble of status) */ > velocity, /* Attack velocity (from note-on) */ > release; /* Release velocity (from note-off) */ > } note; > >(Assuming long = 32 bits, int = 16, char = 8.) > >In writing a MIDI sequencer three years ago, my partner and I committed >ourselves early on to a track format where ons and offs were stored >separately. This became a real pain when we started implementing edit >operations. Good advice! I "discovered" that myself after getting halfway through the project. It was significant enough to warrant rewriting a lot of code. It gets a little trickier during record and playback but makes a lot of other features a lot easier. >For timing on the PC, there are a couple of options. The Roland MPU >interface and its clones will do timing for you, in 120ths of a quarter >note (and other resolutions); this is quite adequate for a sequencer. This is not a flame but I'm not entirely sure that 120 ppq is enough. I use 480 ppq and admit that it might be an overkill but I do a lot of "free-form" sequencing (without a click). When I do use a click and drum machine I almost never quantize except maybe the bass part. Since I use a Yamaha C1 I don't know much about the Roland MPU. The C1 provides an additional interval timer for applications. There are 2 input and 8 output ports that contain on-chip FIFOs (about 16 bytes) so the main application is not overburdened with interrrupt handling. -- Scott Amspoker Basis International, Albuquerque, NM (505) 345-5232 unmvax.cs.unm.edu!bbx!bbxsda!scott
ear@wpi.wpi.edu (Eric A Rasmussen) (10/25/89)
My father's company is considering developing a IBM PC midi card and sequencing software to accompany it. As an informal marketing survey, I would like to ask your opinions on several points: 1) How important is MPU401 compatibility? 2) How important is price? 3) How important would the inclusion of the source code (in C) be so that users could modify the software to suit personal tastes/needs? (or how foolish would it be to include the source code?) 4) Would you be willing to buy a PC midi card and software if it was not MPU401 compatible but cost altogether less than $100. (and possibly included the source code?) 5) What is the best deal you have seen on a midi card (with or without software) for a PC, and do you think it's a good deal? 6) What is your favorite sequencer software for the PC? Thanks for your time. _ _ +-=-=-=-=-=-=-=-=-+ |_ ,_ . _ |_} _ _ ,_ _ _ _ _ ,_ | ear@wpi.wpi.edu | |_ | | |_ | \ |_\ _> | | | |_| _> _> |_' | | | ear%wpi@wpi.edu | --< A real engineer never reads the instructions first! >-- +-=-=-=-=-=-=-=-=-+