AiWander: move idle animation handling to non-delayed section (Fixes #2073)

report
scrawl 10 years ago
parent f9ae0d9d66
commit a1226501fa

@ -282,6 +282,58 @@ namespace MWMechanics
rotate = false;
}
// Check if idle animation finished
short unsigned& playedIdle = storage.mPlayedIdle;
GreetingState& greetingState = storage.mSaidGreeting;
if(idleNow && !checkIdle(actor, playedIdle) && (greetingState == Greet_Done || greetingState == Greet_None))
{
playedIdle = 0;
idleNow = false;
chooseAction = true;
}
MWBase::World *world = MWBase::Environment::get().getWorld();
if(chooseAction)
{
playedIdle = 0;
getRandomIdle(playedIdle); // NOTE: sets mPlayedIdle with a random selection
if(!playedIdle && mDistance)
{
chooseAction = false;
moveNow = true;
}
else
{
// Play idle animation and recreate vanilla (broken?) behavior of resetting start time of AIWander:
MWWorld::TimeStamp currentTime = world->getTimeStamp();
mStartTime = currentTime;
playIdle(actor, playedIdle);
chooseAction = false;
idleNow = true;
// Play idle voiced dialogue entries randomly
int hello = cStats.getAiSetting(CreatureStats::AI_Hello).getModified();
if (hello > 0)
{
int roll = std::rand()/ (static_cast<double> (RAND_MAX) + 1) * 100; // [0, 99]
MWWorld::Ptr player = MWBase::Environment::get().getWorld()->getPlayerPtr();
// Don't bother if the player is out of hearing range
static float fVoiceIdleOdds = MWBase::Environment::get().getWorld()->getStore()
.get<ESM::GameSetting>().find("fVoiceIdleOdds")->getFloat();
// Only say Idle voices when player is in LOS
// A bit counterintuitive, likely vanilla did this to reduce the appearance of
// voices going through walls?
if (roll < fVoiceIdleOdds && Ogre::Vector3(player.getRefData().getPosition().pos).squaredDistance(Ogre::Vector3(pos.pos)) < 1500*1500
&& MWBase::Environment::get().getWorld()->getLOS(player, actor))
MWBase::Environment::get().getDialogueManager()->say(actor, "idle");
}
}
}
float& lastReaction = storage.mReaction;
lastReaction += duration;
if(lastReaction < REACTION_INTERVAL)
@ -293,7 +345,6 @@ namespace MWMechanics
// NOTE: everything below get updated every REACTION_INTERVAL seconds
MWBase::World *world = MWBase::Environment::get().getWorld();
if(mDuration)
{
// End package if duration is complete or mid-night hits:
@ -439,48 +490,6 @@ namespace MWMechanics
}
}
AiWander::GreetingState& greetingState = storage.mSaidGreeting;
short unsigned& playedIdle = storage.mPlayedIdle;
if(chooseAction)
{
playedIdle = 0;
getRandomIdle(playedIdle); // NOTE: sets mPlayedIdle with a random selection
if(!playedIdle && mDistance)
{
chooseAction = false;
moveNow = true;
}
else
{
// Play idle animation and recreate vanilla (broken?) behavior of resetting start time of AIWander:
MWWorld::TimeStamp currentTime = world->getTimeStamp();
mStartTime = currentTime;
playIdle(actor, playedIdle);
chooseAction = false;
idleNow = true;
// Play idle voiced dialogue entries randomly
int hello = cStats.getAiSetting(CreatureStats::AI_Hello).getModified();
if (hello > 0)
{
int roll = std::rand()/ (static_cast<double> (RAND_MAX) + 1) * 100; // [0, 99]
MWWorld::Ptr player = MWBase::Environment::get().getWorld()->getPlayerPtr();
// Don't bother if the player is out of hearing range
static float fVoiceIdleOdds = MWBase::Environment::get().getWorld()->getStore()
.get<ESM::GameSetting>().find("fVoiceIdleOdds")->getFloat();
// Only say Idle voices when player is in LOS
// A bit counterintuitive, likely vanilla did this to reduce the appearance of
// voices going through walls?
if (roll < fVoiceIdleOdds && Ogre::Vector3(player.getRefData().getPosition().pos).squaredDistance(Ogre::Vector3(pos.pos)) < 1500*1500
&& MWBase::Environment::get().getWorld()->getLOS(player, actor))
MWBase::Environment::get().getDialogueManager()->say(actor, "idle");
}
}
}
// Allow interrupting a walking actor to trigger a greeting
if(idleNow || walking)
{
@ -496,7 +505,7 @@ namespace MWMechanics
Ogre::Vector3 playerPos(player.getRefData().getPosition().pos);
Ogre::Vector3 actorPos(actor.getRefData().getPosition().pos);
float playerDistSqr = playerPos.squaredDistance(actorPos);
int& greetingTimer = storage.mGreetingTimer;
if (greetingState == Greet_None)
{
@ -556,14 +565,6 @@ namespace MWMechanics
if (playerDistSqr >= fGreetDistanceReset*fGreetDistanceReset)
greetingState = Greet_None;
}
// Check if idle animation finished
if(!checkIdle(actor, playedIdle) && (playerDistSqr > helloDistance*helloDistance || greetingState == MWMechanics::AiWander::Greet_Done))
{
playedIdle = 0;
idleNow = false;
chooseAction = true;
}
}
if(moveNow && mDistance)

Loading…
Cancel
Save