Placeable objects should not collide unless they have a NiRootCollisionNode

pull/16/head
scrawl 12 years ago
parent e4717d7c92
commit 84afd87321

@ -35,7 +35,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Apparatus::getModel(const MWWorld::Ptr &ptr) const

@ -38,7 +38,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Armor::getModel(const MWWorld::Ptr &ptr) const

@ -33,7 +33,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Book::getModel(const MWWorld::Ptr &ptr) const

@ -36,7 +36,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Clothing::getModel(const MWWorld::Ptr &ptr) const

@ -46,7 +46,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Ingredient::getModel(const MWWorld::Ptr &ptr) const

@ -50,7 +50,7 @@ namespace MWClass
const std::string &model = ref->mBase->mModel;
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,ref->mBase->mData.mFlags & ESM::Light::Carry);
if (!ref->mBase->mSound.empty())
MWBase::Environment::get().getSoundManager()->playSound3D(ptr, ref->mBase->mSound, 1.0, 1.0, MWBase::SoundManager::Play_Loop);

@ -36,7 +36,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Lockpick::getModel(const MWWorld::Ptr &ptr) const

@ -39,7 +39,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Miscellaneous::getModel(const MWWorld::Ptr &ptr) const

@ -38,7 +38,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Potion::getModel(const MWWorld::Ptr &ptr) const

@ -36,7 +36,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Probe::getModel(const MWWorld::Ptr &ptr) const

@ -34,7 +34,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Repair::getModel(const MWWorld::Ptr &ptr) const

@ -36,7 +36,7 @@ namespace MWClass
{
const std::string model = getModel(ptr);
if(!model.empty())
physics.addObject(ptr);
physics.addObject(ptr,true);
}
std::string Weapon::getModel(const MWWorld::Ptr &ptr) const

@ -364,14 +364,15 @@ namespace MWWorld
mEngine->removeHeightField(x, y);
}
void PhysicsSystem::addObject (const Ptr& ptr)
void PhysicsSystem::addObject (const Ptr& ptr, bool placeable)
{
std::string mesh = MWWorld::Class::get(ptr).getModel(ptr);
Ogre::SceneNode* node = ptr.getRefData().getBaseNode();
handleToMesh[node->getName()] = mesh;
OEngine::Physic::RigidBody* body = mEngine->createAndAdjustRigidBody(mesh, node->getName(), node->getScale().x, node->getPosition(), node->getOrientation());
OEngine::Physic::RigidBody* raycastingBody = mEngine->createAndAdjustRigidBody
(mesh, node->getName(), node->getScale().x, node->getPosition(), node->getOrientation(), 0, 0, true);
OEngine::Physic::RigidBody* body = mEngine->createAndAdjustRigidBody(
mesh, node->getName(), node->getScale().x, node->getPosition(), node->getOrientation(), 0, 0, false, placeable);
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);
}
@ -440,8 +441,13 @@ namespace MWWorld
const std::string &handle = node->getName();
if(handleToMesh.find(handle) != handleToMesh.end())
{
bool placeable = false;
if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle,true))
placeable = body->mPlaceable;
else if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle,false))
placeable = body->mPlaceable;
removeObject(handle);
addObject(ptr);
addObject(ptr, placeable);
}
if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle))

@ -29,7 +29,7 @@ namespace MWWorld
PhysicsSystem (OEngine::Render::OgreRenderer &_rend);
~PhysicsSystem ();
void addObject (const MWWorld::Ptr& ptr);
void addObject (const MWWorld::Ptr& ptr, bool placeable=false);
void addActor (const MWWorld::Ptr& ptr);

@ -109,17 +109,17 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource)
return;
}
bool hasCollisionNode = hasRootCollisionNode(node);
cShape->mHasCollisionNode = hasRootCollisionNode(node);
//do a first pass
handleNode(mesh1, node,0,hasCollisionNode,false,false);
handleNode(mesh1, node,0,false,false);
if(mBoundingBox != NULL)
{
cShape->mCollisionShape = mBoundingBox;
delete mesh1;
}
else if (mHasShape && !cShape->mIgnore && cShape->mCollide)
else if (mHasShape && cShape->mCollide)
{
cShape->mCollisionShape = new TriangleMeshShape(mesh1,true);
}
@ -136,14 +136,14 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource)
btTriangleMesh* mesh2 = new btTriangleMesh();
handleNode(mesh2, node,0,hasCollisionNode,true,true);
handleNode(mesh2, node,0,true,true);
if(mBoundingBox != NULL)
{
cShape->mRaycastingShape = mBoundingBox;
delete mesh2;
}
else if (mHasShape && !cShape->mIgnore)
else if (mHasShape)
{
cShape->mRaycastingShape = new TriangleMeshShape(mesh2,true);
}
@ -174,7 +174,7 @@ bool ManualBulletShapeLoader::hasRootCollisionNode(Nif::Node const * node)
}
void ManualBulletShapeLoader::handleNode(btTriangleMesh* mesh, const Nif::Node *node, int flags,
bool hasCollisionNode, bool isCollisionNode,
bool isCollisionNode,
bool raycasting)
{
// Accumulate the flags from all the child nodes. This works for all
@ -223,7 +223,7 @@ void ManualBulletShapeLoader::handleNode(btTriangleMesh* mesh, const Nif::Node *
}
}
if (isCollisionNode || (!hasCollisionNode && !raycasting))
if (isCollisionNode || (!cShape->mHasCollisionNode && !raycasting))
{
if(node->hasBounds)
{
@ -246,7 +246,7 @@ void ManualBulletShapeLoader::handleNode(btTriangleMesh* mesh, const Nif::Node *
for(size_t i = 0;i < list.length();i++)
{
if(!list[i].empty())
handleNode(mesh, list[i].getPtr(), flags, hasCollisionNode, isCollisionNode, raycasting);
handleNode(mesh, list[i].getPtr(), flags, isCollisionNode, raycasting);
}
}
}

@ -82,7 +82,7 @@ private:
/**
*Parse a node.
*/
void handleNode(btTriangleMesh* mesh, Nif::Node const *node, int flags, bool hasCollisionNode, bool isCollisionNode, bool raycasting);
void handleNode(btTriangleMesh* mesh, Nif::Node const *node, int flags, bool isCollisionNode, bool raycasting);
/**
*Helper function

@ -19,8 +19,8 @@ Ogre::Resource(creator, name, handle, group, isManual, loader)
*/
mCollisionShape = NULL;
mRaycastingShape = NULL;
mHasCollisionNode = false;
mCollide = true;
mIgnore = false;
createParamDictionary("BulletShape");
}

@ -35,12 +35,14 @@ public:
btCollisionShape* mCollisionShape;
btCollisionShape* mRaycastingShape;
// Whether or not a NiRootCollisionNode was present in the .nif. If there is none, the collision behaviour
// depends on object type, so we need to expose this variable.
bool mHasCollisionNode;
Ogre::Vector3 mBoxTranslation;
Ogre::Quaternion mBoxRotation;
//this flag indicate if the shape is used for collision or if it's for raycasting only.
bool mCollide;
bool mIgnore;
};
/**

@ -144,6 +144,7 @@ namespace Physic
RigidBody::RigidBody(btRigidBody::btRigidBodyConstructionInfo& CI,std::string name)
: btRigidBody(CI)
, mName(name)
, mPlaceable(false)
{
}
@ -368,7 +369,7 @@ namespace Physic
RigidBody* PhysicEngine::createAndAdjustRigidBody(const std::string &mesh, const std::string &name,
float scale, const Ogre::Vector3 &position, const Ogre::Quaternion &rotation,
Ogre::Vector3* scaledBoxTranslation, Ogre::Quaternion* boxRotation, bool raycasting)
Ogre::Vector3* scaledBoxTranslation, Ogre::Quaternion* boxRotation, bool raycasting, bool placeable)
{
std::string sid = (boost::format("%07.3f") % scale).str();
std::string outputstring = mesh + sid;
@ -378,6 +379,9 @@ namespace Physic
BulletShapeManager::getSingletonPtr()->load(outputstring,"General");
BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General");
if (placeable && !raycasting && shape->mCollisionShape && !shape->mHasCollisionNode)
return NULL;
if (!shape->mCollisionShape && !raycasting)
return NULL;
if (!shape->mRaycastingShape && raycasting)
@ -395,6 +399,7 @@ namespace Physic
btRigidBody::btRigidBodyConstructionInfo CI = btRigidBody::btRigidBodyConstructionInfo
(0,newMotionState, raycasting ? shape->mRaycastingShape : shape->mCollisionShape);
RigidBody* body = new RigidBody(CI,name);
body->mPlaceable = placeable;
if(scaledBoxTranslation != 0)
*scaledBoxTranslation = shape->mBoxTranslation * scale;

@ -164,6 +164,7 @@ namespace Physic
RigidBody(btRigidBody::btRigidBodyConstructionInfo& CI,std::string name);
virtual ~RigidBody();
std::string mName;
bool mPlaceable;
};
struct HeightField
@ -197,7 +198,7 @@ namespace Physic
*/
RigidBody* createAndAdjustRigidBody(const std::string &mesh, const std::string &name,
float scale, const Ogre::Vector3 &position, const Ogre::Quaternion &rotation,
Ogre::Vector3* scaledBoxTranslation = 0, Ogre::Quaternion* boxRotation = 0, bool raycasting=false);
Ogre::Vector3* scaledBoxTranslation = 0, Ogre::Quaternion* boxRotation = 0, bool raycasting=false, bool placeable=false);
/**
* Adjusts a rigid body to the right position and rotation

Loading…
Cancel
Save