--- np2/macosx/cmmidi.cpp 2003/10/16 17:59:37 1.1 +++ np2/macosx/cmmidi.cpp 2003/10/25 09:08:24 1.2 @@ -46,14 +46,31 @@ enum { }; typedef struct { + BYTE prog; + BYTE press; + UINT16 bend; + BYTE ctrl[28]; +} _MIDICH, *MIDICH; + +typedef struct { MIDIHDL vermouth; UINT midictrl; UINT midisyscnt; UINT mpos; BYTE midilast; + _MIDICH mch[16]; BYTE buffer[MIDI_BUFFER]; } _CMMIDI, *CMMIDI; +static const BYTE midictrltbl[] = { 0, 1, 5, 7, 10, 11, 64, + 65, 66, 67, 84, 91, 93, + 94, // for SC-88 + 71, 72, 73, 74}; // for XG + +static BYTE midictrlindex[128]; + + +// ---- static void SOUNDCALL vermouth_getpcm(MIDIHDL hdl, SINT32 *pcm, UINT count) { @@ -91,19 +108,47 @@ static void midireset(CMMIDI midi) { } } +static void midisetparam(CMMIDI midi) { + + BYTE i; + UINT j; + MIDICH mch; + + mch = midi->mch; + sound_sync(); + for (i=0; i<16; i++, mch++) { + if (mch->press != 0xff) { + midiout_shortmsg(midi->vermouth, MIDIOUTS(0xa0+i, mch->press, 0)); + } + if (mch->bend != 0xffff) { + midiout_shortmsg(midi->vermouth, (mch->bend << 8) + 0xe0+i); + } + for (j=0; jctrl[j+1] != 0xff) { + midiout_shortmsg(midi->vermouth, + MIDIOUTS(0xb0+i, midictrltbl[j], mch->ctrl[j+1])); + } + } + if (mch->prog != 0xff) { + midiout_shortmsg(midi->vermouth, MIDIOUTS(0xc0+i, mch->prog, 0)); + } + } +} + // ---- -static UINT midiread(COMMNG self, BYTE *data) { +static UINT midiread(COMMNG self, BYTE *data) { (void)self; (void)data; return(0); } -static UINT midiwrite(COMMNG self, BYTE data) { +static UINT midiwrite(COMMNG self, BYTE data) { CMMIDI midi; + MIDICH mch; midi = (CMMIDI)(self + 1); switch(data) { @@ -179,6 +224,16 @@ static UINT midiwrite(COMMNG self, BYTE case MIDICTRL_2BYTES: if (midi->mpos >= 2) { midi->buffer[1] &= 0x7f; + mch = midi->mch + (midi->buffer[0] & 0xf); + switch(midi->buffer[0] & 0xf0) { + case 0xa0: + mch->press = midi->buffer[1]; + break; + + case 0xc0: + mch->prog = midi->buffer[1]; + break; + } keydisp_midi(midi->buffer); sound_sync(); midiout_shortmsg(midi->vermouth, MIDIOUTS2(midi->buffer)); @@ -191,6 +246,29 @@ static UINT midiwrite(COMMNG self, BYTE if (midi->mpos >= 3) { midi->buffer[1] &= 0x7f; midi->buffer[2] &= 0x7f; + mch = midi->mch + (midi->buffer[0] & 0xf); + switch(midi->buffer[0] & 0xf0) { + case 0xb0: + if (midi->buffer[1] == 123) { + mch->press = 0; + mch->bend = 0x4000; + mch->ctrl[1] = 0; // Modulation + mch->ctrl[5] = 127; // Explession + mch->ctrl[6] = 0; // Hold + mch->ctrl[7] = 0; // Portament + mch->ctrl[8] = 0; // Sostenute + mch->ctrl[9] = 0; // Soft + } + else { + mch->ctrl[midictrlindex[midi->buffer[1]]] + = midi->buffer[2]; + } + break; + + case 0xe0: + mch->bend = LOADINTELWORD(midi->buffer + 1); + break; + } keydisp_midi(midi->buffer); sound_sync(); midiout_shortmsg(midi->vermouth, MIDIOUTS3(midi->buffer)); @@ -233,22 +311,46 @@ static UINT midiwrite(COMMNG self, BYTE return(0); } -static BYTE midigetstat(COMMNG self) { +static BYTE midigetstat(COMMNG self) { return(0x00); } -static UINT midimsg(COMMNG self, UINT msg, long param) { +static long midimsg(COMMNG self, UINT msg, long param) { CMMIDI midi; + COMFLAG flag; midi = (CMMIDI)(self + 1); switch(msg) { case COMMSG_MIDIRESET: midireset(midi); return(1); + + case COMMSG_SETFLAG: + flag = (COMFLAG)param; + if ((flag) && + (flag->size == sizeof(_COMFLAG) + sizeof(midi->mch)) && + (flag->sig == COMSIG_MIDI)) { + CopyMemory(midi->mch, flag + 1, sizeof(midi->mch)); + midisetparam(midi); + return(1); + } + break; + + case COMMSG_GETFLAG: + flag = (COMFLAG)_MALLOC(sizeof(_COMFLAG) + sizeof(midi->mch), + "MIDI FLAG"); + if (flag) { + flag->size = sizeof(_COMFLAG) + sizeof(midi->mch); + flag->sig = COMSIG_MIDI; + flag->ver = 0; + flag->param = 0; + CopyMemory(flag + 1, midi->mch, sizeof(midi->mch)); + return((long)flag); + } + break; } - (void)param; return(0); } @@ -264,6 +366,17 @@ static void midirelease(COMMNG self) { // ---- +void cmmidi_initailize(void) { + + UINT i; + + ZeroMemory(midictrlindex, sizeof(midictrlindex)); + for (i=0; imidisyscnt = 0; // midi->mpos = 0; midi->midilast = 0x80; + FillMemory(midi->mch, sizeof(midi->mch), 0xff); return(ret); cmcre_err2: @@ -304,6 +418,9 @@ cmcre_err1: #else +void cmmidi_initailize(void) { +} + COMMNG cmmidi_create(void) { return(NULL);