[Scummvm-cvs-logs] CVS: scummvm/sound mididrv.cpp,1.27,1.28 mididrv.h,1.7,1.8 midistreamer.h,1.1,1.2

Jamieson Christian jamieson630 at users.sourceforge.net
Tue Nov 26 08:56:03 CET 2002


Update of /cvsroot/scummvm/scummvm/sound
In directory sc8-pr-cvs1:/tmp/cvs-serv12688/sound

Modified Files:
	mididrv.cpp mididrv.h midistreamer.h 
Log Message:
Restructured MIDI channel allocation architecture.
Adlib no longer suffers from 16-channel MIDI restrictions.
Fixes a regression in the MI2 intro music under Adlib.

Index: mididrv.cpp
===================================================================
RCS file: /cvsroot/scummvm/scummvm/sound/mididrv.cpp,v
retrieving revision 1.27
retrieving revision 1.28
diff -u -d -r1.27 -r1.28
--- mididrv.cpp	21 Nov 2002 19:06:07 -0000	1.27
+++ mididrv.cpp	26 Nov 2002 16:54:54 -0000	1.28
@@ -45,8 +45,50 @@
 
 typedef void TimerCallback (void *);
 
+class MidiDriver_MPU401;
+
+class MidiChannel_MPU401 : public MidiChannel {
+	friend MidiDriver_MPU401;
+
+private:
+	MidiDriver_MPU401 *_owner;
+	bool _allocated;
+	byte _channel;
+
+	void init (MidiDriver_MPU401 *owner, byte channel);
+	void allocate() { _allocated = true; }
+
+public:
+	void release() { _allocated = false; }
+
+	// Regular messages
+	void noteOff (byte note);
+	void noteOn (byte note, byte velocity);
+	void programChange (byte program);
+	void pitchBend (int16 bend);
+
+	// Control Change messages
+	void controlChange (byte control, byte value);
+	void modulationWheel (byte value) { controlChange (1, value); }
+	void volume (byte value) { controlChange (7, value); }
+	void panPosition (byte value) { controlChange (10, value); }
+	void pitchBendFactor (byte value) { controlChange (16, value); }
+	void detune (byte value) { controlChange (17, value); }
+	void priority (byte value) { controlChange (18, value); }
+	void sustain (bool value) { controlChange (64, value ? 1 : 0); }
+	void effectLevel (byte value) { controlChange (91, value); }
+	void chorusLevel (byte value) { controlChange (93, value); }
+	void allNotesOff() { controlChange (123, 0); }
+
+	// SysEx messages
+	void sysEx_customInstrument (uint32 type, byte *instr);
+};
+
+
+
 class MidiDriver_MPU401 : public MidiDriver {
 private:
+	MidiChannel_MPU401 _midi_channels [16];
 	bool _started_thread;
 	TimerCallback *_timer_proc;
 	void *_timer_param;
@@ -54,10 +96,60 @@
 	static int midi_driver_thread (void *param);
 
 public:
+	MidiDriver_MPU401();
+
 	virtual void setTimerCallback (void *timer_param, void (*timer_proc) (void *));
 	virtual uint32 getBaseTempo (void) { return 0x4A0000; }
+
+	virtual MidiChannel *allocateChannel();
+	virtual MidiChannel *getPercussionChannel() { return &_midi_channels [9]; }
 };
 
+
+
+void MidiChannel_MPU401::init (MidiDriver_MPU401 *owner, byte channel)
+{
+	_owner = owner;
+	_channel = channel;
+	_allocated = false;
+}
+
+void MidiChannel_MPU401::noteOff (byte note) { _owner->send(note << 8 | 0x80 | _channel); }
+void MidiChannel_MPU401::noteOn (byte note, byte velocity) { _owner->send (velocity << 16 | note << 8 | 0x90 | _channel); }
+void MidiChannel_MPU401::programChange (byte program) { _owner->send(program << 8 | 0xC0 | _channel); }
+void MidiChannel_MPU401::pitchBend (int16 bend) { _owner->send((((bend + 0x2000) >> 7) & 0x7F) << 16 | ((bend + 0x2000) & 0x7F) << 8 | 0xE0 | _channel); }
+void MidiChannel_MPU401::controlChange (byte control, byte value) { _owner->send(value << 16 | control << 8 | 0xB0 | _channel); }
+void MidiChannel_MPU401::sysEx_customInstrument (uint32 type, byte *instr) { _owner->sysEx_customInstrument (_channel, type, instr); }
+
+
+
+MidiDriver_MPU401::MidiDriver_MPU401() : MidiDriver()
+{
+	int i;
+	for (i = 0; i < ARRAYSIZE(_midi_channels); ++i) {
+		_midi_channels [i].init (this, i);
+	}
+}
+
+
+
+MidiChannel *MidiDriver_MPU401::allocateChannel()
+{
+	MidiChannel_MPU401 *chan;
+	uint i;
+	
+	for (i = 0; i < ARRAYSIZE(_midi_channels); ++i) {
+		if (i == 9) continue;
+		chan = &_midi_channels[i];
+		if (!chan->_allocated) {
+			chan->allocate();
+			return (chan);
+		}
+	}
+	return NULL;
+}
+
+
 void MidiDriver_MPU401::setTimerCallback (void *timer_param, void (*timer_proc) (void *))
 {
 	if (!_timer_proc || !timer_proc) {
@@ -92,7 +184,6 @@
 
 	return 0;
 }
-
 
 
 

Index: mididrv.h
===================================================================
RCS file: /cvsroot/scummvm/scummvm/sound/mididrv.h,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -d -r1.7 -r1.8
--- mididrv.h	21 Nov 2002 19:06:07 -0000	1.7
+++ mididrv.h	26 Nov 2002 16:54:57 -0000	1.8
@@ -25,12 +25,14 @@
 
 #include "scummsys.h"
 
+class MidiChannel;
+
 struct MidiEvent {
 	uint32 delta;
 	uint32 event;
 };
 
-/* Lowlevel Abstract Midi Driver Class */
+// Abstract MIDI Driver Class
 class MidiDriver {
 
 public:
@@ -112,11 +114,44 @@
 	// Timing functions - MidiDriver now operates timers
 	virtual void setTimerCallback (void *timer_param, void (*timer_proc) (void *)) = 0;
 	virtual uint32 getBaseTempo (void) = 0;
+
+	// Channel allocation functions
+	virtual MidiChannel *allocateChannel() = 0;
+	virtual MidiChannel *getPercussionChannel() = 0;
 };
 
 
 
-/* driver types */
+class MidiChannel {
+public:
+	virtual void release() = 0;
+
+	// Regular messages
+	virtual void noteOff (byte note) = 0;
+	virtual void noteOn (byte note, byte velocity) = 0;
+	virtual void programChange (byte program) = 0;
+	virtual void pitchBend (int16 bend) = 0; // -0x2000 to +0x1FFF
+
+	// Control Change messages
+	virtual void controlChange (byte control, byte value) = 0;
+	virtual void modulationWheel (byte value) = 0;
+	virtual void volume (byte value) = 0;
+	virtual void panPosition (byte value) = 0;
+	virtual void pitchBendFactor (byte value) = 0;
+	virtual void detune (byte value) = 0;
+	virtual void priority (byte value) = 0;
+	virtual void sustain (bool value) = 0;
+	virtual void effectLevel (byte value) = 0;
+	virtual void chorusLevel (byte value) = 0;
+	virtual void allNotesOff() = 0;
+
+	// SysEx messages
+	virtual void sysEx_customInstrument (uint32 type, byte *instr) = 0;
+};
+
+
+
+// MIDI Driver Types
 enum {
 	MD_AUTO = 0,
 	MD_NULL = 1,

Index: midistreamer.h
===================================================================
RCS file: /cvsroot/scummvm/scummvm/sound/midistreamer.h,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -d -r1.1 -r1.2
--- midistreamer.h	21 Nov 2002 19:26:44 -0000	1.1
+++ midistreamer.h	26 Nov 2002 16:54:58 -0000	1.2
@@ -59,6 +59,9 @@
 
 	void setTimerCallback (void *timer_param, void (*timer_proc) (void *)) { }
 	uint32 getBaseTempo (void) { return _target->getBaseTempo(); }
+
+	MidiChannel *allocateChannel() { return NULL; }
+	MidiChannel *getPercussionChannel() { return NULL; }
 };
 
 #endif





More information about the Scummvm-git-logs mailing list