From ff951d21834e938978b8e8aff13da45314b71890 Mon Sep 17 00:00:00 2001 From: Robin Engman Date: Thu, 13 Feb 2014 19:49:33 +0100 Subject: [PATCH 1/5] Moving fixed Jumping and waiting for camera is next --- Code/Game/GameLogic/Level.cpp | 2 +- Code/Game/GameLogic/Player.cpp | 62 +++-- Code/Game/GameLogic/Player.h | 9 +- Code/GamePhysics/GamePhysics.vcxproj | 6 - Code/GamePhysics/GamePhysics.vcxproj.filters | 18 -- Code/GamePhysics/Implementation/Octree.cpp | 226 ------------------ Code/GamePhysics/Implementation/Octree.h | 85 ------- .../Implementation/PhysicsAPI_Impl.cpp | 52 +++- .../Implementation/PhysicsAPI_Impl.h | 3 +- .../Implementation/SimpleRigidBody.cpp | 77 +++++- .../Implementation/SimpleRigidBody.h | 15 +- .../Implementation/SphericalRigidBody.cpp | 0 .../Implementation/SphericalRigidBody.h | 0 Code/GamePhysics/PhysicsAPI.h | 12 +- Code/GamePhysics/PhysicsFormula-Impl.h | 82 ------- Code/GamePhysics/PhysicsFormula.h | 35 --- 16 files changed, 188 insertions(+), 496 deletions(-) delete mode 100644 Code/GamePhysics/Implementation/Octree.cpp delete mode 100644 Code/GamePhysics/Implementation/Octree.h delete mode 100644 Code/GamePhysics/Implementation/SphericalRigidBody.cpp delete mode 100644 Code/GamePhysics/Implementation/SphericalRigidBody.h delete mode 100644 Code/GamePhysics/PhysicsFormula-Impl.h delete mode 100644 Code/GamePhysics/PhysicsFormula.h diff --git a/Code/Game/GameLogic/Level.cpp b/Code/Game/GameLogic/Level.cpp index 15d855c3..2289b85b 100644 --- a/Code/Game/GameLogic/Level.cpp +++ b/Code/Game/GameLogic/Level.cpp @@ -181,7 +181,7 @@ void Level::InitiateLevel(float radius) this->staticObjects[0]->objectID = idCount++; // add jumppad - ICustomBody* rigidBody_Jumppad = API::Instance().AddCollisionBox(Oyster::Math::Float3(1, 1, 1), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(4, 600.3, 0), 5, 0.5f, 0.8f, 0.6f); + ICustomBody* rigidBody_Jumppad = API::Instance().AddCollisionBox(Oyster::Math::Float3(1, 1, 1), Oyster::Math::Float4(0, 0, 0, 1), Oyster::Math::Float3(4, 600.3, 0), 0, 0.5f, 0.8f, 0.6f); this->staticObjects.Push(new JumpPad(rigidBody_Jumppad, JumpPad::JumpPadActivated, OBJECT_TYPE::OBJECT_TYPE_JUMPPAD, Oyster::Math::Float3(0,2000,0))); rigidBody_Jumppad->SetCustomTag(this->staticObjects[1]); diff --git a/Code/Game/GameLogic/Player.cpp b/Code/Game/GameLogic/Player.cpp index 90f2c66b..19a0bb9c 100644 --- a/Code/Game/GameLogic/Player.cpp +++ b/Code/Game/GameLogic/Player.cpp @@ -47,11 +47,15 @@ void Player::InitPlayer() this->teamID = -1; this->playerState = PLAYER_STATE_IDLE; this->lookDir = Oyster::Math::Float3(0,0,-1); - this->moveDir = Oyster::Math::Float3(0,0,0); key_forward = 0; key_backward = 0; key_strafeRight = 0; key_strafeLeft = 0; + + this->moveDir = Oyster::Math::Float3(0,0,0); + this->moveSpeed = 100; + this->previousMoveSpeed = Oyster::Math::Float3(0,0,0); + } Player::~Player(void) @@ -67,48 +71,60 @@ void Player::BeginFrame() { //weapon->Update(0.002f); Object::BeginFrame(); - Oyster::Math::Float3 forward(0,0,0); - Oyster::Math::Float3 back(0,0,0); - Oyster::Math::Float3 right(0,0,0); - Oyster::Math::Float3 left(0,0,0); - Oyster::Math::Float3 moveDirection(0,0,0); + + if(this->moveDir != Oyster::Math::Float3::null) + { + Oyster::Math::Float3 velocity = this->rigidBody->GetLinearVelocity(); + Oyster::Math::Float3 lostVelocity = (this->previousMoveSpeed - velocity).GetMagnitude()*this->moveDir; + this->rigidBody->SetLinearVelocity(velocity + lostVelocity - this->moveDir*this->moveSpeed ); + } + + this->moveDir = Oyster::Math::Float3::null; + if (key_forward > 0.001) { key_forward -= gameInstance->GetFrameTime(); // fixed timer - forward = this->rigidBody->GetState().GetOrientation().v[2].GetNormalized(); + this->moveDir += this->rigidBody->GetState().GetOrientation().v[2].GetNormalized().xyz; } if (key_backward > 0.001) { key_backward -= gameInstance->GetFrameTime(); - back = -this->rigidBody->GetState().GetOrientation().v[2].GetNormalized(); + this->moveDir -= this->rigidBody->GetState().GetOrientation().v[2].GetNormalized().xyz; } if (key_strafeRight > 0.001) { - key_strafeRight -= gameInstance->GetFrameTime(); - Oyster::Math::Float3 forward = this->rigidBody->GetState().GetOrientation().v[2].GetNormalized(); - Oyster::Math::Float3 up = this->rigidBody->GetState().centerPos.Normalize(); - right = -((up).Cross(forward).Normalize()); - right.Normalize(); + Oyster::Math::Float3 forward = this->rigidBody->GetState().GetOrientation().v[2]; + Oyster::Math::Float3 up = this->rigidBody->GetState().centerPos; + this->moveDir -= (up).Cross(forward).GetNormalized(); } if (key_strafeLeft > 0.001) { key_strafeLeft -= gameInstance->GetFrameTime(); - Oyster::Math::Float3 forward = this->rigidBody->GetState().GetOrientation().v[2].GetNormalized(); - Oyster::Math::Float3 up = this->rigidBody->GetState().centerPos.Normalize(); - left = (up).Cross(forward).Normalize(); - left.Normalize(); + Oyster::Math::Float3 forward = this->rigidBody->GetState().GetOrientation().v[2]; + Oyster::Math::Float3 up = this->rigidBody->GetState().centerPos; + this->moveDir += (up).Cross(forward).GetNormalized(); } - moveDirection = forward + back + left + right; - //moveDirection.Normalize(); - rigidBody->SetLinearVelocity( MOVE_FORCE * moveDirection ); - weapon->Update(0.01f); + if(this->moveDir != Oyster::Math::Float3::null) + { + this->moveDir.Normalize(); + this->rigidBody->SetLinearVelocity(this->moveDir*this->moveSpeed + this->rigidBody->GetLinearVelocity()); + this->previousMoveSpeed = this->rigidBody->GetLinearVelocity(); + } + + + this->weapon->Update(0.01f); } void Player::EndFrame() { // snap to axis + Oyster::Math::Float4 rotation; + + this->rigidBody->SetUp(this->rigidBody->GetState().centerPos.GetNormalized()); + + Object::EndFrame(); } @@ -176,7 +192,6 @@ void Player::Rotate(const Oyster::Math3D::Float3 lookDir, const Oyster::Math3D:: Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1]; this->rigidBody->SetUpAndRight(up, right); - this->rigidBody->SetUpAndRight(this->rigidBody->GetState().centerPos.GetNormalized(), this->rigidBody->GetState().GetOrientation().v[0].xyz.GetNormalized()); } void Player::Jump() @@ -231,5 +246,4 @@ void Player::DamageLife(int damage) playerState = PLAYER_STATE_DEAD; this->gameInstance->onDisableFnc(this, 0.0f); } -} - +} \ No newline at end of file diff --git a/Code/Game/GameLogic/Player.h b/Code/Game/GameLogic/Player.h index d2adb4be..bdd83f41 100644 --- a/Code/Game/GameLogic/Player.h +++ b/Code/Game/GameLogic/Player.h @@ -75,7 +75,6 @@ namespace GameLogic void EndFrame(); static Oyster::Physics::ICustomBody::SubscriptMessage PlayerCollisionAfter(Oyster::Physics::ICustomBody *rigidBodyLevel, Oyster::Physics::ICustomBody *obj, Oyster::Math::Float kineticEnergyLoss); - private: void Jump(); @@ -84,7 +83,6 @@ namespace GameLogic int teamID; Weapon *weapon; PLAYER_STATE playerState; - Oyster::Math::Float3 moveDir; Oyster::Math::Float3 lookDir; float key_forward; float key_backward; @@ -92,9 +90,14 @@ namespace GameLogic float key_strafeLeft; float key_jump; + + Oyster::Math::Float3 moveDir; + Oyster::Math::Float moveSpeed; + Oyster::Math::Float3 previousMoveSpeed; + + bool hasTakenDamage; float invincibleCooldown; - }; } #endif \ No newline at end of file diff --git a/Code/GamePhysics/GamePhysics.vcxproj b/Code/GamePhysics/GamePhysics.vcxproj index 9b883bb3..475a05f9 100644 --- a/Code/GamePhysics/GamePhysics.vcxproj +++ b/Code/GamePhysics/GamePhysics.vcxproj @@ -165,22 +165,16 @@ - - - - - - diff --git a/Code/GamePhysics/GamePhysics.vcxproj.filters b/Code/GamePhysics/GamePhysics.vcxproj.filters index aa3cbd73..5a3c6fb2 100644 --- a/Code/GamePhysics/GamePhysics.vcxproj.filters +++ b/Code/GamePhysics/GamePhysics.vcxproj.filters @@ -30,24 +30,12 @@ Header Files\Implementation - - Header Files\Implementation - - - Header Files\Implementation - Header Files\Include Header Files\Include - - Header Files\Include - - - Header Files\Include - @@ -59,11 +47,5 @@ Source Files - - Source Files - - - Source Files - \ No newline at end of file diff --git a/Code/GamePhysics/Implementation/Octree.cpp b/Code/GamePhysics/Implementation/Octree.cpp deleted file mode 100644 index 4778e5f1..00000000 --- a/Code/GamePhysics/Implementation/Octree.cpp +++ /dev/null @@ -1,226 +0,0 @@ -#include "Octree.h" - -using namespace Oyster; -using namespace Physics; -using namespace ::Utility::DynamicMemory; - -const unsigned int Octree::invalid_ref = ::Utility::Value::numeric_limits::max(); - -Octree::Octree(unsigned int bufferSize, unsigned char numLayers, Math::Float3 worldSize) -{ - this->worldNode.dataPtr = NULL; - - this->worldNode.container.maxVertex = worldSize*0.5f; - this->worldNode.container.minVertex = -worldSize*0.5f; -} - -Octree::~Octree() -{ - -} - -Octree& Octree::operator=(const Octree& orig) -{ - this->leafData = orig.leafData; - this->updateQueue = orig.updateQueue; - this->worldNode = orig.worldNode; - this->mapReferences = orig.mapReferences; - - return *this; -} - -void Octree::AddObject(UniquePointer< ICustomBody > customBodyRef) -{ - //customBodyRef->SetScene( this ); - Data data; - //Data* tempPtr = this->worldNode.dataPtr; - - //data.container = customBodyRef->GetBoundingSphere(); - data.queueRef = -1; - data.next = NULL; - data.prev = NULL; - data.customBodyRef = customBodyRef; - data.limbo = false; - this->mapReferences.insert(std::pair (data.customBodyRef, this->leafData.size())); - this->leafData.push_back(data); - - /*if(tempPtr != NULL) - { - tempPtr->prev->next = &this->leafData[this->leafData.size() - 1]; - this->leafData[this->leafData.size() - 1].prev = tempPtr->prev; - tempPtr->prev = &this->leafData[this->leafData.size() - 1]; - this->leafData[this->leafData.size() - 1].next = tempPtr; - } - else - { - this->worldNode.dataPtr = &this->leafData[this->leafData.size() - 1]; - this->worldNode.dataPtr->next = this->worldNode.dataPtr; - this->worldNode.dataPtr->prev = this->worldNode.dataPtr; - }*/ -} - -void Octree::MoveToUpdateQueue(UniquePointer< ICustomBody > customBodyRef) -{ - /*this->leafData[this->mapReferences[customBodyRef]].queueRef = this->updateQueue.size(); - this->updateQueue.push_back(&this->leafData[this->mapReferences[customBodyRef]]);*/ -} - -void Octree::MoveToLimbo(const ICustomBody* customBodyRef) -{ - auto object = this->mapReferences.find(customBodyRef); - - unsigned int tempRef = object->second; - - this->leafData[tempRef].limbo = true; -} - -bool Octree::IsInLimbo(const ICustomBody* customBodyRef) -{ - auto object = this->mapReferences.find(customBodyRef); - - unsigned int tempRef = object->second; - - return this->leafData[tempRef].limbo; -} - -void Octree::ReleaseFromLimbo(const ICustomBody* customBodyRef) -{ - auto object = this->mapReferences.find(customBodyRef); - - unsigned int tempRef = object->second; - - this->leafData[tempRef].limbo = false; -} - -void Octree::DestroyObject(UniquePointer< ICustomBody > customBodyRef) -{ - std::map::iterator it = this->mapReferences.find(customBodyRef); - - this->mapReferences.erase(it); - - this->leafData.erase(this->leafData.begin() + this->leafData[this->mapReferences[customBodyRef]].queueRef); -} - -std::vector& Octree::Sample(ICustomBody* customBodyRef, std::vector& updateList) -{ - auto object = this->mapReferences.find(customBodyRef); - - if(object == this->mapReferences.end()) - { - return updateList; - } - - unsigned int tempRef = object->second; - - for(unsigned int i = 0; ileafData.size(); i++) - { - if(tempRef != i && !this->leafData[i].limbo) if(this->leafData[tempRef].container.Intersects(this->leafData[i].container)) - { - updateList.push_back(this->leafData[i].customBodyRef); - } - } - - return updateList; -} - -std::vector& Octree::Sample(const Oyster::Collision3D::ICollideable& collideable, std::vector& updateList) -{ - for(unsigned int i = 0; ileafData.size(); i++) - { - if(!this->leafData[i].limbo && this->leafData[i].container.Intersects(collideable)) - { - updateList.push_back(this->leafData[i].customBodyRef); - } - } - - return updateList; -} - -void Octree::Visit(ICustomBody* customBodyRef, VisitorAction hitAction ) -{ - auto object = this->mapReferences.find(customBodyRef); - - // If rigid body is not found - if(object == this->mapReferences.end()) - { - return; - } - - unsigned int tempRef = object->second; - - // Go through all object and test for intersection - for(unsigned int i = 0; ileafData.size(); i++) - { - // If objects intersect call collision response function - if(tempRef != i && !this->leafData[i].limbo) if(this->leafData[tempRef].container.Intersects(this->leafData[i].container)) - { - hitAction(*this, tempRef, i); - } - } -} - -void Octree::Visit(const Oyster::Collision3D::ICollideable& collideable, void* args, VisitorActionCollideable hitAction) -{ - for(unsigned int i = 0; ileafData.size(); i++) - { - if(!this->leafData[i].limbo && collideable.Intersects(this->leafData[i].container)) - { - hitAction( this->GetCustomBody(i), args ); - } - } -} - -ICustomBody* Octree::GetCustomBody(const unsigned int tempRef) -{ - return this->leafData[tempRef].customBodyRef; -} - -UniquePointer Octree::Extract( const ICustomBody* objRef ) -{ // Dan Andersson - auto iter = this->mapReferences.find( objRef ); - if( iter != this->mapReferences.end() ) - { - return this->Extract( iter->second ); - } - else - { - return NULL; - } -} - -UniquePointer Octree::Extract( unsigned int tempRef ) -{ - if( tempRef != Octree::invalid_ref ) - { - //! @todo TODO: implement stub - return NULL; - } - else - { - return NULL; - } -} - -unsigned int Octree::GetTemporaryReferenceOf( const ICustomBody* objRef ) const -{ // Dan Andersson - auto iter = this->mapReferences.find( objRef ); - if( iter != this->mapReferences.end() ) - { - return iter->second; - } - else - { - return Octree::invalid_ref; - } -} - -void Octree::SetAsAltered( unsigned int tempRef ) -{ - //this->leafData[tempRef].container = this->leafData[tempRef].customBodyRef->GetBoundingSphere(); - //! @todo TODO: implement stub -} - -void Octree::EvaluatePosition( unsigned int tempRef ) -{ - //! @todo TODO: implement stub -} \ No newline at end of file diff --git a/Code/GamePhysics/Implementation/Octree.h b/Code/GamePhysics/Implementation/Octree.h deleted file mode 100644 index 573738f2..00000000 --- a/Code/GamePhysics/Implementation/Octree.h +++ /dev/null @@ -1,85 +0,0 @@ -#ifndef OCTREE_H -#define OCTREE_H - -#include -#include -#include "Sphere.h" -#include "BoxAxisAligned.h" -#include "Utilities.h" -#include "../PhysicsAPI.h" - -namespace Oyster -{ - namespace Physics - { - class Octree - { - public: - static const unsigned int invalid_ref; - - typedef void(*VisitorAction)(Octree&, unsigned int, unsigned int); - typedef void(*VisitorActionCollideable)(ICustomBody*, void*); - - struct Data - { - Data* prev; - Data* next; - - Collision3D::Sphere container; - - ::Utility::DynamicMemory::UniquePointer< ICustomBody > customBodyRef; - - bool limbo; - - unsigned int queueRef; - }; - - struct OctreeNode - { - OctreeNode* children[8]; - Data* dataPtr; - Collision3D::BoxAxisAligned container; - }; - - Octree(unsigned int bufferSize = 0, unsigned char numLayers = 0, Math::Float3 worldSize = Math::Float3::null); - virtual ~Octree(); - - Octree& operator=(const Octree& orig); - - void AddObject(::Utility::DynamicMemory::UniquePointer< ICustomBody > customBodyRef); - - void MoveToUpdateQueue(::Utility::DynamicMemory::UniquePointer< ICustomBody > customBodyRef); - - void MoveToLimbo(const ICustomBody* customBodyRef); - bool IsInLimbo(const ICustomBody* customBodyRef); - void ReleaseFromLimbo(const ICustomBody* customBodyRef); - - void DestroyObject(::Utility::DynamicMemory::UniquePointer< ICustomBody > customBodyRef); - - std::vector& Sample(ICustomBody* customBodyRef, std::vector& updateList); - std::vector& Sample(const Oyster::Collision3D::ICollideable& collideable, std::vector& updateList); - void Visit(ICustomBody* customBodyRef, VisitorAction hitAction ); - void Visit(const Oyster::Collision3D::ICollideable& collideable, void* args, VisitorActionCollideable hitAction ); - - ICustomBody* GetCustomBody(const unsigned int tempRef); - - ::Utility::DynamicMemory::UniquePointer Extract( const ICustomBody* objRef ); - ::Utility::DynamicMemory::UniquePointer Extract( unsigned int tempRef ); // Dan vill ha - unsigned int GetTemporaryReferenceOf( const ICustomBody* objRef ) const; // Dan vill ha - void SetAsAltered( unsigned int tempRef ); // Dan vill ha - void EvaluatePosition( unsigned int tempRef ); // Dan vill ha - - private: - std::vector < Data > leafData; - std::vector < Data* > updateQueue; - std::vector < Data* > limbo; - - std::map< const ICustomBody*, unsigned int > mapReferences; - - OctreeNode worldNode; - }; - } - -} - -#endif \ No newline at end of file diff --git a/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp b/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp index 26da0998..b3ad6777 100644 --- a/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp +++ b/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp @@ -1,7 +1,6 @@ #include "PhysicsAPI_Impl.h" #include "OysterPhysics3D.h" #include "SimpleRigidBody.h" -#include "SphericalRigidBody.h" using namespace ::Oyster; using namespace ::Oyster::Physics; @@ -181,6 +180,47 @@ ICustomBody* API_Impl::AddCollisionCylinder(::Oyster::Math::Float3 halfSize, ::O return body; } +ICustomBody* API_Impl::AddCharacter(::Oyster::Math::Float height, ::Oyster::Math::Float radius, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction) +{ + SimpleRigidBody* body = new SimpleRigidBody; + SimpleRigidBody::State state; + + // Add collision shape + btCapsuleShape* collisionShape = new btCapsuleShape(radius, height); + body->SetCollisionShape(collisionShape); + + // Add motion state + btDefaultMotionState* motionState = new btDefaultMotionState(btTransform(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w),btVector3(position.x, position.y, position.z))); + body->SetMotionState(motionState); + + // Add rigid body + btVector3 fallInertia(0, 0, 0); + collisionShape->calculateLocalInertia(mass, fallInertia); + btRigidBody::btRigidBodyConstructionInfo rigidBodyCI(mass, motionState, collisionShape, fallInertia); + btRigidBody* rigidBody = new btRigidBody(rigidBodyCI); + rigidBody->setFriction(staticFriction); + rigidBody->setRestitution(restitution); + rigidBody->setUserPointer(body); + rigidBody->setAngularFactor(0); + rigidBody->setSleepingThresholds(0, 0); + body->SetRigidBody(rigidBody); + + // Add rigid body to world + this->dynamicsWorld->addRigidBody(rigidBody); + this->customBodies.push_back(body); + + state.centerPos = position; + state.reach = Float3(radius, height*0.5f, radius); + state.dynamicFrictionCoeff = 0.5f; + state.staticFrictionCoeff = 0.5f; + state.quaternion = Quaternion(Float3(rotation.xyz), rotation.w); + state.mass = mass; + + body->SetState(state); + + return body; +} + void API_Impl::SetTimeStep(float timeStep) { this->timeStep = timeStep; @@ -204,11 +244,11 @@ void API_Impl::UpdateWorld() trans = simpleBody->GetRigidBody()->getWorldTransform(); this->customBodies[i]->SetPosition(Float3(trans.getOrigin().x(), trans.getOrigin().y(), trans.getOrigin().z())); this->customBodies[i]->SetRotation(Quaternion(Float3(trans.getRotation().x(), trans.getRotation().y(), trans.getRotation().z()), trans.getRotation().w())); - + if(simpleBody->GetRigidBody()->getActivationState() == ACTIVE_TAG) { - simpleBody->CallSubscription_Move(); - } + this->customBodies[i]->CallSubscription_Move(); + } } int numManifolds = this->dynamicsWorld->getDispatcher()->getNumManifolds(); @@ -221,8 +261,8 @@ void API_Impl::UpdateWorld() ICustomBody* bodyA = (ICustomBody*)obA->getUserPointer(); ICustomBody* bodyB = (ICustomBody*)obB->getUserPointer(); - dynamic_cast(bodyA)->CallSubscription_AfterCollisionResponse(bodyA, bodyB, 0.0f); - dynamic_cast(bodyB)->CallSubscription_AfterCollisionResponse(bodyB, bodyA, 0.0f); + bodyA->CallSubscription_AfterCollisionResponse(bodyA, bodyB, 0.0f); + bodyB->CallSubscription_AfterCollisionResponse(bodyB, bodyA, 0.0f); } } diff --git a/Code/GamePhysics/Implementation/PhysicsAPI_Impl.h b/Code/GamePhysics/Implementation/PhysicsAPI_Impl.h index 422e82ef..002cb039 100644 --- a/Code/GamePhysics/Implementation/PhysicsAPI_Impl.h +++ b/Code/GamePhysics/Implementation/PhysicsAPI_Impl.h @@ -2,7 +2,6 @@ #define PHYSICS_API_IMPL_H #include "../PhysicsAPI.h" -#include "Octree.h" #include namespace Oyster @@ -65,6 +64,8 @@ namespace Oyster ICustomBody* AddCollisionBox(::Oyster::Math::Float3 halfSize, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction); ICustomBody* AddCollisionCylinder(::Oyster::Math::Float3 halfSize, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction); + ICustomBody* AddCharacter(::Oyster::Math::Float height, ::Oyster::Math::Float radius, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction); + void SetTimeStep(float timeStep); void UpdateWorld(); diff --git a/Code/GamePhysics/Implementation/SimpleRigidBody.cpp b/Code/GamePhysics/Implementation/SimpleRigidBody.cpp index 5670d32b..81d58f5b 100644 --- a/Code/GamePhysics/Implementation/SimpleRigidBody.cpp +++ b/Code/GamePhysics/Implementation/SimpleRigidBody.cpp @@ -139,6 +139,46 @@ void SimpleRigidBody::SetRotation(Float3 eulerAngles) this->state.quaternion = Quaternion(Float3(trans.getRotation().x(), trans.getRotation().y(), trans.getRotation().z()), trans.getRotation().w()); } +void SimpleRigidBody::SetRotation(::Oyster::Math::Float4x4 rotation) +{ + btTransform trans; + btMatrix3x3 newRotation; + btVector3 rightVector(rotation.v[0].x, rotation.v[0].y, rotation.v[0].z); + btVector3 upVector(rotation.v[1].x, rotation.v[1].y, rotation.v[1].z); + btVector3 forwardVector(rotation.v[2].x, rotation.v[2].y, rotation.v[2].z); + + + newRotation[0] = rightVector; + newRotation[1] = upVector; + newRotation[2] = forwardVector; + + trans = this->rigidBody->getWorldTransform(); + trans.setBasis(newRotation); + this->rigidBody->setWorldTransform(trans); + + btQuaternion quaternion; + quaternion = trans.getRotation(); + this->state.quaternion = Quaternion(Float3(quaternion.x(), quaternion.y(), quaternion.z()), quaternion.w()); +} + +void SimpleRigidBody::SetRotationAsAngularAxis(::Oyster::Math::Float4 angularAxis) +{ + if(angularAxis.xyz.GetMagnitude() == 0) + { + return; + } + + btTransform trans; + btVector3 vector(angularAxis.x, angularAxis.y, angularAxis.z); + btQuaternion quaternion(vector, angularAxis.w); + + trans = this->rigidBody->getWorldTransform(); + trans.setRotation(quaternion); + this->rigidBody->setWorldTransform(trans); + + this->state.quaternion = Quaternion(Float3(quaternion.x(), quaternion.y(), quaternion.z()), quaternion.w()); +} + void SimpleRigidBody::SetAngularFactor(Float factor) { this->rigidBody->setAngularFactor(factor); @@ -177,7 +217,7 @@ void SimpleRigidBody::SetUpAndForward(::Oyster::Math::Float3 up, ::Oyster::Math: btVector3 forwardVector(forward.x, forward.y, forward.z); rotation[1] = upVector.normalized(); rotation[2] = forwardVector.normalized(); - rotation[0] = forwardVector.cross(upVector).normalized(); + rotation[0] = upVector.cross(forwardVector).normalized(); trans = this->rigidBody->getWorldTransform(); trans.setBasis(rotation); this->rigidBody->setWorldTransform(trans); @@ -187,6 +227,27 @@ void SimpleRigidBody::SetUpAndForward(::Oyster::Math::Float3 up, ::Oyster::Math: this->state.quaternion = Quaternion(Float3(quaternion.x(), quaternion.y(), quaternion.z()), quaternion.w()); } +void SimpleRigidBody::SetUp(::Oyster::Math::Float3 up) +{ + Float3 vector = Float3(0, 1, 0).Cross(up); + + if(vector == Float3::null) + { + return; + } + + Float sine = vector.GetLength(); + Float cosine = acos(Float3(0, 1, 0).Dot(up)); + + btQuaternion quaternion(btVector3(vector.x, vector.y, vector.z),cosine); + + btTransform trans; + trans = this->rigidBody->getWorldTransform(); + trans.setRotation(quaternion); + this->rigidBody->setWorldTransform(trans); + this->state.quaternion = Quaternion(Float3(quaternion.x(), quaternion.y(), quaternion.z()), quaternion.w()); +} + Float4x4 SimpleRigidBody::GetRotation() const { return this->state.GetRotation(); @@ -229,6 +290,16 @@ Float4x4 SimpleRigidBody::GetView( const ::Oyster::Math::Float3 &offset ) const return this->state.GetView(offset); } +Float3 SimpleRigidBody::GetGravity() const +{ + return this->rigidBody->getGravity(); +} +Float3 SimpleRigidBody::GetLinearVelocity() const +{ + return this->rigidBody->getLinearVelocity(); +} + + void SimpleRigidBody::CallSubscription_AfterCollisionResponse(ICustomBody* bodyA, ICustomBody* bodyB, Oyster::Math::Float kineticEnergyLoss) { if(this->afterCollision) @@ -265,6 +336,4 @@ void * SimpleRigidBody::GetCustomTag() const void SimpleRigidBody::SetCustomTag( void *ref ) { this->customTag = ref; -} - - +} \ No newline at end of file diff --git a/Code/GamePhysics/Implementation/SimpleRigidBody.h b/Code/GamePhysics/Implementation/SimpleRigidBody.h index 3663c45c..ec162860 100644 --- a/Code/GamePhysics/Implementation/SimpleRigidBody.h +++ b/Code/GamePhysics/Implementation/SimpleRigidBody.h @@ -19,10 +19,6 @@ namespace Oyster void SetState( const State &state ); void ApplyImpulse(Math::Float3 impulse); - - void SetCollisionShape(btCollisionShape* shape); - void SetMotionState(btDefaultMotionState* motionState); - void SetRigidBody(btRigidBody* rigidBody); void SetSubscription(EventAction_AfterCollisionResponse function); void SetSubscription(EventAction_Move function); @@ -32,12 +28,15 @@ namespace Oyster void SetRotation(Math::Float4 quaternion); void SetRotation(Math::Quaternion quaternion); void SetRotation(Math::Float3 eulerAngles); + void SetRotation(::Oyster::Math::Float4x4 rotation); + void SetRotationAsAngularAxis(::Oyster::Math::Float4 angularAxis); void SetAngularFactor(Math::Float factor); void SetGravity(Math::Float3 gravity); void SetUpAndRight(::Oyster::Math::Float3 up, ::Oyster::Math::Float3 right); void SetUpAndForward(::Oyster::Math::Float3 up, ::Oyster::Math::Float3 forward); + void SetUp(::Oyster::Math::Float3 up); Math::Float4x4 GetRotation() const; Math::Float4 GetRotationAsAngularAxis(); @@ -45,6 +44,9 @@ namespace Oyster Math::Float4x4 GetView() const; Math::Float4x4 GetView( const ::Oyster::Math::Float3 &offset ) const; + Math::Float3 GetGravity() const; + ::Oyster::Math::Float3 GetLinearVelocity() const; + void CallSubscription_AfterCollisionResponse(ICustomBody* bodyA, ICustomBody* bodyB, Math::Float kineticEnergyLoss); void CallSubscription_Move(); @@ -55,6 +57,11 @@ namespace Oyster void SetCustomTag( void *ref ); void* GetCustomTag() const; + // Class specific + void SetCollisionShape(btCollisionShape* shape); + void SetMotionState(btDefaultMotionState* motionState); + void SetRigidBody(btRigidBody* rigidBody); + private: btCollisionShape* collisionShape; diff --git a/Code/GamePhysics/Implementation/SphericalRigidBody.cpp b/Code/GamePhysics/Implementation/SphericalRigidBody.cpp deleted file mode 100644 index e69de29b..00000000 diff --git a/Code/GamePhysics/Implementation/SphericalRigidBody.h b/Code/GamePhysics/Implementation/SphericalRigidBody.h deleted file mode 100644 index e69de29b..00000000 diff --git a/Code/GamePhysics/PhysicsAPI.h b/Code/GamePhysics/PhysicsAPI.h index 9fd3722e..25cb7610 100644 --- a/Code/GamePhysics/PhysicsAPI.h +++ b/Code/GamePhysics/PhysicsAPI.h @@ -87,6 +87,8 @@ namespace Oyster virtual ICustomBody* AddCollisionBox(::Oyster::Math::Float3 halfSize, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction) = 0; virtual ICustomBody* AddCollisionCylinder(::Oyster::Math::Float3 halfSize, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction) = 0; + virtual ICustomBody* AddCharacter(::Oyster::Math::Float height, ::Oyster::Math::Float radius, ::Oyster::Math::Float4 rotation, ::Oyster::Math::Float3 position, float mass, float restitution, float staticFriction, float dynamicFriction) = 0; + virtual void SetTimeStep(float timeStep) = 0; virtual void UpdateWorld() = 0; @@ -142,12 +144,15 @@ namespace Oyster virtual void SetRotation(::Oyster::Math::Float4 quaternion) = 0; virtual void SetRotation(::Oyster::Math::Quaternion quaternion) = 0; virtual void SetRotation(::Oyster::Math::Float3 eulerAngles) = 0; + virtual void SetRotation(::Oyster::Math::Float4x4 rotation) = 0; + virtual void SetRotationAsAngularAxis(::Oyster::Math::Float4 angularAxis) = 0; virtual void SetAngularFactor(::Oyster::Math::Float factor) = 0; virtual void SetGravity(::Oyster::Math::Float3 gravity) = 0; virtual void SetUpAndRight(::Oyster::Math::Float3 up, ::Oyster::Math::Float3 right) = 0; virtual void SetUpAndForward(::Oyster::Math::Float3 up, ::Oyster::Math::Float3 forward) = 0; + virtual void SetUp(::Oyster::Math::Float3 up) = 0; virtual ::Oyster::Math::Float4x4 GetRotation() const = 0; virtual ::Oyster::Math::Float4 GetRotationAsAngularAxis() = 0; @@ -155,6 +160,12 @@ namespace Oyster virtual ::Oyster::Math::Float4x4 GetView() const = 0; virtual ::Oyster::Math::Float4x4 GetView(const ::Oyster::Math::Float3 &offset) const = 0; + virtual ::Oyster::Math::Float3 GetGravity() const = 0; + virtual ::Oyster::Math::Float3 GetLinearVelocity() const = 0; + + virtual void CallSubscription_AfterCollisionResponse(ICustomBody* bodyA, ICustomBody* bodyB, Math::Float kineticEnergyLoss) = 0; + virtual void CallSubscription_Move() = 0; + /******************************************************** * @return the void pointer set by SetCustomTag. * nullptr if none is set. @@ -172,6 +183,5 @@ namespace Oyster } #include "PhysicsStructs.h" -#include "PhysicsFormula.h" #endif \ No newline at end of file diff --git a/Code/GamePhysics/PhysicsFormula-Impl.h b/Code/GamePhysics/PhysicsFormula-Impl.h deleted file mode 100644 index 189691f6..00000000 --- a/Code/GamePhysics/PhysicsFormula-Impl.h +++ /dev/null @@ -1,82 +0,0 @@ -#ifndef PHYSICS_FORMULA_IMPL_H -#define PHYSICS_FORMULA_IMPL_H - -#include "PhysicsFormula.h" -#include "OysterPhysics3D.h" - -namespace Oyster { namespace Physics { namespace Formula -{ - namespace MomentOfInertia - { - inline ::Oyster::Math::Float4x4 CreateSphereMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float radius ) - { - return ::Oyster::Physics3D::Formula::MomentOfInertia::Sphere(mass, radius); - } - - inline ::Oyster::Math::Float4x4 CreateHollowSphereMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float radius ) - { - return ::Oyster::Physics3D::Formula::MomentOfInertia::HollowSphere(mass, radius); - } - - inline ::Oyster::Math::Float4x4 CreateCuboidMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float height, const ::Oyster::Math::Float width, const ::Oyster::Math::Float depth ) - { - return ::Oyster::Physics3D::Formula::MomentOfInertia::Cuboid(mass, height, width, depth); - } - - inline ::Oyster::Math::Float4x4 CreateCylinderMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float height, const ::Oyster::Math::Float radius ) - { - return ::Oyster::Physics3D::Formula::MomentOfInertia::Cylinder(mass, height, radius); - } - - inline ::Oyster::Math::Float4x4 CreateRodMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float length ) - { - return ::Oyster::Physics3D::Formula::MomentOfInertia::RodCenter(mass, length); - } - } - - namespace CollisionResponse - { - inline ::Oyster::Math::Float Bounce( ::Oyster::Math::Float e, ::Oyster::Math::Float mA, ::Oyster::Math::Float gA, ::Oyster::Math::Float mB, ::Oyster::Math::Float gB ) - { - //return (e + 1) * (mB*gA - mA*gB) / (mA + mB); - return (e + 1) * (mA*gB - mB*gA) / (mA + mB); - } - - inline ::Oyster::Math::Float4 Friction( ::Oyster::Math::Float i, ::Oyster::Math::Float4 iN, ::Oyster::Math::Float4 momA, ::Oyster::Math::Float sFA, ::Oyster::Math::Float dFA, ::Oyster::Math::Float mA, ::Oyster::Math::Float4 momB, ::Oyster::Math::Float sFB, ::Oyster::Math::Float dFB, ::Oyster::Math::Float mB ) - { - // FRICTION - // Relative momentum after normal impulse - ::Oyster::Math::Float4 relativeMomentum = momB - momA; - - ::Oyster::Math::Float4 tanFriction = relativeMomentum - relativeMomentum.Dot( iN ) * iN; - - if( tanFriction.Dot(tanFriction) > 0.0f ) - { // no friction if moving directly into surface, or not at all. - tanFriction.Normalize(); - - ::Oyster::Math::Float magnitudeFriction = -relativeMomentum.Dot( tanFriction ); - magnitudeFriction = magnitudeFriction * mA * mB / ( mA + mB ); - - ::Oyster::Math::Float mu = 0.5f * ( sFA + sFB ); - - ::Oyster::Math::Float4 frictionImpulse; - if( abs(magnitudeFriction) < i * mu ) - { - frictionImpulse = magnitudeFriction * tanFriction; - } - else - { - ::Oyster::Math::Float dynamicFriction = 0.5f * ( dFA + dFB ); - frictionImpulse = ( -i * dynamicFriction ) * tanFriction; - } - - return ( 1 / mA ) * frictionImpulse; - } - else - return ::Oyster::Math::Float4::null; - } - } - -} } } - -#endif \ No newline at end of file diff --git a/Code/GamePhysics/PhysicsFormula.h b/Code/GamePhysics/PhysicsFormula.h deleted file mode 100644 index fe91ae3a..00000000 --- a/Code/GamePhysics/PhysicsFormula.h +++ /dev/null @@ -1,35 +0,0 @@ -#ifndef PHYSICS_FORMULA_H -#define PHYSICS_FORMULA_H - -#include "OysterMath.h" -#include "OysterPhysics3D.h" - -namespace Oyster { namespace Physics { namespace Formula -{ - namespace MomentOfInertia - { - ::Oyster::Math::Float4x4 CreateSphereMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float radius ); - ::Oyster::Math::Float4x4 CreateHollowSphereMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float radius ); - ::Oyster::Math::Float4x4 CreateCuboidMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float height, const ::Oyster::Math::Float width, const ::Oyster::Math::Float depth ); - ::Oyster::Math::Float4x4 CreateCylinderMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float height, const ::Oyster::Math::Float radius ); - ::Oyster::Math::Float4x4 CreateRodMatrix( const ::Oyster::Math::Float mass, const ::Oyster::Math::Float length ); - } - - namespace CollisionResponse - { - ::Oyster::Math::Float Bounce( ::Oyster::Math::Float coeffOfRestitution, - ::Oyster::Math::Float massA, ::Oyster::Math::Float momentumA, - ::Oyster::Math::Float massB, ::Oyster::Math::Float momentumB ); - - ::Oyster::Math::Float4 Friction( ::Oyster::Math::Float impulse, ::Oyster::Math::Float4 impulseNormal, - ::Oyster::Math::Float4 momentumA, ::Oyster::Math::Float staticFrictionA, - ::Oyster::Math::Float dynamicFrictionA, ::Oyster::Math::Float massA, - ::Oyster::Math::Float4 momentumB, ::Oyster::Math::Float staticFrictionB, - ::Oyster::Math::Float dynamicFrictionB, ::Oyster::Math::Float massB ); - - } -} } } - -#include "PhysicsFormula-Impl.h" - -#endif \ No newline at end of file From 063f57133f40c15d8644b6536d0ba0d4f656db0e Mon Sep 17 00:00:00 2001 From: Robin Engman Date: Fri, 14 Feb 2014 08:29:49 +0100 Subject: [PATCH 2/5] Set mass added --- Code/GamePhysics/Implementation/SimpleRigidBody.cpp | 8 ++++++++ Code/GamePhysics/Implementation/SimpleRigidBody.h | 11 ++++++----- Code/GamePhysics/PhysicsAPI.h | 1 + 3 files changed, 15 insertions(+), 5 deletions(-) diff --git a/Code/GamePhysics/Implementation/SimpleRigidBody.cpp b/Code/GamePhysics/Implementation/SimpleRigidBody.cpp index 81d58f5b..3d9fbc4f 100644 --- a/Code/GamePhysics/Implementation/SimpleRigidBody.cpp +++ b/Code/GamePhysics/Implementation/SimpleRigidBody.cpp @@ -184,6 +184,14 @@ void SimpleRigidBody::SetAngularFactor(Float factor) this->rigidBody->setAngularFactor(factor); } +void SimpleRigidBody::SetMass(Float mass) +{ + btVector3 fallInertia(0, 0, 0); + collisionShape->calculateLocalInertia(mass, fallInertia); + this->rigidBody->setMassProps(mass, fallInertia); + this->state.mass = mass; +} + void SimpleRigidBody::SetGravity(Float3 gravity) { this->rigidBody->setGravity(btVector3(gravity.x, gravity.y, gravity.z)); diff --git a/Code/GamePhysics/Implementation/SimpleRigidBody.h b/Code/GamePhysics/Implementation/SimpleRigidBody.h index ec162860..d08fd886 100644 --- a/Code/GamePhysics/Implementation/SimpleRigidBody.h +++ b/Code/GamePhysics/Implementation/SimpleRigidBody.h @@ -29,20 +29,21 @@ namespace Oyster void SetRotation(Math::Quaternion quaternion); void SetRotation(Math::Float3 eulerAngles); void SetRotation(::Oyster::Math::Float4x4 rotation); - void SetRotationAsAngularAxis(::Oyster::Math::Float4 angularAxis); + void SetRotationAsAngularAxis(Math::Float4 angularAxis); void SetAngularFactor(Math::Float factor); + void SetMass(Math::Float mass); void SetGravity(Math::Float3 gravity); - void SetUpAndRight(::Oyster::Math::Float3 up, ::Oyster::Math::Float3 right); - void SetUpAndForward(::Oyster::Math::Float3 up, ::Oyster::Math::Float3 forward); - void SetUp(::Oyster::Math::Float3 up); + void SetUpAndRight(Math::Float3 up, Math::Float3 right); + void SetUpAndForward(Math::Float3 up, Math::Float3 forward); + void SetUp(Math::Float3 up); Math::Float4x4 GetRotation() const; Math::Float4 GetRotationAsAngularAxis(); Math::Float4x4 GetOrientation() const; Math::Float4x4 GetView() const; - Math::Float4x4 GetView( const ::Oyster::Math::Float3 &offset ) const; + Math::Float4x4 GetView( const Math::Float3 &offset ) const; Math::Float3 GetGravity() const; ::Oyster::Math::Float3 GetLinearVelocity() const; diff --git a/Code/GamePhysics/PhysicsAPI.h b/Code/GamePhysics/PhysicsAPI.h index 25cb7610..1c220d3e 100644 --- a/Code/GamePhysics/PhysicsAPI.h +++ b/Code/GamePhysics/PhysicsAPI.h @@ -147,6 +147,7 @@ namespace Oyster virtual void SetRotation(::Oyster::Math::Float4x4 rotation) = 0; virtual void SetRotationAsAngularAxis(::Oyster::Math::Float4 angularAxis) = 0; virtual void SetAngularFactor(::Oyster::Math::Float factor) = 0; + virtual void SetMass(::Oyster::Math::Float mass) = 0; virtual void SetGravity(::Oyster::Math::Float3 gravity) = 0; From a42dfe96f15c235941775d60eb8924cd8106565a Mon Sep 17 00:00:00 2001 From: Robin Engman Date: Fri, 14 Feb 2014 11:52:44 +0100 Subject: [PATCH 3/5] Jump implemented --- Code/Game/GameLogic/Game_PlayerData.cpp | 2 +- Code/Game/GameLogic/Player.cpp | 44 +++++++++++--- Code/Game/GameLogic/Player.h | 1 + .../Implementation/PhysicsAPI_Impl.cpp | 6 +- .../Implementation/SimpleRigidBody.cpp | 57 +++++++++++++++++++ .../Implementation/SimpleRigidBody.h | 12 +++- Code/GamePhysics/PhysicsAPI.h | 2 + Code/GamePhysics/PhysicsStructs-Impl.h | 4 +- Code/GamePhysics/PhysicsStructs.h | 1 + 9 files changed, 116 insertions(+), 13 deletions(-) diff --git a/Code/Game/GameLogic/Game_PlayerData.cpp b/Code/Game/GameLogic/Game_PlayerData.cpp index 56df13c4..1719da4a 100644 --- a/Code/Game/GameLogic/Game_PlayerData.cpp +++ b/Code/Game/GameLogic/Game_PlayerData.cpp @@ -15,7 +15,7 @@ Game::PlayerData::PlayerData() //sbDesc.quaternion = Oyster::Math::Float3(0, Oyster::Math::pi, 0); //create rigid body - Oyster::Physics::ICustomBody* rigidBody = Oyster::Physics::API::Instance().AddCollisionBox(size, Oyster::Math::Float4(0, 0, 0, 1), centerPosition, mass, 0.5f, 0.8f, 0.6f ); + Oyster::Physics::ICustomBody* rigidBody = Oyster::Physics::API::Instance().AddCharacter(1.5f, 0.5f, Oyster::Math::Float4(0, 0, 0, 1), centerPosition, mass, 0.5f, 0.8f, 0.6f ); rigidBody->SetAngularFactor(0.0f); //create player with this rigid body this->player = new Player(rigidBody, Player::PlayerCollision, OBJECT_TYPE::OBJECT_TYPE_PLAYER); diff --git a/Code/Game/GameLogic/Player.cpp b/Code/Game/GameLogic/Player.cpp index 19a0bb9c..9a780d76 100644 --- a/Code/Game/GameLogic/Player.cpp +++ b/Code/Game/GameLogic/Player.cpp @@ -52,6 +52,7 @@ void Player::InitPlayer() key_strafeRight = 0; key_strafeLeft = 0; + this->previousPosition = Oyster::Math::Float3(0,0,0); this->moveDir = Oyster::Math::Float3(0,0,0); this->moveSpeed = 100; this->previousMoveSpeed = Oyster::Math::Float3(0,0,0); @@ -72,12 +73,34 @@ void Player::BeginFrame() //weapon->Update(0.002f); Object::BeginFrame(); - if(this->moveDir != Oyster::Math::Float3::null) + //Oyster::Math::Float3 previousFall = this->previousMoveSpeed*-this->rigidBody->GetState().centerPos.GetNormalized(); + //Oyster::Math::Float3 currentFall = this->rigidBody->GetLinearVelocity()*-this->rigidBody->GetState().centerPos.GetNormalized(); + + if(this->moveDir != Oyster::Math::Float3::null && this->playerState != PLAYER_STATE_JUMPING) { Oyster::Math::Float3 velocity = this->rigidBody->GetLinearVelocity(); Oyster::Math::Float3 lostVelocity = (this->previousMoveSpeed - velocity).GetMagnitude()*this->moveDir; this->rigidBody->SetLinearVelocity(velocity + lostVelocity - this->moveDir*this->moveSpeed ); } + else + { + + if(this->rigidBody->GetLamda() == 1.0f) + { + this->playerState = PLAYER_STATE_WALKING; + } + + if(this->moveDir != Oyster::Math::Float3::null) + { + Oyster::Math::Float3 velocity = this->rigidBody->GetLinearVelocity(); + this->rigidBody->SetLinearVelocity(velocity - this->moveDir*this->moveSpeed ); + } + } + + if(this->rigidBody->GetLamda() == 1.0f) + { + this->playerState = PLAYER_STATE_WALKING; + } this->moveDir = Oyster::Math::Float3::null; @@ -109,10 +132,12 @@ void Player::BeginFrame() if(this->moveDir != Oyster::Math::Float3::null) { this->moveDir.Normalize(); - this->rigidBody->SetLinearVelocity(this->moveDir*this->moveSpeed + this->rigidBody->GetLinearVelocity()); - this->previousMoveSpeed = this->rigidBody->GetLinearVelocity(); + this->rigidBody->SetLinearVelocity(this->moveDir*this->moveSpeed + this->rigidBody->GetLinearVelocity()); } + this->previousMoveSpeed = this->rigidBody->GetLinearVelocity(); + this->previousPosition = this->rigidBody->GetState().centerPos; + this->weapon->Update(0.01f); } @@ -190,15 +215,18 @@ void Player::Rotate(const Oyster::Math3D::Float3 lookDir, const Oyster::Math3D:: // this is the camera right vector this->lookDir = lookDir; - Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1]; - this->rigidBody->SetUpAndRight(up, right); + //Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1]; + //this->rigidBody->SetUpAndRight(up, right); } void Player::Jump() { - Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1].GetNormalized(); - this->rigidBody->ApplyImpulse(up *1500); - this->playerState == PLAYER_STATE::PLAYER_STATE_JUMPING; + if(this->rigidBody->GetLamda() < 1.0f) + { + Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1].GetNormalized(); + this->rigidBody->ApplyImpulse(up *1500); + this->playerState = PLAYER_STATE::PLAYER_STATE_JUMPING; + } } bool Player::IsWalking() diff --git a/Code/Game/GameLogic/Player.h b/Code/Game/GameLogic/Player.h index bdd83f41..b9ba7c05 100644 --- a/Code/Game/GameLogic/Player.h +++ b/Code/Game/GameLogic/Player.h @@ -91,6 +91,7 @@ namespace GameLogic float key_jump; + Oyster::Math::Float3 previousPosition; Oyster::Math::Float3 moveDir; Oyster::Math::Float moveSpeed; Oyster::Math::Float3 previousMoveSpeed; diff --git a/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp b/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp index b3ad6777..9cd87d1d 100644 --- a/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp +++ b/Code/GamePhysics/Implementation/PhysicsAPI_Impl.cpp @@ -210,7 +210,7 @@ ICustomBody* API_Impl::AddCharacter(::Oyster::Math::Float height, ::Oyster::Math this->customBodies.push_back(body); state.centerPos = position; - state.reach = Float3(radius, height*0.5f, radius); + state.reach = Float3(radius, height, radius); state.dynamicFrictionCoeff = 0.5f; state.staticFrictionCoeff = 0.5f; state.quaternion = Quaternion(Float3(rotation.xyz), rotation.w); @@ -230,7 +230,9 @@ void API_Impl::UpdateWorld() { for(unsigned int i = 0; i < this->customBodies.size(); i++ ) { - this->customBodies[i]->SetGravity(-(this->customBodies[i]->GetState().centerPos - this->gravityPoint).GetNormalized()*this->gravity); + SimpleRigidBody* simpleBody = dynamic_cast(this->customBodies[i]); + this->customBodies[i]->SetGravity(-(this->customBodies[i]->GetState().centerPos - this->gravityPoint).GetNormalized()*this->gravity); + simpleBody->PreStep(this->dynamicsWorld); } this->dynamicsWorld->stepSimulation(this->timeStep, 1, this->timeStep); diff --git a/Code/GamePhysics/Implementation/SimpleRigidBody.cpp b/Code/GamePhysics/Implementation/SimpleRigidBody.cpp index 3d9fbc4f..cd0c1962 100644 --- a/Code/GamePhysics/Implementation/SimpleRigidBody.cpp +++ b/Code/GamePhysics/Implementation/SimpleRigidBody.cpp @@ -344,4 +344,61 @@ void * SimpleRigidBody::GetCustomTag() const void SimpleRigidBody::SetCustomTag( void *ref ) { this->customTag = ref; +} + + +void SimpleRigidBody::PreStep (const btCollisionWorld* collisionWorld) +{ + btTransform xform; + this->rigidBody->getMotionState()->getWorldTransform (xform); + btVector3 down = -xform.getBasis()[1]; + btVector3 forward = xform.getBasis()[2]; + down.normalize (); + forward.normalize(); + + this->raySource[0] = xform.getOrigin(); + this->raySource[1] = xform.getOrigin(); + + this->rayTarget[0] = this->raySource[0] + down * this->state.reach.y * btScalar(1.1); + this->rayTarget[1] = this->raySource[1] + forward * this->state.reach.y * btScalar(1.1); + + class ClosestNotMe : public btCollisionWorld::ClosestRayResultCallback + { + public: + ClosestNotMe (btRigidBody* me) : btCollisionWorld::ClosestRayResultCallback(btVector3(0.0, 0.0, 0.0), btVector3(0.0, 0.0, 0.0)) + { + m_me = me; + } + + virtual btScalar addSingleResult(btCollisionWorld::LocalRayResult& rayResult,bool normalInWorldSpace) + { + if (rayResult.m_collisionObject == m_me) + return 1.0; + + return ClosestRayResultCallback::addSingleResult (rayResult, normalInWorldSpace); + } + protected: + btRigidBody* m_me; + }; + + ClosestNotMe rayCallback(this->rigidBody); + + int i = 0; + for (i = 0; i < 2; i++) + { + rayCallback.m_closestHitFraction = 1.0; + if((this->raySource[i] - this->rayTarget[i]).length() != 0) + collisionWorld->rayTest (this->raySource[i], this->rayTarget[i], rayCallback); + if (rayCallback.hasHit()) + { + this->rayLambda[i] = rayCallback.m_closestHitFraction; + } else { + this->rayLambda[i] = 1.0; + } + } +} + +float SimpleRigidBody::GetLamda() const +{ + return this->rayLambda[0]; } \ No newline at end of file diff --git a/Code/GamePhysics/Implementation/SimpleRigidBody.h b/Code/GamePhysics/Implementation/SimpleRigidBody.h index d08fd886..d67393d1 100644 --- a/Code/GamePhysics/Implementation/SimpleRigidBody.h +++ b/Code/GamePhysics/Implementation/SimpleRigidBody.h @@ -58,11 +58,17 @@ namespace Oyster void SetCustomTag( void *ref ); void* GetCustomTag() const; + + // Class specific void SetCollisionShape(btCollisionShape* shape); void SetMotionState(btDefaultMotionState* motionState); void SetRigidBody(btRigidBody* rigidBody); + void PreStep(const btCollisionWorld* collisionWorld); + + float GetLamda() const; + private: btCollisionShape* collisionShape; @@ -76,7 +82,11 @@ namespace Oyster void *customTag; - ::Oyster::Math::Float3 gravity; + Math::Float3 gravity; + + btVector3 raySource[2]; + btVector3 rayTarget[2]; + btScalar rayLambda[2]; }; } } diff --git a/Code/GamePhysics/PhysicsAPI.h b/Code/GamePhysics/PhysicsAPI.h index 1c220d3e..e83f1d99 100644 --- a/Code/GamePhysics/PhysicsAPI.h +++ b/Code/GamePhysics/PhysicsAPI.h @@ -179,6 +179,8 @@ namespace Oyster * @param ref: Anything castable to a void pointer, the engine won't care. ********************************************************/ virtual void SetCustomTag( void *ref ) = 0; + + virtual float GetLamda() const = 0; }; } } diff --git a/Code/GamePhysics/PhysicsStructs-Impl.h b/Code/GamePhysics/PhysicsStructs-Impl.h index 07ba0bb2..87cfcb17 100644 --- a/Code/GamePhysics/PhysicsStructs-Impl.h +++ b/Code/GamePhysics/PhysicsStructs-Impl.h @@ -10,9 +10,10 @@ namespace Oyster { namespace Struct { - inline CustomBodyState::CustomBodyState( ::Oyster::Math::Float mass, ::Oyster::Math::Float restitutionCoeff, ::Oyster::Math::Float staticFrictionCoeff, ::Oyster::Math::Float dynamicFrictionCoeff, const ::Oyster::Math::Float3 ¢erPos, const ::Oyster::Math::Quaternion& quaternion) + inline CustomBodyState::CustomBodyState( ::Oyster::Math::Float mass, ::Oyster::Math::Float3 reach, ::Oyster::Math::Float restitutionCoeff, ::Oyster::Math::Float staticFrictionCoeff, ::Oyster::Math::Float dynamicFrictionCoeff, const ::Oyster::Math::Float3 ¢erPos, const ::Oyster::Math::Quaternion& quaternion) { this->mass = mass; + this->reach = reach; this->restitutionCoeff = restitutionCoeff; this->staticFrictionCoeff = staticFrictionCoeff; this->dynamicFrictionCoeff = dynamicFrictionCoeff; @@ -24,6 +25,7 @@ namespace Oyster { this->mass = state.mass; this->restitutionCoeff = state.restitutionCoeff; + this->reach = state.reach; this->staticFrictionCoeff = state.staticFrictionCoeff; this->dynamicFrictionCoeff = state.dynamicFrictionCoeff; this->centerPos = state.centerPos; diff --git a/Code/GamePhysics/PhysicsStructs.h b/Code/GamePhysics/PhysicsStructs.h index fa6c023c..2f369b90 100644 --- a/Code/GamePhysics/PhysicsStructs.h +++ b/Code/GamePhysics/PhysicsStructs.h @@ -16,6 +16,7 @@ namespace Oyster public: // Default constructor CustomBodyState( ::Oyster::Math::Float mass = 1.0f, + ::Oyster::Math::Float3 reach = ::Oyster::Math::Float3(0,0,0), ::Oyster::Math::Float restitutionCoeff = 0.5f, ::Oyster::Math::Float staticFrictionCoeff = 1.0f, ::Oyster::Math::Float dynamicFrictionCoeff = 1.0f, From 9fc8a8840f3c6d2310f20168a2a878ac0cf85aa9 Mon Sep 17 00:00:00 2001 From: Erik Persson Date: Fri, 14 Feb 2014 12:03:29 +0100 Subject: [PATCH 4/5] GL - fixed movement(pretty unstable but its working) --- Code/Game/GameLogic/Player.cpp | 21 +++++++++++++++++++-- Code/Game/GameLogic/StaticObject.cpp | 8 ++++---- 2 files changed, 23 insertions(+), 6 deletions(-) diff --git a/Code/Game/GameLogic/Player.cpp b/Code/Game/GameLogic/Player.cpp index 0fb93995..54841b39 100644 --- a/Code/Game/GameLogic/Player.cpp +++ b/Code/Game/GameLogic/Player.cpp @@ -17,17 +17,34 @@ Player::Player() Player::Player(Oyster::Physics::ICustomBody *rigidBody, void (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID, int teamID) :DynamicObject(rigidBody, EventOnCollision, type, objectID) { + this->rigidBody = rigidBody; + + Oyster::Math::Float3 centerPosition = Oyster::Math::Float3(0,400,0); + + Oyster::Math::Float3 size = Oyster::Math::Float3(0.25f,1.0f,0.5f); + Oyster::Math::Float mass = 60; + Oyster::Math::Float restitutionCoeff = 0.5; + Oyster::Math::Float frictionCoeff_Static = 0.4; + Oyster::Math::Float frictionCoeff_Dynamic = 0.3; + + + this->rigidBody = Oyster::Physics::API::Instance().AddCollisionBox(size, Oyster::Math::Float4(0, 0, 0, 1), centerPosition, mass, 0.5f, 0.8f, 0.6f ); + this->rigidBody->SetAngularFactor(0.0f); + weapon = new Weapon(2,this); this->life = 100; - this->teamID = -1; + this->teamID = teamID; this->playerState = PLAYER_STATE_IDLE; this->lookDir = Oyster::Math::Float3(0,0,-1); - this->moveDir = Oyster::Math::Float3(0,0,0); key_forward = 0; key_backward = 0; key_strafeRight = 0; key_strafeLeft = 0; + + this->moveDir = Oyster::Math::Float3(0,0,0); + this->moveSpeed = 100; + this->previousMoveSpeed = Oyster::Math::Float3(0,0,0); } Player::Player(Oyster::Physics::ICustomBody *rigidBody, Oyster::Physics::ICustomBody::SubscriptMessage (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID, int teamID) diff --git a/Code/Game/GameLogic/StaticObject.cpp b/Code/Game/GameLogic/StaticObject.cpp index 158ee87e..7124b14a 100644 --- a/Code/Game/GameLogic/StaticObject.cpp +++ b/Code/Game/GameLogic/StaticObject.cpp @@ -14,25 +14,25 @@ StaticObject::StaticObject() StaticObject::StaticObject(Oyster::Physics::ICustomBody *rigidBody , void (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID) :Object(rigidBody, EventOnCollision, type, objectID) { - //use setMass(when it is made) and set the mass to 0 in order to ensure that the object is static + rigidBody->SetMass(0); } StaticObject::StaticObject(Oyster::Physics::ICustomBody *rigidBody , Oyster::Physics::ICustomBody::SubscriptMessage (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID) :Object(rigidBody, EventOnCollision, type, objectID) { - //use setMass(when it is made) and set the mass to 0 in order to ensure that the object is static + rigidBody->SetMass(0); } StaticObject::StaticObject(Oyster::Physics::ICustomBody *rigidBody , void (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID, Oyster::Math::Float extraDamageOnCollision) { this->extraDamageOnCollision = extraDamageOnCollision; - //use setMass(when it is made) and set the mass to 0 in order to ensure that the object is static + rigidBody->SetMass(0); } StaticObject::StaticObject(Oyster::Physics::ICustomBody *rigidBody , Oyster::Physics::ICustomBody::SubscriptMessage (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID, Oyster::Math::Float extraDamageOnCollision) { this->extraDamageOnCollision = extraDamageOnCollision; - //use setMass(when it is made) and set the mass to 0 in order to ensure that the object is static + rigidBody->SetMass(0); } StaticObject::~StaticObject(void) { From f8e68b95b2011f7e3b43f5275a2a29f93743493f Mon Sep 17 00:00:00 2001 From: Robin Engman Date: Fri, 14 Feb 2014 12:07:49 +0100 Subject: [PATCH 5/5] Temporary jump --- Code/Game/GameLogic/Game_PlayerData.cpp | 2 +- Code/Game/GameLogic/Player.cpp | 16 +++++----------- 2 files changed, 6 insertions(+), 12 deletions(-) diff --git a/Code/Game/GameLogic/Game_PlayerData.cpp b/Code/Game/GameLogic/Game_PlayerData.cpp index 72251c5a..275866b9 100644 --- a/Code/Game/GameLogic/Game_PlayerData.cpp +++ b/Code/Game/GameLogic/Game_PlayerData.cpp @@ -17,7 +17,7 @@ Game::PlayerData::PlayerData() //sbDesc.quaternion = Oyster::Math::Float3(0, Oyster::Math::pi, 0); //create rigid body - Oyster::Physics::ICustomBody* rigidBody = Oyster::Physics::API::Instance().AddCharacter(1.5f, 0.5f, Oyster::Math::Float4(0, 0, 0, 1), centerPosition, mass, 0.5f, 0.8f, 0.6f ); + Oyster::Physics::ICustomBody* rigidBody = Oyster::Physics::API::Instance().AddCharacter(2.0f, 0.5f, Oyster::Math::Float4(0, 0, 0, 1), centerPosition, mass, 0.5f, 0.8f, 0.6f ); rigidBody->SetAngularFactor(0.0f); //create player with this rigid body this->player = new Player(rigidBody, Player::PlayerCollision, ObjectSpecialType_Player,0,0); diff --git a/Code/Game/GameLogic/Player.cpp b/Code/Game/GameLogic/Player.cpp index 66ae7288..508857b9 100644 --- a/Code/Game/GameLogic/Player.cpp +++ b/Code/Game/GameLogic/Player.cpp @@ -28,6 +28,11 @@ Player::Player(Oyster::Physics::ICustomBody *rigidBody, void (*EventOnCollision) key_backward = 0; key_strafeRight = 0; key_strafeLeft = 0; + + this->previousPosition = Oyster::Math::Float3(0,0,0); + this->moveDir = Oyster::Math::Float3(0,0,0); + this->moveSpeed = 100; + this->previousMoveSpeed = Oyster::Math::Float3(0,0,0); } Player::Player(Oyster::Physics::ICustomBody *rigidBody, Oyster::Physics::ICustomBody::SubscriptMessage (*EventOnCollision)(Oyster::Physics::ICustomBody *proto,Oyster::Physics::ICustomBody *deuter,Oyster::Math::Float kineticEnergyLoss), ObjectSpecialType type, int objectID, int teamID) @@ -103,11 +108,6 @@ void Player::BeginFrame() } } - if(this->rigidBody->GetLamda() == 1.0f) - { - this->playerState = PLAYER_STATE_WALKING; - } - this->moveDir = Oyster::Math::Float3::null; if (key_forward > 0.001) @@ -226,18 +226,12 @@ void Player::Rotate(const Oyster::Math3D::Float3 lookDir, const Oyster::Math3D:: void Player::Jump() { -<<<<<<< HEAD if(this->rigidBody->GetLamda() < 1.0f) { Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1].GetNormalized(); this->rigidBody->ApplyImpulse(up *1500); this->playerState = PLAYER_STATE::PLAYER_STATE_JUMPING; } -======= - Oyster::Math::Float3 up = this->rigidBody->GetState().GetOrientation().v[1].GetNormalized(); - this->rigidBody->ApplyImpulse(up *1500); - this->playerState = PLAYER_STATE::PLAYER_STATE_JUMPING; ->>>>>>> origin/GameLogic } bool Player::IsWalking()