From ba006cbc5c9c0522e6cda406d53f59103944171d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 16 Dec 2019 21:45:34 +0100 Subject: [PATCH] - sound engine update. --- src/sound/s_doomsound.cpp | 5 +-- src/sound/s_sound.cpp | 56 +++++++++++++++++++++++----------- src/sound/s_soundinternal.h | 61 ++++++++++++++++++++++++++++++++----- 3 files changed, 96 insertions(+), 26 deletions(-) diff --git a/src/sound/s_doomsound.cpp b/src/sound/s_doomsound.cpp index e974addba..bf3e12fdb 100644 --- a/src/sound/s_doomsound.cpp +++ b/src/sound/s_doomsound.cpp @@ -84,7 +84,8 @@ void S_AddLocalSndInfo(int lump); class DoomSoundEngine : public SoundEngine { // client specific parts of the sound engine go in this class. - void CalcPosVel(int type, const void* source, const float pt[3], int channum, int chanflags, FVector3* pos, FVector3* vel) override; + + void CalcPosVel(int type, const void* source, const float pt[3], int channum, int chanflags, FSoundID soundid, FVector3* pos, FVector3* vel) override; bool ValidatePosVel(int sourcetype, const void* source, const FVector3& pos, const FVector3& vel); TArray ReadSound(int lumpnum); int PickReplacement(int refid); @@ -863,7 +864,7 @@ static void CalcPolyobjSoundOrg(const DVector3& listenpos, const FPolyObj* poly, // //========================================================================= -void DoomSoundEngine::CalcPosVel(int type, const void* source, const float pt[3], int channum, int chanflags, FVector3* pos, FVector3* vel) +void DoomSoundEngine::CalcPosVel(int type, const void* source, const float pt[3], int channum, int chanflags, FSoundID soundid, FVector3* pos, FVector3* vel) { if (pos != nullptr) { diff --git a/src/sound/s_sound.cpp b/src/sound/s_sound.cpp index 33bdb276e..e4ba75b6e 100644 --- a/src/sound/s_sound.cpp +++ b/src/sound/s_sound.cpp @@ -336,8 +336,7 @@ FString SoundEngine::ListSoundChannels() void SoundEngine::CalcPosVel(FSoundChan *chan, FVector3 *pos, FVector3 *vel) { - CalcPosVel(chan->SourceType, chan->Source, chan->Point, - chan->EntChannel, chan->ChanFlags, pos, vel); + CalcPosVel(chan->SourceType, chan->Source, chan->Point, chan->EntChannel, chan->ChanFlags, chan->OrgID, pos, vel); } bool SoundEngine::ValidatePosVel(const FSoundChan* const chan, const FVector3& pos, const FVector3& vel) @@ -401,7 +400,7 @@ FSoundChan *SoundEngine::StartSound(int type, const void *source, chanflags = channel & ~7; channel &= 7; - CalcPosVel(type, source, &pt->X, channel, chanflags, &pos, &vel); + CalcPosVel(type, source, &pt->X, channel, chanflags, sound_id, &pos, &vel); if (!ValidatePosVel(type, source, pos, vel)) { @@ -914,13 +913,35 @@ bool SoundEngine::CheckSoundLimit(sfxinfo_t *sfx, const FVector3 &pos, int near_ // //========================================================================== -void SoundEngine::StopSound (int channel) +void SoundEngine::StopSoundID(int sound_id) +{ + FSoundChan* chan = Channels; + while (chan != NULL) + { + FSoundChan* next = chan->NextChan; + if (sound_id == chan->OrgID) + { + StopChannel(chan); + } + chan = next; + } +} + +//========================================================================== +// +// S_StopSound +// +// Stops an unpositioned sound from playing on a specific channel. +// +//========================================================================== + +void SoundEngine::StopSound (int channel, int sound_id) { FSoundChan *chan = Channels; while (chan != NULL) { FSoundChan *next = chan->NextChan; - if (chan->SourceType == SOURCE_None) + if ((chan->SourceType == SOURCE_None && (sound_id == -1 || sound_id == chan->OrgID)) && (channel == CHAN_AUTO || channel == chan->EntChannel)) { StopChannel(chan); } @@ -936,7 +957,7 @@ void SoundEngine::StopSound (int channel) // //========================================================================== -void SoundEngine::StopSound(int sourcetype, const void* actor, int channel) +void SoundEngine::StopSound(int sourcetype, const void* actor, int channel, int sound_id) { FSoundChan* chan = Channels; while (chan != NULL) @@ -944,7 +965,7 @@ void SoundEngine::StopSound(int sourcetype, const void* actor, int channel) FSoundChan* next = chan->NextChan; if (chan->SourceType == sourcetype && chan->Source == actor && - (chan->EntChannel == channel || channel < 0)) + (sound_id == -1? (chan->EntChannel == channel || channel < 0) : (chan->OrgID == sound_id))) { StopChannel(chan); } @@ -1048,13 +1069,13 @@ void SoundEngine::ChangeSoundVolume(int sourcetype, const void *source, int chan // //========================================================================== -void SoundEngine::ChangeSoundPitch(int sourcetype, const void *source, int channel, double pitch) +void SoundEngine::ChangeSoundPitch(int sourcetype, const void *source, int channel, double pitch, int sound_id) { for (FSoundChan *chan = Channels; chan != NULL; chan = chan->NextChan) { if (chan->SourceType == sourcetype && chan->Source == source && - chan->EntChannel == channel) + (sound_id == -1? (chan->EntChannel == channel) : (chan->OrgID == sound_id))) { SetPitch(chan, (float)pitch); return; @@ -1077,21 +1098,22 @@ void SoundEngine::SetPitch(FSoundChan *chan, float pitch) // Is a sound being played by a specific emitter? //========================================================================== -bool SoundEngine::GetSoundPlayingInfo (int sourcetype, const void *source, int sound_id) +int SoundEngine::GetSoundPlayingInfo (int sourcetype, const void *source, int sound_id) { + int count = 0; if (sound_id > 0) { for (FSoundChan *chan = Channels; chan != NULL; chan = chan->NextChan) { - if (chan->OrgID == sound_id && - chan->SourceType == sourcetype && - chan->Source == source) + if (chan->OrgID == sound_id && (sourcetype == SOURCE_Any || + (chan->SourceType == sourcetype && + chan->Source == source))) { - return true; + count++; } } } - return false; + return count; } //========================================================================== @@ -1503,7 +1525,7 @@ int SoundEngine::FindSoundByLump(int lump) // Adds a new sound mapping to S_sfx. //========================================================================== -int SoundEngine::AddSoundLump(const char* logicalname, int lump, int CurrentPitchMask, int resid) +int SoundEngine::AddSoundLump(const char* logicalname, int lump, int CurrentPitchMask, int resid, int nearlimit) { S_sfx.Reserve(1); sfxinfo_t &newsfx = S_sfx.Last(); @@ -1517,7 +1539,7 @@ int SoundEngine::AddSoundLump(const char* logicalname, int lump, int CurrentPitc newsfx.Volume = 1; newsfx.Attenuation = 1; newsfx.PitchMask = CurrentPitchMask; - newsfx.NearLimit = 2; + newsfx.NearLimit = nearlimit; newsfx.LimitRange = 256 * 256; newsfx.bRandomHeader = false; newsfx.bPlayerReserve = false; diff --git a/src/sound/s_soundinternal.h b/src/sound/s_soundinternal.h index 38502d192..9983eb494 100644 --- a/src/sound/s_soundinternal.h +++ b/src/sound/s_soundinternal.h @@ -55,6 +55,37 @@ struct sfxinfo_t float Attenuation; // Multiplies the attenuation passed to S_Sound. void MarkUsed(); // Marks this sound as used. + + void Clear() + { + data.Clear(); + data3d.Clear(); + lumpnum = -1; // lump number of sfx + next = -1; + index = 0; // [RH] For hashing + Volume = 1.f; + ResourceId = -1; + PitchMask = 0; + NearLimit = 4; // 0 means unlimited + LimitRange = 256*256; + + bRandomHeader = false; + bLoadRAW = false; + b16bit= false; + bUsed = false; + bSingular = false; + + bTentative = true; + + RawRate = 0; // Sample rate to use when bLoadRAW is true + + LoopStart = 0; // -1 means no specific loop defined + + link = NO_LINK; + + Rolloff = {}; + Attenuation = 1.f; + } }; // Rolloff types @@ -208,6 +239,7 @@ enum enum // This cannot be remain as this, but for now it has to suffice. { + SOURCE_Any = -1, // Input for check functions meaning 'any source' SOURCE_None, // Sound is always on top of the listener. SOURCE_Actor, // Sound is coming from an actor. SOURCE_Sector, // Sound is coming from a sector. @@ -253,7 +285,7 @@ private: bool IsChannelUsed(int sourcetype, const void* actor, int channel, int* seen); // This is the actual sound positioning logic which needs to be provided by the client. - virtual void CalcPosVel(int type, const void* source, const float pt[3], int channel, int chanflags, FVector3* pos, FVector3* vel) = 0; + virtual void CalcPosVel(int type, const void* source, const float pt[3], int channel, int chanflags, FSoundID chanSound, FVector3* pos, FVector3* vel) = 0; // This can be overridden by the clent to provide some diagnostics. The default lets everything pass. virtual bool ValidatePosVel(int sourcetype, const void* source, const FVector3& pos, const FVector3& vel) { return true; } @@ -300,16 +332,17 @@ public: const FVector3* pt, int channel, FSoundID sound_id, float volume, float attenuation, FRolloffInfo* rolloff = nullptr, float spitch = 0.0f); // Stops an origin-less sound from playing from this channel. - void StopSound(int channel); - void StopSound(int sourcetype, const void* actor, int channel); + void StopSoundID(int sound_id); + void StopSound(int channel, int sound_id = -1); + void StopSound(int sourcetype, const void* actor, int channel, int sound_id = -1); void RelinkSound(int sourcetype, const void* from, const void* to, const FVector3* optpos); void ChangeSoundVolume(int sourcetype, const void* source, int channel, double dvolume); - void ChangeSoundPitch(int sourcetype, const void* source, int channel, double pitch); + void ChangeSoundPitch(int sourcetype, const void* source, int channel, double pitch, int sound_id = -1); bool IsSourcePlayingSomething(int sourcetype, const void* actor, int channel, int sound_id); // Stop and resume music, during game PAUSE. - bool GetSoundPlayingInfo(int sourcetype, const void* source, int sound_id); + int GetSoundPlayingInfo(int sourcetype, const void* source, int sound_id); void UnloadAllSounds(); void Reset(); void MarkUsed(int num); @@ -347,7 +380,7 @@ public: } const char *GetSoundName(FSoundID id) { - return id == 0 ? "" : S_sfx[id].name; + return id == 0 ? "" : S_sfx[id].name.GetChars(); } TArray &GetSounds() //Thio should only be used for constructing the sound list or for diagnostics code prinring information about the sound list. { @@ -366,6 +399,20 @@ public: S_rnd.Clear(); } + template bool EnumerateChannels(func callback) + { + for (FSoundChan* chan = Channels; chan; chan = chan->NextChan) + { + if (callback(chan)) return true; + } + return false; + } + + void SetDefaultRolloff(FRolloffInfo* ro) + { + S_Rolloff = *ro; + } + void ChannelVirtualChanged(FISoundChannel* ichan, bool is_virtual); FString ListSoundChannels(); @@ -378,7 +425,7 @@ public: int FindSoundByResID(int rid); int FindSoundNoHash(const char* logicalname); int FindSoundByLump(int lump); - int AddSoundLump(const char* logicalname, int lump, int CurrentPitchMask, int resid = -1); + int AddSoundLump(const char* logicalname, int lump, int CurrentPitchMask, int resid = -1, int nearlimit = 2); int FindSoundTentative(const char* name); void CacheRandomSound(sfxinfo_t* sfx); unsigned int GetMSLength(FSoundID sound);