From 339399f8b1dada292ccb038e4b7f039aecfc122d Mon Sep 17 00:00:00 2001 From: mrcheko Date: Sun, 19 Jan 2014 22:09:51 +0200 Subject: [PATCH] bug fix/logic fix/future suggestion --- apps/openmw/mwmechanics/aicombat.cpp | 27 +++++++++++++++---------- apps/openmw/mwmechanics/aicombat.hpp | 2 +- apps/openmw/mwmechanics/character.cpp | 2 +- apps/openmw/mwmechanics/pathfinding.cpp | 17 ++++++++++++++++ apps/openmw/mwmechanics/pathfinding.hpp | 5 +++++ 5 files changed, 40 insertions(+), 13 deletions(-) diff --git a/apps/openmw/mwmechanics/aicombat.cpp b/apps/openmw/mwmechanics/aicombat.cpp index 6bf97f6ac..f12a10f9b 100644 --- a/apps/openmw/mwmechanics/aicombat.cpp +++ b/apps/openmw/mwmechanics/aicombat.cpp @@ -1,4 +1,5 @@ #include "aicombat.hpp" +#include "aifollow.hpp" #include "movement.hpp" @@ -39,7 +40,7 @@ namespace MWMechanics mTimerAttack(0), mTimerReact(0), mTimerCombatMove(0), - mCloseUp(false), + mFollowTarget(false), mReadyToAttack(false), mStrike(false), mCombatMove(false), @@ -184,7 +185,7 @@ namespace MWMechanics Ogre::Vector3 vDir = vDest - vStart; float distBetween = vDir.length(); - if(distBetween < rangeMelee || (distBetween <= rangeCloseUp && mCloseUp) ) + if(distBetween < rangeMelee || (distBetween <= rangeCloseUp && mFollowTarget) ) { //Melee and Close-up combat vDir.z = 0; @@ -194,13 +195,10 @@ namespace MWMechanics // TODO: use movement settings instead of rotating directly MWBase::Environment::get().getWorld()->rotateObject(actor, 0, 0, zAngle, false); - if(mPathFinder.isPathConstructed()) - mPathFinder.clearPath(); - //MWWorld::Class::get(actor).getMovementSettings(actor).mPosition[1] = 0; //bool LOS = MWBase::Environment::get().getWorld()->getLOS(actor, mTarget); - if (mCloseUp && distBetween > rangeMelee) + if (mFollowTarget && distBetween > rangeMelee) { //Close-up combat: just run up on target mMovement.mPosition[1] = 1; @@ -216,7 +214,7 @@ namespace MWMechanics mTimerCombatMove = 0.1f + 0.1f * static_cast(rand())/RAND_MAX; mCombatMove = true; } - else if(!distantCombat || (distantCombat && rangeMelee/5)) + else if(actor.getClass().isNpc() && (!distantCombat || (distantCombat && rangeMelee/5))) { //apply sideway movement (kind of dodging) with some probability if(static_cast(rand())/RAND_MAX < 0.25) @@ -234,13 +232,19 @@ namespace MWMechanics mReadyToAttack = true; //only once got in melee combat, actor is allowed to use close-up shortcutting - mCloseUp = true; + mFollowTarget = true; } } else { - //target is at far distance: build & follow the path - mCloseUp = false; + //target is at far distance: build path to target OR follow target (if previously actor had reached it once) + + /* + //apply when AIFOLLOW package implementation will be existent + if(mFollowTarget) + actor.getClass().getCreatureStats(actor).getAiSequence().stack(AiFollow(mTarget));*/ + + mFollowTarget = false; buildNewPath(actor); @@ -342,7 +346,8 @@ namespace MWMechanics //maybe here is a mistake (?): PathFinder::getPathSize() returns number of grid points in the path, //not the actual path length. Here we should know if the new path is actually more effective. //if(pathFinder2.getPathSize() < mPathFinder.getPathSize()) - mPathFinder = newPathFinder; + newPathFinder.syncStart(mPathFinder.getPath()); + mPathFinder = newPathFinder; } } } diff --git a/apps/openmw/mwmechanics/aicombat.hpp b/apps/openmw/mwmechanics/aicombat.hpp index cb9eee973..27f7f5d95 100644 --- a/apps/openmw/mwmechanics/aicombat.hpp +++ b/apps/openmw/mwmechanics/aicombat.hpp @@ -37,7 +37,7 @@ namespace MWMechanics float mTimerCombatMove; bool mReadyToAttack, mStrike; - bool mCloseUp; + bool mFollowTarget; bool mCombatMove; MWMechanics::Movement mMovement; diff --git a/apps/openmw/mwmechanics/character.cpp b/apps/openmw/mwmechanics/character.cpp index 0ffeb52e5..967f7413a 100644 --- a/apps/openmw/mwmechanics/character.cpp +++ b/apps/openmw/mwmechanics/character.cpp @@ -504,7 +504,7 @@ bool CharacterController::updateCreatureState() } mAnimation->play(mCurrentWeapon, Priority_Weapon, - MWRender::Animation::Group_UpperBody, true, + MWRender::Animation::Group_All, true, 1, "start", "stop", 0.0f, 0); mUpperBodyState = UpperCharState_StartToMinAttack; diff --git a/apps/openmw/mwmechanics/pathfinding.cpp b/apps/openmw/mwmechanics/pathfinding.cpp index c8bc9b49c..fd44fcc4c 100644 --- a/apps/openmw/mwmechanics/pathfinding.cpp +++ b/apps/openmw/mwmechanics/pathfinding.cpp @@ -4,6 +4,7 @@ #include "../mwbase/environment.hpp" #include "OgreMath.h" +#include "OgreVector3.h" #include #include @@ -233,5 +234,21 @@ namespace MWMechanics return false; } + + void PathFinder::syncStart(const std::list &path) + { + std::list::const_iterator oldStart = path.begin(); + std::list::iterator iter = ++mPath.begin(); + + if( (*iter).mX == oldStart->mX + && (*iter).mY == oldStart->mY + && (*iter).mZ == oldStart->mZ + && (*iter).mAutogenerated == oldStart->mAutogenerated + && (*iter).mConnectionNum == oldStart->mConnectionNum ) + { + mPath.pop_front(); + } + + } } diff --git a/apps/openmw/mwmechanics/pathfinding.hpp b/apps/openmw/mwmechanics/pathfinding.hpp index 916df850b..de58f5db8 100644 --- a/apps/openmw/mwmechanics/pathfinding.hpp +++ b/apps/openmw/mwmechanics/pathfinding.hpp @@ -37,6 +37,11 @@ namespace MWMechanics return mPath; } + //When first point of newly created path is the nearest to actor point, then + //the cituation can occure when this point is undesirable (if the 2nd point of new path == the 1st point of old path) + //This functions deletes that point. + void syncStart(const std::list &path); + private: std::list mPath; bool mIsPathConstructed;