First try to improve AI. Does not work yet due to strange bug in physicsystem

actorid
gus 12 years ago
parent 7fe7111c19
commit 006f25d1c0

@ -245,6 +245,9 @@ namespace MWBase
virtual void doPhysics (const MWWorld::PtrMovementList &actors, float duration) = 0;
///< Run physics simulation and modify \a world accordingly.
virtual bool castRay (float x1, float y1, float z1, float x2, float y2, float z2) = 0;
///< cast a Ray and return true if there is an object in the ray path.
virtual bool toggleCollisionMode() = 0;
///< Toggle collision mode for player. If disabled player object should ignore
/// collisions and gravity.

@ -1,4 +1,8 @@
#include "pathfinding.hpp"
#include "../mwbase/world.hpp"
#include "../mwbase/environment.hpp"
#include <boost/graph/dijkstra_shortest_paths.hpp>
#include <boost/graph/adjacency_list.hpp>
#include "boost/tuple/tuple.hpp"
@ -169,15 +173,20 @@ namespace MWMechanics
void PathFinder::buildPath(ESM::Pathgrid::Point startPoint,ESM::Pathgrid::Point endPoint,
const ESM::Pathgrid* pathGrid,float xCell,float yCell)
{
int start = getClosestPoint(pathGrid,startPoint.mX - xCell,startPoint.mY - yCell,startPoint.mZ);
int end = getClosestPoint(pathGrid,endPoint.mX - xCell,endPoint.mY - yCell,endPoint.mZ);
if(start != -1 && end != -1)
//first check if there is an obstacle
if(MWBase::Environment::get().getWorld()->castRay(startPoint.mX,startPoint.mY,startPoint.mZ,
endPoint.mX,endPoint.mY,endPoint.mZ) )
{
PathGridGraph graph = buildGraph(pathGrid,xCell,yCell);
mPath = findPath(start,end,graph);
}
std::cout << "hit";
int start = getClosestPoint(pathGrid,startPoint.mX - xCell,startPoint.mY - yCell,startPoint.mZ);
int end = getClosestPoint(pathGrid,endPoint.mX - xCell,endPoint.mY - yCell,endPoint.mZ);
if(start != -1 && end != -1)
{
PathGridGraph graph = buildGraph(pathGrid,xCell,yCell);
mPath = findPath(start,end,graph);
}
}
mPath.push_back(endPoint);
mIsPathConstructed = true;
}

@ -333,14 +333,14 @@ namespace MWWorld
return result;
}
bool PhysicsSystem::castRay(const Vector3& from, const Vector3& to)
bool PhysicsSystem::castRay(const Vector3& from, const Vector3& to, bool raycastingObjectOnly)
{
btVector3 _from, _to;
_from = btVector3(from.x, from.y, from.z);
_to = btVector3(to.x, to.y, to.z);
std::pair<std::string, float> result = mEngine->rayTest(_from, _to);
std::pair<std::string, float> result = mEngine->rayTest(_from, _to, false);//raycastingObjectOnly);
std::cout << result.first << " " << result.second;
return !(result.first == "");
}
@ -419,6 +419,7 @@ namespace MWWorld
OEngine::Physic::RigidBody* raycastingBody = mEngine->createAndAdjustRigidBody(
mesh, node->getName(), node->getScale().x, node->getPosition(), node->getOrientation(), 0, 0, true, placeable);
mEngine->addRigidBody(body, true, raycastingBody);
std::cout << "Object:" << mesh;
}
void PhysicsSystem::addActor (const Ptr& ptr)
@ -427,6 +428,7 @@ namespace MWWorld
Ogre::SceneNode* node = ptr.getRefData().getBaseNode();
//TODO:optimize this. Searching the std::map isn't very efficient i think.
mEngine->addCharacter(node->getName(), mesh, node->getPosition(), node->getScale().x, node->getOrientation());
std::cout << "Actor:" << mesh;
}
void PhysicsSystem::removeObject (const std::string& handle)

@ -62,8 +62,8 @@ namespace MWWorld
btVector3 getRayPoint(float extent, float mouseX, float mouseY);
// cast ray, return true if it hit something
bool castRay(const Ogre::Vector3& from, const Ogre::Vector3& to);
// cast ray, return true if it hit something. if raycasringObjectOnlt is set to false, it ignores NPCs and objects with no collisions.
bool castRay(const Ogre::Vector3& from, const Ogre::Vector3& to, bool raycastingObjectOnly = true);
std::pair<bool, Ogre::Vector3>
castRay(const Ogre::Vector3 &orig, const Ogre::Vector3 &dir, float len);

@ -1042,6 +1042,13 @@ namespace MWWorld
mPhysEngine->stepSimulation (duration);
}
bool World::castRay (float x1, float y1, float z1, float x2, float y2, float z2)
{
Ogre::Vector3 a(x1,y1,z1);std::cout << x1 << " " << x2;
Ogre::Vector3 b(x2,y2,z2);
return mPhysics->castRay(a,b,false);
}
void World::processDoors(float duration)
{
std::map<MWWorld::Ptr, int>::iterator it = mDoorStates.begin();

@ -279,6 +279,9 @@ namespace MWWorld
virtual void doPhysics(const PtrMovementList &actors, float duration);
///< Run physics simulation and modify \a world accordingly.
virtual bool castRay (float x1, float y1, float z1, float x2, float y2, float z2);
///< cast a Ray and return true if there is an object in the ray path.
virtual bool toggleCollisionMode();
///< Toggle collision mode for player. If disabled player object should ignore
/// collisions and gravity.

@ -28,7 +28,7 @@ namespace Physic
mRaycastingBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation, &mBoxScaledTranslation, &mBoxRotation, true);
Ogre::Quaternion inverse = mBoxRotation.Inverse();
mBoxRotationInverse = btQuaternion(inverse.x, inverse.y, inverse.z,inverse.w);
mEngine->addRigidBody(mBody, false, mRaycastingBody); //Add rigid body to dynamics world, but do not add to object map
//mEngine->addRigidBody(mBody, false, mRaycastingBody,true); //Add rigid body to dynamics world, but do not add to object map
}
PhysicActor::~PhysicActor()
@ -422,15 +422,17 @@ namespace Physic
}
void PhysicEngine::addRigidBody(RigidBody* body, bool addToMap, RigidBody* raycastingBody)
void PhysicEngine::addRigidBody(RigidBody* body, bool addToMap, RigidBody* raycastingBody,bool actor)
{
if(!body && !raycastingBody)
return; // nothing to do
const std::string& name = (body ? body->mName : raycastingBody->mName);
if (body)
dynamicsWorld->addRigidBody(body,CollisionType_World,CollisionType_World|CollisionType_ActorInternal|CollisionType_ActorExternal);
if (body){
if(actor) {dynamicsWorld->addRigidBody(body,CollisionType_ActorInternal,CollisionType_World|CollisionType_ActorInternal);std::cout << "actor";}
else dynamicsWorld->addRigidBody(body,CollisionType_World,CollisionType_World|CollisionType_ActorInternal|CollisionType_ActorExternal);
}
if (raycastingBody)
dynamicsWorld->addRigidBody(raycastingBody,CollisionType_Raycasting,CollisionType_Raycasting|CollisionType_World);
@ -603,14 +605,15 @@ namespace Physic
{
}
std::pair<std::string,float> PhysicEngine::rayTest(btVector3& from,btVector3& to)
std::pair<std::string,float> PhysicEngine::rayTest(btVector3& from,btVector3& to,bool raycastingObjectOnly)
{
std::string name = "";
float d = -1;
float d1 = 10000.;
btCollisionWorld::ClosestRayResultCallback resultCallback1(from, to);
resultCallback1.m_collisionFilterMask = CollisionType_Raycasting;
if(raycastingObjectOnly) resultCallback1.m_collisionFilterMask = CollisionType_Raycasting;
else resultCallback1.m_collisionFilterMask = CollisionType_ActorExternal;
dynamicsWorld->rayTest(from, to, resultCallback1);
if (resultCallback1.hasHit())
{

@ -226,7 +226,7 @@ namespace Physic
/**
* Add a RigidBody to the simulation
*/
void addRigidBody(RigidBody* body, bool addToMap = true, RigidBody* raycastingBody = NULL);
void addRigidBody(RigidBody* body, bool addToMap = true, RigidBody* raycastingBody = NULL,bool actor = false);
/**
* Remove a RigidBody from the simulation. It does not delete it, and does not remove it from the RigidBodyMap.
@ -293,7 +293,7 @@ namespace Physic
/**
* Return the closest object hit by a ray. If there are no objects, it will return ("",-1).
*/
std::pair<std::string,float> rayTest(btVector3& from,btVector3& to);
std::pair<std::string,float> rayTest(btVector3& from,btVector3& to,bool raycastingObjectOnly = true);
/**
* Return all objects hit by a ray.

Loading…
Cancel
Save