mirror of
https://gitlab.com/OpenMW/openmw.git
synced 2025-02-13 21:40:11 +00:00
Merge branch 'master' into characterpreview
This commit is contained in:
commit
d90af9c524
@ -51,7 +51,7 @@ add_openmw_dir (mwworld
|
|||||||
refdata worldimp physicssystem scene globals class action nullaction actionteleport
|
refdata worldimp physicssystem scene globals class action nullaction actionteleport
|
||||||
containerstore actiontalk actiontake manualref player cellfunctors
|
containerstore actiontalk actiontake manualref player cellfunctors
|
||||||
cells localscripts customdata weather inventorystore ptr actionopen actionread
|
cells localscripts customdata weather inventorystore ptr actionopen actionread
|
||||||
actionequip timestamp actionalchemy cellstore actionapply
|
actionequip timestamp actionalchemy cellstore actionapply actioneat
|
||||||
)
|
)
|
||||||
|
|
||||||
add_openmw_dir (mwclass
|
add_openmw_dir (mwclass
|
||||||
|
@ -162,6 +162,10 @@ void OMW::Engine::loadBSA()
|
|||||||
dataDirectory = iter->string();
|
dataDirectory = iter->string();
|
||||||
std::cout << "Data dir " << dataDirectory << std::endl;
|
std::cout << "Data dir " << dataDirectory << std::endl;
|
||||||
Bsa::addDir(dataDirectory, mFSStrict);
|
Bsa::addDir(dataDirectory, mFSStrict);
|
||||||
|
|
||||||
|
// Workaround: Mygui does not find textures in non-BSA subfolders, _unless_ they are explicitely added like this
|
||||||
|
// For splash screens, this is OK to do, but eventually we will need an investigation why this is necessary
|
||||||
|
Bsa::addDir(dataDirectory + "/Splash", mFSStrict);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -218,6 +218,7 @@ namespace MWBase
|
|||||||
virtual void executeInConsole (const std::string& path) = 0;
|
virtual void executeInConsole (const std::string& path) = 0;
|
||||||
|
|
||||||
virtual void setLoadingProgress (const std::string& stage, int depth, int current, int total) = 0;
|
virtual void setLoadingProgress (const std::string& stage, int depth, int current, int total) = 0;
|
||||||
|
virtual void loadingDone() = 0;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -11,6 +11,7 @@
|
|||||||
#include "../mwworld/actiontake.hpp"
|
#include "../mwworld/actiontake.hpp"
|
||||||
#include "../mwworld/cellstore.hpp"
|
#include "../mwworld/cellstore.hpp"
|
||||||
#include "../mwworld/physicssystem.hpp"
|
#include "../mwworld/physicssystem.hpp"
|
||||||
|
#include "../mwworld/actioneat.hpp"
|
||||||
|
|
||||||
#include "../mwgui/tooltips.hpp"
|
#include "../mwgui/tooltips.hpp"
|
||||||
|
|
||||||
@ -19,6 +20,14 @@
|
|||||||
|
|
||||||
namespace MWClass
|
namespace MWClass
|
||||||
{
|
{
|
||||||
|
std::string Ingredient::getId (const MWWorld::Ptr& ptr) const
|
||||||
|
{
|
||||||
|
MWWorld::LiveCellRef<ESM::Ingredient> *ref =
|
||||||
|
ptr.get<ESM::Ingredient>();
|
||||||
|
|
||||||
|
return ref->base->mId;
|
||||||
|
}
|
||||||
|
|
||||||
void Ingredient::insertObjectRendering (const MWWorld::Ptr& ptr, MWRender::RenderingInterface& renderingInterface) const
|
void Ingredient::insertObjectRendering (const MWWorld::Ptr& ptr, MWRender::RenderingInterface& renderingInterface) const
|
||||||
{
|
{
|
||||||
const std::string model = getModel(ptr);
|
const std::string model = getModel(ptr);
|
||||||
@ -84,6 +93,16 @@ namespace MWClass
|
|||||||
return ref->base->data.value;
|
return ref->base->data.value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
boost::shared_ptr<MWWorld::Action> Ingredient::use (const MWWorld::Ptr& ptr) const
|
||||||
|
{
|
||||||
|
boost::shared_ptr<MWWorld::Action> action (new MWWorld::ActionEat (ptr));
|
||||||
|
|
||||||
|
action->setSound ("Swallow");
|
||||||
|
|
||||||
|
return action;
|
||||||
|
}
|
||||||
|
|
||||||
void Ingredient::registerSelf()
|
void Ingredient::registerSelf()
|
||||||
{
|
{
|
||||||
boost::shared_ptr<Class> instance (new Ingredient);
|
boost::shared_ptr<Class> instance (new Ingredient);
|
||||||
|
@ -12,6 +12,9 @@ namespace MWClass
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
virtual std::string getId (const MWWorld::Ptr& ptr) const;
|
||||||
|
///< Return ID of \a ptr
|
||||||
|
|
||||||
virtual void insertObjectRendering (const MWWorld::Ptr& ptr, MWRender::RenderingInterface& renderingInterface) const;
|
virtual void insertObjectRendering (const MWWorld::Ptr& ptr, MWRender::RenderingInterface& renderingInterface) const;
|
||||||
///< Add reference into a cell for rendering
|
///< Add reference into a cell for rendering
|
||||||
|
|
||||||
@ -37,6 +40,10 @@ namespace MWClass
|
|||||||
virtual int getValue (const MWWorld::Ptr& ptr) const;
|
virtual int getValue (const MWWorld::Ptr& ptr) const;
|
||||||
///< Return trade value of the object. Throws an exception, if the object can't be traded.
|
///< Return trade value of the object. Throws an exception, if the object can't be traded.
|
||||||
|
|
||||||
|
virtual boost::shared_ptr<MWWorld::Action> use (const MWWorld::Ptr& ptr)
|
||||||
|
const;
|
||||||
|
///< Generate action for using via inventory menu
|
||||||
|
|
||||||
static void registerSelf();
|
static void registerSelf();
|
||||||
|
|
||||||
virtual std::string getUpSoundId (const MWWorld::Ptr& ptr) const;
|
virtual std::string getUpSoundId (const MWWorld::Ptr& ptr) const;
|
||||||
|
@ -365,7 +365,7 @@ namespace MWClass
|
|||||||
|
|
||||||
/// \todo consider instant effects
|
/// \todo consider instant effects
|
||||||
|
|
||||||
return stats.getActiveSpells().addSpell (id);
|
return stats.getActiveSpells().addSpell (id, actor);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Npc::skillUsageSucceeded (const MWWorld::Ptr& ptr, int skill, int usageType) const
|
void Npc::skillUsageSucceeded (const MWWorld::Ptr& ptr, int skill, int usageType) const
|
||||||
|
@ -11,6 +11,8 @@
|
|||||||
#include "../mwbase/environment.hpp"
|
#include "../mwbase/environment.hpp"
|
||||||
#include "../mwbase/inputmanager.hpp"
|
#include "../mwbase/inputmanager.hpp"
|
||||||
|
|
||||||
|
#include "../mwbase/windowmanager.hpp"
|
||||||
|
|
||||||
namespace MWGui
|
namespace MWGui
|
||||||
{
|
{
|
||||||
|
|
||||||
@ -20,6 +22,8 @@ namespace MWGui
|
|||||||
, WindowBase("openmw_loading_screen.layout", parWindowManager)
|
, WindowBase("openmw_loading_screen.layout", parWindowManager)
|
||||||
, mLoadingOn(false)
|
, mLoadingOn(false)
|
||||||
, mLastRenderTime(0.f)
|
, mLastRenderTime(0.f)
|
||||||
|
, mLastWallpaperChangeTime(0.f)
|
||||||
|
, mFirstLoad(true)
|
||||||
{
|
{
|
||||||
getWidget(mLoadingText, "LoadingText");
|
getWidget(mLoadingText, "LoadingText");
|
||||||
getWidget(mProgressBar, "ProgressBar");
|
getWidget(mProgressBar, "ProgressBar");
|
||||||
@ -77,11 +81,7 @@ namespace MWGui
|
|||||||
mTotalRefsLoading = total;
|
mTotalRefsLoading = total;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mTotalCellsLoading == 0)
|
assert (mTotalCellsLoading != 0);
|
||||||
{
|
|
||||||
loadingOff();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
float refProgress;
|
float refProgress;
|
||||||
if (mTotalRefsLoading <= 1)
|
if (mTotalRefsLoading <= 1)
|
||||||
@ -98,11 +98,6 @@ namespace MWGui
|
|||||||
|
|
||||||
float progress = (float(mCurrentCellLoading)+refProgress) / float(mTotalCellsLoading);
|
float progress = (float(mCurrentCellLoading)+refProgress) / float(mTotalCellsLoading);
|
||||||
assert(progress <= 1 && progress >= 0);
|
assert(progress <= 1 && progress >= 0);
|
||||||
if (progress >= 1)
|
|
||||||
{
|
|
||||||
loadingOff();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mLoadingText->setCaption(stage + "... ");
|
mLoadingText->setCaption(stage + "... ");
|
||||||
mProgressBar->setProgressPosition (static_cast<size_t>(progress * 1000));
|
mProgressBar->setProgressPosition (static_cast<size_t>(progress * 1000));
|
||||||
@ -113,6 +108,11 @@ namespace MWGui
|
|||||||
{
|
{
|
||||||
mLastRenderTime = mTimer.getMilliseconds ();
|
mLastRenderTime = mTimer.getMilliseconds ();
|
||||||
|
|
||||||
|
if (mFirstLoad && mTimer.getMilliseconds () > mLastWallpaperChangeTime + 3000*1)
|
||||||
|
{
|
||||||
|
mLastWallpaperChangeTime = mTimer.getMilliseconds ();
|
||||||
|
changeWallpaper();
|
||||||
|
}
|
||||||
|
|
||||||
// Turn off rendering except the GUI
|
// Turn off rendering except the GUI
|
||||||
mSceneMgr->clearSpecialCaseRenderQueues();
|
mSceneMgr->clearSpecialCaseRenderQueues();
|
||||||
@ -139,8 +139,11 @@ namespace MWGui
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
mBackgroundMaterial->getTechnique(0)->getPass(0)->getTextureUnitState(0)->setTextureName(chain->getCompositor ("gbufferFinalizer")->getTextureInstance ("no_mrt_output", 0)->getName());
|
if (!mFirstLoad)
|
||||||
mRectangle->setVisible(true);
|
{
|
||||||
|
mBackgroundMaterial->getTechnique(0)->getPass(0)->getTextureUnitState(0)->setTextureName(chain->getCompositor ("gbufferFinalizer")->getTextureInstance ("no_mrt_output", 0)->getName());
|
||||||
|
mRectangle->setVisible(true);
|
||||||
|
}
|
||||||
|
|
||||||
for (unsigned int i = 0; i<chain->getNumCompositors(); ++i)
|
for (unsigned int i = 0; i<chain->getNumCompositors(); ++i)
|
||||||
{
|
{
|
||||||
@ -158,19 +161,37 @@ namespace MWGui
|
|||||||
{
|
{
|
||||||
Ogre::CompositorManager::getSingleton().setCompositorEnabled(mWindow->getViewport(0), chain->getCompositor(i)->getCompositor()->getName(), true);
|
Ogre::CompositorManager::getSingleton().setCompositorEnabled(mWindow->getViewport(0), chain->getCompositor(i)->getCompositor()->getName(), true);
|
||||||
}
|
}
|
||||||
mRectangle->setVisible(false);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mRectangle->setVisible(false);
|
||||||
|
|
||||||
// resume 3d rendering
|
// resume 3d rendering
|
||||||
mSceneMgr->clearSpecialCaseRenderQueues();
|
mSceneMgr->clearSpecialCaseRenderQueues();
|
||||||
mSceneMgr->setSpecialCaseRenderQueueMode(Ogre::SceneManager::SCRQM_EXCLUDE);
|
mSceneMgr->setSpecialCaseRenderQueueMode(Ogre::SceneManager::SCRQM_EXCLUDE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void LoadingScreen::loadingDone()
|
||||||
|
{
|
||||||
|
loadingOff();
|
||||||
|
}
|
||||||
|
|
||||||
void LoadingScreen::loadingOn()
|
void LoadingScreen::loadingOn()
|
||||||
{
|
{
|
||||||
setVisible(true);
|
setVisible(true);
|
||||||
mLoadingOn = true;
|
mLoadingOn = true;
|
||||||
|
|
||||||
|
if (mFirstLoad)
|
||||||
|
{
|
||||||
|
changeWallpaper();
|
||||||
|
|
||||||
|
mWindowManager.pushGuiMode(GM_LoadingWallpaper);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mBackgroundImage->setImageTexture("");
|
||||||
|
mWindowManager.pushGuiMode(GM_Loading);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -178,5 +199,28 @@ namespace MWGui
|
|||||||
{
|
{
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
mLoadingOn = false;
|
mLoadingOn = false;
|
||||||
|
mFirstLoad = false;
|
||||||
|
|
||||||
|
mWindowManager.removeGuiMode(GM_Loading);
|
||||||
|
mWindowManager.removeGuiMode(GM_LoadingWallpaper);
|
||||||
|
}
|
||||||
|
|
||||||
|
void LoadingScreen::changeWallpaper ()
|
||||||
|
{
|
||||||
|
/// \todo use a directory listing here
|
||||||
|
std::vector<std::string> splash;
|
||||||
|
splash.push_back ("Splash_Bonelord.tga");
|
||||||
|
splash.push_back ("Splash_ClannDaddy.tga");
|
||||||
|
splash.push_back ("Splash_Clannfear.tga");
|
||||||
|
splash.push_back ("Splash_Daedroth.tga");
|
||||||
|
splash.push_back ("Splash_Hunger.tga");
|
||||||
|
splash.push_back ("Splash_KwamaWarrior.tga");
|
||||||
|
splash.push_back ("Splash_Netch.tga");
|
||||||
|
splash.push_back ("Splash_NixHound.tga");
|
||||||
|
splash.push_back ("Splash_Siltstriker.tga");
|
||||||
|
splash.push_back ("Splash_Skeleton.tga");
|
||||||
|
splash.push_back ("Splash_SphereCenturion.tga");
|
||||||
|
|
||||||
|
mBackgroundImage->setImageTexture (splash[rand() % splash.size()]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -15,13 +15,17 @@ namespace MWGui
|
|||||||
virtual ~LoadingScreen();
|
virtual ~LoadingScreen();
|
||||||
|
|
||||||
void setLoadingProgress (const std::string& stage, int depth, int current, int total);
|
void setLoadingProgress (const std::string& stage, int depth, int current, int total);
|
||||||
|
void loadingDone();
|
||||||
|
|
||||||
void onResChange(int w, int h);
|
void onResChange(int w, int h);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
bool mFirstLoad;
|
||||||
|
|
||||||
Ogre::SceneManager* mSceneMgr;
|
Ogre::SceneManager* mSceneMgr;
|
||||||
Ogre::RenderWindow* mWindow;
|
Ogre::RenderWindow* mWindow;
|
||||||
|
|
||||||
|
unsigned long mLastWallpaperChangeTime;
|
||||||
unsigned long mLastRenderTime;
|
unsigned long mLastRenderTime;
|
||||||
Ogre::Timer mTimer;
|
Ogre::Timer mTimer;
|
||||||
|
|
||||||
@ -43,6 +47,8 @@ namespace MWGui
|
|||||||
|
|
||||||
void loadingOn();
|
void loadingOn();
|
||||||
void loadingOff();
|
void loadingOff();
|
||||||
|
|
||||||
|
void changeWallpaper();
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -35,6 +35,9 @@ namespace MWGui
|
|||||||
// interactive MessageBox
|
// interactive MessageBox
|
||||||
GM_InterMessageBox,
|
GM_InterMessageBox,
|
||||||
|
|
||||||
|
GM_Loading,
|
||||||
|
GM_LoadingWallpaper,
|
||||||
|
|
||||||
GM_QuickKeysMenu
|
GM_QuickKeysMenu
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -248,6 +248,8 @@ void WindowManager::updateVisible()
|
|||||||
mSpellWindow->setVisible(false);
|
mSpellWindow->setVisible(false);
|
||||||
mQuickKeysMenu->setVisible(false);
|
mQuickKeysMenu->setVisible(false);
|
||||||
|
|
||||||
|
mHud->setVisible(true);
|
||||||
|
|
||||||
// Mouse is visible whenever we're not in game mode
|
// Mouse is visible whenever we're not in game mode
|
||||||
MyGUI::PointerManager::getInstance().setVisible(isGuiMode());
|
MyGUI::PointerManager::getInstance().setVisible(isGuiMode());
|
||||||
|
|
||||||
@ -340,6 +342,13 @@ void WindowManager::updateVisible()
|
|||||||
case GM_Journal:
|
case GM_Journal:
|
||||||
mJournal->setVisible(true);
|
mJournal->setVisible(true);
|
||||||
break;
|
break;
|
||||||
|
case GM_LoadingWallpaper:
|
||||||
|
mHud->setVisible(false);
|
||||||
|
MyGUI::PointerManager::getInstance().setVisible(false);
|
||||||
|
break;
|
||||||
|
case GM_Loading:
|
||||||
|
MyGUI::PointerManager::getInstance().setVisible(false);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
// Unsupported mode, switch back to game
|
// Unsupported mode, switch back to game
|
||||||
break;
|
break;
|
||||||
@ -909,3 +918,8 @@ void WindowManager::setLoadingProgress (const std::string& stage, int depth, int
|
|||||||
{
|
{
|
||||||
mLoadingScreen->setLoadingProgress (stage, depth, current, total);
|
mLoadingScreen->setLoadingProgress (stage, depth, current, total);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void WindowManager::loadingDone ()
|
||||||
|
{
|
||||||
|
mLoadingScreen->loadingDone ();
|
||||||
|
}
|
||||||
|
@ -197,6 +197,7 @@ namespace MWGui
|
|||||||
virtual void executeInConsole (const std::string& path);
|
virtual void executeInConsole (const std::string& path);
|
||||||
|
|
||||||
virtual void setLoadingProgress (const std::string& stage, int depth, int current, int total);
|
virtual void setLoadingProgress (const std::string& stage, int depth, int current, int total);
|
||||||
|
virtual void loadingDone();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
OEngine::GUI::MyGUIManager *mGuiManager;
|
OEngine::GUI::MyGUIManager *mGuiManager;
|
||||||
|
@ -5,12 +5,20 @@
|
|||||||
|
|
||||||
#include <components/esm/loadalch.hpp>
|
#include <components/esm/loadalch.hpp>
|
||||||
#include <components/esm/loadspel.hpp>
|
#include <components/esm/loadspel.hpp>
|
||||||
|
#include <components/esm/loadingr.hpp>
|
||||||
|
#include <components/esm/loadmgef.hpp>
|
||||||
|
#include <components/esm/loadskil.hpp>
|
||||||
|
|
||||||
#include <components/esm_store/store.hpp>
|
#include <components/esm_store/store.hpp>
|
||||||
|
|
||||||
#include "../mwbase/environment.hpp"
|
#include "../mwbase/environment.hpp"
|
||||||
#include "../mwbase/world.hpp"
|
#include "../mwbase/world.hpp"
|
||||||
|
|
||||||
|
#include "../mwworld/class.hpp"
|
||||||
|
|
||||||
|
#include "creaturestats.hpp"
|
||||||
|
#include "npcstats.hpp"
|
||||||
|
|
||||||
namespace MWMechanics
|
namespace MWMechanics
|
||||||
{
|
{
|
||||||
void ActiveSpells::update() const
|
void ActiveSpells::update() const
|
||||||
@ -41,47 +49,102 @@ namespace MWMechanics
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (rebuild)
|
if (rebuild)
|
||||||
|
rebuildEffects();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ActiveSpells::rebuildEffects() const
|
||||||
|
{
|
||||||
|
MWWorld::TimeStamp now = MWBase::Environment::get().getWorld()->getTimeStamp();
|
||||||
|
|
||||||
|
mEffects = MagicEffects();
|
||||||
|
|
||||||
|
for (TIterator iter (begin()); iter!=end(); ++iter)
|
||||||
{
|
{
|
||||||
mEffects = MagicEffects();
|
std::pair<ESM::EffectList, bool> effects = getEffectList (iter->first);
|
||||||
|
|
||||||
for (TIterator iter (begin()); iter!=end(); ++iter)
|
const MWWorld::TimeStamp& start = iter->second.first;
|
||||||
|
float magnitude = iter->second.second;
|
||||||
|
|
||||||
|
for (std::vector<ESM::ENAMstruct>::const_iterator iter (effects.first.list.begin());
|
||||||
|
iter!=effects.first.list.end(); ++iter)
|
||||||
{
|
{
|
||||||
const ESM::EffectList& effects = getEffectList (iter->first);
|
if (iter->duration)
|
||||||
|
|
||||||
const MWWorld::TimeStamp& start = iter->second.first;
|
|
||||||
float magnitude = iter->second.second;
|
|
||||||
|
|
||||||
for (std::vector<ESM::ENAMstruct>::const_iterator iter (effects.list.begin());
|
|
||||||
iter!=effects.list.end(); ++iter)
|
|
||||||
{
|
{
|
||||||
if (iter->duration)
|
int duration = iter->duration;
|
||||||
{
|
|
||||||
MWWorld::TimeStamp end = start;
|
if (effects.second)
|
||||||
end += static_cast<double> (iter->duration)*
|
duration *= magnitude;
|
||||||
MWBase::Environment::get().getWorld()->getTimeScaleFactor()/(60*60);
|
|
||||||
|
MWWorld::TimeStamp end = start;
|
||||||
|
end += static_cast<double> (duration)*
|
||||||
|
MWBase::Environment::get().getWorld()->getTimeScaleFactor()/(60*60);
|
||||||
|
|
||||||
if (end>now)
|
if (end>now)
|
||||||
|
{
|
||||||
|
EffectParam param;
|
||||||
|
|
||||||
|
if (effects.second)
|
||||||
{
|
{
|
||||||
EffectParam param;
|
const ESM::MagicEffect *magicEffect =
|
||||||
param.mMagnitude = static_cast<int> (
|
MWBase::Environment::get().getWorld()->getStore().magicEffects.find (
|
||||||
(iter->magnMax-iter->magnMin+1)*magnitude + iter->magnMin);
|
iter->effectID);
|
||||||
mEffects.add (*iter, param);
|
|
||||||
|
if (iter->duration==0)
|
||||||
|
{
|
||||||
|
param.mMagnitude =
|
||||||
|
static_cast<int> (magnitude / (0.1 * magicEffect->data.baseCost));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
param.mMagnitude =
|
||||||
|
static_cast<int> (0.05*magnitude / (0.1 * magicEffect->data.baseCost));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
param.mMagnitude = static_cast<int> (
|
||||||
|
(iter->magnMax-iter->magnMin)*magnitude + iter->magnMin);
|
||||||
|
|
||||||
|
mEffects.add (*iter, param);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const ESM::EffectList& ActiveSpells::getEffectList (const std::string& id) const
|
std::pair<ESM::EffectList, bool> ActiveSpells::getEffectList (const std::string& id) const
|
||||||
{
|
{
|
||||||
if (const ESM::Spell *spell =
|
if (const ESM::Spell *spell =
|
||||||
MWBase::Environment::get().getWorld()->getStore().spells.search (id))
|
MWBase::Environment::get().getWorld()->getStore().spells.search (id))
|
||||||
return spell->effects;
|
return std::make_pair (spell->effects, false);
|
||||||
|
|
||||||
if (const ESM::Potion *potion =
|
if (const ESM::Potion *potion =
|
||||||
MWBase::Environment::get().getWorld()->getStore().potions.search (id))
|
MWBase::Environment::get().getWorld()->getStore().potions.search (id))
|
||||||
return potion->effects;
|
return std::make_pair (potion->effects, false);
|
||||||
|
|
||||||
|
if (const ESM::Ingredient *ingredient =
|
||||||
|
MWBase::Environment::get().getWorld()->getStore().ingreds.search (id))
|
||||||
|
{
|
||||||
|
const ESM::MagicEffect *magicEffect =
|
||||||
|
MWBase::Environment::get().getWorld()->getStore().magicEffects.find (
|
||||||
|
ingredient->data.effectID[0]);
|
||||||
|
|
||||||
|
ESM::ENAMstruct effect;
|
||||||
|
effect.effectID = ingredient->data.effectID[0];
|
||||||
|
effect.skill = ingredient->data.skills[0];
|
||||||
|
effect.attribute = ingredient->data.attributes[0];
|
||||||
|
effect.range = 0;
|
||||||
|
effect.area = 0;
|
||||||
|
effect.duration = magicEffect->data.flags & ESM::MagicEffect::NoDuration ? 0 : 1;
|
||||||
|
effect.magnMin = 1;
|
||||||
|
effect.magnMax = 1;
|
||||||
|
|
||||||
|
std::pair<ESM::EffectList, bool> result;
|
||||||
|
|
||||||
|
result.first.list.push_back (effect);
|
||||||
|
result.second = true;
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
throw std::runtime_error ("ID " + id + " can not produce lasting effects");
|
throw std::runtime_error ("ID " + id + " can not produce lasting effects");
|
||||||
}
|
}
|
||||||
@ -90,14 +153,14 @@ namespace MWMechanics
|
|||||||
: mSpellsChanged (false), mLastUpdate (MWBase::Environment::get().getWorld()->getTimeStamp())
|
: mSpellsChanged (false), mLastUpdate (MWBase::Environment::get().getWorld()->getTimeStamp())
|
||||||
{}
|
{}
|
||||||
|
|
||||||
bool ActiveSpells::addSpell (const std::string& id)
|
bool ActiveSpells::addSpell (const std::string& id, const MWWorld::Ptr& actor)
|
||||||
{
|
{
|
||||||
const ESM::EffectList& effects = getEffectList (id);
|
std::pair<ESM::EffectList, bool> effects = getEffectList (id);
|
||||||
|
|
||||||
bool found = false;
|
bool found = false;
|
||||||
|
|
||||||
for (std::vector<ESM::ENAMstruct>::const_iterator iter (effects.list.begin());
|
for (std::vector<ESM::ENAMstruct>::const_iterator iter (effects.first.list.begin());
|
||||||
iter!=effects.list.end(); ++iter)
|
iter!=effects.first.list.end(); ++iter)
|
||||||
{
|
{
|
||||||
if (iter->duration)
|
if (iter->duration)
|
||||||
{
|
{
|
||||||
@ -113,6 +176,22 @@ namespace MWMechanics
|
|||||||
|
|
||||||
float random = static_cast<float> (std::rand()) / RAND_MAX;
|
float random = static_cast<float> (std::rand()) / RAND_MAX;
|
||||||
|
|
||||||
|
if (effects.second)
|
||||||
|
{
|
||||||
|
// ingredient -> special treatment required.
|
||||||
|
const CreatureStats& creatureStats = MWWorld::Class::get (actor).getCreatureStats (actor);
|
||||||
|
const NpcStats& npcStats = MWWorld::Class::get (actor).getNpcStats (actor);
|
||||||
|
|
||||||
|
float x =
|
||||||
|
(npcStats.getSkill (ESM::Skill::Alchemy).getModified() +
|
||||||
|
0.2 * creatureStats.getAttribute (1).getModified()
|
||||||
|
+ 0.1 * creatureStats.getAttribute (7).getModified())
|
||||||
|
* creatureStats.getFatigueTerm();
|
||||||
|
random *= 100;
|
||||||
|
random = random / std::min (x, 100.0f);
|
||||||
|
random *= 0.25 * x;
|
||||||
|
}
|
||||||
|
|
||||||
if (iter==mSpells.end())
|
if (iter==mSpells.end())
|
||||||
mSpells.insert (std::make_pair (id,
|
mSpells.insert (std::make_pair (id,
|
||||||
std::make_pair (MWBase::Environment::get().getWorld()->getTimeStamp(), random)));
|
std::make_pair (MWBase::Environment::get().getWorld()->getTimeStamp(), random)));
|
||||||
@ -155,17 +234,20 @@ namespace MWMechanics
|
|||||||
|
|
||||||
double ActiveSpells::timeToExpire (const TIterator& iterator) const
|
double ActiveSpells::timeToExpire (const TIterator& iterator) const
|
||||||
{
|
{
|
||||||
const ESM::EffectList& effects = getEffectList (iterator->first);
|
std::pair<ESM::EffectList, bool> effects = getEffectList (iterator->first);
|
||||||
|
|
||||||
int duration = 0;
|
int duration = 0;
|
||||||
|
|
||||||
for (std::vector<ESM::ENAMstruct>::const_iterator iter (effects.list.begin());
|
for (std::vector<ESM::ENAMstruct>::const_iterator iter (effects.first.list.begin());
|
||||||
iter!=effects.list.end(); ++iter)
|
iter!=effects.first.list.end(); ++iter)
|
||||||
{
|
{
|
||||||
if (iter->duration>duration)
|
if (iter->duration>duration)
|
||||||
duration = iter->duration;
|
duration = iter->duration;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (effects.second)
|
||||||
|
duration *= iterator->second.second;
|
||||||
|
|
||||||
double scaledDuration = duration *
|
double scaledDuration = duration *
|
||||||
MWBase::Environment::get().getWorld()->getTimeScaleFactor()/(60*60);
|
MWBase::Environment::get().getWorld()->getTimeScaleFactor()/(60*60);
|
||||||
|
|
||||||
|
@ -15,6 +15,11 @@ namespace ESM
|
|||||||
struct EffectList;
|
struct EffectList;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace MWWorld
|
||||||
|
{
|
||||||
|
class Ptr;
|
||||||
|
}
|
||||||
|
|
||||||
namespace MWMechanics
|
namespace MWMechanics
|
||||||
{
|
{
|
||||||
/// \brief Lasting spell effects
|
/// \brief Lasting spell effects
|
||||||
@ -36,14 +41,16 @@ namespace MWMechanics
|
|||||||
mutable MWWorld::TimeStamp mLastUpdate;
|
mutable MWWorld::TimeStamp mLastUpdate;
|
||||||
|
|
||||||
void update() const;
|
void update() const;
|
||||||
|
|
||||||
|
void rebuildEffects() const;
|
||||||
|
|
||||||
const ESM::EffectList& getEffectList (const std::string& id) const;
|
std::pair<ESM::EffectList, bool> getEffectList (const std::string& id) const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
ActiveSpells();
|
ActiveSpells();
|
||||||
|
|
||||||
bool addSpell (const std::string& id);
|
bool addSpell (const std::string& id, const MWWorld::Ptr& actor);
|
||||||
///< Overwrites an existing spell with the same ID. If the spell does not have any
|
///< Overwrites an existing spell with the same ID. If the spell does not have any
|
||||||
/// non-instant effects, it is ignored.
|
/// non-instant effects, it is ignored.
|
||||||
///
|
///
|
||||||
|
@ -1,51 +1,14 @@
|
|||||||
#include "creaturestats.hpp"
|
#include "creaturestats.hpp"
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
|
||||||
|
#include <components/esm_store/store.hpp>
|
||||||
|
|
||||||
|
#include "../mwbase/environment.hpp"
|
||||||
|
#include "../mwbase/world.hpp"
|
||||||
|
|
||||||
namespace MWMechanics
|
namespace MWMechanics
|
||||||
{
|
{
|
||||||
CreatureStats::CreatureStats()
|
|
||||||
{}
|
|
||||||
|
|
||||||
// Can't use all benefits of members initialization because of
|
|
||||||
// lack of copy constructors
|
|
||||||
CreatureStats::CreatureStats(const CreatureStats &orig)
|
|
||||||
: mLevel(orig.mLevel), mHello(orig.mHello), mFight(orig.mFight),
|
|
||||||
mFlee(orig.mFlee), mAlarm(orig.mAlarm)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < 8; ++i) {
|
|
||||||
mAttributes[i] = orig.mAttributes[i];
|
|
||||||
}
|
|
||||||
for (int i = 0; i < 3; ++i) {
|
|
||||||
mDynamic[i] = orig.mDynamic[i];
|
|
||||||
}
|
|
||||||
mSpells = orig.mSpells;
|
|
||||||
mActiveSpells = orig.mActiveSpells;
|
|
||||||
mMagicEffects = orig.mMagicEffects;
|
|
||||||
}
|
|
||||||
|
|
||||||
CreatureStats::~CreatureStats()
|
|
||||||
{}
|
|
||||||
|
|
||||||
const CreatureStats &
|
|
||||||
CreatureStats::operator=(const CreatureStats &orig)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < 8; ++i) {
|
|
||||||
mAttributes[i] = orig.mAttributes[i];
|
|
||||||
}
|
|
||||||
for (int i = 0; i < 3; ++i) {
|
|
||||||
mDynamic[i] = orig.mDynamic[i];
|
|
||||||
}
|
|
||||||
mLevel = orig.mLevel;
|
|
||||||
mSpells = orig.mSpells;
|
|
||||||
mActiveSpells = orig.mActiveSpells;
|
|
||||||
mMagicEffects = orig.mMagicEffects;
|
|
||||||
mHello = orig.mHello;
|
|
||||||
mFight = orig.mFight;
|
|
||||||
mFlee = orig.mFlee;
|
|
||||||
mAlarm = orig.mAlarm;
|
|
||||||
|
|
||||||
return *this;
|
|
||||||
}
|
|
||||||
|
|
||||||
const AiSequence& CreatureStats::getAiSequence() const
|
const AiSequence& CreatureStats::getAiSequence() const
|
||||||
{
|
{
|
||||||
return mAiSequence;
|
return mAiSequence;
|
||||||
@ -55,4 +18,189 @@ namespace MWMechanics
|
|||||||
{
|
{
|
||||||
return mAiSequence;
|
return mAiSequence;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
float CreatureStats::getFatigueTerm() const
|
||||||
|
{
|
||||||
|
int max = getFatigue().getModified();
|
||||||
|
int current = getFatigue().getCurrent();
|
||||||
|
|
||||||
|
float normalised = max==0 ? 1 : std::max (0.0f, static_cast<float> (current)/max);
|
||||||
|
|
||||||
|
const ESMS::ESMStore& store = MWBase::Environment::get().getWorld()->getStore();
|
||||||
|
|
||||||
|
return store.gameSettings.find ("fFatigueBase")->getFloat()
|
||||||
|
- store.gameSettings.find ("fFatigueMult")->getFloat() * (1-normalised);
|
||||||
|
}
|
||||||
|
|
||||||
|
const Stat<int> &CreatureStats::getAttribute(int index) const
|
||||||
|
{
|
||||||
|
if (index < 0 || index > 7) {
|
||||||
|
throw std::runtime_error("attribute index is out of range");
|
||||||
|
}
|
||||||
|
return mAttributes[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
const DynamicStat<int> &CreatureStats::getHealth() const
|
||||||
|
{
|
||||||
|
return mDynamic[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
const DynamicStat<int> &CreatureStats::getMagicka() const
|
||||||
|
{
|
||||||
|
return mDynamic[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
const DynamicStat<int> &CreatureStats::getFatigue() const
|
||||||
|
{
|
||||||
|
return mDynamic[2];
|
||||||
|
}
|
||||||
|
|
||||||
|
const Spells &CreatureStats::getSpells() const
|
||||||
|
{
|
||||||
|
return mSpells;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ActiveSpells &CreatureStats::getActiveSpells() const
|
||||||
|
{
|
||||||
|
return mActiveSpells;
|
||||||
|
}
|
||||||
|
|
||||||
|
const MagicEffects &CreatureStats::getMagicEffects() const
|
||||||
|
{
|
||||||
|
return mMagicEffects;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CreatureStats::getLevel() const
|
||||||
|
{
|
||||||
|
return mLevel;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CreatureStats::getHello() const
|
||||||
|
{
|
||||||
|
return mHello;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CreatureStats::getFight() const
|
||||||
|
{
|
||||||
|
return mFight;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CreatureStats::getFlee() const
|
||||||
|
{
|
||||||
|
return mFlee;
|
||||||
|
}
|
||||||
|
|
||||||
|
int CreatureStats::getAlarm() const
|
||||||
|
{
|
||||||
|
return mAlarm;
|
||||||
|
}
|
||||||
|
|
||||||
|
Stat<int> &CreatureStats::getAttribute(int index)
|
||||||
|
{
|
||||||
|
if (index < 0 || index > 7) {
|
||||||
|
throw std::runtime_error("attribute index is out of range");
|
||||||
|
}
|
||||||
|
return mAttributes[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
DynamicStat<int> &CreatureStats::getHealth()
|
||||||
|
{
|
||||||
|
return mDynamic[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
DynamicStat<int> &CreatureStats::getMagicka()
|
||||||
|
{
|
||||||
|
return mDynamic[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
DynamicStat<int> &CreatureStats::getFatigue()
|
||||||
|
{
|
||||||
|
return mDynamic[2];
|
||||||
|
}
|
||||||
|
|
||||||
|
DynamicStat<int> &CreatureStats::getDynamic(int index)
|
||||||
|
{
|
||||||
|
if (index < 0 || index > 2) {
|
||||||
|
throw std::runtime_error("dynamic stat index is out of range");
|
||||||
|
}
|
||||||
|
return mDynamic[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
Spells &CreatureStats::getSpells()
|
||||||
|
{
|
||||||
|
return mSpells;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setSpells(const Spells &spells)
|
||||||
|
{
|
||||||
|
mSpells = spells;
|
||||||
|
}
|
||||||
|
|
||||||
|
ActiveSpells &CreatureStats::getActiveSpells()
|
||||||
|
{
|
||||||
|
return mActiveSpells;
|
||||||
|
}
|
||||||
|
|
||||||
|
MagicEffects &CreatureStats::getMagicEffects()
|
||||||
|
{
|
||||||
|
return mMagicEffects;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setAttribute(int index, const Stat<int> &value)
|
||||||
|
{
|
||||||
|
if (index < 0 || index > 7) {
|
||||||
|
throw std::runtime_error("attribute index is out of range");
|
||||||
|
}
|
||||||
|
mAttributes[index] = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setHealth(const DynamicStat<int> &value)
|
||||||
|
{
|
||||||
|
mDynamic[0] = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setMagicka(const DynamicStat<int> &value)
|
||||||
|
{
|
||||||
|
mDynamic[1] = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setFatigue(const DynamicStat<int> &value)
|
||||||
|
{
|
||||||
|
mDynamic[2] = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setLevel(int level)
|
||||||
|
{
|
||||||
|
mLevel = level;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setActiveSpells(const ActiveSpells &active)
|
||||||
|
{
|
||||||
|
mActiveSpells = active;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setMagicEffects(const MagicEffects &effects)
|
||||||
|
{
|
||||||
|
mMagicEffects = effects;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setHello(int value)
|
||||||
|
{
|
||||||
|
mHello = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setFight(int value)
|
||||||
|
{
|
||||||
|
mFight = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setFlee(int value)
|
||||||
|
{
|
||||||
|
mFlee = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CreatureStats::setAlarm(int value)
|
||||||
|
{
|
||||||
|
mAlarm = value;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -31,11 +31,6 @@ namespace MWMechanics
|
|||||||
AiSequence mAiSequence;
|
AiSequence mAiSequence;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
CreatureStats();
|
|
||||||
CreatureStats(const CreatureStats &);
|
|
||||||
virtual ~CreatureStats();
|
|
||||||
|
|
||||||
const CreatureStats & operator=(const CreatureStats &);
|
|
||||||
|
|
||||||
const Stat<int> & getAttribute(int index) const;
|
const Stat<int> & getAttribute(int index) const;
|
||||||
|
|
||||||
@ -106,185 +101,10 @@ namespace MWMechanics
|
|||||||
const AiSequence& getAiSequence() const;
|
const AiSequence& getAiSequence() const;
|
||||||
|
|
||||||
AiSequence& getAiSequence();
|
AiSequence& getAiSequence();
|
||||||
};
|
|
||||||
|
|
||||||
// Inline const getters
|
|
||||||
|
|
||||||
inline const Stat<int> &
|
|
||||||
CreatureStats::getAttribute(int index) const {
|
|
||||||
if (index < 0 || index > 7) {
|
|
||||||
throw std::runtime_error("attribute index is out of range");
|
|
||||||
}
|
|
||||||
return mAttributes[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const DynamicStat<int> &
|
|
||||||
CreatureStats::getHealth() const {
|
|
||||||
return mDynamic[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const DynamicStat<int> &
|
|
||||||
CreatureStats::getMagicka() const {
|
|
||||||
return mDynamic[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const DynamicStat<int> &
|
|
||||||
CreatureStats::getFatigue() const {
|
|
||||||
return mDynamic[2];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const Spells &
|
|
||||||
CreatureStats::getSpells() const {
|
|
||||||
return mSpells;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const ActiveSpells &
|
|
||||||
CreatureStats::getActiveSpells() const {
|
|
||||||
return mActiveSpells;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const MagicEffects &
|
|
||||||
CreatureStats::getMagicEffects() const {
|
|
||||||
return mMagicEffects;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline int
|
|
||||||
CreatureStats::getLevel() const {
|
|
||||||
return mLevel;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline int
|
float getFatigueTerm() const;
|
||||||
CreatureStats::getHello() const {
|
///< Return effective fatigue
|
||||||
return mHello;
|
};
|
||||||
}
|
|
||||||
|
|
||||||
inline int
|
|
||||||
CreatureStats::getFight() const {
|
|
||||||
return mFight;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline int
|
|
||||||
CreatureStats::getFlee() const {
|
|
||||||
return mFlee;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline int
|
|
||||||
CreatureStats::getAlarm() const {
|
|
||||||
return mAlarm;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Inline non-const getters
|
|
||||||
|
|
||||||
inline Stat<int> &
|
|
||||||
CreatureStats::getAttribute(int index) {
|
|
||||||
if (index < 0 || index > 7) {
|
|
||||||
throw std::runtime_error("attribute index is out of range");
|
|
||||||
}
|
|
||||||
return mAttributes[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline DynamicStat<int> &
|
|
||||||
CreatureStats::getHealth() {
|
|
||||||
return mDynamic[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline DynamicStat<int> &
|
|
||||||
CreatureStats::getMagicka() {
|
|
||||||
return mDynamic[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline DynamicStat<int> &
|
|
||||||
CreatureStats::getFatigue() {
|
|
||||||
return mDynamic[2];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline DynamicStat<int> &
|
|
||||||
CreatureStats::getDynamic(int index) {
|
|
||||||
if (index < 0 || index > 2) {
|
|
||||||
throw std::runtime_error("dynamic stat index is out of range");
|
|
||||||
}
|
|
||||||
return mDynamic[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
inline Spells &
|
|
||||||
CreatureStats::getSpells() {
|
|
||||||
return mSpells;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setSpells(const Spells &spells) {
|
|
||||||
mSpells = spells;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline ActiveSpells &
|
|
||||||
CreatureStats::getActiveSpells() {
|
|
||||||
return mActiveSpells;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline MagicEffects &
|
|
||||||
CreatureStats::getMagicEffects() {
|
|
||||||
return mMagicEffects;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Inline setters
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setAttribute(int index, const Stat<int> &value) {
|
|
||||||
if (index < 0 || index > 7) {
|
|
||||||
throw std::runtime_error("attribute index is out of range");
|
|
||||||
}
|
|
||||||
mAttributes[index] = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setHealth(const DynamicStat<int> &value) {
|
|
||||||
mDynamic[0] = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setMagicka(const DynamicStat<int> &value) {
|
|
||||||
mDynamic[1] = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setFatigue(const DynamicStat<int> &value) {
|
|
||||||
mDynamic[2] = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setLevel(int level) {
|
|
||||||
mLevel = level;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setActiveSpells(const ActiveSpells &active) {
|
|
||||||
mActiveSpells = active;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setMagicEffects(const MagicEffects &effects) {
|
|
||||||
mMagicEffects = effects;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setHello(int value) {
|
|
||||||
mHello = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setFight(int value) {
|
|
||||||
mFight = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setFlee(int value) {
|
|
||||||
mFlee = value;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void
|
|
||||||
CreatureStats::setAlarm(int value) {
|
|
||||||
mAlarm = value;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -11,9 +11,6 @@
|
|||||||
#include <OgreBillboardSet.h>
|
#include <OgreBillboardSet.h>
|
||||||
#include <OgreEntity.h>
|
#include <OgreEntity.h>
|
||||||
#include <OgreSubEntity.h>
|
#include <OgreSubEntity.h>
|
||||||
#include <OgreOverlay.h>
|
|
||||||
#include <OgreOverlayManager.h>
|
|
||||||
#include <OgreOverlayContainer.h>
|
|
||||||
|
|
||||||
#include <boost/lexical_cast.hpp>
|
#include <boost/lexical_cast.hpp>
|
||||||
|
|
||||||
|
@ -24,7 +24,6 @@ namespace Ogre
|
|||||||
class Entity;
|
class Entity;
|
||||||
class BillboardSet;
|
class BillboardSet;
|
||||||
class TextureUnitState;
|
class TextureUnitState;
|
||||||
class Overlay;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace MWRender
|
namespace MWRender
|
||||||
|
49
apps/openmw/mwworld/actioneat.cpp
Normal file
49
apps/openmw/mwworld/actioneat.cpp
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
|
||||||
|
#include "actioneat.hpp"
|
||||||
|
|
||||||
|
#include <cstdlib>
|
||||||
|
|
||||||
|
#include <components/esm/loadskil.hpp>
|
||||||
|
|
||||||
|
#include <components/esm_store/store.hpp>
|
||||||
|
|
||||||
|
#include "../mwbase/environment.hpp"
|
||||||
|
#include "../mwbase/world.hpp"
|
||||||
|
|
||||||
|
#include "../mwmechanics/creaturestats.hpp"
|
||||||
|
#include "../mwmechanics/npcstats.hpp"
|
||||||
|
|
||||||
|
#include "class.hpp"
|
||||||
|
|
||||||
|
namespace MWWorld
|
||||||
|
{
|
||||||
|
void ActionEat::executeImp (const Ptr& actor)
|
||||||
|
{
|
||||||
|
// remove used item
|
||||||
|
getTarget().getRefData().setCount (getTarget().getRefData().getCount()-1);
|
||||||
|
|
||||||
|
// check for success
|
||||||
|
const MWMechanics::CreatureStats& creatureStats = MWWorld::Class::get (actor).getCreatureStats (actor);
|
||||||
|
MWMechanics::NpcStats& npcStats = MWWorld::Class::get (actor).getNpcStats (actor);
|
||||||
|
|
||||||
|
float x =
|
||||||
|
(npcStats.getSkill (ESM::Skill::Alchemy).getModified() +
|
||||||
|
0.2 * creatureStats.getAttribute (1).getModified()
|
||||||
|
+ 0.1 * creatureStats.getAttribute (7).getModified())
|
||||||
|
* creatureStats.getFatigueTerm();
|
||||||
|
|
||||||
|
if (x>=100*static_cast<float> (std::rand()) / RAND_MAX)
|
||||||
|
{
|
||||||
|
// apply to actor
|
||||||
|
std::string id = Class::get (getTarget()).getId (getTarget());
|
||||||
|
|
||||||
|
Class::get (actor).apply (actor, id, actor);
|
||||||
|
// we ignore the result here. Skill increases no matter if the ingredient did something or not.
|
||||||
|
|
||||||
|
// increase skill
|
||||||
|
Class::get (actor).skillUsageSucceeded (actor, ESM::Skill::Alchemy, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ActionEat::ActionEat (const MWWorld::Ptr& object) : Action (false, object) {}
|
||||||
|
}
|
19
apps/openmw/mwworld/actioneat.hpp
Normal file
19
apps/openmw/mwworld/actioneat.hpp
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
#ifndef GAME_MWWORLD_ACTIONEAT_H
|
||||||
|
#define GAME_MWWORLD_ACTIONEAT_H
|
||||||
|
|
||||||
|
#include "action.hpp"
|
||||||
|
#include "ptr.hpp"
|
||||||
|
|
||||||
|
namespace MWWorld
|
||||||
|
{
|
||||||
|
class ActionEat : public Action
|
||||||
|
{
|
||||||
|
virtual void executeImp (const Ptr& actor);
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
ActionEat (const MWWorld::Ptr& object);
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
@ -290,7 +290,6 @@ namespace MWWorld
|
|||||||
|
|
||||||
mCurrentCell = *iter;
|
mCurrentCell = *iter;
|
||||||
|
|
||||||
|
|
||||||
// adjust player
|
// adjust player
|
||||||
playerCellChange (mCurrentCell, position, adjustPlayerPos);
|
playerCellChange (mCurrentCell, position, adjustPlayerPos);
|
||||||
|
|
||||||
@ -300,6 +299,8 @@ namespace MWWorld
|
|||||||
mRendering.switchToExterior();
|
mRendering.switchToExterior();
|
||||||
|
|
||||||
mCellChanged = true;
|
mCellChanged = true;
|
||||||
|
|
||||||
|
MWBase::Environment::get().getWindowManager ()->loadingDone ();
|
||||||
}
|
}
|
||||||
|
|
||||||
//We need the ogre renderer and a scene node.
|
//We need the ogre renderer and a scene node.
|
||||||
@ -369,6 +370,8 @@ namespace MWWorld
|
|||||||
MWBase::Environment::get().getWorld()->adjustSky();
|
MWBase::Environment::get().getWorld()->adjustSky();
|
||||||
|
|
||||||
mCellChanged = true;
|
mCellChanged = true;
|
||||||
|
|
||||||
|
MWBase::Environment::get().getWindowManager ()->loadingDone ();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Scene::changeToExteriorCell (const ESM::Position& position)
|
void Scene::changeToExteriorCell (const ESM::Position& position)
|
||||||
|
@ -1,8 +1,15 @@
|
|||||||
#include "loadgmst.hpp"
|
#include "loadgmst.hpp"
|
||||||
|
|
||||||
|
#include <stdexcept>
|
||||||
|
|
||||||
|
#include "defs.hpp"
|
||||||
|
|
||||||
namespace ESM
|
namespace ESM
|
||||||
{
|
{
|
||||||
|
|
||||||
|
/// \todo Review GMST "fixing". Probably remove completely or at least make it optional. Its definitely not
|
||||||
|
/// working properly in its current state and I doubt it can be fixed without breaking other stuff.
|
||||||
|
|
||||||
// Some handy macros
|
// Some handy macros
|
||||||
#define cI(s,x) { if(id == (s)) return (i == (x)); }
|
#define cI(s,x) { if(id == (s)) return (i == (x)); }
|
||||||
#define cF(s,x) { if(id == (s)) return (f == (x)); }
|
#define cF(s,x) { if(id == (s)) return (f == (x)); }
|
||||||
@ -169,4 +176,32 @@ void GameSetting::load(ESMReader &esm)
|
|||||||
dirty = true;
|
dirty = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int GameSetting::getInt() const
|
||||||
|
{
|
||||||
|
switch (type)
|
||||||
|
{
|
||||||
|
case VT_Float: return static_cast<int> (f);
|
||||||
|
case VT_Int: return i;
|
||||||
|
default: throw std::runtime_error ("GMST " + id + " is not of a numeric type");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int GameSetting::getFloat() const
|
||||||
|
{
|
||||||
|
switch (type)
|
||||||
|
{
|
||||||
|
case VT_Float: return f;
|
||||||
|
case VT_Int: return i;
|
||||||
|
default: throw std::runtime_error ("GMST " + id + " is not of a numeric type");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string GameSetting::getString() const
|
||||||
|
{
|
||||||
|
if (type==VT_String)
|
||||||
|
return str;
|
||||||
|
|
||||||
|
throw std::runtime_error ("GMST " + id + " is not a string");
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -83,6 +83,15 @@ struct GameSetting
|
|||||||
bool isDirtyBloodmoon();
|
bool isDirtyBloodmoon();
|
||||||
|
|
||||||
void load(ESMReader &esm);
|
void load(ESMReader &esm);
|
||||||
|
|
||||||
|
int getInt() const;
|
||||||
|
///< Throws an exception if GMST is not of type int or float.
|
||||||
|
|
||||||
|
int getFloat() const;
|
||||||
|
///< Throws an exception if GMST is not of type int or float.
|
||||||
|
|
||||||
|
std::string getString() const;
|
||||||
|
///< Throwns an exception if GMST is not of type string.
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
@ -1,5 +1,30 @@
|
|||||||
#include "loadmgef.hpp"
|
#include "loadmgef.hpp"
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
const int NumberOfHardcodedFlags = 143;
|
||||||
|
const int HardcodedFlags[NumberOfHardcodedFlags] = {
|
||||||
|
0x11c8, 0x11c0, 0x11c8, 0x11e0, 0x11e0, 0x11e0, 0x11e0, 0x11d0,
|
||||||
|
0x11c0, 0x11c0, 0x11e0, 0x11c0, 0x11184, 0x11184, 0x1f0, 0x1f0,
|
||||||
|
0x1f0, 0x11d2, 0x11f0, 0x11d0, 0x11d0, 0x11d1, 0x1d2, 0x1f0,
|
||||||
|
0x1d0, 0x1d0, 0x1d1, 0x1f0, 0x11d0, 0x11d0, 0x11d0, 0x11d0,
|
||||||
|
0x11d0, 0x11d0, 0x11d0, 0x11d0, 0x11d0, 0x1d0, 0x1d0, 0x11c8,
|
||||||
|
0x31c0, 0x11c0, 0x11c0, 0x11c0, 0x1180, 0x11d8, 0x11d8, 0x11d0,
|
||||||
|
0x11d0, 0x11180, 0x11180, 0x11180, 0x11180, 0x11180, 0x11180, 0x11180,
|
||||||
|
0x11180, 0x11c4, 0x111b8, 0x1040, 0x104c, 0x104c, 0x104c, 0x104c,
|
||||||
|
0x1040, 0x1040, 0x1040, 0x11c0, 0x11c0, 0x1cc, 0x1cc, 0x1cc,
|
||||||
|
0x1cc, 0x1cc, 0x1c2, 0x1c0, 0x1c0, 0x1c0, 0x1c1, 0x11c2,
|
||||||
|
0x11c0, 0x11c0, 0x11c0, 0x11c1, 0x11c0, 0x21192, 0x20190, 0x20190,
|
||||||
|
0x20190, 0x21191, 0x11c0, 0x11c0, 0x11c0, 0x11c0, 0x11c0, 0x11c0,
|
||||||
|
0x11c0, 0x11c0, 0x11c0, 0x11c0, 0x1c0, 0x11190, 0x9048, 0x9048,
|
||||||
|
0x9048, 0x9048, 0x9048, 0x9048, 0x9048, 0x9048, 0x9048, 0x9048,
|
||||||
|
0x9048, 0x9048, 0x9048, 0x9048, 0x9048, 0x11c0, 0x1180, 0x1180,
|
||||||
|
0x5048, 0x5048, 0x5048, 0x5048, 0x5048, 0x5048, 0x1188, 0x5048,
|
||||||
|
0x5048, 0x5048, 0x5048, 0x5048, 0x1048, 0x104c, 0x1048, 0x40,
|
||||||
|
0x11c8, 0x1048, 0x1048, 0x1048, 0x1048, 0x1048, 0x1048
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
namespace ESM
|
namespace ESM
|
||||||
{
|
{
|
||||||
|
|
||||||
@ -8,6 +33,10 @@ void MagicEffect::load(ESMReader &esm)
|
|||||||
esm.getHNT(index, "INDX");
|
esm.getHNT(index, "INDX");
|
||||||
|
|
||||||
esm.getHNT(data, "MEDT", 36);
|
esm.getHNT(data, "MEDT", 36);
|
||||||
|
|
||||||
|
if (index>=0 && index<NumberOfHardcodedFlags)
|
||||||
|
data.flags |= HardcodedFlags[index];
|
||||||
|
|
||||||
icon = esm.getHNOString("ITEX");
|
icon = esm.getHNOString("ITEX");
|
||||||
particle = esm.getHNOString("PTEX");
|
particle = esm.getHNOString("PTEX");
|
||||||
|
|
||||||
|
@ -10,6 +10,7 @@ struct MagicEffect
|
|||||||
{
|
{
|
||||||
enum Flags
|
enum Flags
|
||||||
{
|
{
|
||||||
|
NoDuration = 0x4,
|
||||||
SpellMaking = 0x0200,
|
SpellMaking = 0x0200,
|
||||||
Enchanting = 0x0400,
|
Enchanting = 0x0400,
|
||||||
Negative = 0x0800 // A harmful effect. Will determine whether
|
Negative = 0x0800 // A harmful effect. Will determine whether
|
||||||
|
@ -164,6 +164,13 @@ void ManualBulletShapeLoader::handleNode(Nif::Node *node, int flags,
|
|||||||
// the flags we currently use, at least.
|
// the flags we currently use, at least.
|
||||||
flags |= node->flags;
|
flags |= node->flags;
|
||||||
|
|
||||||
|
// Marker objects: no collision
|
||||||
|
/// \todo don't do this in the editor
|
||||||
|
if (node->name.find("marker") != std::string::npos)
|
||||||
|
{
|
||||||
|
flags |= 0x800;
|
||||||
|
}
|
||||||
|
|
||||||
// Check for extra data
|
// Check for extra data
|
||||||
Nif::Extra *e = node;
|
Nif::Extra *e = node;
|
||||||
while (!e->extra.empty())
|
while (!e->extra.empty())
|
||||||
@ -178,12 +185,10 @@ void ManualBulletShapeLoader::handleNode(Nif::Node *node, int flags,
|
|||||||
// affecting the entire subtree of this node
|
// affecting the entire subtree of this node
|
||||||
Nif::NiStringExtraData *sd = (Nif::NiStringExtraData*)e;
|
Nif::NiStringExtraData *sd = (Nif::NiStringExtraData*)e;
|
||||||
|
|
||||||
if (sd->string == "NCO" && !raycastingOnly)
|
if (sd->string == "NCO")
|
||||||
{
|
{
|
||||||
// No collision. Use an internal flag setting to mark this.
|
// No collision. Use an internal flag setting to mark this.
|
||||||
// We ignor this node!
|
|
||||||
flags |= 0x800;
|
flags |= 0x800;
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
else if (sd->string == "MRK" && !raycastingOnly)
|
else if (sd->string == "MRK" && !raycastingOnly)
|
||||||
// Marker objects. These are only visible in the
|
// Marker objects. These are only visible in the
|
||||||
@ -229,7 +234,7 @@ void ManualBulletShapeLoader::handleNode(Nif::Node *node, int flags,
|
|||||||
}
|
}
|
||||||
else if (node->recType == Nif::RC_NiTriShape && (isCollisionNode || !hasCollisionNode))
|
else if (node->recType == Nif::RC_NiTriShape && (isCollisionNode || !hasCollisionNode))
|
||||||
{
|
{
|
||||||
cShape->collide = true;
|
cShape->collide = !(flags&0x800);
|
||||||
handleNiTriShape(dynamic_cast<Nif::NiTriShape*>(node), flags,node->trafo.rotation,node->trafo.pos,node->trafo.scale,raycastingOnly);
|
handleNiTriShape(dynamic_cast<Nif::NiTriShape*>(node), flags,node->trafo.rotation,node->trafo.pos,node->trafo.scale,raycastingOnly);
|
||||||
}
|
}
|
||||||
else if(node->recType == Nif::RC_RootCollisionNode)
|
else if(node->recType == Nif::RC_RootCollisionNode)
|
||||||
|
@ -940,6 +940,11 @@ public:
|
|||||||
{
|
{
|
||||||
flags |= node->flags;
|
flags |= node->flags;
|
||||||
|
|
||||||
|
// Marker objects: just skip the entire node
|
||||||
|
/// \todo don't do this in the editor
|
||||||
|
if (node->name.find("marker") != std::string::npos)
|
||||||
|
return;
|
||||||
|
|
||||||
Nif::ExtraPtr e = node->extra;
|
Nif::ExtraPtr e = node->extra;
|
||||||
while(!e.empty())
|
while(!e.empty())
|
||||||
{
|
{
|
||||||
|
Loading…
x
Reference in New Issue
Block a user