1
0
mirror of https://gitlab.com/OpenMW/openmw.git synced 2025-01-25 15:35:23 +00:00

Merge pull request #2457 from Capostrophic/sneak

Sneaking consistency fixes (bug #5103)
This commit is contained in:
Andrei Kortunov 2019-08-18 08:57:22 +04:00 committed by GitHub
commit ed8828d3bc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 16 additions and 31 deletions

View File

@ -121,6 +121,7 @@
Bug #5092: NPCs with enchanted weapons play sound when out of charges
Bug #5093: Hand to hand sound plays on knocked out enemies
Bug #5099: Non-swimming enemies will enter water if player is water walking
Bug #5103: Sneaking state behavior is still inconsistent
Bug #5104: Black Dart's enchantment doesn't trigger at low Enchant levels
Bug #5105: NPCs start combat with werewolves from any distance
Bug #5106: Still can jump even when encumbered

View File

@ -940,10 +940,9 @@ namespace MWClass
const float normalizedEncumbrance = getNormalizedEncumbrance(ptr);
bool swimming = world->isSwimming(ptr);
bool sneaking = MWBase::Environment::get().getMechanicsManager()->isSneaking(ptr);
bool running = stats.getStance(MWMechanics::CreatureStats::Stance_Run);
bool inair = !world->isOnGround(ptr) && !swimming && !world->isFlying(ptr);
bool sneaking = stats.getStance(MWMechanics::CreatureStats::Stance_Sneak);
sneaking = sneaking && (inair || MWBase::Environment::get().getMechanicsManager()->isSneaking(ptr));
bool running = stats.getStance(MWMechanics::CreatureStats::Stance_Run);
running = running && (inair || MWBase::Environment::get().getMechanicsManager()->isRunning(ptr));
float walkSpeed = gmst.fMinWalkSpeed->mValue.getFloat() + 0.01f*npcdata->mNpcStats.getAttribute(ESM::Attribute::Speed).getModified()*

View File

@ -1785,14 +1785,7 @@ namespace MWMechanics
MWWorld::Ptr player = getPlayer();
CreatureStats& stats = player.getClass().getCreatureStats(player);
MWBase::World* world = MWBase::Environment::get().getWorld();
bool sneaking = stats.getStance(MWMechanics::CreatureStats::Stance_Sneak);
bool inair = !world->isOnGround(player) && !world->isSwimming(player) && !world->isFlying(player);
sneaking = sneaking && (ctrl->isSneaking() || inair);
if (!sneaking)
if (!MWBase::Environment::get().getMechanicsManager()->isSneaking(player))
{
MWBase::Environment::get().getWindowManager()->setSneakVisibility(false);
return;
@ -1800,6 +1793,7 @@ namespace MWMechanics
static float sneakSkillTimer = 0.f; // Times sneak skill progress from "avoid notice"
MWBase::World* world = MWBase::Environment::get().getWorld();
const MWWorld::Store<ESM::GameSetting>& gmst = world->getStore().get<ESM::GameSetting>();
static const float fSneakUseDist = gmst.find("fSneakUseDist")->mValue.getFloat();
static const float fSneakUseDelay = gmst.find("fSneakUseDelay")->mValue.getFloat();

View File

@ -568,10 +568,6 @@ void CharacterController::refreshMovementAnims(const std::string& weapShortGroup
mCurrentMovement = movementAnimName;
if(!mCurrentMovement.empty())
{
bool isflying = MWBase::Environment::get().getWorld()->isFlying(mPtr);
bool isrunning = mPtr.getClass().getCreatureStats(mPtr).getStance(MWMechanics::CreatureStats::Stance_Run) && !isflying;
bool issneaking = mPtr.getClass().getCreatureStats(mPtr).getStance(MWMechanics::CreatureStats::Stance_Sneak) && !isflying;
// For non-flying creatures, MW uses the Walk animation to calculate the animation velocity
// even if we are running. This must be replicated, otherwise the observed speed would differ drastically.
std::string anim = mCurrentMovement;
@ -604,7 +600,7 @@ void CharacterController::refreshMovementAnims(const std::string& weapShortGroup
// The first person anims don't have any velocity to calculate a speed multiplier from.
// We use the third person velocities instead.
// FIXME: should be pulled from the actual animation, but it is not presently loaded.
mMovementAnimSpeed = (issneaking ? 33.5452f : (isrunning ? 222.857f : 154.064f));
mMovementAnimSpeed = (isSneaking() ? 33.5452f : (isRunning() ? 222.857f : 154.064f));
mMovementAnimationControlled = false;
}
}

View File

@ -477,7 +477,12 @@ namespace MWMechanics
bool MechanicsManager::isSneaking(const MWWorld::Ptr& ptr)
{
return mActors.isSneaking(ptr);
CreatureStats& stats = ptr.getClass().getCreatureStats(ptr);
MWBase::World* world = MWBase::Environment::get().getWorld();
bool animActive = mActors.isSneaking(ptr);
bool stanceOn = stats.getStance(MWMechanics::CreatureStats::Stance_Sneak);
bool inair = !world->isOnGround(ptr) && !world->isSwimming(ptr) && !world->isFlying(ptr);
return stanceOn && (animActive || inair);
}
void MechanicsManager::rest(double hours, bool sleep)
@ -965,8 +970,7 @@ namespace MWMechanics
return true;
// check if a player tries to pickpocket a target NPC
if(ptr.getClass().getCreatureStats(ptr).getStance(MWMechanics::CreatureStats::Stance_Sneak)
|| target.getClass().getCreatureStats(target).getKnockedDown())
if (target.getClass().getCreatureStats(target).getKnockedDown() || isSneaking(ptr))
return false;
return true;
@ -1586,9 +1590,7 @@ namespace MWMechanics
return false;
float sneakTerm = 0;
if (ptr.getClass().getCreatureStats(ptr).getStance(CreatureStats::Stance_Sneak)
&& !MWBase::Environment::get().getWorld()->isSwimming(ptr)
&& MWBase::Environment::get().getWorld()->isOnGround(ptr))
if (isSneaking(ptr))
{
static float fSneakSkillMult = store.find("fSneakSkillMult")->mValue.getFloat();
static float fSneakBootMult = store.find("fSneakBootMult")->mValue.getFloat();
@ -1596,7 +1598,7 @@ namespace MWMechanics
int agility = stats.getAttribute(ESM::Attribute::Agility).getModified();
int luck = stats.getAttribute(ESM::Attribute::Luck).getModified();
float bootWeight = 0;
if (ptr.getClass().isNpc())
if (ptr.getClass().isNpc() && MWBase::Environment::get().getWorld()->isOnGround(ptr))
{
const MWWorld::InventoryStore& inv = ptr.getClass().getInventoryStore(ptr);
MWWorld::ConstContainerStoreIterator it = inv.getSlot(MWWorld::InventoryStore::Slot_Boots);

View File

@ -186,14 +186,7 @@ namespace MWScript
virtual void execute (Interpreter::Runtime& runtime)
{
MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPlayerPtr();
MWMechanics::CreatureStats& stats = ptr.getClass().getCreatureStats(ptr);
MWBase::World* world = MWBase::Environment::get().getWorld();
bool stanceOn = stats.getStance(MWMechanics::CreatureStats::Stance_Sneak);
bool sneaking = MWBase::Environment::get().getMechanicsManager()->isSneaking(ptr);
bool inair = !world->isOnGround(ptr) && !world->isSwimming(ptr) && !world->isFlying(ptr);
runtime.push(stanceOn && (sneaking || inair));
runtime.push(MWBase::Environment::get().getMechanicsManager()->isSneaking(ptr));
}
};