home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
C++ Games Programming
/
CPPGAMES.ISO
/
mt
/
makesong.c
< prev
next >
Wrap
C/C++ Source or Header
|
1989-01-14
|
5KB
|
178 lines
/* makesong.c Simple example of creating a song file for MT */
/* writes random quarter notes to file "TESTSONG.SNG" */
#include <stdio.h>
#include <stdlib.h>
#include "standard.h"
#include "screenf.h"
#include "mpu401.h"
#include "filefunc.h"
#define NTRACK 8
#define NUM_EVENTS 50 /* must be even number */
#define HIGH_NOTE 72
#define LOW_NOTE 60
#define METER 4
#define TICKS_PER_BEAT 120
#define NOTE_ON 0x90
/* function prototypes */
void write_event(FILE *stream, int nbytes, int b0, int b1, int b2, int b3);
void putc_to_file(char *addr, int size, FILE *stream);
void puti_to_file(int *addr, int size, FILE *stream);
void putl_to_file(long *addr, int size, FILE *stream);
void
main()
{
int metrate, meter, pitchbend, exclusive, channel, i, midivol,
event_count, active, divisor, time, note;
long numevents;
char event_data[5];
char *song_title = "Random notes test file. From MAKESONG.C output.";
char *track1_name = "TestTrak";
char *empty_name = "< >";
FILE *stream;
metrate = 100;
meter = METER;
pitchbend = FALSE;
exclusive = FALSE;
channel = 0;
midivol = 100;
numevents = NUM_EVENTS;
active = FALSE;
stream = fopen("TESTSONG.SNG", "wb");
if (stream == NULL){
fputs("\nCould not open file TESTSONG.SNG.", stdout);
exit(0);
}
fputs("\nBuilding file TESTSONG.SNG...\n", stdout);
putc_to_file(song_title, 51, stream); /* store common data */
puti_to_file(&metrate, 1, stream);
puti_to_file(&meter, 1, stream);
puti_to_file(&pitchbend, 1, stream);
puti_to_file(&exclusive, 1, stream);
putc_to_file(track1_name, 9, stream); /* store track 1 header */
puti_to_file(&channel, 1, stream);
putl_to_file(&numevents, 1, stream);
puti_to_file(&active, 1, stream);
puti_to_file(&midivol, 1, stream);
numevents = 1;
for (i = 1; i < NTRACK; i++){ /* store other track's headers */
putc_to_file(empty_name, 9, stream);
puti_to_file(&channel, 1, stream);
putl_to_file(&numevents, 1, stream);
puti_to_file(&active, 1, stream);
puti_to_file(&midivol, 1, stream);
}
/* rand() produces random digits between 0 and 32767 */
divisor = 32767/(HIGH_NOTE - LOW_NOTE);
time = 0;
/* write track 1 midi data */
write_event(stream, 2, 0, MES_END, 0, 0); /* starting mes_end event */
event_count = 1;
while (event_count < NUM_EVENTS - 2){
if (time >= meter * TICKS_PER_BEAT){ /* add mes_end if needed */
write_event(stream, 2, 0, MES_END, 0, 0);
time -= meter * TICKS_PER_BEAT;
event_count += 1;
}
else {
note = LOW_NOTE + ((HIGH_NOTE - LOW_NOTE) * rand()/divisor);
write_event(stream, 4, 0, NOTE_ON + channel, note, 64);
write_event(stream, 4, TICKS_PER_BEAT, NOTE_ON + channel,
note, 0);
event_count += 2;
time += TICKS_PER_BEAT;
}
}
write_event(stream, 2, 0, ALL_END, 0, 0); /* write track terminator */
for (i = 1; i < NTRACK; i++) /* rest of tracks have only one event */
write_event(stream, 2, 0, MES_END, 0, 0);
fclose(stream);
}
/* Writes the five data bytes in an event with one call to putc_to_file() */
void
write_event(stream, nbytes, b0, b1, b2, b3)
FILE *stream;
int nbytes, b0, b1, b2, b3;
{
char data[5];
data[0] = nbytes;
data[1] = b0;
data[2] = b1;
data[3] = b2;
data[4] = b3;
putc_to_file(data, 5, stream);
}
void
putc_to_file(addr, size, stream) /* put near char data to stream */
char *addr;
int size;
FILE *stream;
{
int i;
for(i = 0; i < size; i++){
fputc(*addr++, stream);
}
}
void
puti_to_file(addr, size, stream) /* put near int data to stream */
int *addr;
int size;
FILE *stream;
{
int i, end;
char *caddr;
caddr = (char *)addr;
end = size * sizeof(int);
for(i = 0; i < end; i++){
fputc(*caddr++, stream);
}
}
void
putl_to_file(addr, size, stream) /* put near long int data to stream */
long *addr;
int size;
FILE *stream;
{
int i, end;
char *caddr;
caddr = (char *)addr;
end = size * sizeof(long);
for(i = 0; i < end; i++){
fputc(*caddr++, stream);
}
}