diff options
Diffstat (limited to 'indra')
-rw-r--r-- | indra/newview/CMakeLists.txt | 2 | ||||
-rw-r--r-- | indra/newview/llface.cpp | 1 | ||||
-rw-r--r-- | indra/newview/llsculptidsize.cpp | 154 | ||||
-rw-r--r-- | indra/newview/llsculptidsize.h | 134 | ||||
-rw-r--r-- | indra/newview/llvovolume.cpp | 127 | ||||
-rw-r--r-- | indra/newview/llvovolume.h | 86 |
6 files changed, 312 insertions, 192 deletions
diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt index 2100c91cfe..1594711197 100644 --- a/indra/newview/CMakeLists.txt +++ b/indra/newview/CMakeLists.txt @@ -528,6 +528,7 @@ set(viewer_SOURCE_FILES llscriptfloater.cpp llscrollingpanelparam.cpp llscrollingpanelparambase.cpp + llsculptidsize.cpp llsearchcombobox.cpp llsearchhistory.cpp llsecapi.cpp @@ -1140,6 +1141,7 @@ set(viewer_HEADER_FILES llscriptruntimeperms.h llscrollingpanelparam.h llscrollingpanelparambase.h + llsculptidsize.h llsearchcombobox.h llsearchhistory.h llsecapi.h diff --git a/indra/newview/llface.cpp b/indra/newview/llface.cpp index 51bb2e3087..7f7d7f3dcc 100644 --- a/indra/newview/llface.cpp +++ b/indra/newview/llface.cpp @@ -53,6 +53,7 @@ #include "llviewershadermgr.h" #include "llviewertexture.h" #include "llvoavatar.h" +#include "llsculptidsize.h" #if LL_LINUX // Work-around spurious used before init warning on Vector4a diff --git a/indra/newview/llsculptidsize.cpp b/indra/newview/llsculptidsize.cpp new file mode 100644 index 0000000000..9edd78bff0 --- /dev/null +++ b/indra/newview/llsculptidsize.cpp @@ -0,0 +1,154 @@ +/** +* @file llsculptidsize.cpp +* @brief LLSculptIDSize class implementation +* +* $LicenseInfo:firstyear=2002&license=viewerlgpl$ +* Second Life Viewer Source Code +* Copyright (C) 2010, Linden Research, Inc. +* +* This library is free software; you can redistribute it and/or +* modify it under the terms of the GNU Lesser General Public +* License as published by the Free Software Foundation; +* version 2.1 of the License only. +* +* This library is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +* Lesser General Public License for more details. +* +* You should have received a copy of the GNU Lesser General Public +* License along with this library; if not, write to the Free Software +* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +* +* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA +* $/LicenseInfo$ +*/ + +#include "llviewerprecompiledheaders.h" +#include "llsculptidsize.h" +#include "llvovolume.h" +#include "lldrawable.h" +#include "llvoavatar.h" +//boost +#include "boost/make_shared.hpp" + +//........... + +extern LLControlGroup gSavedSettings; + +//........... + +typedef std::pair<LLSculptIDSize::container_BY_SCULPT_ID_view::iterator, LLSculptIDSize::container_BY_SCULPT_ID_view::iterator> pair_iter_iter_BY_SCULPT_ID_t; + +//........... + +void _nothing_to_do_func(int) { /*nothing todo here because of the size it's a shared member*/ } + +void LLSculptIDSize::inc(const LLDrawable *pdrawable, int sz) +{ + llassert(sz >= 0); + + if (!pdrawable) return; + LLVOVolume* vvol = pdrawable->getVOVolume(); + if (!vvol) return; + if (!vvol->isAttachment()) return; + if (!vvol->getAvatar()) return; + if (vvol->getAvatar()->isSelf()) return; + LLVolume *vol = vvol->getVolume(); + if (!vol) return; + + const LLUUID &sculptId = vol->getParams().getSculptID(); + if (sculptId.isNull()) return; + + unsigned int total_size = 0; + + pair_iter_iter_BY_SCULPT_ID_t itLU = mSizeInfo.get<tag_BY_SCULPT_ID>().equal_range(sculptId); + if (itLU.first == itLU.second) + { //register + llassert(mSizeInfo.get<tag_BY_DRAWABLE>().end() == mSizeInfo.get<tag_BY_DRAWABLE>().find(pdrawable)); + mSizeInfo.get<tag_BY_DRAWABLE>().insert(Info(pdrawable, sz, boost::make_shared<SizeSum>(sz), sculptId)); + total_size = sz; + } + else + { //update + register + Info &nfo = const_cast<Info &>(*itLU.first); + //calc new size + total_size = nfo.getSizeSum() + sz; + nfo.mSharedSizeSum->mSizeSum = total_size; + nfo.mSize = sz; + //update size for all LLDrwable in range of sculptId + for (pair_iter_iter_BY_SCULPT_ID_t::first_type it = itLU.first; it != itLU.second; ++it) + { + mSizeInfo.get<tag_BY_SIZE>().modify_key(mSizeInfo.project<tag_BY_SIZE>(it), boost::bind(&_nothing_to_do_func, _1)); + } + + //trying insert the LLDrawable + mSizeInfo.get<tag_BY_DRAWABLE>().insert(Info(pdrawable, sz, nfo.mSharedSizeSum, sculptId)); + } + + static LLCachedControl<U32> render_auto_mute_byte_limit(gSavedSettings, "RenderAutoMuteByteLimit", 0U); + + if (0 != render_auto_mute_byte_limit && total_size > render_auto_mute_byte_limit) + { + pair_iter_iter_BY_SCULPT_ID_t it_eqr = mSizeInfo.get<tag_BY_SCULPT_ID>().equal_range(sculptId); + for (; it_eqr.first != it_eqr.second; ++it_eqr.first) + { + const Info &i = *it_eqr.first; + LLVOVolume *pVVol = i.mDrawable->getVOVolume(); + if (pVVol + && !pVVol->isDead() + && pVVol->isAttachment() + && !pVVol->getAvatar()->isSelf() + && LLVOVolume::NO_LOD != pVVol->getLOD() + ) + { + addToUnloaded(sculptId); + //immediately + const_cast<LLDrawable*>(i.mDrawable)->unload(); + } + } + } +} + +void LLSculptIDSize::dec(const LLDrawable *pdrawable) +{ + container_BY_DRAWABLE_view::iterator it = mSizeInfo.get<tag_BY_DRAWABLE>().find(pdrawable); + if (mSizeInfo.get<tag_BY_DRAWABLE>().end() == it) return; + + unsigned int size = it->getSizeSum() - it->getSize(); + + if (0 == size) + { + mSizeInfo.get<tag_BY_SCULPT_ID>().erase(it->getSculptId()); + } + else + { + Info &nfo = const_cast<Info &>(*it); + nfo.mSize = 0; + pair_iter_iter_BY_SCULPT_ID_t itLU = mSizeInfo.get<tag_BY_SCULPT_ID>().equal_range(it->getSculptId()); + it->mSharedSizeSum->mSizeSum = size; + for (pair_iter_iter_BY_SCULPT_ID_t::first_type it = itLU.first; it != itLU.second; ++it) + { + mSizeInfo.get<tag_BY_SIZE>().modify_key(mSizeInfo.project<tag_BY_SIZE>(it), boost::bind(&_nothing_to_do_func, _1)); + } + } +} + +void LLSculptIDSize::rem(const LLUUID &sculptId) +{ + mSizeInfo.get<tag_BY_SCULPT_ID>().erase(sculptId); +} + +void LLSculptIDSize::resetSizeSum(const LLUUID &sculptId) +{ + const pair_iter_iter_BY_SCULPT_ID_t itLU = mSizeInfo.get<tag_BY_SCULPT_ID>().equal_range(sculptId); + + if (itLU.first != itLU.second) { + itLU.first->mSharedSizeSum->mSizeSum = 0; + } + + for (pair_iter_iter_BY_SCULPT_ID_t::first_type it = itLU.first, itE = itLU.second; it != itE; ++it) + { + mSizeInfo.get<tag_BY_SIZE>().modify_key(mSizeInfo.project<tag_BY_SIZE>(it), boost::bind(&_nothing_to_do_func, _1)); + } +} diff --git a/indra/newview/llsculptidsize.h b/indra/newview/llsculptidsize.h new file mode 100644 index 0000000000..87ee417b86 --- /dev/null +++ b/indra/newview/llsculptidsize.h @@ -0,0 +1,134 @@ +/** +* @file llsculptidsize.h +* @brief LLSculptIDSize class definition +* +* $LicenseInfo:firstyear=2009&license=viewerlgpl$ +* Second Life Viewer Source Code +* Copyright (C) 2010, Linden Research, Inc. +* +* This library is free software; you can redistribute it and/or +* modify it under the terms of the GNU Lesser General Public +* License as published by the Free Software Foundation; +* version 2.1 of the License only. +* +* This library is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +* Lesser General Public License for more details. +* +* You should have received a copy of the GNU Lesser General Public +* License along with this library; if not, write to the Free Software +* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +* +* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA +* $/LicenseInfo$ +*/ + +#ifndef LL_LLSCULPTIDSIZE_H +#define LL_LLSCULPTIDSIZE_H + +#include "lluuid.h" + +//std +#include <set> +//boost +#include "boost/multi_index_container.hpp" +#include "boost/multi_index/ordered_index.hpp" +#include "boost/multi_index/mem_fun.hpp" + +class LLDrawable; + + +class LLSculptIDSize +{ +public: + struct SizeSum + { + SizeSum(int size) + : mSizeSum(size) + {} + unsigned int mSizeSum; + }; + + struct Info + { + typedef boost::shared_ptr<SizeSum> PtrSizeSum; + + Info(const LLDrawable *drawable, int size, PtrSizeSum sizeInfo, LLUUID sculptId) + : mDrawable(drawable) + , mSize(size) + , mSharedSizeSum(sizeInfo) + , mSculptId(sculptId) + {} + + const LLDrawable *mDrawable; + unsigned int mSize; + PtrSizeSum mSharedSizeSum; + LLUUID mSculptId; + + inline const LLDrawable* getPtrLLDrawable() const { return mDrawable; } + inline unsigned int getSize() const { return mSize; } + inline unsigned int getSizeSum() const { return mSharedSizeSum->mSizeSum; } + inline LLUUID getSculptId() const { return mSculptId; } + PtrSizeSum getSizeInfo() { return mSharedSizeSum; } + }; + +public: + //tags + struct tag_BY_DRAWABLE {}; + struct tag_BY_SCULPT_ID {}; + struct tag_BY_SIZE {}; + + //container + typedef boost::multi_index_container < + Info, + boost::multi_index::indexed_by < + boost::multi_index::ordered_unique< boost::multi_index::tag<tag_BY_DRAWABLE> + , boost::multi_index::const_mem_fun<Info, const LLDrawable*, &Info::getPtrLLDrawable> + > + , boost::multi_index::ordered_non_unique<boost::multi_index::tag<tag_BY_SCULPT_ID> + , boost::multi_index::const_mem_fun<Info, LLUUID, &Info::getSculptId> + > + , boost::multi_index::ordered_non_unique < boost::multi_index::tag<tag_BY_SIZE> + , boost::multi_index::const_mem_fun < Info, unsigned int, &Info::getSizeSum > + > + > + > container; + + //views + typedef container::index<tag_BY_DRAWABLE>::type container_BY_DRAWABLE_view; + typedef container::index<tag_BY_SCULPT_ID>::type container_BY_SCULPT_ID_view; + typedef container::index<tag_BY_SIZE>::type container_BY_SIZE_view; + +private: + LLSculptIDSize() + {} + +public: + static LLSculptIDSize & instance() + { + static LLSculptIDSize inst; + return inst; + } + +public: + void inc(const LLDrawable *pdrawable, int sz); + void dec(const LLDrawable *pdrawable); + void rem(const LLUUID &sculptId); + + inline void addToUnloaded(const LLUUID &sculptId) { mMarkAsUnloaded.insert(sculptId); } + inline void remFromUnloaded(const LLUUID &sculptId) { mMarkAsUnloaded.erase(sculptId); } + inline bool isUnloaded(const LLUUID &sculptId) const { return mMarkAsUnloaded.end() != mMarkAsUnloaded.find(sculptId); } + inline void clearUnloaded() { mMarkAsUnloaded.clear(); } + + void resetSizeSum(const LLUUID &sculptId); + + inline const container & getSizeInfo() const { return mSizeInfo; } + +private: + container mSizeInfo; + typedef std::set<LLUUID> std_LLUUID; + std_LLUUID mMarkAsUnloaded; +}; + +#endif diff --git a/indra/newview/llvovolume.cpp b/indra/newview/llvovolume.cpp index 5292eb7067..4ea3c1b56b 100644 --- a/indra/newview/llvovolume.cpp +++ b/indra/newview/llvovolume.cpp @@ -78,6 +78,7 @@ #include "llvoavatar.h" #include "llvocache.h" #include "llmaterialmgr.h" +#include "llsculptidsize.h" const F32 FORCE_SIMPLE_RENDER_AREA = 512.f; const F32 FORCE_CULL_AREA = 8.f; @@ -1057,12 +1058,13 @@ BOOL LLVOVolume::setVolume(const LLVolumeParams ¶ms_in, const S32 detail, bo LLFace::cacheFaceInVRAM(face); } } - return TRUE; } - - + else if (NO_LOD == lod) + { + LLSculptIDSize::instance().resetSizeSum(volume_params.getSculptID()); + } return FALSE; } @@ -1304,7 +1306,8 @@ BOOL LLVOVolume::calcLOD() if (cur_detail != mLOD) { mAppAngle = ll_round((F32) atan2( mDrawable->getRadius(), mDrawable->mDistanceWRTCamera) * RAD_TO_DEG, 0.01f); - mLOD = cur_detail; + mLOD = cur_detail; + return TRUE; } @@ -1318,7 +1321,16 @@ BOOL LLVOVolume::updateLOD() return FALSE; } - BOOL lod_changed = calcLOD(); + BOOL lod_changed = FALSE; + + if (!LLSculptIDSize::instance().isUnloaded(getVolume()->getParams().getSculptID())) + { + lod_changed = calcLOD(); + } + else + { + return FALSE; + } if (lod_changed) { @@ -4679,6 +4691,7 @@ void handleRenderAutoMuteByteLimitChanged(const LLSD& new_value) { //postponed pVVol->markForUnload(); + LLSculptIDSize::instance().addToUnloaded(nfo.getSculptId()); } } @@ -4697,6 +4710,7 @@ void handleRenderAutoMuteByteLimitChanged(const LLSD& new_value) && LLVOVolume::NO_LOD == pVVol->getLOD() ) { + LLSculptIDSize::instance().remFromUnloaded(nfo.getSculptId()); pVVol->updateLOD(); pVVol->markForUpdate(TRUE); } @@ -4704,6 +4718,8 @@ void handleRenderAutoMuteByteLimitChanged(const LLSD& new_value) } else { + LLSculptIDSize::instance().clearUnloaded(); + LLSculptIDSize::container_BY_SIZE_view::iterator itL = LLSculptIDSize::instance().getSizeInfo().get<LLSculptIDSize::tag_BY_SIZE>().begin(), itU = LLSculptIDSize::instance().getSizeInfo().get<LLSculptIDSize::tag_BY_SIZE>().end(); @@ -6168,104 +6184,3 @@ void LLHUDPartition::shift(const LLVector4a &offset) { //HUD objects don't shift with region crossing. That would be silly. } - - -//........... - -void _nothing_to_do_func(int) { /*nothing todo here because of the size it's a shared member*/ } - -void LLSculptIDSize::inc(const LLDrawable *pdrawable, int sz) -{ - llassert(sz >= 0); - - if (!pdrawable) return; - LLVOVolume* vvol = pdrawable->getVOVolume(); - if (!vvol) return; - if (!vvol->isAttachment()) return; - if (!vvol->getAvatar()) return; - if (vvol->getAvatar()->isSelf()) return; - LLVolume *vol = vvol->getVolume(); - if (!vol) return; - - const LLUUID &sculptId = vol->getParams().getSculptID(); - - unsigned int total_size = 0; - - typedef std::pair<container_BY_SCULPT_ID_view::iterator, container_BY_SCULPT_ID_view::iterator> pair_iter_iter_t; - - pair_iter_iter_t itLU = m_size_info.get<tag_BY_SCULPT_ID>().equal_range(sculptId); - if (itLU.first == itLU.second) - { //register - llassert(m_size_info.get<tag_BY_DRAWABLE>().end() == m_size_info.get<tag_BY_DRAWABLE>().find(pdrawable)); - m_size_info.get<tag_BY_DRAWABLE>().insert(Info( pdrawable, sz, boost::make_shared<SizeInfo>(sz), sculptId )); - total_size = sz; - } - else - { //update + register - Info &nfo = const_cast<Info &>(*itLU.first); - //calc new size - total_size = nfo.getTotalSize() + sz; - nfo.m_p_size_info->m_size = total_size; - nfo.m_size = sz; - //update size for all LLDrwable in range of sculptId - for (pair_iter_iter_t::first_type it = itLU.first; it != itLU.second; ++it) - { - m_size_info.get<tag_BY_SIZE>().modify_key(m_size_info.project<tag_BY_SIZE>(it), boost::bind(&_nothing_to_do_func, _1)); - } - - //trying insert the LLDrawable - m_size_info.get<tag_BY_DRAWABLE>().insert(Info(pdrawable, sz, nfo.m_p_size_info, sculptId)); - } - - static LLCachedControl<U32> render_auto_mute_byte_limit(gSavedSettings, "RenderAutoMuteByteLimit", 0U); - - if (0 != render_auto_mute_byte_limit && total_size > render_auto_mute_byte_limit) - { - pair_iter_iter_t it_eqr = m_size_info.get<tag_BY_SCULPT_ID>().equal_range(sculptId); - for (; it_eqr.first != it_eqr.second; ++it_eqr.first) - { - const Info &i = *it_eqr.first; - LLVOVolume *pVVol = i.m_p_drawable->getVOVolume(); - if (pVVol - && !pVVol->isDead() - && pVVol->isAttachment() - && !pVVol->getAvatar()->isSelf() - && LLVOVolume::NO_LOD != pVVol->getLOD() - ) - { - //immediately - const_cast<LLDrawable*>(i.m_p_drawable)->unload(); - } - } - } -} - -void LLSculptIDSize::dec(const LLDrawable *pdrawable) -{ - container_BY_DRAWABLE_view::iterator it = m_size_info.get<tag_BY_DRAWABLE>().find(pdrawable); - if (m_size_info.get<tag_BY_DRAWABLE>().end() == it) return; - - unsigned int size = it->getTotalSize() - it->getSize(); - - if (0 == size) - { - m_size_info.get<tag_BY_SCULPT_ID>().erase(it->getSculptId()); - } - else - { - Info &nfo = const_cast<Info &>(*it); - nfo.m_size = 0; - typedef std::pair<container_BY_SCULPT_ID_view::iterator, container_BY_SCULPT_ID_view::iterator> pair_iter_iter_t; - pair_iter_iter_t itLU = m_size_info.get<tag_BY_SCULPT_ID>().equal_range(it->getSculptId()); - it->m_p_size_info->m_size = size; - for (pair_iter_iter_t::first_type it = itLU.first; it != itLU.second; ++it) - { - m_size_info.get<tag_BY_SIZE>().modify_key(m_size_info.project<tag_BY_SIZE>(it), boost::bind(&_nothing_to_do_func, _1)); - } - } -} - -void LLSculptIDSize::rem(LLUUID sculptId) -{ - m_size_info.get<tag_BY_SCULPT_ID>().erase(sculptId); -} diff --git a/indra/newview/llvovolume.h b/indra/newview/llvovolume.h index 09b342b153..2d9315df70 100644 --- a/indra/newview/llvovolume.h +++ b/indra/newview/llvovolume.h @@ -36,10 +36,6 @@ #include "m4math.h" // LLMatrix4 #include <map> #include <set> -//boost -#include "boost/multi_index_container.hpp" -#include "boost/multi_index/ordered_index.hpp" -#include "boost/multi_index/mem_fun.hpp" class LLViewerTextureAnim; @@ -418,87 +414,5 @@ private: }; -//........... - -class LLSculptIDSize -{ -public: - struct SizeInfo - { - SizeInfo(int size) : m_size(size) {} - unsigned int m_size; - }; - - struct Info - { - typedef boost::shared_ptr<SizeInfo> PtrSizeInfo; - - Info(const LLDrawable *pdrawable, int size, PtrSizeInfo psize_info, LLUUID sculpt_id) - : m_p_drawable(pdrawable) - , m_size(size) - , m_p_size_info(psize_info) - , m_sculpt_id(sculpt_id) - {} - - const LLDrawable *m_p_drawable; - unsigned int m_size; - PtrSizeInfo m_p_size_info; - LLUUID m_sculpt_id; - - inline const LLDrawable* getPtrLLDrawable() const { return m_p_drawable; } - inline unsigned int getSize() const { return m_size; } - inline unsigned int getTotalSize() const { return m_p_size_info->m_size; } - inline LLUUID getSculptId() const { return m_sculpt_id; } - PtrSizeInfo getSizeInfo() { return m_p_size_info; } - }; - -public: - //tags - struct tag_BY_DRAWABLE {}; - struct tag_BY_SCULPT_ID {}; - struct tag_BY_SIZE {}; - - //container - typedef boost::multi_index_container < - Info, - boost::multi_index::indexed_by < - boost::multi_index::ordered_unique< boost::multi_index::tag<tag_BY_DRAWABLE> - , boost::multi_index::const_mem_fun<Info, const LLDrawable*, &Info::getPtrLLDrawable> - > - , boost::multi_index::ordered_non_unique<boost::multi_index::tag<tag_BY_SCULPT_ID> - , boost::multi_index::const_mem_fun<Info, LLUUID, &Info::getSculptId> - > - , boost::multi_index::ordered_non_unique<boost::multi_index::tag<tag_BY_SIZE> - , boost::multi_index::const_mem_fun<Info, unsigned int, &Info::getTotalSize> - > - > - > container; - - //views - typedef container::index<tag_BY_DRAWABLE>::type container_BY_DRAWABLE_view; - typedef container::index<tag_BY_SCULPT_ID>::type container_BY_SCULPT_ID_view; - typedef container::index<tag_BY_SIZE>::type container_BY_SIZE_view; - -private: - LLSculptIDSize() - {} - -public: - static LLSculptIDSize & instance() { - static LLSculptIDSize inst; - return inst; - } - -public: - void inc(const LLDrawable *pdrawable, int sz); - void dec(const LLDrawable *pdrawable); - void rem(LLUUID sculptId); - - const container & getSizeInfo() const { return m_size_info; } - -private: - container m_size_info; -}; - #endif // LL_LLVOVOLUME_H |