Reorder active sound data to make lookup by Ptr better

This commit is contained in:
Chris Robinson 2015-11-23 03:07:04 -08:00
parent 495e138907
commit 9d0018e1bc
2 changed files with 135 additions and 93 deletions

View file

@ -226,12 +226,15 @@ namespace MWSound
bool SoundManager::isPlaying(const MWWorld::Ptr &ptr, const std::string &id) const bool SoundManager::isPlaying(const MWWorld::Ptr &ptr, const std::string &id) const
{ {
SoundMap::const_iterator snditer = mActiveSounds.begin(); SoundMap::const_iterator snditer = mActiveSounds.find(ptr);
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == ptr && snditer->second.second == id && snditer->first->isPlaying()) SoundNamePairList::const_iterator sndname = snditer->second.begin();
return true; for(;sndname != snditer->second.end();++sndname)
++snditer; {
if(sndname->second == id && sndname->first->isPlaying())
return true;
}
} }
return false; return false;
} }
@ -336,7 +339,7 @@ namespace MWSound
MWBase::SoundPtr sound = mOutput->playSound3D(sfx->mHandle, MWBase::SoundPtr sound = mOutput->playSound3D(sfx->mHandle,
objpos, sfx->mVolume, basevol, 1.0f, sfx->mMinDist, sfx->mMaxDist, Play_Normal|Play_TypeVoice, 0 objpos, sfx->mVolume, basevol, 1.0f, sfx->mMinDist, sfx->mMaxDist, Play_Normal|Play_TypeVoice, 0
); );
mActiveSounds[sound] = std::make_pair(ptr, std::string("_say_sound")); mActiveSounds[ptr].push_back(std::make_pair(sound, std::string("_say_sound")));
} }
catch(std::exception &e) catch(std::exception &e)
{ {
@ -346,15 +349,16 @@ namespace MWSound
float SoundManager::getSaySoundLoudness(const MWWorld::Ptr &ptr) const float SoundManager::getSaySoundLoudness(const MWWorld::Ptr &ptr) const
{ {
SoundMap::const_iterator snditer = mActiveSounds.begin(); SoundMap::const_iterator snditer = mActiveSounds.find(ptr);
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == ptr && snditer->second.second == "_say_sound") SoundNamePairList::const_iterator sndname = snditer->second.begin();
break; for(;sndname != snditer->second.end();++sndname)
++snditer; {
if(sndname->second == "_say_sound")
return 0.0f;
}
} }
if (snditer == mActiveSounds.end())
return 0.f;
return 0.0f; return 0.0f;
} }
@ -371,7 +375,7 @@ namespace MWSound
MWBase::SoundPtr sound = mOutput->playSound(sfx->mHandle, MWBase::SoundPtr sound = mOutput->playSound(sfx->mHandle,
sfx->mVolume, basevol, 1.0f, Play_Normal|Play_TypeVoice, 0 sfx->mVolume, basevol, 1.0f, Play_Normal|Play_TypeVoice, 0
); );
mActiveSounds[sound] = std::make_pair(MWWorld::Ptr(), std::string("_say_sound")); mActiveSounds[MWWorld::Ptr()].push_back(std::make_pair(sound, std::string("_say_sound")));
} }
catch(std::exception &e) catch(std::exception &e)
{ {
@ -386,16 +390,21 @@ namespace MWSound
void SoundManager::stopSay(const MWWorld::Ptr &ptr) void SoundManager::stopSay(const MWWorld::Ptr &ptr)
{ {
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.find(ptr);
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == ptr && snditer->second.second == "_say_sound") SoundNamePairList::iterator sndname = snditer->second.begin();
for(;sndname != snditer->second.end();++sndname)
{ {
snditer->first->stop(); if(sndname->second != "_say_sound")
mActiveSounds.erase(snditer++); continue;
sndname->first->stop();
snditer->second.erase(sndname);
if(snditer->second.empty())
mActiveSounds.erase(snditer);
return;
} }
else
++snditer;
} }
} }
@ -430,7 +439,7 @@ namespace MWSound
sound = mOutput->playSound(sfx->mHandle, sound = mOutput->playSound(sfx->mHandle,
volume * sfx->mVolume, basevol, pitch, mode|type, offset volume * sfx->mVolume, basevol, pitch, mode|type, offset
); );
mActiveSounds[sound] = std::make_pair(MWWorld::Ptr(), soundId); mActiveSounds[MWWorld::Ptr()].push_back(std::make_pair(sound, soundId));
} }
catch(std::exception&) catch(std::exception&)
{ {
@ -460,9 +469,9 @@ namespace MWSound
objpos, volume * sfx->mVolume, basevol, pitch, sfx->mMinDist, sfx->mMaxDist, mode|type, offset objpos, volume * sfx->mVolume, basevol, pitch, sfx->mMinDist, sfx->mMaxDist, mode|type, offset
); );
if((mode&Play_NoTrack)) if((mode&Play_NoTrack))
mActiveSounds[sound] = std::make_pair(MWWorld::Ptr(), soundId); mActiveSounds[MWWorld::Ptr()].push_back(std::make_pair(sound, soundId));
else else
mActiveSounds[sound] = std::make_pair(ptr, soundId); mActiveSounds[ptr].push_back(std::make_pair(sound, soundId));
} }
catch(std::exception&) catch(std::exception&)
{ {
@ -486,7 +495,7 @@ namespace MWSound
sound = mOutput->playSound3D(sfx->mHandle, sound = mOutput->playSound3D(sfx->mHandle,
initialPos, volume * sfx->mVolume, basevol, pitch, sfx->mMinDist, sfx->mMaxDist, mode|type, offset initialPos, volume * sfx->mVolume, basevol, pitch, sfx->mMinDist, sfx->mMaxDist, mode|type, offset
); );
mActiveSounds[sound] = std::make_pair(MWWorld::Ptr(), soundId); mActiveSounds[MWWorld::Ptr()].push_back(std::make_pair(sound, soundId));
} }
catch(std::exception &) catch(std::exception &)
{ {
@ -500,43 +509,50 @@ namespace MWSound
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end()) while(snditer != mActiveSounds.end())
{ {
if(snditer->first == sound) SoundNamePairList::iterator sndname = snditer->second.begin();
for(;sndname != snditer->second.end();++sndname)
{ {
snditer->first->stop(); if(sndname->first != sound)
mActiveSounds.erase(snditer++); continue;
sndname->first->stop();
snditer->second.erase(sndname);
if(snditer->second.empty())
mActiveSounds.erase(snditer);
return;
} }
else
++snditer;
} }
} }
void SoundManager::stopSound3D(const MWWorld::Ptr &ptr, const std::string& soundId) void SoundManager::stopSound3D(const MWWorld::Ptr &ptr, const std::string& soundId)
{ {
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.find(ptr);
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == ptr && snditer->second.second == soundId) SoundNamePairList::iterator sndname = snditer->second.begin();
for(;sndname != snditer->second.end();++sndname)
{ {
snditer->first->stop(); if(sndname->second != soundId)
mActiveSounds.erase(snditer++); continue;
sndname->first->stop();
snditer->second.erase(sndname);
if(snditer->second.empty())
mActiveSounds.erase(snditer);
return;
} }
else
++snditer;
} }
} }
void SoundManager::stopSound3D(const MWWorld::Ptr &ptr) void SoundManager::stopSound3D(const MWWorld::Ptr &ptr)
{ {
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.find(ptr);
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == ptr) SoundNamePairList::iterator sndname = snditer->second.begin();
{ for(;sndname != snditer->second.end();++sndname)
snditer->first->stop(); sndname->first->stop();
mActiveSounds.erase(snditer++); mActiveSounds.erase(snditer);
}
else
++snditer;
} }
} }
@ -545,11 +561,13 @@ namespace MWSound
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end()) while(snditer != mActiveSounds.end())
{ {
if(snditer->second.first != MWWorld::Ptr() && if(snditer->first != MWWorld::Ptr() &&
snditer->second.first != MWMechanics::getPlayer() && snditer->first != MWMechanics::getPlayer() &&
snditer->second.first.getCell() == cell) snditer->first.getCell() == cell)
{ {
snditer->first->stop(); SoundNamePairList::iterator sndname = snditer->second.begin();
for(;sndname != snditer->second.end();++sndname)
sndname->first->stop();
mActiveSounds.erase(snditer++); mActiveSounds.erase(snditer++);
} }
else else
@ -559,31 +577,36 @@ namespace MWSound
void SoundManager::stopSound(const std::string& soundId) void SoundManager::stopSound(const std::string& soundId)
{ {
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.find(MWWorld::Ptr());
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == MWWorld::Ptr() && SoundNamePairList::iterator sndname = snditer->second.begin();
snditer->second.second == soundId) for(;sndname != snditer->second.end();++sndname)
{ {
snditer->first->stop(); if(sndname->second != soundId)
mActiveSounds.erase(snditer++); continue;
sndname->first->stop();
snditer->second.erase(sndname);
if(snditer->second.empty())
mActiveSounds.erase(snditer);
return;
} }
else
++snditer;
} }
} }
void SoundManager::fadeOutSound3D(const MWWorld::Ptr &ptr, void SoundManager::fadeOutSound3D(const MWWorld::Ptr &ptr,
const std::string& soundId, float duration) const std::string& soundId, float duration)
{ {
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.find(ptr);
while(snditer != mActiveSounds.end()) if(snditer != mActiveSounds.end())
{ {
if(snditer->second.first == ptr && snditer->second.second == soundId) SoundNamePairList::iterator sndname = snditer->second.begin();
for(;sndname != snditer->second.end();++sndname)
{ {
snditer->first->setFadeout(duration); if(sndname->second == soundId)
sndname->first->setFadeout(duration);
} }
++snditer;
} }
} }
@ -714,37 +737,47 @@ namespace MWSound
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end()) while(snditer != mActiveSounds.end())
{ {
if(!snditer->first->isPlaying()) SoundNamePairList::iterator sndname = snditer->second.begin();
mActiveSounds.erase(snditer++); while(sndname != snditer->second.end())
else
{ {
const MWWorld::Ptr &ptr = snditer->second.first; if(!sndname->first->isPlaying())
{
sndname = snditer->second.erase(sndname);
continue;
}
const MWWorld::Ptr &ptr = snditer->first;
if(!ptr.isEmpty()) if(!ptr.isEmpty())
{ {
const ESM::Position &pos = ptr.getRefData().getPosition(); const ESM::Position &pos = ptr.getRefData().getPosition();
const osg::Vec3f objpos(pos.asVec3()); const osg::Vec3f objpos(pos.asVec3());
snditer->first->setPosition(objpos); sndname->first->setPosition(objpos);
if ((snditer->first->mFlags & Play_RemoveAtDistance) if ((sndname->first->mFlags & Play_RemoveAtDistance)
&& (mListenerPos - ptr.getRefData().getPosition().asVec3()).length2() > 2000*2000) && (mListenerPos - ptr.getRefData().getPosition().asVec3()).length2() > 2000*2000)
{ {
mActiveSounds.erase(snditer++); sndname = snditer->second.erase(sndname);
continue; continue;
} }
} }
//update fade out //update fade out
if(snditer->first->mFadeOutTime>0) if(sndname->first->mFadeOutTime > 0.0f)
{ {
float soundDuration=duration; float soundDuration = duration;
if(soundDuration>snditer->first->mFadeOutTime) if(soundDuration > sndname->first->mFadeOutTime)
soundDuration=snditer->first->mFadeOutTime; soundDuration = sndname->first->mFadeOutTime;
snditer->first->setVolume(snditer->first->mVolume sndname->first->setVolume(sndname->first->mVolume
- soundDuration / snditer->first->mFadeOutTime * snditer->first->mVolume); - soundDuration / sndname->first->mFadeOutTime * sndname->first->mVolume);
snditer->first->mFadeOutTime -= soundDuration; sndname->first->mFadeOutTime -= soundDuration;
} }
snditer->first->update(); sndname->first->update();
++snditer; ++sndname;
} }
if(snditer->second.empty())
mActiveSounds.erase(snditer++);
else
++snditer;
} }
} }
@ -771,11 +804,14 @@ namespace MWSound
mVoiceVolume = Settings::Manager::getFloat("voice volume", "Sound"); mVoiceVolume = Settings::Manager::getFloat("voice volume", "Sound");
SoundMap::iterator snditer = mActiveSounds.begin(); SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end()) for(;snditer != mActiveSounds.end();++snditer)
{ {
snditer->first->mBaseVolume = volumeFromType(snditer->first->getPlayType()); SoundNamePairList::iterator sndname = snditer->second.begin();
snditer->first->update(); for(;sndname != snditer->second.end();++sndname)
++snditer; {
sndname->first->mBaseVolume = volumeFromType(sndname->first->getPlayType());
sndname->first->update();
}
} }
if(mMusic) if(mMusic)
{ {
@ -790,8 +826,7 @@ namespace MWSound
mListenerDir = dir; mListenerDir = dir;
mListenerUp = up; mListenerUp = up;
MWWorld::Ptr player = MWWorld::Ptr player = MWMechanics::getPlayer();
MWMechanics::getPlayer();
const MWWorld::CellStore *cell = player.getCell(); const MWWorld::CellStore *cell = player.getCell();
mListenerUnderwater = ((cell->getCell()->mData.mFlags&ESM::Cell::HasWater) && mListenerPos.z() < cell->getWaterLevel()); mListenerUnderwater = ((cell->getCell()->mData.mFlags&ESM::Cell::HasWater) && mListenerPos.z() < cell->getWaterLevel());
@ -799,10 +834,12 @@ namespace MWSound
void SoundManager::updatePtr(const MWWorld::Ptr &old, const MWWorld::Ptr &updated) void SoundManager::updatePtr(const MWWorld::Ptr &old, const MWWorld::Ptr &updated)
{ {
for (SoundMap::iterator snditer = mActiveSounds.begin(); snditer != mActiveSounds.end(); ++snditer) SoundMap::iterator snditer = mActiveSounds.find(old);
if(snditer != mActiveSounds.end())
{ {
if (snditer->second.first == old) SoundNamePairList sndlist = snditer->second;
snditer->second.first = updated; mActiveSounds.erase(snditer);
mActiveSounds[updated] = sndlist;
} }
} }
@ -873,9 +910,13 @@ namespace MWSound
void SoundManager::clear() void SoundManager::clear()
{ {
for (SoundMap::iterator iter (mActiveSounds.begin()); iter!=mActiveSounds.end(); ++iter) SoundMap::iterator snditer = mActiveSounds.begin();
iter->first->stop(); for(;snditer != mActiveSounds.end();++snditer)
{
SoundNamePairList::iterator sndname = snditer->second.begin();
for(;sndname != snditer->second.end();++sndname)
sndname->first->stop();
}
mActiveSounds.clear(); mActiveSounds.clear();
stopMusic(); stopMusic();
} }

View file

@ -53,8 +53,9 @@ namespace MWSound
boost::shared_ptr<Sound> mMusic; boost::shared_ptr<Sound> mMusic;
std::string mCurrentPlaylist; std::string mCurrentPlaylist;
typedef std::pair<MWWorld::Ptr,std::string> PtrIDPair; typedef std::pair<MWBase::SoundPtr,std::string> SoundNamePair;
typedef std::map<MWBase::SoundPtr,PtrIDPair> SoundMap; typedef std::vector<SoundNamePair> SoundNamePairList;
typedef std::map<MWWorld::Ptr,SoundNamePairList> SoundMap;
SoundMap mActiveSounds; SoundMap mActiveSounds;
MWBase::SoundPtr mUnderwaterSound; MWBase::SoundPtr mUnderwaterSound;