mirror of
https://github.com/OpenMW/openmw.git
synced 2025-02-05 17:45:34 +00:00
Improve save cleaning
This commit is contained in:
parent
cd9fb2adad
commit
86c50ece92
3 changed files with 50 additions and 1 deletions
|
@ -844,7 +844,12 @@ namespace MWWorld
|
||||||
if (type == 0)
|
if (type == 0)
|
||||||
{
|
{
|
||||||
Log(Debug::Warning) << "Dropping reference to '" << cref.mRefID << "' (object no longer exists)";
|
Log(Debug::Warning) << "Dropping reference to '" << cref.mRefID << "' (object no longer exists)";
|
||||||
reader.skipHSubUntil("OBJE");
|
// Skip until the next OBJE or MVRF
|
||||||
|
while(reader.hasMoreSubs() && !reader.peekNextSub("OBJE") && !reader.peekNextSub("MVRF"))
|
||||||
|
{
|
||||||
|
reader.getSubName();
|
||||||
|
reader.skipHSub();
|
||||||
|
}
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -109,6 +109,21 @@ namespace
|
||||||
|
|
||||||
return npcsToReplace;
|
return npcsToReplace;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Custom enchanted items can reference scripts that no longer exist, this doesn't necessarily mean the base item no longer exists however.
|
||||||
|
// So instead of removing the item altogether, we're only removing the script.
|
||||||
|
template<class T>
|
||||||
|
void removeMissingScripts(const MWWorld::Store<ESM::Script>& scripts, std::map<std::string, T>& items)
|
||||||
|
{
|
||||||
|
for(auto& [id, item] : items)
|
||||||
|
{
|
||||||
|
if(!item.mScript.empty() && !scripts.search(item.mScript))
|
||||||
|
{
|
||||||
|
item.mScript.clear();
|
||||||
|
Log(Debug::Verbose) << "Item '" << id << "' (" << item.mName << ") has nonexistent script '" << item.mScript << "', ignoring it.";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace MWWorld
|
namespace MWWorld
|
||||||
|
@ -366,6 +381,32 @@ void ESMStore::validateDynamic()
|
||||||
|
|
||||||
for (const ESM::NPC &npc : npcsToReplace)
|
for (const ESM::NPC &npc : npcsToReplace)
|
||||||
mNpcs.insert(npc);
|
mNpcs.insert(npc);
|
||||||
|
|
||||||
|
removeMissingScripts(mScripts, mArmors.mDynamic);
|
||||||
|
removeMissingScripts(mScripts, mBooks.mDynamic);
|
||||||
|
removeMissingScripts(mScripts, mClothes.mDynamic);
|
||||||
|
removeMissingScripts(mScripts, mWeapons.mDynamic);
|
||||||
|
|
||||||
|
removeMissingObjects(mCreatureLists);
|
||||||
|
removeMissingObjects(mItemLists);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Leveled lists can be modified by scripts. This removes items that no longer exist (presumably because the plugin was removed) from modified lists
|
||||||
|
template<class T>
|
||||||
|
void ESMStore::removeMissingObjects(Store<T>& store)
|
||||||
|
{
|
||||||
|
for(auto& [id, list] : store.mDynamic)
|
||||||
|
{
|
||||||
|
std::remove_if(list.mList.begin(), list.mList.end(), [&] (const auto& item)
|
||||||
|
{
|
||||||
|
if(!find(item.mId))
|
||||||
|
{
|
||||||
|
Log(Debug::Verbose) << "Leveled list '" << id << "' has nonexistent object '" << item.mId << "', ignoring it.";
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int ESMStore::countSavedGameRecords() const
|
int ESMStore::countSavedGameRecords() const
|
||||||
|
|
|
@ -89,6 +89,9 @@ namespace MWWorld
|
||||||
void validate();
|
void validate();
|
||||||
|
|
||||||
void countRecords();
|
void countRecords();
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
void removeMissingObjects(Store<T>& store);
|
||||||
public:
|
public:
|
||||||
/// \todo replace with SharedIterator<StoreBase>
|
/// \todo replace with SharedIterator<StoreBase>
|
||||||
typedef std::map<int, StoreBase *>::const_iterator iterator;
|
typedef std::map<int, StoreBase *>::const_iterator iterator;
|
||||||
|
|
Loading…
Reference in a new issue