forked from mirror/openmw-tes3mp
Merge pull request #954 from Allofich/AIWanderDuration
Improve duration calculations in Wander AI
This commit is contained in:
commit
a14f1bc222
4 changed files with 35 additions and 20 deletions
|
@ -97,8 +97,8 @@ namespace MWMechanics
|
||||||
};
|
};
|
||||||
|
|
||||||
AiWander::AiWander(int distance, int duration, int timeOfDay, const std::vector<unsigned char>& idle, bool repeat):
|
AiWander::AiWander(int distance, int duration, int timeOfDay, const std::vector<unsigned char>& idle, bool repeat):
|
||||||
mDistance(distance), mDuration(duration), mTimeOfDay(timeOfDay), mIdle(idle), mRepeat(repeat)
|
mDistance(distance), mDuration(duration), mRemainingDuration(duration), mTimeOfDay(timeOfDay), mIdle(idle),
|
||||||
, mStoredInitialActorPosition(false)
|
mRepeat(repeat), mStoredInitialActorPosition(false)
|
||||||
{
|
{
|
||||||
mIdle.resize(8, 0);
|
mIdle.resize(8, 0);
|
||||||
init();
|
init();
|
||||||
|
@ -122,6 +122,11 @@ namespace MWMechanics
|
||||||
mDuration = 0;
|
mDuration = 0;
|
||||||
if(mDuration == 0)
|
if(mDuration == 0)
|
||||||
mTimeOfDay = 0;
|
mTimeOfDay = 0;
|
||||||
|
if(mDuration > 24)
|
||||||
|
{
|
||||||
|
mDuration = 24;
|
||||||
|
mRemainingDuration = (mDuration);
|
||||||
|
}
|
||||||
|
|
||||||
mPopulateAvailableNodes = true;
|
mPopulateAvailableNodes = true;
|
||||||
|
|
||||||
|
@ -200,12 +205,7 @@ namespace MWMechanics
|
||||||
mPopulateAvailableNodes = true;
|
mPopulateAvailableNodes = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mStarted)
|
mRemainingDuration -= ((duration*MWBase::Environment::get().getWorld()->getTimeScaleFactor()) / 3600);
|
||||||
{
|
|
||||||
// Set mStartTime once this package starts being executed
|
|
||||||
mStartTime = MWBase::Environment::get().getWorld()->getTimeStamp();
|
|
||||||
mStarted = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
cStats.setDrawState(DrawState_Nothing);
|
cStats.setDrawState(DrawState_Nothing);
|
||||||
cStats.setMovementFlag(CreatureStats::Flag_Run, false);
|
cStats.setMovementFlag(CreatureStats::Flag_Run, false);
|
||||||
|
@ -235,8 +235,9 @@ namespace MWMechanics
|
||||||
|
|
||||||
if (isPackageCompleted(actor, storage))
|
if (isPackageCompleted(actor, storage))
|
||||||
{
|
{
|
||||||
// Reset mStarted so that package will get a new mStarttime when it repeats
|
// Reset package so it can be used again
|
||||||
mStarted = false;
|
mRemainingDuration=mDuration;
|
||||||
|
init();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -317,10 +318,8 @@ namespace MWMechanics
|
||||||
{
|
{
|
||||||
if (mDuration)
|
if (mDuration)
|
||||||
{
|
{
|
||||||
// End package if duration is complete or mid-night hits:
|
// End package if duration is complete
|
||||||
MWWorld::TimeStamp currentTime = MWBase::Environment::get().getWorld()->getTimeStamp();
|
if (mRemainingDuration <= 0)
|
||||||
if ((currentTime.getHour() >= mStartTime.getHour() + mDuration) ||
|
|
||||||
(int(currentTime.getHour()) == 0 && currentTime.getDay() != mStartTime.getDay()))
|
|
||||||
{
|
{
|
||||||
stopWalking(actor, storage);
|
stopWalking(actor, storage);
|
||||||
return true;
|
return true;
|
||||||
|
@ -784,6 +783,8 @@ namespace MWMechanics
|
||||||
|
|
||||||
void AiWander::fastForward(const MWWorld::Ptr& actor, AiState &state)
|
void AiWander::fastForward(const MWWorld::Ptr& actor, AiState &state)
|
||||||
{
|
{
|
||||||
|
// Update duration counter
|
||||||
|
mRemainingDuration--;
|
||||||
if (mDistance == 0)
|
if (mDistance == 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
@ -923,11 +924,17 @@ namespace MWMechanics
|
||||||
|
|
||||||
void AiWander::writeState(ESM::AiSequence::AiSequence &sequence) const
|
void AiWander::writeState(ESM::AiSequence::AiSequence &sequence) const
|
||||||
{
|
{
|
||||||
|
float remainingDuration;
|
||||||
|
if (mRemainingDuration > 0 && mRemainingDuration < 24)
|
||||||
|
remainingDuration = mRemainingDuration;
|
||||||
|
else
|
||||||
|
remainingDuration = mDuration;
|
||||||
|
|
||||||
std::auto_ptr<ESM::AiSequence::AiWander> wander(new ESM::AiSequence::AiWander());
|
std::auto_ptr<ESM::AiSequence::AiWander> wander(new ESM::AiSequence::AiWander());
|
||||||
wander->mData.mDistance = mDistance;
|
wander->mData.mDistance = mDistance;
|
||||||
wander->mData.mDuration = mDuration;
|
wander->mData.mDuration = mDuration;
|
||||||
wander->mData.mTimeOfDay = mTimeOfDay;
|
wander->mData.mTimeOfDay = mTimeOfDay;
|
||||||
wander->mStartTime = mStartTime.toEsm();
|
wander->mDurationData.mRemainingDuration = remainingDuration;
|
||||||
assert (mIdle.size() == 8);
|
assert (mIdle.size() == 8);
|
||||||
for (int i=0; i<8; ++i)
|
for (int i=0; i<8; ++i)
|
||||||
wander->mData.mIdle[i] = mIdle[i];
|
wander->mData.mIdle[i] = mIdle[i];
|
||||||
|
@ -945,15 +952,18 @@ namespace MWMechanics
|
||||||
AiWander::AiWander (const ESM::AiSequence::AiWander* wander)
|
AiWander::AiWander (const ESM::AiSequence::AiWander* wander)
|
||||||
: mDistance(wander->mData.mDistance)
|
: mDistance(wander->mData.mDistance)
|
||||||
, mDuration(wander->mData.mDuration)
|
, mDuration(wander->mData.mDuration)
|
||||||
|
, mRemainingDuration(wander->mDurationData.mRemainingDuration)
|
||||||
, mTimeOfDay(wander->mData.mTimeOfDay)
|
, mTimeOfDay(wander->mData.mTimeOfDay)
|
||||||
, mRepeat(wander->mData.mShouldRepeat != 0)
|
, mRepeat(wander->mData.mShouldRepeat != 0)
|
||||||
, mStoredInitialActorPosition(wander->mStoredInitialActorPosition)
|
, mStoredInitialActorPosition(wander->mStoredInitialActorPosition)
|
||||||
, mStartTime(MWWorld::TimeStamp(wander->mStartTime))
|
|
||||||
{
|
{
|
||||||
if (mStoredInitialActorPosition)
|
if (mStoredInitialActorPosition)
|
||||||
mInitialActorPosition = wander->mInitialActorPosition;
|
mInitialActorPosition = wander->mInitialActorPosition;
|
||||||
for (int i=0; i<8; ++i)
|
for (int i=0; i<8; ++i)
|
||||||
mIdle.push_back(wander->mData.mIdle[i]);
|
mIdle.push_back(wander->mData.mIdle[i]);
|
||||||
|
if (mRemainingDuration <= 0 || mRemainingDuration >= 24)
|
||||||
|
mRemainingDuration = mDuration;
|
||||||
|
|
||||||
|
|
||||||
init();
|
init();
|
||||||
}
|
}
|
||||||
|
|
|
@ -103,6 +103,7 @@ namespace MWMechanics
|
||||||
|
|
||||||
int mDistance; // how far the actor can wander from the spawn point
|
int mDistance; // how far the actor can wander from the spawn point
|
||||||
int mDuration;
|
int mDuration;
|
||||||
|
float mRemainingDuration;
|
||||||
int mTimeOfDay;
|
int mTimeOfDay;
|
||||||
std::vector<unsigned char> mIdle;
|
std::vector<unsigned char> mIdle;
|
||||||
bool mRepeat;
|
bool mRepeat;
|
||||||
|
@ -123,7 +124,6 @@ namespace MWMechanics
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
MWWorld::TimeStamp mStartTime;
|
|
||||||
|
|
||||||
// allowed pathgrid nodes based on mDistance from the spawn point
|
// allowed pathgrid nodes based on mDistance from the spawn point
|
||||||
// in local coordinates of mCell
|
// in local coordinates of mCell
|
||||||
|
|
|
@ -15,7 +15,7 @@ namespace AiSequence
|
||||||
void AiWander::load(ESMReader &esm)
|
void AiWander::load(ESMReader &esm)
|
||||||
{
|
{
|
||||||
esm.getHNT (mData, "DATA");
|
esm.getHNT (mData, "DATA");
|
||||||
esm.getHNT(mStartTime, "STAR");
|
esm.getHNT(mDurationData, "STAR");
|
||||||
mStoredInitialActorPosition = false;
|
mStoredInitialActorPosition = false;
|
||||||
if (esm.isNextSub("POS_"))
|
if (esm.isNextSub("POS_"))
|
||||||
{
|
{
|
||||||
|
@ -27,7 +27,7 @@ namespace AiSequence
|
||||||
void AiWander::save(ESMWriter &esm) const
|
void AiWander::save(ESMWriter &esm) const
|
||||||
{
|
{
|
||||||
esm.writeHNT ("DATA", mData);
|
esm.writeHNT ("DATA", mData);
|
||||||
esm.writeHNT ("STAR", mStartTime);
|
esm.writeHNT ("STAR", mDurationData);
|
||||||
if (mStoredInitialActorPosition)
|
if (mStoredInitialActorPosition)
|
||||||
esm.writeHNT ("POS_", mInitialActorPosition);
|
esm.writeHNT ("POS_", mInitialActorPosition);
|
||||||
}
|
}
|
||||||
|
|
|
@ -46,6 +46,11 @@ namespace ESM
|
||||||
unsigned char mIdle[8];
|
unsigned char mIdle[8];
|
||||||
unsigned char mShouldRepeat;
|
unsigned char mShouldRepeat;
|
||||||
};
|
};
|
||||||
|
struct AiWanderDuration
|
||||||
|
{
|
||||||
|
float mRemainingDuration;
|
||||||
|
int unused;
|
||||||
|
};
|
||||||
struct AiTravelData
|
struct AiTravelData
|
||||||
{
|
{
|
||||||
float mX, mY, mZ;
|
float mX, mY, mZ;
|
||||||
|
@ -61,7 +66,7 @@ namespace ESM
|
||||||
struct AiWander : AiPackage
|
struct AiWander : AiPackage
|
||||||
{
|
{
|
||||||
AiWanderData mData;
|
AiWanderData mData;
|
||||||
ESM::TimeStamp mStartTime;
|
AiWanderDuration mDurationData; // was ESM::TimeStamp mStartTime;
|
||||||
|
|
||||||
bool mStoredInitialActorPosition;
|
bool mStoredInitialActorPosition;
|
||||||
ESM::Vector3 mInitialActorPosition;
|
ESM::Vector3 mInitialActorPosition;
|
||||||
|
|
Loading…
Reference in a new issue