1 /* ScummVM - Graphic Adventure Engine 2 * 3 * ScummVM is the legal property of its developers, whose names 4 * are too numerous to list here. Please refer to the COPYRIGHT 5 * file distributed with this source distribution. 6 * 7 * This program is free software; you can redistribute it and/or 8 * modify it under the terms of the GNU General Public License 9 * as published by the Free Software Foundation; either version 2 10 * of the License, or (at your option) any later version. 11 * 12 * This program is distributed in the hope that it will be useful, 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 * GNU General Public License for more details. 16 * 17 * You should have received a copy of the GNU General Public License 18 * along with this program; if not, write to the Free Software 19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 20 * 21 */ 22 23 #ifndef TSAGE_SOUND_H 24 #define TSAGE_SOUND_H 25 26 #include "common/scummsys.h" 27 #include "common/mutex.h" 28 #include "common/queue.h" 29 #include "audio/mixer.h" 30 #include "common/list.h" 31 #include "tsage/saveload.h" 32 #include "tsage/core.h" 33 34 namespace Audio { 35 class QueuingAudioStream; 36 } 37 38 namespace OPL { 39 class OPL; 40 } 41 42 namespace TsAGE { 43 44 class Sound; 45 46 #define SOUND_ARR_SIZE 16 47 #define ROLAND_DRIVER_NUM 2 48 #define ADLIB_DRIVER_NUM 3 49 #define SBLASTER_DRIVER_NUM 4 50 #define CALLBACKS_PER_SECOND 60 51 52 struct trackInfoStruct { 53 int _numTracks; 54 int _chunks[SOUND_ARR_SIZE]; 55 int _voiceTypes[SOUND_ARR_SIZE]; 56 }; 57 58 enum SoundDriverStatus {SNDSTATUS_FAILED = 0, SNDSTATUS_DETECTED = 1, SNDSTATUS_SKIPPED = 2}; 59 enum VoiceType {VOICETYPE_0 = 0, VOICETYPE_1 = 1}; 60 61 class SoundDriverEntry { 62 public: 63 int _driverNum; 64 SoundDriverStatus _status; 65 int _field2, _field6; 66 Common::String _shortDescription; 67 Common::String _longDescription; 68 }; 69 70 struct GroupData { 71 uint32 _groupMask; 72 const byte *_pData; 73 }; 74 75 struct RegisterValue { 76 uint8 _regNum; 77 uint8 _value; 78 RegisterValueRegisterValue79 RegisterValue(int regNum, int value) { 80 _regNum = regNum; _value = value; 81 } 82 }; 83 84 class SoundDriver { 85 public: 86 Common::String _shortDescription, _longDescription; 87 int _minVersion, _maxVersion; 88 // The following fields were originally held in separate arrays in the SoundManager class 89 uint32 _groupMask; 90 const GroupData *_groupOffset; 91 int _driverResID; 92 public: 93 SoundDriver(); ~SoundDriver()94 virtual ~SoundDriver() {} 95 getShortDriverDescription()96 const Common::String &getShortDriverDescription() { return _shortDescription; } getLongDriverDescription()97 const Common::String &getLongDriverDescription() { return _longDescription; } 98 open()99 virtual bool open() { return true; } // Method #0 close()100 virtual void close() {} // Method #1 reset()101 virtual bool reset() { return true; } // Method #2 getGroupData()102 virtual const GroupData *getGroupData() { return NULL; } // Method #3 installPatch(const byte * data,int size)103 virtual void installPatch(const byte *data, int size) {} // Method #4 poll()104 virtual void poll() {} // Method #5 method6()105 virtual void method6() {} // Method #6 setMasterVolume(int volume)106 virtual int setMasterVolume(int volume) { return 0; } // Method #7 proc16()107 virtual void proc16() {} // Method #8 proc18(int al,VoiceType voiceType)108 virtual void proc18(int al, VoiceType voiceType) {} // Method #9 proc20(int al,VoiceType voiceType)109 virtual void proc20(int al, VoiceType voiceType) {} // Method #10 proc22(int al,VoiceType voiceType,int v3)110 virtual void proc22(int al, VoiceType voiceType, int v3) {} // Method #11 proc24(int channel,int voiceIndex,Sound * sound,int v1,int v2)111 virtual void proc24(int channel, int voiceIndex, Sound *sound, int v1, int v2) {} setProgram(int channel,int program)112 virtual void setProgram(int channel, int program) {} // Method #13 setVolume1(int channel,int v2,int v3,int volume)113 virtual void setVolume1(int channel, int v2, int v3, int volume) {} setPitchBlend(int channel,int pitchBlend)114 virtual void setPitchBlend(int channel, int pitchBlend) {} // Method #15 playSound(const byte * channelData,int dataOffset,int program,int channel,int v0,int v1)115 virtual void playSound(const byte *channelData, int dataOffset, int program, int channel, int v0, int v1) {}// Method #16 updateVoice(int channel)116 virtual void updateVoice(int channel) {} // Method #17 proc36()117 virtual void proc36() {} // Method #18 proc38(int channel,int cmd,int value)118 virtual void proc38(int channel, int cmd, int value) {} // Method #19 setPitch(int channel,int pitchBlend)119 virtual void setPitch(int channel, int pitchBlend) {} // Method #20 proc42(int channel,int cmd,int value,int * v1,int * v2)120 virtual void proc42(int channel, int cmd, int value, int *v1, int *v2) {} // Method #21 121 }; 122 123 struct VoiceStructEntryType0 { 124 Sound *_sound; 125 int _channelNum; 126 int _priority; 127 bool _fieldA; 128 Sound *_sound2; 129 int _channelNum2; 130 int _priority2; 131 bool _field12; 132 Sound *_sound3; 133 int _channelNum3; 134 int _priority3; 135 }; 136 137 struct VoiceStructEntryType1 { 138 int _field4; 139 int _field5; 140 int _field6; 141 Sound *_sound; 142 int _channelNum; 143 int _priority; 144 Sound *_sound2; 145 int _channelNum2; 146 int _priority2; 147 Sound *_sound3; 148 int _channelNum3; 149 int _priority3; 150 }; 151 152 struct VoiceStructEntry { 153 int _voiceNum; 154 int _field1; 155 SoundDriver *_driver; 156 157 VoiceStructEntryType0 _type0; 158 VoiceStructEntryType1 _type1; 159 }; 160 161 class VoiceTypeStruct { 162 public: 163 VoiceType _voiceType; 164 int _total; 165 int _numVoices; 166 int _field3; 167 168 Common::Array<VoiceStructEntry> _entries; 169 }; 170 171 class SoundManager : public SaveListener { 172 private: 173 SoundDriver *instantiateDriver(int driverNum); 174 public: 175 bool _sndmgrReady; 176 int _ourSndResVersion, _ourDrvResVersion; 177 SynchronizedList<Sound *> _playList; 178 Common::List<SoundDriver *> _installedDrivers; 179 VoiceTypeStruct *_voiceTypeStructPtrs[SOUND_ARR_SIZE]; 180 uint32 _groupsAvail; 181 int _masterVol; 182 int _newVolume; 183 Common::Mutex _serverDisabledMutex; 184 Common::Mutex _serverSuspendedMutex; 185 bool _driversDetected; 186 SynchronizedList<Sound *> _soundList; 187 Common::List<SoundDriverEntry> _availableDrivers; 188 bool _needToRethink; 189 // Misc flags 190 bool _soTimeIndexFlag; 191 public: 192 SoundManager(); 193 ~SoundManager(); 194 195 void dispatch(); 196 virtual void listenerSynchronize(Serializer &s); 197 virtual void postInit(); 198 void syncSounds(); 199 200 static void saveNotifier(bool postFlag); 201 void saveNotifierProc(bool postFlag); 202 static void loadNotifier(bool postFlag); 203 void loadNotifierProc(bool postFlag); 204 205 void installConfigDrivers(); 206 Common::List<SoundDriverEntry> &buildDriverList(bool detectFlag); 207 Common::List<SoundDriverEntry> &getDriverList(bool detectFlag); 208 void dumpDriverList(); 209 void installDriver(int driverNum); 210 bool isInstalled(int driverNum) const; 211 void unInstallDriver(int driverNum); 212 void checkResVersion(const byte *soundData); 213 int determineGroup(const byte *soundData); 214 int extractPriority(const byte *soundData); 215 int extractLoop(const byte *soundData); 216 bool isOnPlayList(Sound *sound); 217 void extractTrackInfo(trackInfoStruct *trackInfo, const byte *soundData, int groupNum); 218 void addToSoundList(Sound *sound); 219 void removeFromSoundList(Sound *sound); 220 void addToPlayList(Sound *sound); 221 void removeFromPlayList(Sound *sound); 222 void rethinkVoiceTypes(); 223 void updateSoundVol(Sound *sound); 224 void updateSoundPri(Sound *sound); 225 void updateSoundLoop(Sound *sound); 226 void setMasterVol(int volume); 227 int getMasterVol() const; 228 void loadSound(int soundNum, bool showErrors); 229 void unloadSound(int soundNum); 230 bool isFading(); 231 232 // _sf methods 233 static SoundManager &sfManager(); 234 static void sfTerminate(); 235 static int sfDetermineGroup(const byte *soundData); 236 static void sfAddToPlayList(Sound *sound); 237 static void sfRemoveFromPlayList(Sound *sound); 238 static bool sfIsOnPlayList(Sound *sound); 239 static void sfRethinkSoundDrivers(); 240 static void sfRethinkVoiceTypes(); 241 static void sfUpdateVolume(Sound *sound); 242 static void sfDereferenceAll(); 243 static void sfUpdatePriority(Sound *sound); 244 static void sfUpdateLoop(Sound *sound); 245 static void sfSetMasterVol(int volume); 246 static void sfExtractTrackInfo(trackInfoStruct *trackInfo, const byte *soundData, int groupNum); 247 static void sfExtractGroupMask(); 248 static bool sfInstallDriver(SoundDriver *driver); 249 static void sfUnInstallDriver(SoundDriver *driver); 250 static void sfInstallPatchBank(SoundDriver *driver, const byte *bankData); 251 static void sfDoAddToPlayList(Sound *sound); 252 static bool sfDoRemoveFromPlayList(Sound *sound); 253 static void sfDoUpdateVolume(Sound *sound); 254 static void sfSoundServer(void *); 255 static void sfProcessFading(); 256 static void sfUpdateVoiceStructs(); 257 static void sfUpdateVoiceStructs2(); 258 }; 259 260 class Sound: public EventHandler { 261 private: 262 void _prime(int soundResID, bool dontQueue); 263 void _primeBuffer(const byte *soundData); 264 void _unPrime(); 265 public: 266 bool _stoppedAsynchronously; 267 int _soundResID; 268 int _group; 269 int _sndResPriority; 270 int _fixedPriority; 271 int _sndResLoop; 272 int _fixedLoop; 273 int _priority; 274 int _volume; 275 int _loop; 276 int _pausedCount; 277 int _mutedCount; 278 int _hold; 279 int _cueValue; 280 int _fadeDest; 281 int _fadeSteps; 282 int _fadeTicks; 283 int _fadeCounter; 284 bool _stopAfterFadeFlag; 285 uint32 _timer; 286 uint32 _newTimeIndex; 287 int _loopTimer; 288 int _chProgram[SOUND_ARR_SIZE]; 289 int _chModulation[SOUND_ARR_SIZE]; 290 int _chVolume[SOUND_ARR_SIZE]; 291 int _chPan[SOUND_ARR_SIZE]; 292 int _chDamper[SOUND_ARR_SIZE]; 293 int _chPitchBlend[SOUND_ARR_SIZE]; 294 int _chVoiceType[SOUND_ARR_SIZE]; 295 int _chNumVoices[SOUND_ARR_SIZE]; 296 int _chSubPriority[SOUND_ARR_SIZE]; 297 int _chFlags[SOUND_ARR_SIZE]; 298 bool _chWork[SOUND_ARR_SIZE]; 299 trackInfoStruct _trackInfo; 300 byte *_channelData[SOUND_ARR_SIZE]; 301 int _trkChannel[SOUND_ARR_SIZE]; 302 int _trkState[SOUND_ARR_SIZE]; 303 int _trkLoopState[SOUND_ARR_SIZE]; 304 int _trkIndex[SOUND_ARR_SIZE]; 305 int _trkLoopIndex[SOUND_ARR_SIZE]; 306 int _trkRest[SOUND_ARR_SIZE]; 307 int _trkLoopRest[SOUND_ARR_SIZE]; 308 309 bool _primed; 310 bool _isEmpty; 311 byte *_remoteReceiver; 312 public: 313 Sound(); 314 ~Sound(); 315 316 void synchronize(Serializer &s); 317 void orientAfterRestore(); 318 319 void play(int soundResID); 320 void stop(); 321 void prime(int soundResID); 322 void unPrime(); 323 void go(); 324 void halt(void); 325 bool isPlaying(); 326 int getSoundNum() const; 327 bool isPrimed() const; 328 bool isPaused() const; 329 bool isMuted() const; 330 void pause(bool flag); 331 void mute(bool flag); 332 void fade(int fadeDest, int fadeSteps, int fadeTicks, bool stopAfterFadeFlag); 333 void setTimeIndex(uint32 timeIndex); 334 uint32 getTimeIndex() const; 335 int getCueValue() const; 336 void setCueValue(int cueValue); 337 void setVol(int volume); 338 int getVol() const; 339 void setPri(int priority); 340 void setLoop(int flag); 341 int getPri() const; 342 int getLoop(); 343 void holdAt(int amount); 344 void release(); 345 void orientAfterDriverChange(); 346 347 // _so methods 348 void soPrimeSound(bool dontQueue); 349 void soSetTimeIndex(uint timeIndex); 350 bool soServiceTracks(); 351 void soPrimeChannelData(); 352 void soRemoteReceive(); 353 void soServiceTrackType0(int trackIndex, const byte *channelData); 354 void soUpdateDamper(VoiceTypeStruct *voiceType, int channelNum, VoiceType mode, int v0); 355 void soPlaySound(VoiceTypeStruct *vtStruct, const byte *channelData, int channelNum, VoiceType voiceType, int v0, int v1); 356 void soPlaySound2(VoiceTypeStruct *vtStruct, const byte *channelData, int channelNum, VoiceType voiceType, int v0); 357 void soProc38(VoiceTypeStruct *vtStruct, int channelNum, VoiceType voiceType, int cmd, int value); 358 void soProc40(VoiceTypeStruct *vtStruct, int channelNum, int pitchBlend); 359 void soDoTrackCommand(int channelNum, int command, int value); 360 bool soDoUpdateTracks(int command, int value); 361 void soSetTrackPos(int trackIndex, int trackPos, int cueValue); 362 363 void soServiceTrackType1(int trackIndex, const byte *channelData); 364 int soFindSound(VoiceTypeStruct *vtStruct, int channelNum); 365 }; 366 367 class ASound: public EventHandler { 368 public: 369 Sound _sound; 370 EventHandler *_endAction; 371 int _cueValue; 372 373 ASound(); 374 ~ASound(); 375 virtual void synchronize(Serializer &s); 376 virtual void dispatch(); 377 378 void play(int soundNum, EventHandler *endAction = NULL, int volume = 127); 379 void stop(); 380 void prime(int soundNum, Action *action = NULL); 381 void unPrime(); go()382 void go() { _sound.go(); } hault(void)383 void hault(void) { _sound.halt(); } isPlaying()384 bool isPlaying() { return _sound.isPlaying(); } getSoundNum()385 int getSoundNum() const { return _sound.getSoundNum(); } isPaused()386 bool isPaused() const { return _sound.isPaused(); } isMuted()387 bool isMuted() const { return _sound.isMuted(); } pause(bool flag)388 void pause(bool flag) { _sound.pause(flag); } mute(bool flag)389 void mute(bool flag) { _sound.mute(flag); } 390 void fade(int fadeDest, int fadeSteps, int fadeTicks, bool stopAfterFadeFlag, EventHandler *endAction); fadeIn()391 void fadeIn() { fade(127, 5, 10, false, NULL); } fadeOut(Action * action)392 void fadeOut(Action *action) { fade(0, 5, 10, true, action); } setTimeIndex(uint32 timeIndex)393 void setTimeIndex(uint32 timeIndex) { _sound.setTimeIndex(timeIndex); } getTimeIndex()394 uint32 getTimeIndex() const { return _sound.getTimeIndex(); } setPri(int v)395 void setPri(int v) { _sound.setPri(v); } setLoop(int total)396 void setLoop(int total) { _sound.setLoop(total); } getPri()397 int getPri() const { return _sound.getPri(); } getLoop()398 int getLoop() { return _sound.getLoop(); } setVol(int volume)399 void setVol(int volume) { _sound.setVol(volume); } getVol()400 int getVol() const { return _sound.getVol(); } holdAt(int v)401 void holdAt(int v) { _sound.holdAt(v); } release()402 void release() { _sound.release(); } 403 void fadeSound(int soundNum); 404 }; 405 406 class ASoundExt: public ASound { 407 public: 408 int _soundNum; 409 410 ASoundExt(); 411 void fadeOut2(EventHandler *endAction); 412 void changeSound(int soundNum); 413 getClassName()414 virtual Common::String getClassName() { return "ASoundExt"; } 415 virtual void synchronize(Serializer &s); 416 virtual void signal(); 417 }; 418 419 class PlayStream: public EventHandler { 420 class ResFileData { 421 public: 422 int _fileChunkSize; 423 uint _indexSize; 424 uint _chunkSize; 425 426 void load(Common::SeekableReadStream &stream); 427 }; 428 private: 429 Common::File _file; 430 ResFileData _resData; 431 Audio::QueuingAudioStream *_audioStream; 432 Audio::SoundHandle _soundHandle; 433 uint16 *_index; 434 EventHandler *_endAction; 435 int _voiceNum; 436 437 static uint32 getFileOffset(const uint16 *data, int count, int voiceNum); 438 public: 439 PlayStream(); 440 virtual ~PlayStream(); 441 442 bool setFile(const Common::String &filename); 443 bool play(int voiceNum, EventHandler *endAction); 444 void stop(); 445 bool isPlaying() const; 446 447 virtual void remove(); 448 virtual void dispatch(); 449 }; 450 451 #define ADLIB_CHANNEL_COUNT 9 452 453 class AdlibSoundDriver: public SoundDriver { 454 private: 455 GroupData _groupData; 456 Audio::Mixer *_mixer; 457 OPL::OPL *_opl; 458 byte _portContents[256]; 459 const byte *_patchData; 460 int _masterVolume; 461 Common::Mutex _queueMutex; 462 Common::Queue<RegisterValue> _queue; 463 464 bool _channelVoiced[ADLIB_CHANNEL_COUNT]; 465 int _channelVolume[ADLIB_CHANNEL_COUNT]; 466 int _v4405E[ADLIB_CHANNEL_COUNT]; 467 int _v44067[ADLIB_CHANNEL_COUNT]; 468 int _v44070[ADLIB_CHANNEL_COUNT]; 469 int _v44079[ADLIB_CHANNEL_COUNT]; 470 int _v44082[ADLIB_CHANNEL_COUNT + 1]; 471 int _pitchBlend[ADLIB_CHANNEL_COUNT]; 472 int _v4409E[ADLIB_CHANNEL_COUNT]; 473 474 475 void write(byte reg, byte value); 476 void flush(); 477 void updateChannelVolume(int channel); 478 void setVoice(int channel); 479 void clearVoice(int channel); 480 void updateChannel(int channel); 481 void setFrequency(int channel); 482 public: 483 AdlibSoundDriver(); 484 virtual ~AdlibSoundDriver(); 485 486 virtual bool open(); 487 virtual void close(); 488 virtual bool reset(); 489 virtual const GroupData *getGroupData(); 490 virtual void installPatch(const byte *data, int size); 491 virtual int setMasterVolume(int volume); 492 virtual void playSound(const byte *channelData, int dataOffset, int program, int channel, int v0, int v1); 493 virtual void updateVoice(int channel); 494 virtual void proc38(int channel, int cmd, int value); 495 virtual void setPitch(int channel, int pitchBlend); 496 497 private: 498 void onTimer(); 499 }; 500 501 class SoundBlasterDriver: public SoundDriver { 502 private: 503 GroupData _groupData; 504 Audio::Mixer *_mixer; 505 Audio::SoundHandle _soundHandle; 506 Audio::QueuingAudioStream *_audioStream; 507 int _sampleRate; 508 509 byte _masterVolume; 510 byte _channelVolume; 511 const byte *_channelData; 512 public: 513 SoundBlasterDriver(); 514 virtual ~SoundBlasterDriver(); 515 516 virtual bool open(); 517 virtual void close(); 518 virtual bool reset(); 519 virtual const GroupData *getGroupData(); 520 virtual int setMasterVolume(int volume); 521 virtual void playSound(const byte *channelData, int dataOffset, int program, int channel, int v0, int v1); 522 virtual void updateVoice(int channel); 523 virtual void proc38(int channel, int cmd, int value); 524 virtual void proc42(int channel, int cmd, int value, int *v1, int *v2); 525 }; 526 527 528 } // End of namespace TsAGE 529 530 #endif 531