diff --git a/engines/sci/engine/savegame.cpp b/engines/sci/engine/savegame.cpp index e43c7097ed6..c30518ab42a 100644 --- a/engines/sci/engine/savegame.cpp +++ b/engines/sci/engine/savegame.cpp @@ -626,12 +626,8 @@ void SoundCommandParser::reconstructPlayList() { const MusicList::iterator end = _music->getPlayListEnd(); for (MusicList::iterator i = _music->getPlayListStart(); i != end; ++i) { - if ((*i)->resourceId && _resMan->testResource(ResourceId(kResourceTypeSound, (*i)->resourceId))) { - (*i)->soundRes = new SoundResource((*i)->resourceId, _resMan, _soundVersion); - _music->soundInitSnd(*i); - } else { - (*i)->soundRes = 0; - } + initSoundResource(*i); + if ((*i)->status == kSoundPlaying) { // Sync the sound object's selectors related to playing with the stored // ones in the playlist, as they may have been invalidated when loading. diff --git a/engines/sci/sound/soundcmd.cpp b/engines/sci/sound/soundcmd.cpp index b7231178118..a91b1032149 100644 --- a/engines/sci/sound/soundcmd.cpp +++ b/engines/sci/sound/soundcmd.cpp @@ -37,6 +37,7 @@ SoundCommandParser::SoundCommandParser(ResourceManager *resMan, SegManager *segM _music = new SciMusic(_soundVersion); _music->init(); + _bMultiMidi = ConfMan.getBool("multi_midi"); } SoundCommandParser::~SoundCommandParser() { @@ -63,31 +64,12 @@ int SoundCommandParser::getSoundResourceId(reg_t obj) { return resourceId; } -void SoundCommandParser::processInitSound(reg_t obj) { - int resourceId = getSoundResourceId(obj); - - // Check if a track with the same sound object is already playing - MusicEntry *oldSound = _music->getSlot(obj); - if (oldSound) - processDisposeSound(obj); - - MusicEntry *newSound = new MusicEntry(); - newSound->resourceId = resourceId; - if (resourceId && _resMan->testResource(ResourceId(kResourceTypeSound, resourceId))) - newSound->soundRes = new SoundResource(resourceId, _resMan, _soundVersion); +void SoundCommandParser::initSoundResource(MusicEntry *newSound) { + if (newSound->resourceId && _resMan->testResource(ResourceId(kResourceTypeSound, newSound->resourceId))) + newSound->soundRes = new SoundResource(newSound->resourceId, _resMan, _soundVersion); else newSound->soundRes = 0; - newSound->soundObj = obj; - newSound->loop = readSelectorValue(_segMan, obj, SELECTOR(loop)); - newSound->priority = readSelectorValue(_segMan, obj, SELECTOR(pri)) & 0xFF; - if (_soundVersion >= SCI_VERSION_1_EARLY) - newSound->volume = CLIP(readSelectorValue(_segMan, obj, SELECTOR(vol)), 0, MUSIC_VOLUME_MAX); - newSound->reverb = -1; // initialize to SCI invalid, it'll be set correctly in soundInitSnd() below - - debugC(kDebugLevelSound, "kDoSound(init): %04x:%04x number %d, loop %d, prio %d, vol %d", PRINT_REG(obj), - resourceId, newSound->loop, newSound->priority, newSound->volume); - // In SCI1.1 games, sound effects are started from here. If we can find // a relevant audio resource, play it, otherwise switch to synthesized // effects. If the resource exists, play it using map 65535 (sound @@ -98,16 +80,41 @@ void SoundCommandParser::processInitSound(reg_t obj) { // if we play those, we will only make the user deaf and break speakers. Sierra SCI doesn't play anything // on soundblaster. FIXME: check, why this is - if (checkAudioResource && _resMan->testResource(ResourceId(kResourceTypeAudio, resourceId))) { - // Found a relevant audio resource, play it - int sampleLen; - newSound->pStreamAud = _audio->getAudioStream(resourceId, 65535, &sampleLen); - newSound->soundType = Audio::Mixer::kSpeechSoundType; - } else { - if (newSound->soundRes) - _music->soundInitSnd(newSound); + if (checkAudioResource && _resMan->testResource(ResourceId(kResourceTypeAudio, newSound->resourceId))) { + // Found a relevant audio resource, create an audio stream + if (_bMultiMidi || !newSound->soundRes) { + int sampleLen; + newSound->pStreamAud = _audio->getAudioStream(newSound->resourceId, 65535, &sampleLen); + newSound->soundType = Audio::Mixer::kSpeechSoundType; + } } + if (!newSound->pStreamAud && newSound->soundRes) + _music->soundInitSnd(newSound); +} + +void SoundCommandParser::processInitSound(reg_t obj) { + int resourceId = getSoundResourceId(obj); + + // Check if a track with the same sound object is already playing + MusicEntry *oldSound = _music->getSlot(obj); + if (oldSound) + processDisposeSound(obj); + + MusicEntry *newSound = new MusicEntry(); + newSound->resourceId = resourceId; + newSound->soundObj = obj; + newSound->loop = readSelectorValue(_segMan, obj, SELECTOR(loop)); + newSound->priority = readSelectorValue(_segMan, obj, SELECTOR(pri)) & 0xFF; + if (_soundVersion >= SCI_VERSION_1_EARLY) + newSound->volume = CLIP(readSelectorValue(_segMan, obj, SELECTOR(vol)), 0, MUSIC_VOLUME_MAX); + newSound->reverb = -1; // initialize to SCI invalid, it'll be set correctly in soundInitSnd() below + + debugC(kDebugLevelSound, "kDoSound(init): %04x:%04x number %d, loop %d, prio %d, vol %d", PRINT_REG(obj), + resourceId, newSound->loop, newSound->priority, newSound->volume); + + initSoundResource(newSound); + _music->pushBackSlot(newSound); if (newSound->soundRes || newSound->pStreamAud) { diff --git a/engines/sci/sound/soundcmd.h b/engines/sci/sound/soundcmd.h index 7f6e2a0fe86..c1dce014d2d 100644 --- a/engines/sci/sound/soundcmd.h +++ b/engines/sci/sound/soundcmd.h @@ -32,6 +32,7 @@ namespace Sci { class Console; class SciMusic; class SoundCommandParser; +class MusicEntry; //typedef void (SoundCommandParser::*SoundCommand)(reg_t obj, int16 value); //struct MusicEntryCommand { @@ -64,6 +65,7 @@ public: void processPlaySound(reg_t obj); void processStopSound(reg_t obj, bool sampleFinishedPlaying); + void initSoundResource(MusicEntry *newSound); MusicType getMusicType() const; @@ -109,6 +111,7 @@ private: SciMusic *_music; AudioPlayer *_audio; SciVersion _soundVersion; + bool _bMultiMidi; void processInitSound(reg_t obj); void processDisposeSound(reg_t obj);