From 51bfa5cde3be379ceb1ebc541bbb830dc05c8f68 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 10 Dec 2013 15:09:58 +0100 Subject: [PATCH] rewrote global variable storage (using ESM variant type now) --- apps/openmw/mwworld/globals.cpp | 132 ++++++------------------------- apps/openmw/mwworld/globals.hpp | 49 ++++-------- apps/openmw/mwworld/worldimp.cpp | 75 +++++++++--------- apps/openmw/mwworld/worldimp.hpp | 3 +- 4 files changed, 80 insertions(+), 179 deletions(-) diff --git a/apps/openmw/mwworld/globals.cpp b/apps/openmw/mwworld/globals.cpp index a905f8aae..19bfa1529 100644 --- a/apps/openmw/mwworld/globals.cpp +++ b/apps/openmw/mwworld/globals.cpp @@ -7,15 +7,14 @@ namespace MWWorld { - std::vector Globals::getGlobals () const + std::vector Globals::getGlobals() const { - std::vector retval; - Collection::const_iterator it; - for(it = mVariables.begin(); it != mVariables.end(); ++it){ - retval.push_back(it->first); - } + std::vector ids; - return retval; + for (Collection::const_iterator iter = mVariables.begin(); iter!=mVariables.end(); ++iter) + ids.push_back (iter->first); + + return ids; } Globals::Collection::const_iterator Globals::find (const std::string& name) const @@ -38,112 +37,27 @@ namespace MWWorld return iter; } - Globals::Globals (const MWWorld::ESMStore& store) + void Globals::fill (const MWWorld::ESMStore& store) { - const MWWorld::Store &globals = store.get(); - MWWorld::Store::iterator iter = globals.begin(); - for (; iter != globals.end(); ++iter) + mVariables.clear(); + + const MWWorld::Store& globals = store.get(); + + for (MWWorld::Store::iterator iter = globals.begin(); iter!=globals.end(); + ++iter) { - char type = ' '; - Data value; - - switch (iter->mValue.getType()) - { - case ESM::VT_Short: - - type = 's'; - value.mShort = iter->mValue.getInteger(); - break; - - case ESM::VT_Long: - - type = 'l'; - value.mLong = iter->mValue.getInteger(); - break; - - case ESM::VT_Float: - - type = 'f'; - value.mFloat = iter->mValue.getFloat(); - break; - - default: - - throw std::runtime_error ("unsupported global variable type"); - } - - mVariables.insert (std::make_pair (iter->mId, std::make_pair (type, value))); + mVariables.insert (std::make_pair (iter->mId, iter->mValue)); } } - const Globals::Data& Globals::operator[] (const std::string& name) const + const ESM::Variant& Globals::operator[] (const std::string& name) const { - Collection::const_iterator iter = find (name); - - return iter->second.second; + return find (name)->second; } - Globals::Data& Globals::operator[] (const std::string& name) + ESM::Variant& Globals::operator[] (const std::string& name) { - Collection::iterator iter = find (name); - - return iter->second.second; - } - - void Globals::setInt (const std::string& name, int value) - { - Collection::iterator iter = find (name); - - switch (iter->second.first) - { - case 's': iter->second.second.mShort = value; break; - case 'l': iter->second.second.mLong = value; break; - case 'f': iter->second.second.mFloat = value; break; - - default: throw std::runtime_error ("unsupported global variable type"); - } - } - - void Globals::setFloat (const std::string& name, float value) - { - Collection::iterator iter = find (name); - - switch (iter->second.first) - { - case 's': iter->second.second.mShort = value; break; - case 'l': iter->second.second.mLong = value; break; - case 'f': iter->second.second.mFloat = value; break; - - default: throw std::runtime_error ("unsupported global variable type"); - } - } - - int Globals::getInt (const std::string& name) const - { - Collection::const_iterator iter = find (name); - - switch (iter->second.first) - { - case 's': return iter->second.second.mShort; - case 'l': return iter->second.second.mLong; - case 'f': return iter->second.second.mFloat; - - default: throw std::runtime_error ("unsupported global variable type"); - } - } - - float Globals::getFloat (const std::string& name) const - { - Collection::const_iterator iter = find (name); - - switch (iter->second.first) - { - case 's': return iter->second.second.mShort; - case 'l': return iter->second.second.mLong; - case 'f': return iter->second.second.mFloat; - - default: throw std::runtime_error ("unsupported global variable type"); - } + return find (name)->second; } char Globals::getType (const std::string& name) const @@ -153,7 +67,13 @@ namespace MWWorld if (iter==mVariables.end()) return ' '; - return iter->second.first; + switch (iter->second.getType()) + { + case ESM::VT_Short: return 's'; + case ESM::VT_Long: return 'l'; + case ESM::VT_Float: return 'f'; + + default: return ' '; + } } } - diff --git a/apps/openmw/mwworld/globals.hpp b/apps/openmw/mwworld/globals.hpp index 681bd560e..587dd2092 100644 --- a/apps/openmw/mwworld/globals.hpp +++ b/apps/openmw/mwworld/globals.hpp @@ -6,6 +6,7 @@ #include #include +#include namespace MWWorld { @@ -13,49 +14,29 @@ namespace MWWorld class Globals { - public: - - union Data - { - Interpreter::Type_Float mFloat; - Interpreter::Type_Float mLong; // Why Morrowind, why? :( - Interpreter::Type_Float mShort; - }; - - typedef std::map > Collection; - private: - + + typedef std::map Collection; + Collection mVariables; // type, value - + Collection::const_iterator find (const std::string& name) const; Collection::iterator find (const std::string& name); - - public: - - Globals (const MWWorld::ESMStore& store); - - const Data& operator[] (const std::string& name) const; - Data& operator[] (const std::string& name); - - void setInt (const std::string& name, int value); - ///< Set value independently from real type. - - void setFloat (const std::string& name, float value); - ///< Set value independently from real type. - - int getInt (const std::string& name) const; - ///< Get value independently from real type. - - float getFloat (const std::string& name) const; - ///< Get value independently from real type. - + public: + + const ESM::Variant& operator[] (const std::string& name) const; + + ESM::Variant& operator[] (const std::string& name); + char getType (const std::string& name) const; ///< If there is no global variable with this name, ' ' is returned. - std::vector getGlobals () const; + std::vector getGlobals() const; + + void fill (const MWWorld::ESMStore& store); + ///< Replace variables with variables from \a store with default values. }; } diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index c4615c099..7e9647167 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -172,9 +172,9 @@ namespace MWWorld { if (mSky && (isCellExterior() || isCellQuasiExterior())) { - mRendering->skySetHour (mGlobalVariables->getFloat ("gamehour")); - mRendering->skySetDate (mGlobalVariables->getInt ("day"), - mGlobalVariables->getInt ("month")); + mRendering->skySetHour (mGlobalVariables["gamehour"].getFloat()); + mRendering->skySetDate (mGlobalVariables["day"].getInteger(), + mGlobalVariables["month"].getInteger()); mRendering->skyEnable(); } @@ -187,7 +187,7 @@ namespace MWWorld const std::vector& contentFiles, const boost::filesystem::path& resDir, const boost::filesystem::path& cacheDir, ToUTF8::Utf8Encoder* encoder, const std::map& fallbackMap, int mActivationDistanceOverride) - : mPlayer (0), mLocalScripts (mStore), mGlobalVariables (0), + : mPlayer (0), mLocalScripts (mStore), mSky (true), mCells (mStore, mEsm), mActivationDistanceOverride (mActivationDistanceOverride), mFallback(fallbackMap), mPlayIntro(0), mTeleportEnabled(true), mLevitationEnabled(false), @@ -227,7 +227,7 @@ namespace MWWorld mStore.setUp(); mStore.movePlayerRecord(); - mGlobalVariables = new Globals (mStore); + mGlobalVariables.fill (mStore); mWorldScene = new Scene(*mRendering, mPhysics); } @@ -254,12 +254,9 @@ namespace MWWorld // FIXME: should be set to 1, but the sound manager won't pause newly started sounds mPlayIntro = 2; - // global variables - *mGlobalVariables = Globals (mStore); - // set new game mark - mGlobalVariables->setInt ("chargenstate", 1); - mGlobalVariables->setInt ("pcrace", 3); + mGlobalVariables["chargenstate"].setInteger (1); + mGlobalVariables["pcrace"].setInteger (3); // we don't want old weather to persist on a new game delete mWeatherManager; @@ -298,6 +295,8 @@ namespace MWWorld mTeleportEnabled = true; mPlayIntro = 0; mFacedDistance = FLT_MAX; + + mGlobalVariables.fill (mStore); } int World::countSavedGameRecords() const @@ -358,7 +357,6 @@ namespace MWWorld { delete mWeatherManager; delete mWorldScene; - delete mGlobalVariables; delete mRendering; delete mPhysics; @@ -436,7 +434,7 @@ namespace MWWorld else if (name=="month") setMonth (value); else - mGlobalVariables->setInt (name, value); + mGlobalVariables[name].setInteger (value); } void World::setGlobalFloat (const std::string& name, float value) @@ -448,27 +446,27 @@ namespace MWWorld else if (name=="month") setMonth (value); else - mGlobalVariables->setFloat (name, value); + mGlobalVariables[name].setFloat (value); } int World::getGlobalInt (const std::string& name) const { - return mGlobalVariables->getInt (name); + return mGlobalVariables[name].getInteger(); } float World::getGlobalFloat (const std::string& name) const { - return mGlobalVariables->getFloat (name); + return mGlobalVariables[name].getFloat(); } char World::getGlobalVariableType (const std::string& name) const { - return mGlobalVariables->getType (name); + return mGlobalVariables.getType (name); } - std::vector World::getGlobals () const + std::vector World::getGlobals() const { - return mGlobalVariables->getGlobals(); + return mGlobalVariables.getGlobals(); } std::string World::getCellName (const MWWorld::CellStore *cell) const @@ -618,14 +616,15 @@ namespace MWWorld mWeatherManager->advanceTime (hours); - hours += mGlobalVariables->getFloat ("gamehour"); + hours += mGlobalVariables["gamehour"].getFloat(); setHour (hours); int days = hours / 24; if (days>0) - mGlobalVariables->setInt ("dayspassed", days + mGlobalVariables->getInt ("dayspassed")); + mGlobalVariables["dayspassed"].setInteger ( + days + mGlobalVariables["dayspassed"].getInteger()); } void World::setHour (double hour) @@ -637,14 +636,14 @@ namespace MWWorld hour = std::fmod (hour, 24); - mGlobalVariables->setFloat ("gamehour", hour); + mGlobalVariables["gamehour"].setFloat (hour); mRendering->skySetHour (hour); mWeatherManager->setHour (hour); if (days>0) - setDay (days + mGlobalVariables->getInt ("day")); + setDay (days + mGlobalVariables["day"].getInteger()); } void World::setDay (int day) @@ -652,7 +651,7 @@ namespace MWWorld if (day<1) day = 1; - int month = mGlobalVariables->getInt ("month"); + int month = mGlobalVariables["month"].getInteger(); while (true) { @@ -667,14 +666,14 @@ namespace MWWorld else { month = 0; - mGlobalVariables->setInt ("year", mGlobalVariables->getInt ("year")+1); + mGlobalVariables["year"].setInteger (mGlobalVariables["year"].getInteger()+1); } day -= days; } - mGlobalVariables->setInt ("day", day); - mGlobalVariables->setInt ("month", month); + mGlobalVariables["day"].setInteger (day); + mGlobalVariables["month"].setInteger (month); mRendering->skySetDate (day, month); @@ -691,30 +690,30 @@ namespace MWWorld int days = getDaysPerMonth (month); - if (mGlobalVariables->getInt ("day")>days) - mGlobalVariables->setInt ("day", days); + if (mGlobalVariables["day"].getInteger()>days) + mGlobalVariables["day"].setInteger (days); - mGlobalVariables->setInt ("month", month); + mGlobalVariables["month"].setInteger (month); if (years>0) - mGlobalVariables->setInt ("year", years+mGlobalVariables->getInt ("year")); + mGlobalVariables["year"].setInteger (years+mGlobalVariables["year"].getInteger()); - mRendering->skySetDate (mGlobalVariables->getInt ("day"), month); + mRendering->skySetDate (mGlobalVariables["day"].getInteger(), month); } int World::getDay() const { - return mGlobalVariables->getInt("day"); + return mGlobalVariables["day"].getInteger(); } int World::getMonth() const { - return mGlobalVariables->getInt("month"); + return mGlobalVariables["month"].getInteger(); } int World::getYear() const { - return mGlobalVariables->getInt("year"); + return mGlobalVariables["year"].getInteger(); } std::string World::getMonthName (int month) const @@ -739,8 +738,8 @@ namespace MWWorld TimeStamp World::getTimeStamp() const { - return TimeStamp (mGlobalVariables->getFloat ("gamehour"), - mGlobalVariables->getInt ("dayspassed")); + return TimeStamp (mGlobalVariables["gamehour"].getFloat(), + mGlobalVariables["dayspassed"].getInteger()); } bool World::toggleSky() @@ -776,7 +775,7 @@ namespace MWWorld float World::getTimeScaleFactor() const { - return mGlobalVariables->getFloat ("timescale"); + return mGlobalVariables["timescale"].getFloat(); } void World::changeToInteriorCell (const std::string& cellName, const ESM::Position& position) @@ -1267,7 +1266,7 @@ namespace MWWorld if (Misc::StringUtils::ciEqual (ids[i], record.mRace)) break; - mGlobalVariables->setInt ("pcrace", (i == ids.size()) ? 0 : i+1); + mGlobalVariables["pcrace"].setInteger (i == ids.size() ? 0 : i+1); const ESM::NPC *player = mPlayer->getPlayer().get()->mBase; diff --git a/apps/openmw/mwworld/worldimp.hpp b/apps/openmw/mwworld/worldimp.hpp index 40245b78d..92c99733e 100644 --- a/apps/openmw/mwworld/worldimp.hpp +++ b/apps/openmw/mwworld/worldimp.hpp @@ -11,6 +11,7 @@ #include "localscripts.hpp" #include "timestamp.hpp" #include "fallback.hpp" +#include "globals.hpp" #include "../mwbase/world.hpp" @@ -64,7 +65,7 @@ namespace MWWorld std::vector mEsm; MWWorld::ESMStore mStore; LocalScripts mLocalScripts; - MWWorld::Globals *mGlobalVariables; + MWWorld::Globals mGlobalVariables; MWWorld::PhysicsSystem *mPhysics; bool mSky;