mirror of
https://gitlab.com/OpenMW/openmw.git
synced 2025-03-28 19:21:04 +00:00
NPC. Still WIP.
This commit is contained in:
parent
f04a727af6
commit
03235bf0a2
@ -3,6 +3,7 @@
|
|||||||
#include <sstream>
|
#include <sstream>
|
||||||
#include <map>
|
#include <map>
|
||||||
#include <cassert>
|
#include <cassert>
|
||||||
|
#include <boost/graph/graph_concepts.hpp>
|
||||||
|
|
||||||
#include "../world/record.hpp"
|
#include "../world/record.hpp"
|
||||||
|
|
||||||
@ -22,7 +23,10 @@ CSMTools::ReferenceableCheckStage::ReferenceableCheckStage(const CSMWorld::RefId
|
|||||||
mIngredientsSize(mReferencables.getIngredients().getSize()),
|
mIngredientsSize(mReferencables.getIngredients().getSize()),
|
||||||
mCreaturesLevListsSize(mReferencables.getCreatureLevelledLists().getSize()),
|
mCreaturesLevListsSize(mReferencables.getCreatureLevelledLists().getSize()),
|
||||||
mItemLevelledListsSize(mReferencables.getItemLevelledList().getSize()),
|
mItemLevelledListsSize(mReferencables.getItemLevelledList().getSize()),
|
||||||
mLightsSize(mReferencables.getLights().getSize())
|
mLightsSize(mReferencables.getLights().getSize()),
|
||||||
|
mLockpicksSize(mReferencables.getLocpicks().getSize()),
|
||||||
|
mMiscellaneousSize(mReferencables.getMiscellaneous().getSize()),
|
||||||
|
mNPCsSize(mReferencables.getNPCs().getSize())
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -111,11 +115,35 @@ void CSMTools::ReferenceableCheckStage::perform(int stage, std::vector< std::str
|
|||||||
|
|
||||||
if (stage < mItemLevelledListsSize)
|
if (stage < mItemLevelledListsSize)
|
||||||
{
|
{
|
||||||
mItemLevelledListCheck(stage, mReferencables.getItemLevelledList(), messages);
|
itemLevelledListCheck(stage, mReferencables.getItemLevelledList(), messages);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
stage -= mItemLevelledListsSize;
|
stage -= mItemLevelledListsSize;
|
||||||
|
|
||||||
|
if (stage < mLightsSize)
|
||||||
|
{
|
||||||
|
lightCheck(stage, mReferencables.getLights(), messages);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
stage -= mLightsSize;
|
||||||
|
|
||||||
|
if (stage < mLockpicksSize)
|
||||||
|
{
|
||||||
|
lockpickCheck(stage, mReferencables.getLocpicks(), messages);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
stage -= mLockpicksSize;
|
||||||
|
|
||||||
|
if (stage < mMiscellaneousSize)
|
||||||
|
{
|
||||||
|
miscCheck(stage, mReferencables.getMiscellaneous(), messages);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
stage -= mMiscellaneousSize;
|
||||||
}
|
}
|
||||||
|
|
||||||
int CSMTools::ReferenceableCheckStage::setup()
|
int CSMTools::ReferenceableCheckStage::setup()
|
||||||
@ -602,7 +630,7 @@ void CSMTools::ReferenceableCheckStage::creaturesLevListCheck(int stage, const C
|
|||||||
const ESM::CreatureLevList& CreatureLevList = (static_cast<const CSMWorld::Record<ESM::CreatureLevList>& >(baserecord)).get();
|
const ESM::CreatureLevList& CreatureLevList = (static_cast<const CSMWorld::Record<ESM::CreatureLevList>& >(baserecord)).get();
|
||||||
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_CreatureLevelledList, CreatureLevList.mId); //CreatureLevList but Type_CreatureLevelledList :/
|
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_CreatureLevelledList, CreatureLevList.mId); //CreatureLevList but Type_CreatureLevelledList :/
|
||||||
|
|
||||||
for (int i = 0; i < CreatureLevList.mList.size(); ++i)
|
for (unsigned i = 0; i < CreatureLevList.mList.size(); ++i)
|
||||||
{
|
{
|
||||||
if (CreatureLevList.mList[i].mId.empty())
|
if (CreatureLevList.mList[i].mId.empty())
|
||||||
{
|
{
|
||||||
@ -614,14 +642,9 @@ void CSMTools::ReferenceableCheckStage::creaturesLevListCheck(int stage, const C
|
|||||||
messages.push_back(id.toString() + "|" + CreatureLevList.mId + " contains item with non-positive level");
|
messages.push_back(id.toString() + "|" + CreatureLevList.mId + " contains item with non-positive level");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CreatureLevList.mChanceNone < 0 or CreatureLevList.mChanceNone > 100)
|
|
||||||
{
|
|
||||||
messages.push_back(id.toString() + "|" + CreatureLevList.mId + " chance to be empty is not beetween 0 and 100");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSMTools::ReferenceableCheckStage::mItemLevelledListCheck(int stage, const CSMWorld::RefIdDataContainer< ESM::ItemLevList >& records, std::vector< std::string >& messages)
|
void CSMTools::ReferenceableCheckStage::itemLevelledListCheck(int stage, const CSMWorld::RefIdDataContainer< ESM::ItemLevList >& records, std::vector< std::string >& messages)
|
||||||
{
|
{
|
||||||
const CSMWorld::RecordBase& baserecord = records.getRecord(stage);
|
const CSMWorld::RecordBase& baserecord = records.getRecord(stage);
|
||||||
|
|
||||||
@ -633,7 +656,7 @@ void CSMTools::ReferenceableCheckStage::mItemLevelledListCheck(int stage, const
|
|||||||
const ESM::ItemLevList& ItemLevList = (static_cast<const CSMWorld::Record<ESM::ItemLevList>& >(baserecord)).get();
|
const ESM::ItemLevList& ItemLevList = (static_cast<const CSMWorld::Record<ESM::ItemLevList>& >(baserecord)).get();
|
||||||
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_ItemLevelledList, ItemLevList.mId);
|
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_ItemLevelledList, ItemLevList.mId);
|
||||||
|
|
||||||
for (int i = 0; i < ItemLevList.mList.size(); ++i)
|
for (unsigned i = 0; i < ItemLevList.mList.size(); ++i)
|
||||||
{
|
{
|
||||||
if (ItemLevList.mList[i].mId.empty())
|
if (ItemLevList.mList[i].mId.empty())
|
||||||
{
|
{
|
||||||
@ -645,9 +668,222 @@ void CSMTools::ReferenceableCheckStage::mItemLevelledListCheck(int stage, const
|
|||||||
messages.push_back(id.toString() + "|" + ItemLevList.mId + " contains item with non-positive level");
|
messages.push_back(id.toString() + "|" + ItemLevList.mId + " contains item with non-positive level");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (ItemLevList.mChanceNone < 0 or ItemLevList.mChanceNone > 100)
|
void CSMTools::ReferenceableCheckStage::lightCheck(int stage, const CSMWorld::RefIdDataContainer< ESM::Light >& records, std::vector< std::string >& messages)
|
||||||
|
{
|
||||||
|
const CSMWorld::RecordBase& baserecord = records.getRecord(stage);
|
||||||
|
|
||||||
|
if (baserecord.isDeleted())
|
||||||
{
|
{
|
||||||
messages.push_back(id.toString() + "|" + ItemLevList.mId + " chance to be empty is not beetween 0 and 100");
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ESM::Light& Light = (static_cast<const CSMWorld::Record<ESM::Light>& >(baserecord)).get();
|
||||||
|
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_Light, Light.mId);
|
||||||
|
|
||||||
|
if (Light.mData.mRadius < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Light.mId + " has negative light radius");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Light.mData.mFlags & ESM::Light::Carry)
|
||||||
|
{
|
||||||
|
if (Light.mIcon.empty()) //Needs to be checked with carrable flag
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Light.mId + " has no icon");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Light.mData.mWeight < 0) //probabbly needs to be checked only for carrable lights TODO
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Light.mId + " has negative weight");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Light.mData.mValue < 0) //probabbly needs to be checked only for carrable lights TODO
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Light.mId + " has negative value");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Light.mModel.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Light.mId + " has no model");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Light.mData.mTime < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Light.mId + " has negative duration");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CSMTools::ReferenceableCheckStage::lockpickCheck(int stage, const CSMWorld::RefIdDataContainer< ESM::Lockpick >& records, std::vector< std::string >& messages)
|
||||||
|
{
|
||||||
|
const CSMWorld::RecordBase& baserecord = records.getRecord(stage);
|
||||||
|
|
||||||
|
if (baserecord.isDeleted())
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ESM::Lockpick& Lockpick = (static_cast<const CSMWorld::Record<ESM::Lockpick>& >(baserecord)).get();
|
||||||
|
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_Lockpick, Lockpick.mId);
|
||||||
|
|
||||||
|
//Checking for name
|
||||||
|
if (Lockpick.mName.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has an empty name");
|
||||||
|
}
|
||||||
|
|
||||||
|
//Checking for weight
|
||||||
|
if (Lockpick.mData.mWeight < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has negative weight");
|
||||||
|
}
|
||||||
|
|
||||||
|
//Checking for value
|
||||||
|
if (Lockpick.mData.mValue < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has negative value");
|
||||||
|
}
|
||||||
|
|
||||||
|
//checking for model
|
||||||
|
if (Lockpick.mModel.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has no model");
|
||||||
|
}
|
||||||
|
|
||||||
|
//checking for icon
|
||||||
|
if (Lockpick.mIcon.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has no icon");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Lockpick.mData.mQuality <= 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has non-positive quality");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Lockpick.mData.mUses <= 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Lockpick.mId + " has no uses left");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void CSMTools::ReferenceableCheckStage::miscCheck(int stage, const CSMWorld::RefIdDataContainer< ESM::Miscellaneous >& records, std::vector< std::string >& messages)
|
||||||
|
{
|
||||||
|
const CSMWorld::RecordBase& baserecord = records.getRecord(stage);
|
||||||
|
|
||||||
|
if (baserecord.isDeleted())
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ESM::Miscellaneous& Miscellaneous = (static_cast<const CSMWorld::Record<ESM::Miscellaneous>& >(baserecord)).get();
|
||||||
|
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_Miscellaneous, Miscellaneous.mId);
|
||||||
|
|
||||||
|
//Checking for name
|
||||||
|
if (Miscellaneous.mName.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Miscellaneous.mId + " has an empty name");
|
||||||
|
}
|
||||||
|
|
||||||
|
//Checking for weight
|
||||||
|
if (Miscellaneous.mData.mWeight < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Miscellaneous.mId + " has negative weight");
|
||||||
|
}
|
||||||
|
|
||||||
|
//Checking for value
|
||||||
|
if (Miscellaneous.mData.mValue < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Miscellaneous.mId + " has negative value");
|
||||||
|
}
|
||||||
|
|
||||||
|
//checking for model
|
||||||
|
if (Miscellaneous.mModel.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Miscellaneous.mId + " has no model");
|
||||||
|
}
|
||||||
|
|
||||||
|
//checking for icon
|
||||||
|
if (Miscellaneous.mIcon.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + Miscellaneous.mId + " has no icon");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void CSMTools::ReferenceableCheckStage::npcCheck(int stage, const CSMWorld::RefIdDataContainer< ESM::NPC >& records, std::vector< std::string >& messages)
|
||||||
|
{
|
||||||
|
const CSMWorld::RecordBase& baserecord = records.getRecord(stage);
|
||||||
|
|
||||||
|
if (baserecord.isDeleted())
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ESM::NPC& NPC = (static_cast<const CSMWorld::Record<ESM::NPC>& >(baserecord)).get();
|
||||||
|
CSMWorld::UniversalId id(CSMWorld::UniversalId::Type_Npc, NPC.mId);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
short level(NPC.mNpdt52.mLevel);
|
||||||
|
char Disposition(NPC.mNpdt52.mDisposition);
|
||||||
|
char Reputation(NPC.mNpdt52.mReputation);
|
||||||
|
char Rank(NPC.mNpdt52.mRank);
|
||||||
|
//Don't know what unknown is for
|
||||||
|
int Gold(NPC.mNpdt52.mGold);
|
||||||
|
|
||||||
|
if (NPC.mNpdtType == 12)
|
||||||
|
{
|
||||||
|
if (NPC.mFlags ^ ESM::NPC::Flags::Autocalc)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " mNpdtType and flags mismatch!"); //should not happend?
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
level = NPC.mNpdt12.mLevel;
|
||||||
|
Disposition = NPC.mNpdt12.mDisposition;
|
||||||
|
Reputation = NPC.mNpdt12.mReputation;
|
||||||
|
Rank = NPC.mNpdt12.mRank;
|
||||||
|
Gold = NPC.mNpdt12.mGold;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (NPC.mNpdt52.mHealth < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " health is negative value");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (NPC.mNpdt52.mMana < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " mana is negative value");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (NPC.mNpdt52.mFatigue < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " fatigue is negative value");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (level < 1)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " level is non positive");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Gold < 0)
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " gold is negative value");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (NPC.mName.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " has any empty name");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (NPC.mClass.empty())
|
||||||
|
{
|
||||||
|
messages.push_back(id.toString() + "|" + NPC.mId + " has any empty class");
|
||||||
|
}
|
||||||
|
|
||||||
|
//TODO: reputation, Disposition, rank, everything else
|
||||||
|
}
|
||||||
|
@ -28,7 +28,11 @@ namespace CSMTools
|
|||||||
void doorCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Door>& records, std::vector<std::string>& messages);
|
void doorCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Door>& records, std::vector<std::string>& messages);
|
||||||
void ingredientCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Ingredient>& records, std::vector<std::string>& messages);
|
void ingredientCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Ingredient>& records, std::vector<std::string>& messages);
|
||||||
void creaturesLevListCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::CreatureLevList>& records, std::vector<std::string>& messages);
|
void creaturesLevListCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::CreatureLevList>& records, std::vector<std::string>& messages);
|
||||||
void mItemLevelledListCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::ItemLevList>& records, std::vector<std::string>& messages);
|
void itemLevelledListCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::ItemLevList>& records, std::vector<std::string>& messages);
|
||||||
|
void lightCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Light>& records, std::vector<std::string>& messages);
|
||||||
|
void lockpickCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Lockpick>& records, std::vector<std::string>& messages);
|
||||||
|
void miscCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::Miscellaneous>& records, std::vector<std::string>& messages);
|
||||||
|
void npcCheck(int stage, const CSMWorld::RefIdDataContainer<ESM::NPC>& records, std::vector<std::string>& messages);
|
||||||
|
|
||||||
const CSMWorld::RefIdData mReferencables;
|
const CSMWorld::RefIdData mReferencables;
|
||||||
|
|
||||||
@ -46,6 +50,9 @@ namespace CSMTools
|
|||||||
const int mCreaturesLevListsSize;
|
const int mCreaturesLevListsSize;
|
||||||
const int mItemLevelledListsSize;
|
const int mItemLevelledListsSize;
|
||||||
const int mLightsSize;
|
const int mLightsSize;
|
||||||
|
const int mLockpicksSize;
|
||||||
|
const int mMiscellaneousSize;
|
||||||
|
const int mNPCsSize;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
#endif // REFERENCEABLECHECKSTAGE_H
|
#endif // REFERENCEABLECHECKSTAGE_H
|
||||||
|
@ -9,187 +9,187 @@ CSMWorld::RefIdDataContainerBase::~RefIdDataContainerBase() {}
|
|||||||
|
|
||||||
CSMWorld::RefIdData::RefIdData()
|
CSMWorld::RefIdData::RefIdData()
|
||||||
{
|
{
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Activator, &mActivators));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Activator, &mActivators));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Potion, &mPotions));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Potion, &mPotions));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Apparatus, &mApparati));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Apparatus, &mApparati));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Armor, &mArmors));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Armor, &mArmors));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Book, &mBooks));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Book, &mBooks));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Clothing, &mClothing));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Clothing, &mClothing));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Container, &mContainers));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Container, &mContainers));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Creature, &mCreatures));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Creature, &mCreatures));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Door, &mDoors));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Door, &mDoors));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Ingredient, &mIngredients));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Ingredient, &mIngredients));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_CreatureLevelledList,
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_CreatureLevelledList,
|
||||||
&mCreatureLevelledLists));
|
&mCreatureLevelledLists));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_ItemLevelledList, &mItemLevelledLists));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_ItemLevelledList, &mItemLevelledLists));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Light, &mLights));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Light, &mLights));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Lockpick, &mLockpicks));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Lockpick, &mLockpicks));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Miscellaneous, &mMiscellaneous));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Miscellaneous, &mMiscellaneous));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Npc, &mNpcs));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Npc, &mNpcs));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Probe, &mProbes));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Probe, &mProbes));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Repair, &mRepairs));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Repair, &mRepairs));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Static, &mStatics));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Static, &mStatics));
|
||||||
mRecordContainers.insert (std::make_pair (UniversalId::Type_Weapon, &mWeapons));
|
mRecordContainers.insert(std::make_pair(UniversalId::Type_Weapon, &mWeapons));
|
||||||
}
|
}
|
||||||
|
|
||||||
CSMWorld::RefIdData::LocalIndex CSMWorld::RefIdData::globalToLocalIndex (int index) const
|
CSMWorld::RefIdData::LocalIndex CSMWorld::RefIdData::globalToLocalIndex(int index) const
|
||||||
{
|
{
|
||||||
for (std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator iter (
|
for (std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator iter(
|
||||||
mRecordContainers.begin()); iter!=mRecordContainers.end(); ++iter)
|
mRecordContainers.begin()); iter != mRecordContainers.end(); ++iter)
|
||||||
{
|
{
|
||||||
if (index<iter->second->getSize())
|
if (index < iter->second->getSize())
|
||||||
return LocalIndex (index, iter->first);
|
return LocalIndex(index, iter->first);
|
||||||
|
|
||||||
index -= iter->second->getSize();
|
index -= iter->second->getSize();
|
||||||
}
|
}
|
||||||
|
|
||||||
throw std::runtime_error ("RefIdData index out of range");
|
throw std::runtime_error("RefIdData index out of range");
|
||||||
}
|
}
|
||||||
|
|
||||||
int CSMWorld::RefIdData::localToGlobalIndex (const LocalIndex& index)
|
int CSMWorld::RefIdData::localToGlobalIndex(const LocalIndex& index)
|
||||||
const
|
const
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator end =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator end =
|
||||||
mRecordContainers.find (index.second);
|
mRecordContainers.find(index.second);
|
||||||
|
|
||||||
if (end==mRecordContainers.end())
|
if (end == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
int globalIndex = index.first;
|
int globalIndex = index.first;
|
||||||
|
|
||||||
for (std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator iter (
|
for (std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator iter(
|
||||||
mRecordContainers.begin()); iter!=end; ++iter)
|
mRecordContainers.begin()); iter != end; ++iter)
|
||||||
globalIndex += iter->second->getSize();
|
globalIndex += iter->second->getSize();
|
||||||
|
|
||||||
return globalIndex;
|
return globalIndex;
|
||||||
}
|
}
|
||||||
|
|
||||||
CSMWorld::RefIdData::LocalIndex CSMWorld::RefIdData::searchId (
|
CSMWorld::RefIdData::LocalIndex CSMWorld::RefIdData::searchId(
|
||||||
const std::string& id) const
|
const std::string& id) const
|
||||||
{
|
{
|
||||||
std::string id2 = Misc::StringUtils::lowerCase (id);
|
std::string id2 = Misc::StringUtils::lowerCase(id);
|
||||||
|
|
||||||
std::map<std::string, std::pair<int, UniversalId::Type> >::const_iterator iter = mIndex.find (id2);
|
std::map<std::string, std::pair<int, UniversalId::Type> >::const_iterator iter = mIndex.find(id2);
|
||||||
|
|
||||||
if (iter==mIndex.end())
|
if (iter == mIndex.end())
|
||||||
return std::make_pair (-1, CSMWorld::UniversalId::Type_None);
|
return std::make_pair(-1, CSMWorld::UniversalId::Type_None);
|
||||||
|
|
||||||
return iter->second;
|
return iter->second;
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSMWorld::RefIdData::erase (int index, int count)
|
void CSMWorld::RefIdData::erase(int index, int count)
|
||||||
{
|
{
|
||||||
LocalIndex localIndex = globalToLocalIndex (index);
|
LocalIndex localIndex = globalToLocalIndex(index);
|
||||||
|
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator iter =
|
||||||
mRecordContainers.find (localIndex.second);
|
mRecordContainers.find(localIndex.second);
|
||||||
|
|
||||||
while (count>0 && iter!=mRecordContainers.end())
|
while (count > 0 && iter != mRecordContainers.end())
|
||||||
{
|
{
|
||||||
int size = iter->second->getSize();
|
int size = iter->second->getSize();
|
||||||
|
|
||||||
if (localIndex.first+count>size)
|
if (localIndex.first + count > size)
|
||||||
{
|
{
|
||||||
erase (localIndex, size-localIndex.first);
|
erase(localIndex, size - localIndex.first);
|
||||||
count -= size-localIndex.first;
|
count -= size - localIndex.first;
|
||||||
|
|
||||||
++iter;
|
++iter;
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::runtime_error ("invalid count value for erase operation");
|
throw std::runtime_error("invalid count value for erase operation");
|
||||||
|
|
||||||
localIndex.first = 0;
|
localIndex.first = 0;
|
||||||
localIndex.second = iter->first;
|
localIndex.second = iter->first;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
erase (localIndex, count);
|
erase(localIndex, count);
|
||||||
count = 0;
|
count = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const CSMWorld::RecordBase& CSMWorld::RefIdData::getRecord (const LocalIndex& index) const
|
const CSMWorld::RecordBase& CSMWorld::RefIdData::getRecord(const LocalIndex& index) const
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator iter =
|
||||||
mRecordContainers.find (index.second);
|
mRecordContainers.find(index.second);
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
return iter->second->getRecord (index.first);
|
return iter->second->getRecord(index.first);
|
||||||
}
|
}
|
||||||
|
|
||||||
CSMWorld::RecordBase& CSMWorld::RefIdData::getRecord (const LocalIndex& index)
|
CSMWorld::RecordBase& CSMWorld::RefIdData::getRecord(const LocalIndex& index)
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::iterator iter =
|
||||||
mRecordContainers.find (index.second);
|
mRecordContainers.find(index.second);
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
return iter->second->getRecord (index.first);
|
return iter->second->getRecord(index.first);
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSMWorld::RefIdData::appendRecord (UniversalId::Type type, const std::string& id)
|
void CSMWorld::RefIdData::appendRecord(UniversalId::Type type, const std::string& id)
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::iterator iter =
|
||||||
mRecordContainers.find (type);
|
mRecordContainers.find(type);
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
iter->second->appendRecord (id);
|
iter->second->appendRecord(id);
|
||||||
|
|
||||||
mIndex.insert (std::make_pair (Misc::StringUtils::lowerCase (id),
|
mIndex.insert(std::make_pair(Misc::StringUtils::lowerCase(id),
|
||||||
LocalIndex (iter->second->getSize()-1, type)));
|
LocalIndex(iter->second->getSize() - 1, type)));
|
||||||
}
|
}
|
||||||
|
|
||||||
int CSMWorld::RefIdData::getAppendIndex (UniversalId::Type type) const
|
int CSMWorld::RefIdData::getAppendIndex(UniversalId::Type type) const
|
||||||
{
|
{
|
||||||
int index = 0;
|
int index = 0;
|
||||||
|
|
||||||
for (std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator iter (
|
for (std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator iter(
|
||||||
mRecordContainers.begin()); iter!=mRecordContainers.end(); ++iter)
|
mRecordContainers.begin()); iter != mRecordContainers.end(); ++iter)
|
||||||
{
|
{
|
||||||
index += iter->second->getSize();
|
index += iter->second->getSize();
|
||||||
|
|
||||||
if (type==iter->first)
|
if (type == iter->first)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return index;
|
return index;
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSMWorld::RefIdData::load (const LocalIndex& index, ESM::ESMReader& reader, bool base)
|
void CSMWorld::RefIdData::load(const LocalIndex& index, ESM::ESMReader& reader, bool base)
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::iterator iter =
|
||||||
mRecordContainers.find (index.second);
|
mRecordContainers.find(index.second);
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
iter->second->load (index.first, reader, base);
|
iter->second->load(index.first, reader, base);
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSMWorld::RefIdData::erase (const LocalIndex& index, int count)
|
void CSMWorld::RefIdData::erase(const LocalIndex& index, int count)
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::iterator iter =
|
||||||
mRecordContainers.find (index.second);
|
mRecordContainers.find(index.second);
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
for (int i=index.first; i<index.first+count; ++i)
|
for (int i = index.first; i < index.first + count; ++i)
|
||||||
{
|
{
|
||||||
std::map<std::string, LocalIndex>::iterator result =
|
std::map<std::string, LocalIndex>::iterator result =
|
||||||
mIndex.find (Misc::StringUtils::lowerCase (iter->second->getId (i)));
|
mIndex.find(Misc::StringUtils::lowerCase(iter->second->getId(i)));
|
||||||
|
|
||||||
if (result!=mIndex.end())
|
if (result != mIndex.end())
|
||||||
mIndex.erase (result);
|
mIndex.erase(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
iter->second->erase (index.first, count);
|
iter->second->erase(index.first, count);
|
||||||
}
|
}
|
||||||
|
|
||||||
int CSMWorld::RefIdData::getSize() const
|
int CSMWorld::RefIdData::getSize() const
|
||||||
@ -197,39 +197,39 @@ int CSMWorld::RefIdData::getSize() const
|
|||||||
return mIndex.size();
|
return mIndex.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> CSMWorld::RefIdData::getIds (bool listDeleted) const
|
std::vector<std::string> CSMWorld::RefIdData::getIds(bool listDeleted) const
|
||||||
{
|
{
|
||||||
std::vector<std::string> ids;
|
std::vector<std::string> ids;
|
||||||
|
|
||||||
for (std::map<std::string, LocalIndex>::const_iterator iter (mIndex.begin()); iter!=mIndex.end();
|
for (std::map<std::string, LocalIndex>::const_iterator iter(mIndex.begin()); iter != mIndex.end();
|
||||||
++iter)
|
++iter)
|
||||||
{
|
{
|
||||||
if (listDeleted || !getRecord (iter->second).isDeleted())
|
if (listDeleted || !getRecord(iter->second).isDeleted())
|
||||||
{
|
{
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator container =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator container =
|
||||||
mRecordContainers.find (iter->second.second);
|
mRecordContainers.find(iter->second.second);
|
||||||
|
|
||||||
if (container==mRecordContainers.end())
|
if (container == mRecordContainers.end())
|
||||||
throw std::logic_error ("Invalid referenceable ID type");
|
throw std::logic_error("Invalid referenceable ID type");
|
||||||
|
|
||||||
ids.push_back (container->second->getId (iter->second.first));
|
ids.push_back(container->second->getId(iter->second.first));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return ids;
|
return ids;
|
||||||
}
|
}
|
||||||
|
|
||||||
void CSMWorld::RefIdData::save (int index, ESM::ESMWriter& writer) const
|
void CSMWorld::RefIdData::save(int index, ESM::ESMWriter& writer) const
|
||||||
{
|
{
|
||||||
LocalIndex localIndex = globalToLocalIndex (index);
|
LocalIndex localIndex = globalToLocalIndex(index);
|
||||||
|
|
||||||
std::map<UniversalId::Type, RefIdDataContainerBase *>::const_iterator iter =
|
std::map<UniversalId::Type, RefIdDataContainerBase*>::const_iterator iter =
|
||||||
mRecordContainers.find (localIndex.second);
|
mRecordContainers.find(localIndex.second);
|
||||||
|
|
||||||
if (iter==mRecordContainers.end())
|
if (iter == mRecordContainers.end())
|
||||||
throw std::logic_error ("invalid local index type");
|
throw std::logic_error("invalid local index type");
|
||||||
|
|
||||||
iter->second->save (localIndex.first, writer);
|
iter->second->save(localIndex.first, writer);
|
||||||
}
|
}
|
||||||
|
|
||||||
const CSMWorld::RefIdDataContainer< ESM::Book >& CSMWorld::RefIdData::getBooks() const
|
const CSMWorld::RefIdDataContainer< ESM::Book >& CSMWorld::RefIdData::getBooks() const
|
||||||
@ -296,3 +296,18 @@ const CSMWorld::RefIdDataContainer< ESM::Light >& CSMWorld::RefIdData::getLights
|
|||||||
{
|
{
|
||||||
return mLights;
|
return mLights;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const CSMWorld::RefIdDataContainer< ESM::Lockpick >& CSMWorld::RefIdData::getLocpicks() const
|
||||||
|
{
|
||||||
|
return mLockpicks;
|
||||||
|
}
|
||||||
|
|
||||||
|
const CSMWorld::RefIdDataContainer< ESM::Miscellaneous >& CSMWorld::RefIdData::getMiscellaneous() const
|
||||||
|
{
|
||||||
|
return mMiscellaneous;
|
||||||
|
}
|
||||||
|
|
||||||
|
const CSMWorld::RefIdDataContainer< ESM::NPC >& CSMWorld::RefIdData::getNPCs() const
|
||||||
|
{
|
||||||
|
return mNpcs;
|
||||||
|
}
|
||||||
|
@ -234,7 +234,11 @@ namespace CSMWorld
|
|||||||
const RefIdDataContainer<ESM::CreatureLevList>& getCreatureLevelledLists() const;
|
const RefIdDataContainer<ESM::CreatureLevList>& getCreatureLevelledLists() const;
|
||||||
const RefIdDataContainer<ESM::ItemLevList>& getItemLevelledList() const;
|
const RefIdDataContainer<ESM::ItemLevList>& getItemLevelledList() const;
|
||||||
const RefIdDataContainer<ESM::Light>& getLights() const;
|
const RefIdDataContainer<ESM::Light>& getLights() const;
|
||||||
|
const RefIdDataContainer<ESM::Lockpick>& getLocpicks() const;
|
||||||
|
const RefIdDataContainer<ESM::Miscellaneous>& getMiscellaneous() const;
|
||||||
|
const RefIdDataContainer<ESM::NPC>& getNPCs() const;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -105,7 +105,7 @@ struct NPC
|
|||||||
|
|
||||||
char mNpdtType;
|
char mNpdtType;
|
||||||
NPDTstruct52 mNpdt52;
|
NPDTstruct52 mNpdt52;
|
||||||
NPDTstruct12 mNpdt12; // Use this if npdt52.gold == -10
|
NPDTstruct12 mNpdt12; //for autocalculated characters
|
||||||
|
|
||||||
int mFlags;
|
int mFlags;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user