From a0c7a0e2d34a13f2c3e86f662e352977ebe2ae73 Mon Sep 17 00:00:00 2001 From: Andrei Karas Date: Wed, 10 Apr 2013 00:33:27 +0300 Subject: Add option to left all per map sprites in memory if once was loaded. This can prevent random lags and also can use more memory. --- src/resources/resource.h | 8 ++++++++ src/resources/resourcemanager.cpp | 30 +++++++++++++++++++++++++++--- src/resources/resourcemanager.h | 3 +++ src/resources/spritedef.cpp | 10 ++++++++-- src/resources/spritedef.h | 2 +- 5 files changed, 47 insertions(+), 6 deletions(-) (limited to 'src/resources') diff --git a/src/resources/resource.h b/src/resources/resource.h index 2e73cd3f0..0577a3569 100644 --- a/src/resources/resource.h +++ b/src/resources/resource.h @@ -43,6 +43,7 @@ class Resource */ Resource() : mTimeStamp(0), + mProtected(false), #ifdef DEBUG_DUMP_LEAKS mRefCount(0), mDumped(false) @@ -86,6 +87,12 @@ class Resource std::string getSource() const A_WARN_UNUSED { return mSource; } + void setProtected(bool b) + { mProtected = b; } + + bool isProtected() const + { return mProtected; } + #ifdef DEBUG_DUMP_LEAKS bool getDumped() const A_WARN_UNUSED { return mDumped; } @@ -105,6 +112,7 @@ class Resource private: time_t mTimeStamp; /**< Time at which the resource was orphaned. */ + bool mProtected; unsigned mRefCount; /**< Reference count. */ #ifdef DEBUG_DUMP_LEAKS bool mDumped; diff --git a/src/resources/resourcemanager.cpp b/src/resources/resourcemanager.cpp index ef5ccf128..2baf09340 100644 --- a/src/resources/resourcemanager.cpp +++ b/src/resources/resourcemanager.cpp @@ -63,7 +63,8 @@ ResourceManager::ResourceManager() : mOldestOrphan(0), mSelectedSkin(""), mSkinName(""), - mDestruction(0) + mDestruction(0), + mUseLongLiveSprites(config.getBoolValue("uselonglivesprites")) { logger->log1("Initializing resource manager..."); } @@ -188,6 +189,27 @@ void ResourceManager::cleanUp(Resource *const res) #endif } +void ResourceManager::cleanProtected() +{ + ResourceIterator iter = mResources.begin(); + while (iter != mResources.end()) + { + Resource *res = iter->second; + if (!res) + { + ++ iter; + continue; + } + if (res->isProtected()) + { + res->setProtected(false); + res->decRef(); + } + + ++ iter; + } +} + bool ResourceManager::cleanOrphans(const bool always) { timeval tv; @@ -772,6 +794,7 @@ struct SpriteDefLoader { std::string path; int variant; + bool useLongLiveSprites; static Resource *load(const void *const v) { if (!v) @@ -779,14 +802,14 @@ struct SpriteDefLoader const SpriteDefLoader *const rl = static_cast(v); - return SpriteDef::load(rl->path, rl->variant); + return SpriteDef::load(rl->path, rl->variant, rl->useLongLiveSprites); } }; SpriteDef *ResourceManager::getSprite(const std::string &path, const int variant) { - SpriteDefLoader rl = { path, variant }; + SpriteDefLoader rl = { path, variant, mUseLongLiveSprites }; std::stringstream ss; ss << path << "[" << variant << "]"; return static_cast(get(ss.str(), SpriteDefLoader::load, &rl)); @@ -888,6 +911,7 @@ void ResourceManager::deleteInstance() if (instance) { logger->log("clean orphans start"); + instance->cleanProtected(); while (instance->cleanOrphans(true)); logger->log("clean orphans end"); ResourceIterator iter = instance->mResources.begin(); diff --git a/src/resources/resourcemanager.h b/src/resources/resourcemanager.h index 72efe8693..e2352136e 100644 --- a/src/resources/resourcemanager.h +++ b/src/resources/resourcemanager.h @@ -317,6 +317,8 @@ class ResourceManager final bool cleanOrphans(const bool always = false); + void cleanProtected(); + bool isInCache(const std::string &idPath) const A_WARN_UNUSED; Resource *getTempResource(const std::string &idPath) A_WARN_UNUSED; @@ -346,6 +348,7 @@ class ResourceManager final std::string mSelectedSkin; std::string mSkinName; bool mDestruction; + bool mUseLongLiveSprites; static DelayedAnim mDelayedAnimations; }; diff --git a/src/resources/spritedef.cpp b/src/resources/spritedef.cpp index ff9b71901..b417345fd 100644 --- a/src/resources/spritedef.cpp +++ b/src/resources/spritedef.cpp @@ -73,7 +73,8 @@ unsigned SpriteDef::findNumber(const unsigned num) const return min; } -SpriteDef *SpriteDef::load(const std::string &animationFile, const int variant) +SpriteDef *SpriteDef::load(const std::string &animationFile, + const int variant, bool prot) { const size_t pos = animationFile.find('|'); std::string palettes; @@ -90,7 +91,7 @@ SpriteDef *SpriteDef::load(const std::string &animationFile, const int variant) std::string errorFile = paths.getStringValue("sprites").append( paths.getStringValue("spriteErrorFile")); if (animationFile != errorFile) - return load(errorFile, 0); + return load(errorFile, 0, prot); else return nullptr; } @@ -101,6 +102,11 @@ SpriteDef *SpriteDef::load(const std::string &animationFile, const int variant) def->substituteActions(); if (serverVersion < 1) def->fixDeadAction(); + if (prot) + { + def->incRef(); + def->setProtected(true); + } return def; } diff --git a/src/resources/spritedef.h b/src/resources/spritedef.h index ebccc2bd7..3a8fe5a01 100644 --- a/src/resources/spritedef.h +++ b/src/resources/spritedef.h @@ -118,7 +118,7 @@ class SpriteDef final : public Resource * Loads a sprite definition file. */ static SpriteDef *load(const std::string &file, - const int variant) A_WARN_UNUSED; + const int variant, bool prot) A_WARN_UNUSED; /** * Returns the specified action. -- cgit v1.2.3-60-g2f50