Add PhysicsCommon class and use it as a factory for other library objects and add pile demo in testbed application

This commit is contained in:
Daniel Chappuis 2019-12-12 07:13:27 +01:00
parent 8eacae4b7b
commit 45b02abaec
67 changed files with 1515 additions and 648 deletions

View File

@ -8,6 +8,16 @@
- The CollisionWorld::testOverlap() methods do not have the 'categoryMaskBits' parameter anymore.
- Many methods in the EventListener class have changed. Check the user manual for more information.
- The way to retrieve contacts from a CollisionCallbackInfo object has changed. Check the user manual for more information.
- Now, the collision shapes need be be created with the PhysicsWorld::createXXXShape() methods instead of using the constructor of the shape as before. For instance, you need to use the PhysicsWorld::createBoxShape() method to create a BoxShape.
- There is now a single MemoryManager (with memory allocators) per PhysicsWorld. The memory allocators are no longer shared between worlds.
- An instance of the BoxShape class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createBoxShape() method.
- An instance of the SphereShape class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createSphereShape() method.
- An instance of the CapsuleShape class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createCapsuleShape() method.
- An instance of the ConvexMeshShape class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createConvexMeshShape() method.
- An instance of the HeightFieldShape class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createHeightFieldShape() method.
- An instance of the ConcaveMeshShape class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createConcaveMeshShape() method.
- An instance of the PolyhedronMesh class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createPolyhedronMesh() method.
- An instance of the TriangleMesh class cannot be instanciated directly anymore. You need to use the PhysicsCommon::createTriangleMesh() method.
### Removed
@ -24,7 +34,7 @@
- Make possible for the user to get vertices, normals and triangle indices of a ConcaveMeshShape
- Make possible for the user to get vertices and height values of the HeightFieldShape
- Make possible for the user to use a custom single frame and pool memory allocator
- Add PhysicsCommon class that needs to be instanciated at the beginning and is used as a factory for other objects of the library
### Fixed

View File

@ -128,6 +128,7 @@ SET (REACTPHYSICS3D_HEADERS
"src/engine/Entity.h"
"src/engine/EntityManager.h"
"src/engine/CollisionWorld.h"
"src/engine/PhysicsCommon.h"
"src/systems/ConstraintSolverSystem.h"
"src/systems/ContactSolverSystem.h"
"src/systems/DynamicsSystem.h"
@ -228,6 +229,7 @@ SET (REACTPHYSICS3D_SOURCES
"src/constraint/Joint.cpp"
"src/constraint/SliderJoint.cpp"
"src/engine/CollisionWorld.cpp"
"src/engine/PhysicsCommon.cpp"
"src/systems/ConstraintSolverSystem.cpp"
"src/systems/ContactSolverSystem.cpp"
"src/systems/DynamicsSystem.cpp"

View File

@ -36,10 +36,8 @@ using namespace reactphysics3d;
* Create a polyhedron mesh given an array of polygons.
* @param polygonVertexArray Pointer to the array of polygons and their vertices
*/
PolyhedronMesh::PolyhedronMesh(PolygonVertexArray* polygonVertexArray)
: mHalfEdgeStructure(MemoryManager::getBaseAllocator(),
polygonVertexArray->getNbFaces(),
polygonVertexArray->getNbVertices(),
PolyhedronMesh::PolyhedronMesh(PolygonVertexArray* polygonVertexArray, MemoryAllocator &allocator)
: mMemoryAllocator(allocator), mHalfEdgeStructure(allocator, polygonVertexArray->getNbFaces(), polygonVertexArray->getNbVertices(),
(polygonVertexArray->getNbFaces() + polygonVertexArray->getNbVertices() - 2) * 2) {
mPolygonVertexArray = polygonVertexArray;
@ -76,7 +74,7 @@ void PolyhedronMesh::createHalfEdgeStructure() {
// Get the polygon face
PolygonVertexArray::PolygonFace* face = mPolygonVertexArray->getPolygonFace(f);
List<uint> faceVertices(MemoryManager::getBaseAllocator(), face->nbVertices);
List<uint> faceVertices(mMemoryAllocator, face->nbVertices);
// For each vertex of the face
for (uint v=0; v < face->nbVertices; v++) {

View File

@ -47,6 +47,9 @@ class PolyhedronMesh {
// -------------------- Attributes -------------------- //
/// Reference to the memory allocator
MemoryAllocator& mMemoryAllocator;
/// Pointer the the polygon vertex array with vertices and faces
/// of the mesh
PolygonVertexArray* mPolygonVertexArray;
@ -62,6 +65,9 @@ class PolyhedronMesh {
// -------------------- Methods -------------------- //
/// Constructor
PolyhedronMesh(PolygonVertexArray* polygonVertexArray, MemoryAllocator& allocator);
/// Create the half-edge structure of the mesh
void createHalfEdgeStructure();
@ -75,9 +81,6 @@ class PolyhedronMesh {
// -------------------- Methods -------------------- //
/// Constructor
PolyhedronMesh(PolygonVertexArray* polygonVertexArray);
/// Destructor
~PolyhedronMesh();
@ -98,6 +101,10 @@ class PolyhedronMesh {
/// Return the centroid of the polyhedron
Vector3 getCentroid() const;
// ---------- Friendship ---------- //
friend class PhysicsCommon;
};
// Return the number of vertices

View File

@ -25,12 +25,15 @@
// Libraries
#include "TriangleMesh.h"
#include "memory/MemoryManager.h"
using namespace reactphysics3d;
// Constructor
TriangleMesh::TriangleMesh()
: mTriangleArrays(MemoryManager::getBaseAllocator()) {
TriangleMesh::TriangleMesh(MemoryAllocator& allocator) : mTriangleArrays(allocator) {
}
// Destructor
TriangleMesh::~TriangleMesh() {
}

View File

@ -29,12 +29,12 @@
// Libraries
#include <cassert>
#include "containers/List.h"
#include "memory/MemoryAllocator.h"
namespace reactphysics3d {
// Declarations
class TriangleVertexArray;
class MemoryManager;
// Class TriangleMesh
/**
@ -51,13 +51,13 @@ class TriangleMesh {
/// All the triangle arrays of the mesh (one triangle array per part)
List<TriangleVertexArray*> mTriangleArrays;
/// Constructor
TriangleMesh(reactphysics3d::MemoryAllocator& allocator);
public:
/// Constructor
TriangleMesh();
/// Destructor
~TriangleMesh() = default;
~TriangleMesh();
/// Add a subpart of the mesh
void addSubpart(TriangleVertexArray* triangleVertexArray);
@ -67,6 +67,11 @@ class TriangleMesh {
/// Return the number of subparts of the mesh
uint getNbSubparts() const;
// ---------- Friendship ---------- //
friend class PhysicsCommon;
};
// Add a subpart of the mesh

View File

@ -37,9 +37,9 @@ using namespace reactphysics3d;
/**
* @param extent The vector with the three extents of the box (in meters)
*/
BoxShape::BoxShape(const Vector3& extent)
BoxShape::BoxShape(const Vector3& extent, MemoryAllocator& allocator)
: ConvexPolyhedronShape(CollisionShapeName::BOX), mExtent(extent),
mHalfEdgeStructure(MemoryManager::getBaseAllocator(), 6, 8, 24) {
mHalfEdgeStructure(allocator, 6, 8, 24) {
assert(extent.x > decimal(0.0));
assert(extent.y > decimal(0.0));
@ -55,8 +55,6 @@ BoxShape::BoxShape(const Vector3& extent)
mHalfEdgeStructure.addVertex(6);
mHalfEdgeStructure.addVertex(7);
MemoryAllocator& allocator = MemoryManager::getBaseAllocator();
// Faces
List<uint> face0(allocator, 4);
face0.add(0); face0.add(1); face0.add(2); face0.add(3);

View File

@ -58,6 +58,9 @@ class BoxShape : public ConvexPolyhedronShape {
// -------------------- Methods -------------------- //
/// Constructor
BoxShape(const Vector3& extent, MemoryAllocator& allocator);
/// Return a local support point in a given direction without the object margin
virtual Vector3 getLocalSupportPointWithoutMargin(const Vector3& direction) const override;
@ -70,16 +73,13 @@ class BoxShape : public ConvexPolyhedronShape {
/// Return the number of bytes used by the collision shape
virtual size_t getSizeInBytes() const override;
/// Destructor
virtual ~BoxShape() override = default;
public :
// -------------------- Methods -------------------- //
/// Constructor
BoxShape(const Vector3& extent);
/// Destructor
virtual ~BoxShape() override = default;
/// Deleted copy-constructor
BoxShape(const BoxShape& shape) = delete;
@ -124,6 +124,10 @@ class BoxShape : public ConvexPolyhedronShape {
/// Return the string representation of the shape
virtual std::string to_string() const override;
// ----- Friendship ----- //
friend class PhysicsCommon;
};
// Return the extents of the box

View File

@ -57,6 +57,9 @@ class CapsuleShape : public ConvexShape {
// -------------------- Methods -------------------- //
/// Constructor
CapsuleShape(decimal radius, decimal height);
/// Return a local support point in a given direction without the object margin
virtual Vector3 getLocalSupportPointWithoutMargin(const Vector3& direction) const override;
@ -74,16 +77,13 @@ class CapsuleShape : public ConvexShape {
/// Return the number of bytes used by the collision shape
virtual size_t getSizeInBytes() const override;
/// Destructor
virtual ~CapsuleShape() override = default;
public :
// -------------------- Methods -------------------- //
/// Constructor
CapsuleShape(decimal radius, decimal height);
/// Destructor
virtual ~CapsuleShape() override = default;
/// Deleted copy-constructor
CapsuleShape(const CapsuleShape& shape) = delete;
@ -107,6 +107,10 @@ class CapsuleShape : public ConvexShape {
/// Return the string representation of the shape
virtual std::string to_string() const override;
// ----- Friendship ----- //
friend class PhysicsCommon;
};
// Get the radius of the capsule

View File

@ -34,9 +34,9 @@
using namespace reactphysics3d;
// Constructor
ConcaveMeshShape::ConcaveMeshShape(TriangleMesh* triangleMesh, const Vector3& scaling)
ConcaveMeshShape::ConcaveMeshShape(TriangleMesh* triangleMesh, MemoryAllocator& allocator, const Vector3& scaling)
// TODO : Do not use the default base allocator here
: ConcaveShape(CollisionShapeName::TRIANGLE_MESH), mDynamicAABBTree(MemoryManager::getBaseAllocator()),
: ConcaveShape(CollisionShapeName::TRIANGLE_MESH), mDynamicAABBTree(allocator),
mScaling(scaling) {
mTriangleMesh = triangleMesh;
mRaycastTestType = TriangleRaycastSide::FRONT;

View File

@ -146,6 +146,9 @@ class ConcaveMeshShape : public ConcaveShape {
// -------------------- Methods -------------------- //
/// Constructor
ConcaveMeshShape(TriangleMesh* triangleMesh, MemoryAllocator& allocator, const Vector3& scaling = Vector3(1, 1, 1));
/// Raycast method with feedback information
virtual bool raycast(const Ray& ray, RaycastInfo& raycastInfo, ProxyShape* proxyShape, MemoryAllocator& allocator) const override;
@ -169,14 +172,11 @@ class ConcaveMeshShape : public ConcaveShape {
List<Vector3> &triangleVerticesNormals, List<uint>& shapeIds,
MemoryAllocator& allocator) const override;
public:
/// Constructor
ConcaveMeshShape(TriangleMesh* triangleMesh, const Vector3& scaling = Vector3(1, 1, 1));
/// Destructor
virtual ~ConcaveMeshShape() override = default;
public:
/// Deleted copy-constructor
ConcaveMeshShape(const ConcaveMeshShape& shape) = delete;
@ -215,6 +215,7 @@ class ConcaveMeshShape : public ConcaveShape {
friend class ConvexTriangleAABBOverlapCallback;
friend class ConcaveMeshRaycastCallback;
friend class PhysicsCommon;
};
// Return the number of bytes used by the collision shape

View File

@ -66,6 +66,9 @@ class ConvexMeshShape : public ConvexPolyhedronShape {
// -------------------- Methods -------------------- //
/// Constructor
ConvexMeshShape(PolyhedronMesh* polyhedronMesh, const Vector3& scaling = Vector3(1,1,1));
/// Recompute the bounds of the mesh
void recalculateBounds();
@ -81,16 +84,13 @@ class ConvexMeshShape : public ConvexPolyhedronShape {
/// Return the number of bytes used by the collision shape
virtual size_t getSizeInBytes() const override;
/// Destructor
virtual ~ConvexMeshShape() override = default;
public :
// -------------------- Methods -------------------- //
/// Constructor
ConvexMeshShape(PolyhedronMesh* polyhedronMesh, const Vector3& scaling = Vector3(1,1,1));
/// Destructor
virtual ~ConvexMeshShape() override = default;
/// Deleted copy-constructor
ConvexMeshShape(const ConvexMeshShape& shape) = delete;
@ -135,6 +135,10 @@ class ConvexMeshShape : public ConvexPolyhedronShape {
/// Return the string representation of the shape
virtual std::string to_string() const override;
// ----- Friendship ----- //
friend class PhysicsCommon;
};
// Return the number of bytes used by the collision shape

View File

@ -96,6 +96,12 @@ class HeightFieldShape : public ConcaveShape {
// -------------------- Methods -------------------- //
/// Constructor
HeightFieldShape(int nbGridColumns, int nbGridRows, decimal minHeight, decimal maxHeight,
const void* heightFieldData, HeightDataType dataType,
int upAxis = 1, decimal integerHeightScale = 1.0f,
const Vector3& scaling = Vector3(1,1,1));
/// Raycast method with feedback information
virtual bool raycast(const Ray& ray, RaycastInfo& raycastInfo, ProxyShape* proxyShape, MemoryAllocator& allocator) const override;
@ -119,17 +125,11 @@ class HeightFieldShape : public ConcaveShape {
/// Compute the shape Id for a given triangle
uint computeTriangleShapeId(uint iIndex, uint jIndex, uint secondTriangleIncrement) const;
public:
/// Constructor
HeightFieldShape(int nbGridColumns, int nbGridRows, decimal minHeight, decimal maxHeight,
const void* heightFieldData, HeightDataType dataType,
int upAxis = 1, decimal integerHeightScale = 1.0f,
const Vector3& scaling = Vector3(1,1,1));
/// Destructor
virtual ~HeightFieldShape() override = default;
public:
/// Deleted copy-constructor
HeightFieldShape(const HeightFieldShape& shape) = delete;
@ -172,6 +172,7 @@ class HeightFieldShape : public ConcaveShape {
friend class ConvexTriangleAABBOverlapCallback;
friend class ConcaveMeshRaycastCallback;
friend class PhysicsCommon;
};
// Return the scaling factor

View File

@ -50,6 +50,9 @@ class SphereShape : public ConvexShape {
// -------------------- Methods -------------------- //
/// Constructor
SphereShape(decimal radius);
/// Return a local support point in a given direction without the object margin
virtual Vector3 getLocalSupportPointWithoutMargin(const Vector3& direction) const override;
@ -62,16 +65,13 @@ class SphereShape : public ConvexShape {
/// Return the number of bytes used by the collision shape
virtual size_t getSizeInBytes() const override;
/// Destructor
virtual ~SphereShape() override = default;
public :
// -------------------- Methods -------------------- //
/// Constructor
SphereShape(decimal radius);
/// Destructor
virtual ~SphereShape() override = default;
/// Deleted copy-constructor
SphereShape(const SphereShape& shape) = delete;
@ -95,6 +95,10 @@ class SphereShape : public ConvexShape {
/// Return the string representation of the shape
virtual std::string to_string() const override;
// ----- Friendship ----- //
friend class PhysicsCommon;
};
// Get the radius of the sphere

View File

@ -107,10 +107,6 @@ class TriangleShape : public ConvexPolyhedronShape {
const Transform& worldToOtherShapeTransform, decimal penetrationDepth, bool isTriangleShape1,
Vector3& outNewLocalContactPointOtherShape, Vector3& outSmoothWorldContactTriangleNormal) const;
public:
// -------------------- Methods -------------------- //
/// Constructor
TriangleShape(const Vector3* vertices, const Vector3* verticesNormals,
uint shapeId, MemoryAllocator& allocator);
@ -118,6 +114,10 @@ class TriangleShape : public ConvexPolyhedronShape {
/// Destructor
virtual ~TriangleShape() override = default;
public:
// -------------------- Methods -------------------- //
/// Deleted copy-constructor
TriangleShape(const TriangleShape& shape) = delete;
@ -181,6 +181,7 @@ class TriangleShape : public ConvexPolyhedronShape {
friend class TriangleOverlapCallback;
friend class MiddlePhaseTriangleCallback;
friend class HeightFieldShape;
friend class CollisionDetectionSystem;
};
// Return the number of bytes used by the collision shape

View File

@ -36,8 +36,8 @@ using namespace std;
uint CollisionWorld::mNbWorlds = 0;
// Constructor
CollisionWorld::CollisionWorld(const WorldSettings& worldSettings, Logger* logger, Profiler* profiler)
: mConfig(worldSettings), mEntityManager(mMemoryManager.getPoolAllocator()),
CollisionWorld::CollisionWorld(const WorldSettings& worldSettings, Logger* logger, Profiler* profiler, MemoryAllocator* baseMemoryAllocator)
: mMemoryManager(baseMemoryAllocator), mConfig(worldSettings), mEntityManager(mMemoryManager.getPoolAllocator()),
mCollisionBodyComponents(mMemoryManager.getBaseAllocator()), mRigidBodyComponents(mMemoryManager.getBaseAllocator()),
mTransformComponents(mMemoryManager.getBaseAllocator()), mProxyShapesComponents(mMemoryManager.getBaseAllocator()),
mJointsComponents(mMemoryManager.getBaseAllocator()), mBallAndSocketJointsComponents(mMemoryManager.getBaseAllocator()),

View File

@ -143,23 +143,23 @@ class CollisionWorld {
// -------------------- Methods -------------------- //
/// Constructor
CollisionWorld(const WorldSettings& worldSettings = WorldSettings(), Logger* logger = nullptr,
Profiler* profiler = nullptr, MemoryAllocator* baseMemoryAllocator = nullptr);
/// Notify the world if a body is disabled (slepping or inactive) or not
void setBodyDisabled(Entity entity, bool isDisabled);
/// Notify the world whether a joint is disabled or not
void setJointDisabled(Entity jointEntity, bool isDisabled);
/// Destructor
virtual ~CollisionWorld();
public :
// -------------------- Methods -------------------- //
/// Constructor
CollisionWorld(const WorldSettings& worldSettings = WorldSettings(), Logger* logger = nullptr,
Profiler* profiler = nullptr);
/// Destructor
virtual ~CollisionWorld();
/// Deleted copy-constructor
CollisionWorld(const CollisionWorld& world) = delete;
@ -221,6 +221,7 @@ class CollisionWorld {
// -------------------- Friendship -------------------- //
friend class PhysicsCommon;
friend class CollisionDetectionSystem;
friend class CollisionBody;
friend class RigidBody;

View File

@ -520,7 +520,7 @@ void DynamicsWorld::createIslands() {
uint nbTotalManifolds = 0;
// For each dynamic component
// For each rigid body component
for (uint b=0; b < mRigidBodyComponents.getNbEnabledComponents(); b++) {
// If the body has already been added to an island, we go to the next body

View File

@ -100,6 +100,10 @@ class DynamicsWorld : public CollisionWorld {
// -------------------- Methods -------------------- //
/// Constructor
DynamicsWorld(const Vector3& mGravity, const WorldSettings& worldSettings = WorldSettings(),
Logger* logger = nullptr, Profiler* profiler = nullptr);
/// Solve the contacts and constraints
void solveContactsAndConstraints(decimal timeStep);
@ -118,17 +122,13 @@ class DynamicsWorld : public CollisionWorld {
/// Add the joint to the list of joints of the two bodies involved in the joint
void addJointToBodies(Entity body1, Entity body2, Entity joint);
/// Destructor
virtual ~DynamicsWorld() override;
public :
// -------------------- Methods -------------------- //
/// Constructor
DynamicsWorld(const Vector3& mGravity, const WorldSettings& worldSettings = WorldSettings(),
Logger* logger = nullptr, Profiler* profiler = nullptr);
/// Destructor
virtual ~DynamicsWorld() override;
/// Deleted copy-constructor
DynamicsWorld(const DynamicsWorld& world) = delete;
@ -212,6 +212,7 @@ class DynamicsWorld : public CollisionWorld {
// -------------------- Friendship -------------------- //
friend class PhysicsCommon;
friend class RigidBody;
friend class Joint;
friend class BallAndSocketJoint;

View File

@ -0,0 +1,340 @@
/********************************************************************************
* ReactPhysics3D physics library, http://www.reactphysics3d.com *
* Copyright (c) 2010-2019 Daniel Chappuis *
*********************************************************************************
* *
* This software is provided 'as-is', without any express or implied warranty. *
* In no event will the authors be held liable for any damages arising from the *
* use of this software. *
* *
* Permission is granted to anyone to use this software for any purpose, *
* including commercial applications, and to alter it and redistribute it *
* freely, subject to the following restrictions: *
* *
* 1. The origin of this software must not be misrepresented; you must not claim *
* that you wrote the original software. If you use this software in a *
* product, an acknowledgment in the product documentation would be *
* appreciated but is not required. *
* *
* 2. Altered source versions must be plainly marked as such, and must not be *
* misrepresented as being the original software. *
* *
* 3. This notice may not be removed or altered from any source distribution. *
* *
********************************************************************************/
// Libraries
#include "PhysicsCommon.h"
using namespace reactphysics3d;
/// Constructor
PhysicsCommon::PhysicsCommon(MemoryAllocator* baseMemoryAllocator)
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
: mMemoryManager(baseMemoryAllocator), mCollisionWorlds(mMemoryManager.getPoolAllocator()),
mDynamicsWorlds(mMemoryManager.getPoolAllocator()), mSphereShapes(mMemoryManager.getPoolAllocator()),
mBoxShapes(mMemoryManager.getPoolAllocator()), mCapsuleShapes(mMemoryManager.getPoolAllocator()),
mConvexMeshShapes(mMemoryManager.getPoolAllocator()), mConcaveMeshShapes(mMemoryManager.getPoolAllocator()),
mHeightFieldShapes(mMemoryManager.getPoolAllocator()), mPolyhedronMeshes(mMemoryManager.getPoolAllocator()),
mTriangleMeshes(mMemoryManager.getPoolAllocator()) {
}
// Destructor
PhysicsCommon::~PhysicsCommon() {
// Release the allocated memory
release();
}
// Destroy and release everything that has been allocated
void PhysicsCommon::release() {
// Destroy the collision worlds
for (auto it = mCollisionWorlds.begin(); it != mCollisionWorlds.end(); ++it) {
destroyCollisionWorld(*it);
}
// Destroy the dynamics worlds
for (auto it = mDynamicsWorlds.begin(); it != mDynamicsWorlds.end(); ++it) {
destroyDynamicsWorld(*it);
}
// Destroy the sphere shapes
for (auto it = mSphereShapes.begin(); it != mSphereShapes.end(); ++it) {
destroySphereShape(*it);
}
// Destroy the box shapes
for (auto it = mBoxShapes.begin(); it != mBoxShapes.end(); ++it) {
destroyBoxShape(*it);
}
// Destroy the capsule shapes
for (auto it = mCapsuleShapes.begin(); it != mCapsuleShapes.end(); ++it) {
destroyCapsuleShape(*it);
}
// Destroy the convex mesh shapes
for (auto it = mConvexMeshShapes.begin(); it != mConvexMeshShapes.end(); ++it) {
destroyConvexMeshShape(*it);
}
// Destroy the heigh-field shapes
for (auto it = mHeightFieldShapes.begin(); it != mHeightFieldShapes.end(); ++it) {
destroyHeightFieldShape(*it);
}
// Destroy the concave mesh shapes
for (auto it = mConcaveMeshShapes.begin(); it != mConcaveMeshShapes.end(); ++it) {
destroyConcaveMeshShape(*it);
}
// Destroy the polyhedron mesh
for (auto it = mPolyhedronMeshes.begin(); it != mPolyhedronMeshes.end(); ++it) {
destroyPolyhedronMesh(*it);
}
// Destroy the triangle mesh
for (auto it = mTriangleMeshes.begin(); it != mTriangleMeshes.end(); ++it) {
destroyTriangleMesh(*it);
}
}
// Create and return an instance of CollisionWorld
CollisionWorld* PhysicsCommon::createCollisionWorld(const WorldSettings& worldSettings, Logger* logger, Profiler* profiler) {
// TODO : Allocate in heap allocator here instead of pool
CollisionWorld* world = new(mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(CollisionWorld))) CollisionWorld(worldSettings, logger, profiler);
mCollisionWorlds.add(world);
return world;
}
// Destroy an instance of CollisionWorld
void PhysicsCommon::destroyCollisionWorld(CollisionWorld* world) {
// Call the destructor of the world
world->~CollisionWorld();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, world, sizeof(CollisionWorld));
mCollisionWorlds.remove(world);
}
// Create and return an instance of DynamicsWorld
DynamicsWorld* PhysicsCommon::createDynamicsWorld(const Vector3& gravity, const WorldSettings& worldSettings,
Logger* logger, Profiler* profiler) {
// TODO : Allocate in heap allocator here instead of pool
DynamicsWorld* world = new(mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(DynamicsWorld))) DynamicsWorld(gravity, worldSettings, logger, profiler);
mDynamicsWorlds.add(world);
return world;
}
// Destroy an instance of DynamicsWorld
DynamicsWorld* PhysicsCommon::destroyDynamicsWorld(DynamicsWorld* world) {
// Call the destructor of the world
world->~DynamicsWorld();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, world, sizeof(DynamicsWorld));
mDynamicsWorlds.remove(world);
}
// Create and return a sphere collision shape
SphereShape* PhysicsCommon::createSphereShape(const decimal radius) {
SphereShape* shape = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(SphereShape))) SphereShape(radius);
mSphereShapes.add(shape);
return shape;
}
// Destroy a sphere collision shape
void PhysicsCommon::destroySphereShape(SphereShape* sphereShape) {
// Call the destructor of the shape
sphereShape->~SphereShape();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, sphereShape, sizeof(SphereShape));
mSphereShapes.remove(sphereShape);
}
// Create and return a box collision shape
BoxShape* PhysicsCommon::createBoxShape(const Vector3& extent) {
// TODO : Pass heap allocator here in parameter
BoxShape* shape = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(BoxShape))) BoxShape(extent, mMemoryManager.getPoolAllocator());
mBoxShapes.add(shape);
return shape;
}
// Destroy a box collision shape
void PhysicsCommon::destroyBoxShape(BoxShape* boxShape) {
// Call the destructor of the shape
boxShape->~BoxShape();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, boxShape, sizeof(BoxShape));
mBoxShapes.remove(boxShape);
}
// Create and return a capsule shape
CapsuleShape* PhysicsCommon::createCapsuleShape(decimal radius, decimal height) {
CapsuleShape* shape = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(CapsuleShape))) CapsuleShape(radius, height);
mCapsuleShapes.add(shape);
return shape;
}
// Destroy a capsule collision shape
void PhysicsCommon::destroyCapsuleShape(CapsuleShape* capsuleShape) {
// Call the destructor of the shape
capsuleShape->~CapsuleShape();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, capsuleShape, sizeof(CapsuleShape));
mCapsuleShapes.remove(capsuleShape);
}
// Create and return a convex mesh shape
ConvexMeshShape* PhysicsCommon::createConvexMeshShape(PolyhedronMesh* polyhedronMesh, const Vector3& scaling) {
ConvexMeshShape* shape = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(ConvexMeshShape))) ConvexMeshShape(polyhedronMesh, scaling);
mConvexMeshShapes.add(shape);
return shape;
}
// Destroy a convex mesh shape
void PhysicsCommon::destroyConvexMeshShape(ConvexMeshShape* convexMeshShape) {
// Call the destructor of the shape
convexMeshShape->~ConvexMeshShape();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, convexMeshShape, sizeof(ConvexMeshShape));
mConvexMeshShapes.remove(convexMeshShape);
}
// Create and return a height-field shape
HeightFieldShape* PhysicsCommon::createHeightFieldShape(int nbGridColumns, int nbGridRows, decimal minHeight, decimal maxHeight,
const void* heightFieldData, HeightFieldShape::HeightDataType dataType,
int upAxis, decimal integerHeightScale, const Vector3& scaling) {
HeightFieldShape* shape = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(HeightFieldShape))) HeightFieldShape(nbGridColumns, nbGridRows, minHeight, maxHeight,
heightFieldData, dataType, upAxis, integerHeightScale, scaling);
mHeightFieldShapes.add(shape);
return shape;
}
// Destroy a height-field shape
void PhysicsCommon::destroyHeightFieldShape(HeightFieldShape* heightFieldShape) {
// Call the destructor of the shape
heightFieldShape->~HeightFieldShape();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, heightFieldShape, sizeof(HeightFieldShape));
mHeightFieldShapes.remove(heightFieldShape);
}
// Create and return a concave mesh shape
ConcaveMeshShape* PhysicsCommon::createConcaveMeshShape(TriangleMesh* triangleMesh, const Vector3& scaling) {
// TODO : Pass heap allocator here in parameter
ConcaveMeshShape* shape = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(ConcaveMeshShape))) ConcaveMeshShape(triangleMesh, mMemoryManager.getPoolAllocator(), scaling);
mConcaveMeshShapes.add(shape);
return shape;
}
// Destroy a concave mesh shape
void PhysicsCommon::destroyConcaveMeshShape(ConcaveMeshShape* concaveMeshShape) {
// Call the destructor of the shape
concaveMeshShape->~ConcaveMeshShape();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, concaveMeshShape, sizeof(ConcaveMeshShape));
mConcaveMeshShapes.remove(concaveMeshShape);
}
// Create a polyhedron mesh
PolyhedronMesh* PhysicsCommon::createPolyhedronMesh(PolygonVertexArray* polygonVertexArray) {
// TODO : Pass heap allocator here in parameter
PolyhedronMesh* mesh = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(PolyhedronMesh))) PolyhedronMesh(polygonVertexArray, mMemoryManager.getPoolAllocator());
mPolyhedronMeshes.add(mesh);
return mesh;
}
// Destroy a polyhedron mesh
void PhysicsCommon::destroyPolyhedronMesh(PolyhedronMesh* polyhedronMesh) {
// Call the destructor of the shape
polyhedronMesh->~PolyhedronMesh();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, polyhedronMesh, sizeof(PolyhedronMesh));
mPolyhedronMeshes.remove(polyhedronMesh);
}
// Create a triangle mesh
TriangleMesh* PhysicsCommon::createTriangleMesh() {
// TODO : Pass heap allocator here in parameter
TriangleMesh* mesh = new (mMemoryManager.allocate(MemoryManager::AllocationType::Pool, sizeof(TriangleMesh))) TriangleMesh(mMemoryManager.getPoolAllocator());
mTriangleMeshes.add(mesh);
return mesh;
}
// Destroy a triangle mesh
void PhysicsCommon::destroyTriangleMesh(TriangleMesh* triangleMesh) {
// Call the destructor of the shape
triangleMesh->~TriangleMesh();
// Release allocated memory
// TODO : Use Heap allocator for internal Sets<> here instead of Pool allocator
mMemoryManager.release(MemoryManager::AllocationType::Pool, triangleMesh, sizeof(TriangleMesh));
mTriangleMeshes.remove(triangleMesh);
}

175
src/engine/PhysicsCommon.h Normal file
View File

@ -0,0 +1,175 @@
/********************************************************************************
* ReactPhysics3D physics library, http://www.reactphysics3d.com *
* Copyright (c) 2010-2019 Daniel Chappuis *
*********************************************************************************
* *
* This software is provided 'as-is', without any express or implied warranty. *
* In no event will the authors be held liable for any damages arising from the *
* use of this software. *
* *
* Permission is granted to anyone to use this software for any purpose, *
* including commercial applications, and to alter it and redistribute it *
* freely, subject to the following restrictions: *
* *
* 1. The origin of this software must not be misrepresented; you must not claim *
* that you wrote the original software. If you use this software in a *
* product, an acknowledgment in the product documentation would be *
* appreciated but is not required. *
* *
* 2. Altered source versions must be plainly marked as such, and must not be *
* misrepresented as being the original software. *
* *
* 3. This notice may not be removed or altered from any source distribution. *
* *
********************************************************************************/
#ifndef REACTPHYSICS3D_PHYSICS_COMMON_H
#define REACTPHYSICS3D_PHYSICS_COMMON_H
// Libraries
#include "memory/MemoryManager.h"
#include "engine/CollisionWorld.h"
#include "engine/DynamicsWorld.h"
#include "collision/shapes/SphereShape.h"
#include "collision/shapes/BoxShape.h"
#include "collision/shapes/CapsuleShape.h"
#include "collision/shapes/HeightFieldShape.h"
#include "collision/shapes/ConvexMeshShape.h"
#include "collision/shapes/ConcaveMeshShape.h"
#include "collision/TriangleMesh.h"
/// ReactPhysics3D namespace
namespace reactphysics3d {
// Class PhysicsCommon
/**
* This class is a singleton that needs to be instanciated once at the beginning.
* Then this class is used by the user as a factory to create the physics world and
* other objects.
*/
class PhysicsCommon {
private :
// -------------------- Attributes -------------------- //
/// Memory manager
MemoryManager mMemoryManager;
/// Set of collision worlds
Set<CollisionWorld*> mCollisionWorlds;
/// Set of dynamics worlds
Set<DynamicsWorld*> mDynamicsWorlds;
/// Set of sphere shapes
Set<SphereShape*> mSphereShapes;
/// Set of box shapes
Set<BoxShape*> mBoxShapes;
/// Set of capsule shapes
Set<CapsuleShape*> mCapsuleShapes;
/// Set of convex mesh shapes
Set<ConvexMeshShape*> mConvexMeshShapes;
/// Set of concave mesh shapes
Set<ConcaveMeshShape*> mConcaveMeshShapes;
/// Set of height field shapes
Set<HeightFieldShape*> mHeightFieldShapes;
/// Set of polyhedron meshes
Set<PolyhedronMesh*> mPolyhedronMeshes;
/// Set of triangle meshes
Set<TriangleMesh*> mTriangleMeshes;
// -------------------- Methods -------------------- //
/// Destroy and release everything that has been allocated
void release();
public :
// -------------------- Methods -------------------- //
/// Constructor
/**
* @param baseMemoryAllocator Pointer to a user custom memory allocator
*/
PhysicsCommon(MemoryAllocator* baseMemoryAllocator = nullptr);
/// Destructor
~PhysicsCommon();
/// Create and return an instance of CollisionWorld
CollisionWorld* createCollisionWorld(const WorldSettings& worldSettings = WorldSettings(), Logger* logger = nullptr,
Profiler* profiler = nullptr);
/// Destroy an instance of CollisionWorld
void destroyCollisionWorld(CollisionWorld* world);
/// Create and return an instance of DynamicsWorld
DynamicsWorld* createDynamicsWorld(const Vector3& gravity, const WorldSettings& worldSettings = WorldSettings(),
Logger* logger = nullptr, Profiler* profiler = nullptr);
/// Destroy an instance of DynamicsWorld
DynamicsWorld* destroyDynamicsWorld(DynamicsWorld* world);
/// Create and return a sphere collision shape
SphereShape* createSphereShape(const decimal radius);
/// Destroy a sphere collision shape
void destroySphereShape(SphereShape* sphereShape);
/// Create and return a box collision shape
BoxShape* createBoxShape(const Vector3& extent);
/// Destroy a box collision shape
void destroyBoxShape(BoxShape* boxShape);
/// Create and return a capsule shape
CapsuleShape* createCapsuleShape(decimal radius, decimal height);
/// Destroy a capsule collision shape
void destroyCapsuleShape(CapsuleShape* capsuleShape);
/// Create and return a convex mesh shape
ConvexMeshShape* createConvexMeshShape(PolyhedronMesh* polyhedronMesh, const Vector3& scaling = Vector3(1,1,1));
/// Destroy a convex mesh shape
void destroyConvexMeshShape(ConvexMeshShape* convexMeshShape);
/// Create and return a height-field shape
HeightFieldShape* createHeightFieldShape(int nbGridColumns, int nbGridRows, decimal minHeight, decimal maxHeight,
const void* heightFieldData, HeightFieldShape::HeightDataType dataType,
int upAxis = 1, decimal integerHeightScale = 1.0f,
const Vector3& scaling = Vector3(1,1,1));
/// Destroy a height-field shape
void destroyHeightFieldShape(HeightFieldShape* heightFieldShape);
/// Create and return a concave mesh shape
ConcaveMeshShape* createConcaveMeshShape(TriangleMesh* triangleMesh, const Vector3& scaling = Vector3(1, 1, 1));
/// Destroy a concave mesh shape
void destroyConcaveMeshShape(ConcaveMeshShape* concaveMeshShape);
/// Create a polyhedron mesh
PolyhedronMesh* createPolyhedronMesh(PolygonVertexArray* polygonVertexArray);
/// Destroy a polyhedron mesh
void destroyPolyhedronMesh(PolyhedronMesh* polyhedronMesh);
/// Create a triangle mesh
TriangleMesh* createTriangleMesh();
/// Destroy a triangle mesh
void destroyTriangleMesh(TriangleMesh* triangleMesh);
};
}
#endif

View File

@ -24,11 +24,14 @@
********************************************************************************/
// Libraries
#include "MemoryManager.h"
#include "memory/MemoryManager.h"
using namespace reactphysics3d;
// Static variables
DefaultAllocator MemoryManager::mDefaultAllocator;
MemoryAllocator* MemoryManager::mBaseAllocator = &mDefaultAllocator;
// Constructor
MemoryManager::MemoryManager(MemoryAllocator* baseAllocator) :
mBaseAllocator(baseAllocator == nullptr ? &mDefaultAllocator : baseAllocator),
mPoolAllocator(baseAllocator == nullptr ? mDefaultAllocator : *baseAllocator),
mSingleFrameAllocator(baseAllocator == nullptr ? mDefaultAllocator : *baseAllocator) {
}

View File

@ -47,10 +47,10 @@ class MemoryManager {
private:
/// Default malloc/free memory allocator
static DefaultAllocator mDefaultAllocator;
DefaultAllocator mDefaultAllocator;
/// Pointer to the base memory allocator to use
static MemoryAllocator* mBaseAllocator;
MemoryAllocator* mBaseAllocator;
/// Memory pool allocator
PoolAllocator mPoolAllocator;
@ -68,7 +68,7 @@ class MemoryManager {
};
/// Constructor
MemoryManager() = default;
MemoryManager(MemoryAllocator* baseAllocator);
/// Destructor
~MemoryManager() = default;
@ -86,10 +86,10 @@ class MemoryManager {
SingleFrameAllocator& getSingleFrameAllocator();
/// Return the base memory allocator
static MemoryAllocator& getBaseAllocator();
MemoryAllocator& getBaseAllocator();
/// Set the base memory allocator
static void setBaseAllocator(MemoryAllocator* memoryAllocator);
void setBaseAllocator(MemoryAllocator* memoryAllocator);
/// Reset the single frame allocator
void resetFrameAllocator();

View File

@ -37,13 +37,13 @@ size_t PoolAllocator::mUnitSizes[NB_HEAPS];
int PoolAllocator::mMapSizeToHeapIndex[MAX_UNIT_SIZE + 1];
// Constructor
PoolAllocator::PoolAllocator() {
PoolAllocator::PoolAllocator(MemoryAllocator& baseAllocator) : mBaseAllocator(baseAllocator) {
// Allocate some memory to manage the blocks
mNbAllocatedMemoryBlocks = 64;
mNbCurrentMemoryBlocks = 0;
const size_t sizeToAllocate = mNbAllocatedMemoryBlocks * sizeof(MemoryBlock);
mMemoryBlocks = static_cast<MemoryBlock*>(MemoryManager::getBaseAllocator().allocate(sizeToAllocate));
mMemoryBlocks = static_cast<MemoryBlock*>(baseAllocator.allocate(sizeToAllocate));
memset(mMemoryBlocks, 0, sizeToAllocate);
memset(mFreeMemoryUnits, 0, sizeof(mFreeMemoryUnits));
@ -83,10 +83,10 @@ PoolAllocator::~PoolAllocator() {
// Release the memory allocated for each block
for (uint i=0; i<mNbCurrentMemoryBlocks; i++) {
MemoryManager::getBaseAllocator().release(mMemoryBlocks[i].memoryUnits, BLOCK_SIZE);
mBaseAllocator.release(mMemoryBlocks[i].memoryUnits, BLOCK_SIZE);
}
MemoryManager::getBaseAllocator().release(mMemoryBlocks, mNbAllocatedMemoryBlocks * sizeof(MemoryBlock));
mBaseAllocator.release(mMemoryBlocks, mNbAllocatedMemoryBlocks * sizeof(MemoryBlock));
#ifndef NDEBUG
// Check that the allocate() and release() methods have been called the same
@ -113,7 +113,7 @@ void* PoolAllocator::allocate(size_t size) {
if (size > MAX_UNIT_SIZE) {
// Allocate memory using default allocation
return MemoryManager::getBaseAllocator().allocate(size);
return mBaseAllocator.allocate(size);
}
// Get the index of the heap that will take care of the allocation request
@ -136,16 +136,16 @@ void* PoolAllocator::allocate(size_t size) {
// Allocate more memory to contain the blocks
MemoryBlock* currentMemoryBlocks = mMemoryBlocks;
mNbAllocatedMemoryBlocks += 64;
mMemoryBlocks = static_cast<MemoryBlock*>(MemoryManager::getBaseAllocator().allocate(mNbAllocatedMemoryBlocks * sizeof(MemoryBlock)));
mMemoryBlocks = static_cast<MemoryBlock*>(mBaseAllocator.allocate(mNbAllocatedMemoryBlocks * sizeof(MemoryBlock)));
memcpy(mMemoryBlocks, currentMemoryBlocks, mNbCurrentMemoryBlocks * sizeof(MemoryBlock));
memset(mMemoryBlocks + mNbCurrentMemoryBlocks, 0, 64 * sizeof(MemoryBlock));
MemoryManager::getBaseAllocator().release(currentMemoryBlocks, mNbCurrentMemoryBlocks * sizeof(MemoryBlock));
mBaseAllocator.release(currentMemoryBlocks, mNbCurrentMemoryBlocks * sizeof(MemoryBlock));
}
// Allocate a new memory blocks for the corresponding heap and divide it in many
// memory units
MemoryBlock* newBlock = mMemoryBlocks + mNbCurrentMemoryBlocks;
newBlock->memoryUnits = static_cast<MemoryUnit*>(MemoryManager::getBaseAllocator().allocate(BLOCK_SIZE));
newBlock->memoryUnits = static_cast<MemoryUnit*>(mBaseAllocator.allocate(BLOCK_SIZE));
assert(newBlock->memoryUnits != nullptr);
size_t unitSize = mUnitSizes[indexHeap];
uint nbUnits = BLOCK_SIZE / unitSize;
@ -188,7 +188,7 @@ void PoolAllocator::release(void* pointer, size_t size) {
if (size > MAX_UNIT_SIZE) {
// Release the memory using the default deallocation
MemoryManager::getBaseAllocator().release(pointer, size);
mBaseAllocator.release(pointer, size);
return;
}

View File

@ -101,6 +101,9 @@ class PoolAllocator : public MemoryAllocator {
/// True if the mMapSizeToHeapIndex array has already been initialized
static bool isMapSizeToHeadIndexInitialized;
/// Base memory allocator
MemoryAllocator& mBaseAllocator;
/// Pointers to the first free memory unit for each heap
MemoryUnit* mFreeMemoryUnits[NB_HEAPS];
@ -126,7 +129,7 @@ class PoolAllocator : public MemoryAllocator {
// -------------------- Methods -------------------- //
/// Constructor
PoolAllocator();
PoolAllocator(MemoryAllocator& baseAllocator);
/// Destructor
virtual ~PoolAllocator() override;

View File

@ -32,12 +32,12 @@
using namespace reactphysics3d;
// Constructor
SingleFrameAllocator::SingleFrameAllocator()
: mTotalSizeBytes(INIT_SINGLE_FRAME_ALLOCATOR_NB_BYTES),
mCurrentOffset(0), mNbFramesTooMuchAllocated(0), mNeedToAllocatedMore(false) {
SingleFrameAllocator::SingleFrameAllocator(MemoryAllocator& baseAllocator) : mBaseAllocator(baseAllocator),
mTotalSizeBytes(INIT_SINGLE_FRAME_ALLOCATOR_NB_BYTES),
mCurrentOffset(0), mNbFramesTooMuchAllocated(0), mNeedToAllocatedMore(false) {
// Allocate a whole block of memory at the beginning
mMemoryBufferStart = static_cast<char*>(MemoryManager::getBaseAllocator().allocate(mTotalSizeBytes));
mMemoryBufferStart = static_cast<char*>(mBaseAllocator.allocate(mTotalSizeBytes));
assert(mMemoryBufferStart != nullptr);
}
@ -45,7 +45,7 @@ SingleFrameAllocator::SingleFrameAllocator()
SingleFrameAllocator::~SingleFrameAllocator() {
// Release the memory allocated at the beginning
MemoryManager::getBaseAllocator().release(mMemoryBufferStart, mTotalSizeBytes);
mBaseAllocator.release(mMemoryBufferStart, mTotalSizeBytes);
}
@ -60,7 +60,7 @@ void* SingleFrameAllocator::allocate(size_t size) {
mNeedToAllocatedMore = true;
// Return default memory allocation
return MemoryManager::getBaseAllocator().allocate(size);
return mBaseAllocator.allocate(size);
}
// Next available memory location
@ -81,7 +81,7 @@ void SingleFrameAllocator::release(void* pointer, size_t size) {
if (p < mMemoryBufferStart || p > mMemoryBufferStart + mTotalSizeBytes) {
// Use default deallocation
MemoryManager::getBaseAllocator().release(pointer, size);
mBaseAllocator.release(pointer, size);
}
}
@ -96,14 +96,14 @@ void SingleFrameAllocator::reset() {
if (mNbFramesTooMuchAllocated > NB_FRAMES_UNTIL_SHRINK) {
// Release the memory allocated at the beginning
MemoryManager::getBaseAllocator().release(mMemoryBufferStart, mTotalSizeBytes);
mBaseAllocator.release(mMemoryBufferStart, mTotalSizeBytes);
// Divide the total memory to allocate by two
mTotalSizeBytes /= 2;
if (mTotalSizeBytes == 0) mTotalSizeBytes = 1;
// Allocate a whole block of memory at the beginning
mMemoryBufferStart = static_cast<char*>(MemoryManager::getBaseAllocator().allocate(mTotalSizeBytes));
mMemoryBufferStart = static_cast<char*>(mBaseAllocator.allocate(mTotalSizeBytes));
assert(mMemoryBufferStart != nullptr);
mNbFramesTooMuchAllocated = 0;
@ -117,13 +117,13 @@ void SingleFrameAllocator::reset() {
if (mNeedToAllocatedMore) {
// Release the memory allocated at the beginning
MemoryManager::getBaseAllocator().release(mMemoryBufferStart, mTotalSizeBytes);
mBaseAllocator.release(mMemoryBufferStart, mTotalSizeBytes);
// Multiply the total memory to allocate by two
mTotalSizeBytes *= 2;
// Allocate a whole block of memory at the beginning
mMemoryBufferStart = static_cast<char*>(MemoryManager::getBaseAllocator().allocate(mTotalSizeBytes));
mMemoryBufferStart = static_cast<char*>(mBaseAllocator.allocate(mTotalSizeBytes));
assert(mMemoryBufferStart != nullptr);
mNeedToAllocatedMore = false;

View File

@ -53,6 +53,9 @@ class SingleFrameAllocator : public MemoryAllocator {
// -------------------- Attributes -------------------- //
/// Reference to the base memory allocator
MemoryAllocator& mBaseAllocator;
/// Total size (in bytes) of memory of the allocator
size_t mTotalSizeBytes;
@ -74,7 +77,7 @@ class SingleFrameAllocator : public MemoryAllocator {
// -------------------- Methods -------------------- //
/// Constructor
SingleFrameAllocator();
SingleFrameAllocator(MemoryAllocator& baseAllocator);
/// Destructor
virtual ~SingleFrameAllocator() override;

View File

@ -39,6 +39,7 @@
#include "mathematics/mathematics.h"
#include "body/CollisionBody.h"
#include "body/RigidBody.h"
#include "engine/PhysicsCommon.h"
#include "engine/DynamicsWorld.h"
#include "engine/CollisionWorld.h"
#include "engine/Material.h"

View File

@ -155,11 +155,15 @@ void ProfileNodeIterator::enterParent() {
}
// Constructor
Profiler::Profiler() :mRootNode("Root", nullptr), mDestinations(MemoryManager::getBaseAllocator()) {
Profiler::Profiler() :mRootNode("Root", nullptr) {
mCurrentNode = &mRootNode;
mNbDestinations = 0;
mNbAllocatedDestinations = 0;
mProfilingStartTime = Timer::getCurrentSystemTime() * 1000.0L;
mFrameCounter = 0;
allocatedDestinations(1);
}
// Destructor
@ -174,11 +178,11 @@ Profiler::~Profiler() {
void Profiler::removeAllDestinations() {
// Delete all the destinations
for (uint i=0; i<mDestinations.size(); i++) {
for (uint i=0; i<mNbDestinations; i++) {
delete mDestinations[i];
}
mDestinations.clear();
mNbDestinations = 0;
}
// Method called when we want to start profiling a block of code.
@ -217,12 +221,12 @@ void Profiler::reset() {
void Profiler::printReport() {
// For each destination
for (auto it = mDestinations.begin(); it != mDestinations.end(); ++it) {
for (uint i=0; i < mNbDestinations; i++) {
ProfileNodeIterator* iterator = Profiler::getIterator();
// Recursively print the report of each node of the profiler tree
printRecursiveNodeReport(iterator, 0, (*it)->getOutputStream());
printRecursiveNodeReport(iterator, 0, mDestinations[i]->getOutputStream());
// Destroy the iterator
destroyIterator(iterator);
@ -232,15 +236,39 @@ void Profiler::printReport() {
// Add a file destination to the profiler
void Profiler::addFileDestination(const std::string& filePath, Format format) {
if (mNbAllocatedDestinations == mNbDestinations) {
allocatedDestinations(mNbAllocatedDestinations * 2);
}
FileDestination* destination = new FileDestination(filePath, format);
mDestinations.add(destination);
mDestinations[mNbDestinations] = destination;
mNbDestinations++;
}
// Allocate memory for the destinations
void Profiler::allocatedDestinations(uint nbDestinationsToAllocate) {
if (mNbAllocatedDestinations >= nbDestinationsToAllocate) return;
Destination** newArray = static_cast<Destination**>(std::malloc(nbDestinationsToAllocate * sizeof(Destination*)));
std::memcpy(newArray, mDestinations, mNbAllocatedDestinations * sizeof(Destination*));
mDestinations = newArray;
mNbAllocatedDestinations = nbDestinationsToAllocate;
}
// Add a stream destination to the profiler
void Profiler::addStreamDestination(std::ostream& outputStream, Format format) {
if (mNbAllocatedDestinations == mNbDestinations) {
allocatedDestinations(mNbAllocatedDestinations * 2);
}
StreamDestination* destination = new StreamDestination(outputStream, format);
mDestinations.add(destination);
mDestinations[mNbDestinations] = destination;
mNbDestinations++;
}
// Recursively print the report of a given node of the profiler tree

View File

@ -291,8 +291,14 @@ class Profiler {
/// Starting profiling time
long double mProfilingStartTime;
/// All the output destinations
List<Destination*> mDestinations;
/// Number of allocated destinations
uint mNbAllocatedDestinations;
/// Number of destinations
uint mNbDestinations;
/// Array with all the output destinations
Destination** mDestinations;
/// Recursively print the report of a given node of the profiler tree
void printRecursiveNodeReport(ProfileNodeIterator* iterator, int spacing,
@ -336,6 +342,9 @@ class Profiler {
/// Return an iterator over the profiler tree starting at the root
ProfileNodeIterator* getIterator();
// Allocate memory for the destinations
void allocatedDestinations(uint nbDestinationsToAllocate);
// Add a file destination to the profiler
void addFileDestination(const std::string& filePath, Format format);

View File

@ -265,6 +265,8 @@ class TestCollisionWorld : public Test {
// ---------- Atributes ---------- //
PhysicsCommon mPhysicsCommon;
// Physics world
CollisionWorld* mWorld;
@ -330,37 +332,37 @@ class TestCollisionWorld : public Test {
TestCollisionWorld(const std::string& name) : Test(name) {
// Create the collision world
mWorld = new CollisionWorld();
mWorld = mPhysicsCommon.createCollisionWorld();
// ---------- Boxes ---------- //
Transform boxTransform1(Vector3(-20, 20, 0), Quaternion::identity());
mBoxBody1 = mWorld->createCollisionBody(boxTransform1);
mBoxShape1 = new BoxShape(Vector3(3, 3, 3));
mBoxShape1 = mPhysicsCommon.createBoxShape(Vector3(3, 3, 3));
mBoxProxyShape1 = mBoxBody1->addCollisionShape(mBoxShape1, Transform::identity());
Transform boxTransform2(Vector3(-10, 20, 0), Quaternion::identity());
mBoxBody2 = mWorld->createCollisionBody(boxTransform2);
mBoxShape2 = new BoxShape(Vector3(4, 2, 8));
mBoxShape2 = mPhysicsCommon.createBoxShape(Vector3(4, 2, 8));
mBoxProxyShape2 = mBoxBody2->addCollisionShape(mBoxShape2, Transform::identity());
// ---------- Spheres ---------- //
mSphereShape1 = new SphereShape(3.0);
mSphereShape1 = mPhysicsCommon.createSphereShape(3.0);
Transform sphereTransform1(Vector3(10, 20, 0), Quaternion::identity());
mSphereBody1 = mWorld->createCollisionBody(sphereTransform1);
mSphereProxyShape1 = mSphereBody1->addCollisionShape(mSphereShape1, Transform::identity());
mSphereShape2 = new SphereShape(5.0);
mSphereShape2 = mPhysicsCommon.createSphereShape(5.0);
Transform sphereTransform2(Vector3(20, 20, 0), Quaternion::identity());
mSphereBody2 = mWorld->createCollisionBody(sphereTransform2);
mSphereProxyShape2 = mSphereBody2->addCollisionShape(mSphereShape2, Transform::identity());
// ---------- Capsules ---------- //
mCapsuleShape1 = new CapsuleShape(2, 6);
mCapsuleShape1 = mPhysicsCommon.createCapsuleShape(2, 6);
Transform capsuleTransform1(Vector3(-10, 0, 0), Quaternion::identity());
mCapsuleBody1 = mWorld->createCollisionBody(capsuleTransform1);
mCapsuleProxyShape1 = mCapsuleBody1->addCollisionShape(mCapsuleShape1, Transform::identity());
mCapsuleShape2 = new CapsuleShape(3, 4);
mCapsuleShape2 = mPhysicsCommon.createCapsuleShape(3, 4);
Transform capsuleTransform2(Vector3(-20, 0, 0), Quaternion::identity());
mCapsuleBody2 = mWorld->createCollisionBody(capsuleTransform2);
mCapsuleProxyShape2 = mCapsuleBody2->addCollisionShape(mCapsuleShape2, Transform::identity());
@ -393,8 +395,8 @@ class TestCollisionWorld : public Test {
&(mConvexMeshCubeIndices[0]), sizeof(int), 6, mConvexMeshPolygonFaces,
rp3d::PolygonVertexArray::VertexDataType::VERTEX_FLOAT_TYPE,
rp3d::PolygonVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
mConvexMesh1PolyhedronMesh = new rp3d::PolyhedronMesh(mConvexMesh1PolygonVertexArray);
mConvexMeshShape1 = new rp3d::ConvexMeshShape(mConvexMesh1PolyhedronMesh);
mConvexMesh1PolyhedronMesh = mPhysicsCommon.createPolyhedronMesh(mConvexMesh1PolygonVertexArray);
mConvexMeshShape1 = mPhysicsCommon.createConvexMeshShape(mConvexMesh1PolyhedronMesh);
Transform convexMeshTransform1(Vector3(10, 0, 0), Quaternion::identity());
mConvexMeshBody1 = mWorld->createCollisionBody(convexMeshTransform1);
mConvexMeshProxyShape1 = mConvexMeshBody1->addCollisionShape(mConvexMeshShape1, Transform::identity());
@ -412,8 +414,8 @@ class TestCollisionWorld : public Test {
&(mConvexMeshCubeIndices[0]), sizeof(int), 6, mConvexMeshPolygonFaces,
rp3d::PolygonVertexArray::VertexDataType::VERTEX_FLOAT_TYPE,
rp3d::PolygonVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
mConvexMesh2PolyhedronMesh = new rp3d::PolyhedronMesh(mConvexMesh2PolygonVertexArray);
mConvexMeshShape2 = new rp3d::ConvexMeshShape(mConvexMesh2PolyhedronMesh);
mConvexMesh2PolyhedronMesh = mPhysicsCommon.createPolyhedronMesh(mConvexMesh2PolygonVertexArray);
mConvexMeshShape2 = mPhysicsCommon.createConvexMeshShape(mConvexMesh2PolyhedronMesh);
Transform convexMeshTransform2(Vector3(20, 0, 0), Quaternion::identity());
mConvexMeshBody2 = mWorld->createCollisionBody(convexMeshTransform2);
mConvexMeshProxyShape2 = mConvexMeshBody2->addCollisionShape(mConvexMeshShape2, Transform::identity());
@ -449,9 +451,9 @@ class TestCollisionWorld : public Test {
// Add the triangle vertex array of the subpart to the triangle mesh
Transform concaveMeshTransform(Vector3(0, -20, 0), Quaternion::identity());
mConcaveTriangleMesh = new TriangleMesh();
mConcaveTriangleMesh = mPhysicsCommon.createTriangleMesh();
mConcaveTriangleMesh->addSubpart(mConcaveMeshTriangleVertexArray);
mConcaveMeshShape = new rp3d::ConcaveMeshShape(mConcaveTriangleMesh);
mConcaveMeshShape = mPhysicsCommon.createConcaveMeshShape(mConcaveTriangleMesh);
mConcaveMeshBody = mWorld->createCollisionBody(concaveMeshTransform);
mConcaveMeshProxyShape = mConcaveMeshBody->addCollisionShape(mConcaveMeshShape, rp3d::Transform::identity());
}
@ -459,28 +461,32 @@ class TestCollisionWorld : public Test {
/// Destructor
virtual ~TestCollisionWorld() {
delete mBoxShape1;
delete mBoxShape2;
mPhysicsCommon.destroyBoxShape(mBoxShape1);
mPhysicsCommon.destroyBoxShape(mBoxShape2);
delete mSphereShape1;
delete mSphereShape2;
mPhysicsCommon.destroySphereShape(mSphereShape1);
mPhysicsCommon.destroySphereShape(mSphereShape2);
delete mCapsuleShape1;
delete mCapsuleShape2;
mPhysicsCommon.destroyCapsuleShape(mCapsuleShape1);
mPhysicsCommon.destroyCapsuleShape(mCapsuleShape2);
mPhysicsCommon.destroyConvexMeshShape(mConvexMeshShape1);
mPhysicsCommon.destroyConvexMeshShape(mConvexMeshShape2);
mPhysicsCommon.destroyPolyhedronMesh(mConvexMesh1PolyhedronMesh);
mPhysicsCommon.destroyPolyhedronMesh(mConvexMesh2PolyhedronMesh);
delete mConvexMeshShape1;
delete mConvexMeshShape2;
delete mConvexMesh1PolyhedronMesh;
delete mConvexMesh2PolyhedronMesh;
delete mConvexMesh1PolygonVertexArray;
delete mConvexMesh2PolygonVertexArray;
delete[] mConvexMeshPolygonFaces;
delete mConcaveMeshShape;
delete mConcaveTriangleMesh;
mPhysicsCommon.destroyConcaveMeshShape(mConcaveMeshShape);
mPhysicsCommon.destroyTriangleMesh(mConcaveTriangleMesh);
delete mConcaveMeshTriangleVertexArray;
delete mWorld;
mPhysicsCommon.destroyCollisionWorld(mWorld);
}
/// Run the tests

View File

@ -30,6 +30,7 @@
#include "Test.h"
#include "collision/broadphase/DynamicAABBTree.h"
#include "memory/MemoryManager.h"
#include "engine/PhysicsCommon.h"
#include "utils/Profiler.h"
#include <vector>
@ -57,6 +58,28 @@ class DynamicTreeRaycastCallback : public DynamicAABBTreeRaycastCallback {
}
};
class DefaultTestTreeAllocator : public MemoryAllocator {
public:
/// Destructor
virtual ~DefaultTestTreeAllocator() override = default;
/// Assignment operator
DefaultTestTreeAllocator& operator=(DefaultTestTreeAllocator& allocator) = default;
/// Allocate memory of a given size (in bytes) and return a pointer to the
/// allocated memory.
virtual void* allocate(size_t size) override {
return malloc(size);
}
/// Release previously allocated memory.
virtual void release(void* pointer, size_t size) override {
free(pointer);
}
};
// Class TestDynamicAABBTree
/**
@ -68,8 +91,9 @@ class TestDynamicAABBTree : public Test {
// ---------- Atributes ---------- //
DefaultTestTreeAllocator mAllocator;
DynamicTreeRaycastCallback mRaycastCallback;
PoolAllocator mAllocator;
public :
@ -99,7 +123,7 @@ class TestDynamicAABBTree : public Test {
// ------------ Create tree ---------- //
// Dynamic AABB Tree
DynamicAABBTree tree(MemoryManager::getBaseAllocator());
DynamicAABBTree tree(mAllocator);
#ifdef IS_PROFILING_ACTIVE
/// Pointer to the profiler
@ -155,7 +179,7 @@ class TestDynamicAABBTree : public Test {
// ------------- Create tree ----------- //
// Dynamic AABB Tree
DynamicAABBTree tree(MemoryManager::getBaseAllocator());
DynamicAABBTree tree(mAllocator);
#ifdef IS_PROFILING_ACTIVE
/// Pointer to the profiler
@ -356,7 +380,7 @@ class TestDynamicAABBTree : public Test {
// ------------- Create tree ----------- //
// Dynamic AABB Tree
DynamicAABBTree tree(MemoryManager::getBaseAllocator());
DynamicAABBTree tree(mAllocator);
#ifdef IS_PROFILING_ACTIVE
/// Pointer to the profiler

View File

@ -33,6 +33,7 @@
#include "collision/shapes/CapsuleShape.h"
#include "collision/shapes/ConvexMeshShape.h"
#include "engine/CollisionWorld.h"
#include "engine/PhysicsCommon.h"
#include "collision/PolygonVertexArray.h"
/// Reactphysics3D namespace
@ -48,6 +49,9 @@ class TestPointInside : public Test {
// ---------- Atributes ---------- //
// Physics common
PhysicsCommon mPhysicsCommon;
// Physics world
CollisionWorld* mWorld;
@ -93,7 +97,7 @@ class TestPointInside : public Test {
TestPointInside(const std::string& name) : Test(name) {
// Create the world
mWorld = new CollisionWorld();
mWorld = mPhysicsCommon.createCollisionWorld();
// Body transform
Vector3 position(-3, 2, 7);
@ -120,13 +124,13 @@ class TestPointInside : public Test {
mLocalShapeToWorld = mBodyTransform * mShapeTransform;
// Create collision shapes
mBoxShape = new BoxShape(Vector3(2, 3, 4));
mBoxShape = mPhysicsCommon.createBoxShape(Vector3(2, 3, 4));
mBoxProxyShape = mBoxBody->addCollisionShape(mBoxShape, mShapeTransform);
mSphereShape = new SphereShape(3);
mSphereShape = mPhysicsCommon.createSphereShape(3);
mSphereProxyShape = mSphereBody->addCollisionShape(mSphereShape, mShapeTransform);
mCapsuleShape = new CapsuleShape(3, 10);
mCapsuleShape = mPhysicsCommon.createCapsuleShape(3, 10);
mCapsuleProxyShape = mCapsuleBody->addCollisionShape(mCapsuleShape, mShapeTransform);
mConvexMeshCubeVertices[0] = Vector3(-2, -3, 4);
@ -156,8 +160,8 @@ class TestPointInside : public Test {
&(mConvexMeshCubeIndices[0]), sizeof(int), 6, mConvexMeshPolygonFaces,
PolygonVertexArray::VertexDataType::VERTEX_FLOAT_TYPE,
PolygonVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
mConvexMeshPolyhedronMesh = new PolyhedronMesh(mConvexMeshPolygonVertexArray);
mConvexMeshShape = new ConvexMeshShape(mConvexMeshPolyhedronMesh);
mConvexMeshPolyhedronMesh = mPhysicsCommon.createPolyhedronMesh(mConvexMeshPolygonVertexArray);
mConvexMeshShape = mPhysicsCommon.createConvexMeshShape(mConvexMeshPolyhedronMesh);
Transform convexMeshTransform(Vector3(10, 0, 0), Quaternion::identity());
mConvexMeshProxyShape = mConvexMeshBody->addCollisionShape(mConvexMeshShape, mShapeTransform);
@ -172,11 +176,11 @@ class TestPointInside : public Test {
/// Destructor
virtual ~TestPointInside() {
delete mWorld;
delete mBoxShape;
delete mSphereShape;
delete mCapsuleShape;
delete mConvexMeshShape;
mPhysicsCommon.destroyBoxShape(mBoxShape);
mPhysicsCommon.destroySphereShape(mSphereShape);
mPhysicsCommon.destroyCapsuleShape(mCapsuleShape);
mPhysicsCommon.destroyConvexMeshShape(mConvexMeshShape);
mPhysicsCommon.destroyCollisionWorld(mWorld);
delete[] mConvexMeshPolygonFaces;
delete mConvexMeshPolygonVertexArray;
delete mConvexMeshPolyhedronMesh;

View File

@ -28,6 +28,7 @@
// Libraries
#include "Test.h"
#include "engine/PhysicsCommon.h"
#include "engine/CollisionWorld.h"
#include "body/CollisionBody.h"
#include "collision/shapes/BoxShape.h"
@ -40,6 +41,8 @@
#include "collision/TriangleMesh.h"
#include "collision/TriangleVertexArray.h"
#include "collision/RaycastInfo.h"
#include "collision/PolygonVertexArray.h"
#include <vector>
/// Reactphysics3D namespace
namespace reactphysics3d {
@ -99,6 +102,8 @@ class TestRaycast : public Test {
// ---------- Atributes ---------- //
PhysicsCommon mPhysicsCommon;
// Raycast callback class
WorldRaycastCallback mCallback;
@ -117,7 +122,6 @@ class TestRaycast : public Test {
CollisionBody* mConvexMeshBody;
CollisionBody* mCylinderBody;
CollisionBody* mCompoundBody;
CollisionBody* mTriangleBody;
CollisionBody* mConcaveMeshBody;
CollisionBody* mHeightFieldBody;
@ -132,8 +136,7 @@ class TestRaycast : public Test {
SphereShape* mSphereShape;
CapsuleShape* mCapsuleShape;
ConvexMeshShape* mConvexMeshShape;
TriangleShape* mTriangleShape;
ConcaveShape* mConcaveMeshShape;
ConcaveMeshShape* mConcaveMeshShape;
HeightFieldShape* mHeightFieldShape;
// Proxy Shapes
@ -143,12 +146,11 @@ class TestRaycast : public Test {
ProxyShape* mConvexMeshProxyShape;
ProxyShape* mCompoundSphereProxyShape;
ProxyShape* mCompoundCapsuleProxyShape;
ProxyShape* mTriangleProxyShape;
ProxyShape* mConcaveMeshProxyShape;
ProxyShape* mHeightFieldProxyShape;
// Triangle meshes
TriangleMesh mConcaveTriangleMesh;
TriangleMesh* mConcaveTriangleMesh;
std::vector<Vector3> mConcaveMeshVertices;
std::vector<uint> mConcaveMeshIndices;
@ -170,7 +172,7 @@ class TestRaycast : public Test {
epsilon = decimal(0.0001);
// Create the world
mWorld = new CollisionWorld();
mWorld = mPhysicsCommon.createCollisionWorld();
// Body transform
Vector3 position(-3, 2, 7);
@ -184,7 +186,6 @@ class TestRaycast : public Test {
mConvexMeshBody = mWorld->createCollisionBody(mBodyTransform);
mCylinderBody = mWorld->createCollisionBody(mBodyTransform);
mCompoundBody = mWorld->createCollisionBody(mBodyTransform);
mTriangleBody = mWorld->createCollisionBody(mBodyTransform);
mConcaveMeshBody = mWorld->createCollisionBody(mBodyTransform);
mHeightFieldBody = mWorld->createCollisionBody(mBodyTransform);
@ -197,21 +198,13 @@ class TestRaycast : public Test {
mLocalShapeToWorld = mBodyTransform * mShapeTransform;
// Create collision shapes
mBoxShape = new BoxShape(Vector3(2, 3, 4));
mBoxShape = mPhysicsCommon.createBoxShape(Vector3(2, 3, 4));
mBoxProxyShape = mBoxBody->addCollisionShape(mBoxShape, mShapeTransform);
mSphereShape = new SphereShape(3);
mSphereShape = mPhysicsCommon.createSphereShape(3);
mSphereProxyShape = mSphereBody->addCollisionShape(mSphereShape, mShapeTransform);
Vector3 triangleVertices[3];
triangleVertices[0] = Vector3(100, 100, 0);
triangleVertices[1] = Vector3(105, 100, 0);
triangleVertices[2] = Vector3(100, 103, 0);
Vector3 triangleVerticesNormals[3] = {Vector3(0, 0, 1), Vector3(0, 0, 1), Vector3(0, 0, 1)};
mTriangleShape = new TriangleShape(triangleVertices, triangleVerticesNormals, 0, mAllocator);
mTriangleProxyShape = mTriangleBody->addCollisionShape(mTriangleShape, mShapeTransform);
mCapsuleShape = new CapsuleShape(2, 5);
mCapsuleShape = mPhysicsCommon.createCapsuleShape(2, 5);
mCapsuleProxyShape = mCapsuleBody->addCollisionShape(mCapsuleShape, mShapeTransform);
mPolyhedronVertices[0] = Vector3(-2, -3, 4);
@ -244,8 +237,8 @@ class TestRaycast : public Test {
PolygonVertexArray::VertexDataType::VERTEX_FLOAT_TYPE,
PolygonVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
mPolyhedronMesh = new PolyhedronMesh(mPolygonVertexArray);
mConvexMeshShape = new ConvexMeshShape(mPolyhedronMesh);
mPolyhedronMesh = mPhysicsCommon.createPolyhedronMesh(mPolygonVertexArray);
mConvexMeshShape = mPhysicsCommon.createConvexMeshShape(mPolyhedronMesh);
mConvexMeshProxyShape = mConvexMeshBody->addCollisionShape(mConvexMeshShape, mShapeTransform);
// Compound shape is a cylinder and a sphere
@ -285,16 +278,15 @@ class TestRaycast : public Test {
12, &(mConcaveMeshIndices[0]), 3 * sizeof(uint),
vertexType, TriangleVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
// Add the triangle vertex array of the subpart to the triangle mesh
mConcaveTriangleMesh.addSubpart(mConcaveMeshVertexArray);
mConcaveMeshShape = new ConcaveMeshShape(&mConcaveTriangleMesh);
mConcaveTriangleMesh->addSubpart(mConcaveMeshVertexArray);
mConcaveMeshShape = mPhysicsCommon.createConcaveMeshShape(mConcaveTriangleMesh);
mConcaveMeshProxyShape = mConcaveMeshBody->addCollisionShape(mConcaveMeshShape, mShapeTransform);
// Heightfield shape (plane height field at height=4)
for (int i=0; i<100; i++) mHeightFieldData[i] = 4;
mHeightFieldShape = new HeightFieldShape(10, 10, 0, 4, mHeightFieldData, HeightFieldShape::HeightDataType::HEIGHT_FLOAT_TYPE);
mHeightFieldShape = mPhysicsCommon.createHeightFieldShape(10, 10, 0, 4, mHeightFieldData, HeightFieldShape::HeightDataType::HEIGHT_FLOAT_TYPE);
mHeightFieldProxyShape = mHeightFieldBody->addCollisionShape(mHeightFieldShape, mShapeTransform);
// Assign proxy shapes to the different categories
@ -304,22 +296,21 @@ class TestRaycast : public Test {
mConvexMeshProxyShape->setCollisionCategoryBits(CATEGORY2);
mCompoundSphereProxyShape->setCollisionCategoryBits(CATEGORY2);
mCompoundCapsuleProxyShape->setCollisionCategoryBits(CATEGORY2);
mTriangleProxyShape->setCollisionCategoryBits(CATEGORY1);
mConcaveMeshProxyShape->setCollisionCategoryBits(CATEGORY2);
mHeightFieldProxyShape->setCollisionCategoryBits(CATEGORY2);
}
/// Destructor
virtual ~TestRaycast() {
delete mWorld;
delete mBoxShape;
delete mSphereShape;
delete mCapsuleShape;
delete mConvexMeshShape;
delete mTriangleShape;
delete mConcaveMeshShape;
delete mHeightFieldShape;
mPhysicsCommon.destroyBoxShape(mBoxShape);
mPhysicsCommon.destroySphereShape(mSphereShape);
mPhysicsCommon.destroyCapsuleShape(mCapsuleShape);
mPhysicsCommon.destroyConvexMeshShape(mConvexMeshShape);
mPhysicsCommon.destroyConcaveMeshShape(mConcaveMeshShape);
mPhysicsCommon.destroyHeightFieldShape(mHeightFieldShape);
mPhysicsCommon.destroyCollisionWorld(mWorld);
delete mConcaveMeshVertexArray;
delete mPolygonVertexArray;
@ -333,7 +324,6 @@ class TestRaycast : public Test {
testCapsule();
testConvexMesh();
testCompound();
testTriangle();
testConcaveMesh();
testHeightField();
}
@ -1000,304 +990,6 @@ class TestRaycast : public Test {
rp3d_test(mCallback.isHit);
}
/// Test the ProxySphereShape::raycast(), CollisionBody::raycast() and
/// CollisionWorld::raycast() methods.
void testTriangle() {
// ----- Test feedback data ----- //
Vector3 point1 = mLocalShapeToWorld * Vector3(101, 101, 400);
Vector3 point2 = mLocalShapeToWorld * Vector3(101, 101, -200);
Ray ray(point1, point2);
Ray rayBackward(point2, point1);
Vector3 hitPoint = mLocalShapeToWorld * Vector3(101, 101, 0);
Vector3 hitNormal = mLocalShapeToWorld.getOrientation() * Vector3(0, 0, 1);
hitNormal.normalize();
mCallback.shapeToTest = mTriangleProxyShape;
// CollisionWorld::raycast()
mCallback.reset();
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT);
mWorld->raycast(ray, &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mCallback.raycastInfo.body == mTriangleBody);
rp3d_test(mCallback.raycastInfo.proxyShape == mTriangleProxyShape);
rp3d_test(approxEqual(mCallback.raycastInfo.hitFraction, 0.6666, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.x, hitPoint.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.y, hitPoint.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.z, hitPoint.z, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.x, hitNormal.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.y, hitNormal.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.z, hitNormal.z, epsilon));
mCallback.reset();
mTriangleShape->setRaycastTestType(TriangleRaycastSide::BACK);
mWorld->raycast(rayBackward, &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mCallback.raycastInfo.body == mTriangleBody);
rp3d_test(mCallback.raycastInfo.proxyShape == mTriangleProxyShape);
rp3d_test(approxEqual(mCallback.raycastInfo.hitFraction, 0.3333, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.x, hitPoint.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.y, hitPoint.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.z, hitPoint.z, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.x, -hitNormal.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.y, -hitNormal.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.z, -hitNormal.z, epsilon));
mCallback.reset();
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT_AND_BACK);
mWorld->raycast(ray, &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mCallback.raycastInfo.body == mTriangleBody);
rp3d_test(mCallback.raycastInfo.proxyShape == mTriangleProxyShape);
rp3d_test(approxEqual(mCallback.raycastInfo.hitFraction, 0.6666, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.x, hitPoint.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.y, hitPoint.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.z, hitPoint.z, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.x, hitNormal.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.y, hitNormal.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.z, hitNormal.z, epsilon));
mCallback.reset();
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT_AND_BACK);
mWorld->raycast(rayBackward, &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mCallback.raycastInfo.body == mTriangleBody);
rp3d_test(mCallback.raycastInfo.proxyShape == mTriangleProxyShape);
rp3d_test(approxEqual(mCallback.raycastInfo.hitFraction, 0.3333, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.x, hitPoint.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.y, hitPoint.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldPoint.z, hitPoint.z, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.x, -hitNormal.x, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.y, -hitNormal.y, epsilon));
rp3d_test(approxEqual(mCallback.raycastInfo.worldNormal.z, -hitNormal.z, epsilon));
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT);
// Correct category filter mask
mCallback.reset();
mWorld->raycast(ray, &mCallback, CATEGORY1);
rp3d_test(mCallback.isHit);
// Wrong category filter mask
mCallback.reset();
mWorld->raycast(ray, &mCallback, CATEGORY2);
rp3d_test(!mCallback.isHit);
// CollisionBody::raycast()
RaycastInfo raycastInfo2;
rp3d_test(mTriangleBody->raycast(ray, raycastInfo2));
rp3d_test(raycastInfo2.body == mTriangleBody);
rp3d_test(raycastInfo2.proxyShape == mTriangleProxyShape);
rp3d_test(approxEqual(raycastInfo2.hitFraction, 0.6666, epsilon));
rp3d_test(approxEqual(raycastInfo2.worldPoint.x, hitPoint.x, epsilon));
rp3d_test(approxEqual(raycastInfo2.worldPoint.y, hitPoint.y, epsilon));
rp3d_test(approxEqual(raycastInfo2.worldPoint.z, hitPoint.z, epsilon));
// ProxyCollisionShape::raycast()
RaycastInfo raycastInfo3;
rp3d_test(mTriangleProxyShape->raycast(ray, raycastInfo3));
rp3d_test(raycastInfo3.body == mTriangleBody);
rp3d_test(raycastInfo3.proxyShape == mTriangleProxyShape);
rp3d_test(approxEqual(raycastInfo3.hitFraction, 0.6666, epsilon));
rp3d_test(approxEqual(raycastInfo3.worldPoint.x, hitPoint.x, epsilon));
rp3d_test(approxEqual(raycastInfo3.worldPoint.y, hitPoint.y, epsilon));
rp3d_test(approxEqual(raycastInfo3.worldPoint.z, hitPoint.z, epsilon));
Ray ray1(mLocalShapeToWorld * Vector3(-10, 10, 4), mLocalShapeToWorld * Vector3(15, 6, -4));
Ray ray2(mLocalShapeToWorld * Vector3(102, 107, 5), mLocalShapeToWorld * Vector3(102, 107, -5));
Ray ray3(mLocalShapeToWorld * Vector3(106, 102, 6), mLocalShapeToWorld * Vector3(106, 102, -8));
Ray ray4(mLocalShapeToWorld * Vector3(100.2, 101, 5), mLocalShapeToWorld * Vector3(100.2, 101, -5));
Ray ray5(mLocalShapeToWorld * Vector3(100.5, 101.5, 4), mLocalShapeToWorld * Vector3(100.5, 101.5, -54));
Ray ray6(mLocalShapeToWorld * Vector3(102, 101, 1), mLocalShapeToWorld * Vector3(102, 102, -1));
Ray ray4Back(mLocalShapeToWorld * Vector3(100.2, 101, -5), mLocalShapeToWorld * Vector3(100.2, 101, 5));
Ray ray5Back(mLocalShapeToWorld * Vector3(100.5, 101.5, -54), mLocalShapeToWorld * Vector3(100.5, 101.5, 4));
Ray ray6Back(mLocalShapeToWorld * Vector3(102, 102, -1), mLocalShapeToWorld * Vector3(102, 101, 1));
// ----- Test raycast miss ----- //
rp3d_test(!mTriangleBody->raycast(ray1, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray1, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray1, &mCallback);
rp3d_test(!mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray1.point1, ray1.point2, decimal(0.01)), &mCallback);
rp3d_test(!mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray1.point1, ray1.point2, decimal(100.0)), &mCallback);
rp3d_test(!mCallback.isHit);
rp3d_test(!mTriangleBody->raycast(ray2, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray2, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray2, &mCallback);
rp3d_test(!mCallback.isHit);
rp3d_test(!mTriangleBody->raycast(ray3, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray3, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray3, &mCallback);
rp3d_test(!mCallback.isHit);
// Test backward ray against front triangles (not hit should occur)
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT);
rp3d_test(!mTriangleBody->raycast(ray4Back, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray4Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray4Back, &mCallback);
rp3d_test(!mCallback.isHit);
rp3d_test(!mTriangleBody->raycast(ray5Back, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray5Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray5Back, &mCallback);
rp3d_test(!mCallback.isHit);
rp3d_test(!mTriangleBody->raycast(ray6Back, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray6Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray6Back, &mCallback);
rp3d_test(!mCallback.isHit);
// Test front ray against back triangles (not hit should occur)
mTriangleShape->setRaycastTestType(TriangleRaycastSide::BACK);
rp3d_test(!mTriangleBody->raycast(ray4, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray4, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray4, &mCallback);
rp3d_test(!mCallback.isHit);
rp3d_test(!mTriangleBody->raycast(ray5, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray5, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray5, &mCallback);
rp3d_test(!mCallback.isHit);
rp3d_test(!mTriangleBody->raycast(ray6, raycastInfo3));
rp3d_test(!mTriangleProxyShape->raycast(ray6, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray6, &mCallback);
rp3d_test(!mCallback.isHit);
// ----- Test raycast hits ----- //
// Test front ray against front triangles
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT);
rp3d_test(mTriangleBody->raycast(ray4, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray4, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray4, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray4.point1, ray4.point2, decimal(0.8)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray5, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray5, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray5, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray5.point1, ray5.point2, decimal(0.8)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray6, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray6, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray6, &mCallback);
mCallback.reset();
mWorld->raycast(Ray(ray6.point1, ray6.point2, decimal(0.8)), &mCallback);
// Test back ray against back triangles
mTriangleShape->setRaycastTestType(TriangleRaycastSide::BACK);
rp3d_test(mTriangleBody->raycast(ray4Back, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray4Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray4Back, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray4Back.point1, ray4Back.point2, decimal(0.8)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray5Back, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray5Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray5Back, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray5Back.point1, ray5Back.point2, decimal(1.0)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray6Back, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray6Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray6Back, &mCallback);
mCallback.reset();
mWorld->raycast(Ray(ray6Back.point1, ray6Back.point2, decimal(0.8)), &mCallback);
// Test front ray against front-back triangles
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT_AND_BACK);
rp3d_test(mTriangleBody->raycast(ray4, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray4, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray4, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray4.point1, ray4.point2, decimal(0.8)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray5, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray5, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray5, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray5.point1, ray5.point2, decimal(0.8)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray6, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray6, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray6, &mCallback);
mCallback.reset();
mWorld->raycast(Ray(ray6.point1, ray6.point2, decimal(0.8)), &mCallback);
// Test back ray against front-back triangles
mTriangleShape->setRaycastTestType(TriangleRaycastSide::FRONT_AND_BACK);
rp3d_test(mTriangleBody->raycast(ray4Back, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray4Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray4Back, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray4Back.point1, ray4Back.point2, decimal(0.8)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray5Back, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray5Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray5Back, &mCallback);
rp3d_test(mCallback.isHit);
mCallback.reset();
mWorld->raycast(Ray(ray5Back.point1, ray5Back.point2, decimal(1.0)), &mCallback);
rp3d_test(mCallback.isHit);
rp3d_test(mTriangleBody->raycast(ray6Back, raycastInfo3));
rp3d_test(mTriangleProxyShape->raycast(ray6Back, raycastInfo3));
mCallback.reset();
mWorld->raycast(ray6Back, &mCallback);
mCallback.reset();
mWorld->raycast(Ray(ray6Back.point1, ray6Back.point2, decimal(0.8)), &mCallback);
}
/// Test the ProxyConvexMeshShape::raycast(), CollisionBody::raycast() and
/// CollisionWorld::raycast() methods.
void testConvexMesh() {

View File

@ -116,6 +116,8 @@ SET(SCENES_SOURCES
scenes/heightfield/HeightFieldScene.cpp
scenes/cubestack/CubeStackScene.h
scenes/cubestack/CubeStackScene.cpp
scenes/pile/PileScene.h
scenes/pile/PileScene.cpp
)
# Add .user file to set debug path in Visual Studio

View File

@ -38,9 +38,9 @@ openglframework::VertexArrayObject Box::mVAO;
int Box::totalNbBoxes = 0;
// Constructor
Box::Box(const openglframework::Vector3& size, reactphysics3d::CollisionWorld* world,
Box::Box(const openglframework::Vector3& size, reactphysics3d::PhysicsCommon& physicsCommon, reactphysics3d::CollisionWorld* world,
const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "cube.obj") {
: PhysicsObject(physicsCommon, meshFolderPath + "cube.obj") {
// Initialize the size of the box
mSize[0] = size.x * 0.5f;
@ -56,7 +56,7 @@ Box::Box(const openglframework::Vector3& size, reactphysics3d::CollisionWorld* w
// Create the collision shape for the rigid body (box shape)
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
mBoxShape = new rp3d::BoxShape(rp3d::Vector3(mSize[0], mSize[1], mSize[2]));
mBoxShape = mPhysicsCommon.createBoxShape(rp3d::Vector3(mSize[0], mSize[1], mSize[2]));
//mBoxShape->setLocalScaling(rp3d::Vector3(2, 2, 2));
mPreviousTransform = rp3d::Transform::identity();
@ -80,9 +80,9 @@ Box::Box(const openglframework::Vector3& size, reactphysics3d::CollisionWorld* w
}
// Constructor
Box::Box(const openglframework::Vector3& size, float mass, reactphysics3d::DynamicsWorld* world,
Box::Box(const openglframework::Vector3& size, float mass, reactphysics3d::PhysicsCommon &physicsCommon, reactphysics3d::DynamicsWorld* world,
const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "cube.obj") {
: PhysicsObject(physicsCommon, meshFolderPath + "cube.obj") {
// Load the mesh from a file
openglframework::MeshReaderWriter::loadMeshFromFile(meshFolderPath + "cube.obj", *this);
@ -104,7 +104,7 @@ Box::Box(const openglframework::Vector3& size, float mass, reactphysics3d::Dynam
// Create the collision shape for the rigid body (box shape)
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
mBoxShape = new rp3d::BoxShape(rp3d::Vector3(mSize[0], mSize[1], mSize[2]));
mBoxShape = mPhysicsCommon.createBoxShape(rp3d::Vector3(mSize[0], mSize[1], mSize[2]));
mPreviousTransform = rp3d::Transform::identity();
@ -138,7 +138,7 @@ Box::~Box() {
mVBONormals.destroy();
mVAO.destroy();
}
delete mBoxShape;
mPhysicsCommon.destroyBoxShape(mBoxShape);
totalNbBoxes--;
}

View File

@ -75,10 +75,11 @@ class Box : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
Box(const openglframework::Vector3& size, reactphysics3d::CollisionWorld* world, const std::string& meshFolderPath);
Box(const openglframework::Vector3& size, reactphysics3d::PhysicsCommon& physicsCommon,
reactphysics3d::CollisionWorld* world, const std::string& meshFolderPath);
/// Constructor
Box(const openglframework::Vector3& size, float mass, reactphysics3d::DynamicsWorld *world, const std::string& meshFolderPath);
Box(const openglframework::Vector3& size, float mass, reactphysics3d::PhysicsCommon& physicsCommon, reactphysics3d::DynamicsWorld *world, const std::string& meshFolderPath);
/// Destructor
~Box();

View File

@ -34,8 +34,8 @@ openglframework::VertexArrayObject Capsule::mVAO;
int Capsule::totalNbCapsules = 0;
// Constructor
Capsule::Capsule(float radius, float height, rp3d::CollisionWorld* world, const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "capsule.obj"), mRadius(radius), mHeight(height) {
Capsule::Capsule(float radius, float height, rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshFolderPath)
: PhysicsObject(physicsCommon, meshFolderPath + "capsule.obj"), mRadius(radius), mHeight(height) {
// Compute the scaling matrix
mScalingMatrix = openglframework::Matrix4(mRadius, 0, 0, 0,
@ -46,7 +46,7 @@ Capsule::Capsule(float radius, float height, rp3d::CollisionWorld* world, const
// Create the collision shape for the rigid body (sphere shape)
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
mCapsuleShape = new rp3d::CapsuleShape(mRadius, mHeight);
mCapsuleShape = mPhysicsCommon.createCapsuleShape(mRadius, mHeight);
//mCapsuleShape->setLocalScaling(rp3d::Vector3(2, 2, 2));
mPreviousTransform = rp3d::Transform::identity();
@ -68,9 +68,9 @@ Capsule::Capsule(float radius, float height, rp3d::CollisionWorld* world, const
}
// Constructor
Capsule::Capsule(float radius, float height, float mass, rp3d::DynamicsWorld* dynamicsWorld,
Capsule::Capsule(float radius, float height, float mass, reactphysics3d::PhysicsCommon &physicsCommon, rp3d::DynamicsWorld* dynamicsWorld,
const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "capsule.obj"), mRadius(radius), mHeight(height) {
: PhysicsObject(physicsCommon, meshFolderPath + "capsule.obj"), mRadius(radius), mHeight(height) {
// Compute the scaling matrix
mScalingMatrix = openglframework::Matrix4(mRadius, 0, 0, 0,
@ -83,7 +83,7 @@ Capsule::Capsule(float radius, float height, float mass, rp3d::DynamicsWorld* dy
// Create the collision shape for the rigid body (sphere shape)
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
mCapsuleShape = new rp3d::CapsuleShape(mRadius, mHeight);
mCapsuleShape = mPhysicsCommon.createCapsuleShape(mRadius, mHeight);
// Create a rigid body corresponding in the dynamics world
rp3d::RigidBody* body = dynamicsWorld->createRigidBody(mPreviousTransform);
@ -118,7 +118,7 @@ Capsule::~Capsule() {
mVBOTextureCoords.destroy();
mVAO.destroy();
}
delete mCapsuleShape;
mPhysicsCommon.destroyCapsuleShape(mCapsuleShape);
totalNbCapsules--;
}

View File

@ -82,10 +82,10 @@ class Capsule : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
Capsule(float radius, float height, rp3d::CollisionWorld* world, const std::string& meshFolderPath);
Capsule(float radius, float height, reactphysics3d::PhysicsCommon &physicsCommon, rp3d::CollisionWorld* world, const std::string& meshFolderPath);
/// Constructor
Capsule(float radius, float height, float mass, rp3d::DynamicsWorld* dynamicsWorld,
Capsule(float radius, float height, float mass, reactphysics3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld,
const std::string& meshFolderPath);
/// Destructor

View File

@ -27,14 +27,18 @@
#include "ConcaveMesh.h"
// Constructor
ConcaveMesh::ConcaveMesh(rp3d::CollisionWorld* world, const std::string& meshPath)
: PhysicsObject(meshPath), mVBOVertices(GL_ARRAY_BUFFER),
ConcaveMesh::ConcaveMesh(rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshPath)
: PhysicsObject(physicsCommon, meshPath), mVBOVertices(GL_ARRAY_BUFFER),
mVBONormals(GL_ARRAY_BUFFER), mVBOTextureCoords(GL_ARRAY_BUFFER),
mVBOIndices(GL_ELEMENT_ARRAY_BUFFER) {
mPhysicsTriangleMesh = mPhysicsCommon.createTriangleMesh();
// Compute the scaling matrix
mScalingMatrix = openglframework::Matrix4::identity();
mPhysicsTriangleMesh = mPhysicsCommon.createTriangleMesh();
// For each subpart of the mesh
for (unsigned int i=0; i<getNbParts(); i++) {
@ -46,12 +50,12 @@ ConcaveMesh::ConcaveMesh(rp3d::CollisionWorld* world, const std::string& meshPat
rp3d::TriangleVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
// Add the triangle vertex array of the subpart to the triangle mesh
mPhysicsTriangleMesh.addSubpart(vertexArray);
mPhysicsTriangleMesh->addSubpart(vertexArray);
}
// Create the collision shape for the rigid body (convex mesh shape) and
// do not forget to delete it at the end
mConcaveShape = new rp3d::ConcaveMeshShape(&mPhysicsTriangleMesh);
mConcaveShape = mPhysicsCommon.createConcaveMeshShape(mPhysicsTriangleMesh);
mPreviousTransform = rp3d::Transform::identity();
@ -68,14 +72,16 @@ ConcaveMesh::ConcaveMesh(rp3d::CollisionWorld* world, const std::string& meshPat
}
// Constructor
ConcaveMesh::ConcaveMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath)
: PhysicsObject(meshPath), mVBOVertices(GL_ARRAY_BUFFER),
ConcaveMesh::ConcaveMesh(float mass, reactphysics3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath)
: PhysicsObject(physicsCommon, meshPath), mVBOVertices(GL_ARRAY_BUFFER),
mVBONormals(GL_ARRAY_BUFFER), mVBOTextureCoords(GL_ARRAY_BUFFER),
mVBOIndices(GL_ELEMENT_ARRAY_BUFFER) {
// Compute the scaling matrix
mScalingMatrix = openglframework::Matrix4::identity();
mPhysicsTriangleMesh = mPhysicsCommon.createTriangleMesh();
// For each subpart of the mesh
for (unsigned int i=0; i<getNbParts(); i++) {
@ -87,12 +93,12 @@ ConcaveMesh::ConcaveMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const s
rp3d::TriangleVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
// Add the triangle vertex array of the subpart to the triangle mesh
mPhysicsTriangleMesh.addSubpart(vertexArray);
mPhysicsTriangleMesh->addSubpart(vertexArray);
}
// Create the collision shape for the rigid body (convex mesh shape) and
// do not forget to delete it at the end
mConcaveShape = new rp3d::ConcaveMeshShape(&mPhysicsTriangleMesh);
mConcaveShape = mPhysicsCommon.createConcaveMeshShape(mPhysicsTriangleMesh);
mPreviousTransform = rp3d::Transform::identity();
@ -114,8 +120,8 @@ ConcaveMesh::ConcaveMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const s
ConcaveMesh::~ConcaveMesh() {
// Destroy the triangle mesh data for the physics engine
for (unsigned int i=0; i<mPhysicsTriangleMesh.getNbSubparts(); i++) {
delete mPhysicsTriangleMesh.getSubpart(i);
for (unsigned int i=0; i<mPhysicsTriangleMesh->getNbSubparts(); i++) {
delete mPhysicsTriangleMesh->getSubpart(i);
}
// Destroy the mesh
@ -128,7 +134,7 @@ ConcaveMesh::~ConcaveMesh() {
mVBOTextureCoords.destroy();
mVAO.destroy();
delete mConcaveShape;
mPhysicsCommon.destroyConcaveMeshShape(mConcaveShape);
}
// Render the sphere at the correct position and with the correct orientation

View File

@ -64,7 +64,7 @@ class ConcaveMesh : public PhysicsObject {
openglframework::VertexArrayObject mVAO;
/// Structure with pointer to the shared mesh data (vertices, indices, ...)
rp3d::TriangleMesh mPhysicsTriangleMesh;
rp3d::TriangleMesh* mPhysicsTriangleMesh;
// -------------------- Methods -------------------- //
@ -76,10 +76,10 @@ class ConcaveMesh : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
ConcaveMesh(rp3d::CollisionWorld* world, const std::string& meshPath);
ConcaveMesh(reactphysics3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshPath);
/// Constructor
ConcaveMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath);
ConcaveMesh(float mass, reactphysics3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath);
/// Destructor
~ConcaveMesh();

View File

@ -27,8 +27,8 @@
#include "ConvexMesh.h"
// Constructor
ConvexMesh::ConvexMesh(rp3d::CollisionWorld* world, const std::string& meshPath)
: PhysicsObject(meshPath), mVBOVertices(GL_ARRAY_BUFFER),
ConvexMesh::ConvexMesh(rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshPath)
: PhysicsObject(physicsCommon, meshPath), mVBOVertices(GL_ARRAY_BUFFER),
mVBONormals(GL_ARRAY_BUFFER), mVBOTextureCoords(GL_ARRAY_BUFFER),
mVBOIndices(GL_ELEMENT_ARRAY_BUFFER) {
@ -53,11 +53,11 @@ ConvexMesh::ConvexMesh(rp3d::CollisionWorld* world, const std::string& meshPath)
rp3d::PolygonVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
// Create the polyhedron mesh
mPolyhedronMesh = new rp3d::PolyhedronMesh(mPolygonVertexArray);
mPolyhedronMesh = mPhysicsCommon.createPolyhedronMesh(mPolygonVertexArray);
// Create the collision shape for the rigid body (convex mesh shape) and
// do not forget to delete it at the end
mConvexShape = new rp3d::ConvexMeshShape(mPolyhedronMesh);
mConvexShape = mPhysicsCommon.createConvexMeshShape(mPolyhedronMesh);
mPreviousTransform = rp3d::Transform::identity();
@ -74,8 +74,8 @@ ConvexMesh::ConvexMesh(rp3d::CollisionWorld* world, const std::string& meshPath)
}
// Constructor
ConvexMesh::ConvexMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath)
: PhysicsObject(meshPath), mVBOVertices(GL_ARRAY_BUFFER),
ConvexMesh::ConvexMesh(float mass, rp3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath)
: PhysicsObject(physicsCommon, meshPath), mVBOVertices(GL_ARRAY_BUFFER),
mVBONormals(GL_ARRAY_BUFFER), mVBOTextureCoords(GL_ARRAY_BUFFER),
mVBOIndices(GL_ELEMENT_ARRAY_BUFFER) {
@ -100,11 +100,11 @@ ConvexMesh::ConvexMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const std
rp3d::PolygonVertexArray::IndexDataType::INDEX_INTEGER_TYPE);
// Create the polyhedron mesh
mPolyhedronMesh = new rp3d::PolyhedronMesh(mPolygonVertexArray);
mPolyhedronMesh = mPhysicsCommon.createPolyhedronMesh(mPolygonVertexArray);
// Create the collision shape for the rigid body (convex mesh shape) and do
// not forget to delete it at the end
mConvexShape = new rp3d::ConvexMeshShape(mPolyhedronMesh);
mConvexShape = mPhysicsCommon.createConvexMeshShape(mPolyhedronMesh);
mPreviousTransform = rp3d::Transform::identity();
@ -135,10 +135,10 @@ ConvexMesh::~ConvexMesh() {
mVBOTextureCoords.destroy();
mVAO.destroy();
delete mPolyhedronMesh;
mPhysicsCommon.destroyConvexMeshShape(mConvexShape);
mPhysicsCommon.destroyPolyhedronMesh(mPolyhedronMesh);
delete mPolygonVertexArray;
delete[] mPolygonFaces;
delete mConvexShape;
}
// Render the sphere at the correct position and with the correct orientation

View File

@ -79,10 +79,10 @@ class ConvexMesh : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
ConvexMesh(rp3d::CollisionWorld* world, const std::string& meshPath);
ConvexMesh(rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshPath);
/// Constructor
ConvexMesh(float mass, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath);
ConvexMesh(float mass, rp3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshPath);
/// Destructor
~ConvexMesh();

View File

@ -34,8 +34,8 @@ openglframework::VertexArrayObject Dumbbell::mVAO;
int Dumbbell::totalNbDumbbells = 0;
// Constructor
Dumbbell::Dumbbell(rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "dumbbell.obj") {
Dumbbell::Dumbbell(rp3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFolderPath)
: PhysicsObject(physicsCommon, meshFolderPath + "dumbbell.obj") {
// Identity scaling matrix
mScalingMatrix.setToIdentity();
@ -47,7 +47,7 @@ Dumbbell::Dumbbell(rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFo
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
const rp3d::decimal radiusSphere = rp3d::decimal(1.5);
const rp3d::decimal massSphere = rp3d::decimal(2.0);
mSphereShape = new rp3d::SphereShape(radiusSphere);
mSphereShape = mPhysicsCommon.createSphereShape(radiusSphere);
// Create a capsule collision shape for the middle of the dumbbell
// ReactPhysics3D will clone this object to create an internal one. Therefore,
@ -55,7 +55,7 @@ Dumbbell::Dumbbell(rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFo
const rp3d::decimal radiusCapsule = rp3d::decimal(0.5);
const rp3d::decimal heightCapsule = rp3d::decimal(7.0);
const rp3d::decimal massCylinder = rp3d::decimal(1.0);
mCapsuleShape = new rp3d::CapsuleShape(radiusCapsule, heightCapsule);
mCapsuleShape = mPhysicsCommon.createCapsuleShape(radiusCapsule, heightCapsule);
mPreviousTransform = rp3d::Transform::identity();
@ -89,8 +89,8 @@ Dumbbell::Dumbbell(rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFo
}
// Constructor
Dumbbell::Dumbbell(rp3d::CollisionWorld* world, const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "dumbbell.obj"){
Dumbbell::Dumbbell(reactphysics3d::PhysicsCommon &physicsCommon, rp3d::CollisionWorld* world, const std::string& meshFolderPath)
: PhysicsObject(physicsCommon, meshFolderPath + "dumbbell.obj"){
// Identity scaling matrix
mScalingMatrix.setToIdentity();
@ -101,14 +101,14 @@ Dumbbell::Dumbbell(rp3d::CollisionWorld* world, const std::string& meshFolderPat
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
const rp3d::decimal radiusSphere = rp3d::decimal(1.5);
mSphereShape = new rp3d::SphereShape(radiusSphere);
mSphereShape = mPhysicsCommon.createSphereShape(radiusSphere);
// Create a cylinder collision shape for the middle of the dumbbell
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
const rp3d::decimal radiusCapsule = rp3d::decimal(0.5);
const rp3d::decimal heightCapsule = rp3d::decimal(7.0);
mCapsuleShape = new rp3d::CapsuleShape(radiusCapsule, heightCapsule);
mCapsuleShape = mPhysicsCommon.createCapsuleShape(radiusCapsule, heightCapsule);
// Initial transform of the first sphere collision shape of the dumbbell (in local-space)
rp3d::Transform transformSphereShape1(rp3d::Vector3(0, mDistanceBetweenSphere / 2.0f, 0), rp3d::Quaternion::identity());
@ -154,8 +154,8 @@ Dumbbell::~Dumbbell() {
mVBOTextureCoords.destroy();
mVAO.destroy();
}
delete mSphereShape;
delete mCapsuleShape;
mPhysicsCommon.destroySphereShape(mSphereShape);
mPhysicsCommon.destroyCapsuleShape(mCapsuleShape);
totalNbDumbbells--;
}

View File

@ -82,10 +82,10 @@ class Dumbbell : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
Dumbbell(rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFolderPath);
Dumbbell(reactphysics3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFolderPath);
/// Constructor
Dumbbell(rp3d::CollisionWorld* world, const std::string& meshFolderPath);
Dumbbell(reactphysics3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshFolderPath);
/// Destructor
~Dumbbell();

View File

@ -28,8 +28,8 @@
#include "PerlinNoise.h"
// Constructor
HeightField::HeightField(rp3d::CollisionWorld* world)
: mVBOVertices(GL_ARRAY_BUFFER),
HeightField::HeightField(rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world)
: PhysicsObject(physicsCommon), mVBOVertices(GL_ARRAY_BUFFER),
mVBONormals(GL_ARRAY_BUFFER), mVBOTextureCoords(GL_ARRAY_BUFFER),
mVBOIndices(GL_ELEMENT_ARRAY_BUFFER) {
@ -44,7 +44,7 @@ HeightField::HeightField(rp3d::CollisionWorld* world)
// Create the collision shape for the rigid body (convex mesh shape) and
// do not forget to delete it at the end
mHeightFieldShape = new rp3d::HeightFieldShape(NB_POINTS_WIDTH, NB_POINTS_LENGTH, mMinHeight, mMaxHeight,
mHeightFieldShape = mPhysicsCommon.createHeightFieldShape(NB_POINTS_WIDTH, NB_POINTS_LENGTH, mMinHeight, mMaxHeight,
mHeightData, rp3d::HeightFieldShape::HeightDataType::HEIGHT_FLOAT_TYPE);
mPreviousTransform = rp3d::Transform::identity();
@ -62,8 +62,8 @@ HeightField::HeightField(rp3d::CollisionWorld* world)
}
// Constructor
HeightField::HeightField(float mass, rp3d::DynamicsWorld* dynamicsWorld)
: mVBOVertices(GL_ARRAY_BUFFER),
HeightField::HeightField(float mass, reactphysics3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld)
: PhysicsObject(physicsCommon), mVBOVertices(GL_ARRAY_BUFFER),
mVBONormals(GL_ARRAY_BUFFER), mVBOTextureCoords(GL_ARRAY_BUFFER),
mVBOIndices(GL_ELEMENT_ARRAY_BUFFER) {
@ -78,7 +78,7 @@ HeightField::HeightField(float mass, rp3d::DynamicsWorld* dynamicsWorld)
// Create the collision shape for the rigid body (convex mesh shape) and
// do not forget to delete it at the end
mHeightFieldShape = new rp3d::HeightFieldShape(NB_POINTS_WIDTH, NB_POINTS_LENGTH, mMinHeight, mMaxHeight,
mHeightFieldShape = mPhysicsCommon.createHeightFieldShape(NB_POINTS_WIDTH, NB_POINTS_LENGTH, mMinHeight, mMaxHeight,
mHeightData, rp3d::HeightFieldShape::HeightDataType::HEIGHT_FLOAT_TYPE);
mPreviousTransform = rp3d::Transform::identity();
@ -110,7 +110,7 @@ HeightField::~HeightField() {
mVBOTextureCoords.destroy();
mVAO.destroy();
delete mHeightFieldShape;
mPhysicsCommon.destroyHeightFieldShape(mHeightFieldShape);
}
// Render the sphere at the correct position and with the correct orientation

View File

@ -89,10 +89,10 @@ class HeightField : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
HeightField(rp3d::CollisionWorld* world);
HeightField(reactphysics3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world);
/// Constructor
HeightField(float mass, rp3d::DynamicsWorld* dynamicsWorld);
HeightField(float mass, rp3d::PhysicsCommon& physicsCommon, rp3d::DynamicsWorld* dynamicsWorld);
/// Destructor
~HeightField();

View File

@ -27,7 +27,8 @@
#include "PhysicsObject.h"
/// Constructor
PhysicsObject::PhysicsObject() : openglframework::Mesh() {
PhysicsObject::PhysicsObject(rp3d::PhysicsCommon& physicsCommon)
: openglframework::Mesh(), mPhysicsCommon(physicsCommon) {
mBody = nullptr;
mColor = openglframework::Color(1, 1, 1, 1);
@ -35,7 +36,7 @@ PhysicsObject::PhysicsObject() : openglframework::Mesh() {
}
/// Constructor
PhysicsObject::PhysicsObject(const std::string& meshPath) : PhysicsObject() {
PhysicsObject::PhysicsObject(rp3d::PhysicsCommon& physicsCommon, const std::string& meshPath) : PhysicsObject(physicsCommon) {
// Load the mesh from a file
openglframework::MeshReaderWriter::loadMeshFromFile(meshPath, *this);

View File

@ -35,6 +35,9 @@ class PhysicsObject : public openglframework::Mesh {
protected:
/// Reference to the physics common object
rp3d::PhysicsCommon& mPhysicsCommon;
/// Body used to simulate the dynamics of the box
rp3d::CollisionBody* mBody;
@ -54,10 +57,10 @@ class PhysicsObject : public openglframework::Mesh {
public:
/// Constructor
PhysicsObject();
PhysicsObject(rp3d::PhysicsCommon& physicsCommon);
/// Constructor
PhysicsObject(const std::string& meshPath);
PhysicsObject(rp3d::PhysicsCommon& physicsCommon, const std::string& meshPath);
/// Update the transform matrix of the object
virtual void updateTransform(float interpolationFactor)=0;

View File

@ -34,9 +34,9 @@ openglframework::VertexArrayObject Sphere::mVAO;
int Sphere::totalNbSpheres = 0;
// Constructor
Sphere::Sphere(float radius, rp3d::CollisionWorld* world,
Sphere::Sphere(float radius, rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world,
const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "sphere.obj"), mRadius(radius) {
: PhysicsObject(physicsCommon, meshFolderPath + "sphere.obj"), mRadius(radius) {
// Compute the scaling matrix
mScalingMatrix = openglframework::Matrix4(mRadius, 0, 0, 0,
@ -47,7 +47,7 @@ Sphere::Sphere(float radius, rp3d::CollisionWorld* world,
// Create the collision shape for the rigid body (sphere shape)
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
mCollisionShape = new rp3d::SphereShape(mRadius);
mCollisionShape = mPhysicsCommon.createSphereShape(mRadius);
//mCollisionShape->setLocalScaling(rp3d::Vector3(2, 2, 2));
mPreviousTransform = rp3d::Transform::identity();
@ -69,9 +69,9 @@ Sphere::Sphere(float radius, rp3d::CollisionWorld* world,
}
// Constructor
Sphere::Sphere(float radius, float mass, reactphysics3d::DynamicsWorld* world,
Sphere::Sphere(float radius, float mass, rp3d::PhysicsCommon& physicsCommon,reactphysics3d::DynamicsWorld* world,
const std::string& meshFolderPath)
: PhysicsObject(meshFolderPath + "sphere.obj"), mRadius(radius) {
: PhysicsObject(physicsCommon, meshFolderPath + "sphere.obj"), mRadius(radius) {
// Compute the scaling matrix
mScalingMatrix = openglframework::Matrix4(mRadius, 0, 0, 0,
@ -82,7 +82,7 @@ Sphere::Sphere(float radius, float mass, reactphysics3d::DynamicsWorld* world,
// Create the collision shape for the rigid body (sphere shape)
// ReactPhysics3D will clone this object to create an internal one. Therefore,
// it is OK if this object is destroyed right after calling RigidBody::addCollisionShape()
mCollisionShape = new rp3d::SphereShape(mRadius);
mCollisionShape = mPhysicsCommon.createSphereShape(mRadius);
mPreviousTransform = rp3d::Transform::identity();
@ -118,7 +118,7 @@ Sphere::~Sphere() {
mVBOTextureCoords.destroy();
mVAO.destroy();
}
delete mCollisionShape;
mPhysicsCommon.destroySphereShape(mCollisionShape);
totalNbSpheres--;
}

View File

@ -79,10 +79,10 @@ class Sphere : public PhysicsObject {
// -------------------- Methods -------------------- //
/// Constructor
Sphere(float radius, rp3d::CollisionWorld* world, const std::string& meshFolderPath);
Sphere(float radius, rp3d::PhysicsCommon& physicsCommon, rp3d::CollisionWorld* world, const std::string& meshFolderPath);
/// Constructor
Sphere(float radius, float mass, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFolderPath);
Sphere(float radius, float mass, reactphysics3d::PhysicsCommon &physicsCommon, rp3d::DynamicsWorld* dynamicsWorld, const std::string& meshFolderPath);
/// Destructor
~Sphere();

116
testbed/meshes/sandbox.obj Normal file
View File

@ -0,0 +1,116 @@
# Blender v2.79 (sub 0) OBJ File: ''
# www.blender.org
v -31.880749 -0.589469 22.622011
v -25.786182 -0.589469 22.622011
v -19.691614 -0.589469 22.622011
v -13.597046 -0.589469 22.622011
v -7.502479 -0.589469 22.622011
v -1.407912 -0.589469 22.622011
v 4.686658 -0.589469 22.622011
v 10.781222 -0.589469 22.622011
v -31.880749 -0.589469 16.527445
v -25.786182 -0.589469 16.527445
v -19.691614 -0.589469 16.527445
v -13.597046 -0.589469 16.527445
v -7.502479 -0.589469 16.527445
v -1.407912 -0.589469 16.527445
v 4.686658 -0.589469 16.527445
v 10.781222 -0.589469 16.527445
v -31.880749 -0.589469 10.432877
v -25.786182 -0.589469 10.432877
v -19.691614 -13.260081 10.432877
v -13.597046 -13.260081 10.432877
v -7.502479 -13.260081 10.432877
v -1.407912 -13.260081 10.432877
v 4.686658 -13.260081 10.432877
v 10.781222 -0.589469 10.432877
v -31.880749 -0.589469 4.338308
v -25.786182 -0.589469 4.338308
v -19.691614 -13.260081 4.338308
v -13.597046 -13.260081 4.338308
v -7.502479 -13.260081 4.338308
v -1.407912 -13.260081 4.338308
v 4.686658 -13.260081 4.338308
v 10.781222 -0.589469 4.338308
v -31.880749 -0.589469 -1.756259
v -25.786182 -0.589469 -1.756259
v -19.691614 -13.260081 -1.756259
v -13.597046 -13.260081 -1.756259
v -7.502479 -13.260081 -1.756259
v -1.407912 -13.260081 -1.756259
v 4.686658 -13.260081 -1.756259
v 10.781222 -0.589469 -1.756259
v -31.880749 -0.589469 -7.850826
v -25.786182 -0.589469 -7.850826
v -19.691614 -13.260081 -7.850826
v -13.597046 -13.260081 -7.850826
v -7.502479 -13.260081 -7.850826
v -1.407912 -13.260081 -7.850826
v 4.686658 -13.260081 -7.850826
v 10.781222 -0.589469 -7.850826
v -31.880749 -0.589469 -13.945395
v -25.786182 -0.589469 -13.945395
v -19.691614 -0.589469 -13.945395
v -13.597046 -0.589469 -13.945395
v -7.502479 -0.589469 -13.945395
v -1.407912 -0.589469 -13.945395
v 4.686658 -0.589469 -13.945395
v 10.781222 -0.589469 -13.945395
v -31.880749 -0.589469 -20.039961
v -25.786182 -0.589469 -20.039961
v -19.691614 -0.589469 -20.039961
v -13.597046 -0.589469 -20.039961
v -7.502479 -0.589469 -20.039961
v -1.407912 -0.589469 -20.039961
v 4.686658 -0.589469 -20.039961
v 10.781222 -0.589469 -20.039961
s off
f 1 2 10 9
f 2 3 11 10
f 3 4 12 11
f 4 5 13 12
f 5 6 14 13
f 6 7 15 14
f 7 8 16 15
f 9 10 18 17
f 10 11 19 18
f 11 12 20 19
f 12 13 21 20
f 13 14 22 21
f 14 15 23 22
f 15 16 24 23
f 17 18 26 25
f 18 19 27 26
f 19 20 28 27
f 20 21 29 28
f 21 22 30 29
f 22 23 31 30
f 23 24 32 31
f 25 26 34 33
f 26 27 35 34
f 27 28 36 35
f 28 29 37 36
f 29 30 38 37
f 30 31 39 38
f 31 32 40 39
f 33 34 42 41
f 34 35 43 42
f 35 36 44 43
f 36 37 45 44
f 37 38 46 45
f 38 39 47 46
f 39 40 48 47
f 41 42 50 49
f 42 43 51 50
f 43 44 52 51
f 44 45 53 52
f 45 46 54 53
f 46 47 55 54
f 47 48 56 55
f 49 50 58 57
f 50 51 59 58
f 51 52 60 59
f 52 53 61 60
f 53 54 62 61
f 54 55 63 62
f 55 56 64 63

View File

@ -52,12 +52,12 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
mPhysicsWorld = new rp3d::CollisionWorld(worldSettings);
mPhysicsWorld = mPhysicsCommon.createCollisionWorld(worldSettings);
// ---------- Sphere 1 ---------- //
// Create a sphere and a corresponding collision body in the dynamics world
mSphere1 = new Sphere(4, mPhysicsWorld, mMeshFolderPath);
mSphere1 = new Sphere(4, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mAllShapes.push_back(mSphere1);
// Set the color
@ -69,7 +69,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Sphere 2 ---------- //
// Create a sphere and a corresponding collision body in the dynamics world
mSphere2 = new Sphere(2, mPhysicsWorld, mMeshFolderPath);
mSphere2 = new Sphere(2, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mAllShapes.push_back(mSphere2);
// Set the color
@ -81,7 +81,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Capsule 1 ---------- //
// Create a cylinder and a corresponding collision body in the dynamics world
mCapsule1 = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, mPhysicsWorld, mMeshFolderPath);
mCapsule1 = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mAllShapes.push_back(mCapsule1);
// Set the color
@ -92,7 +92,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Capsule 2 ---------- //
// Create a cylinder and a corresponding collision body in the dynamics world
mCapsule2 = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, mPhysicsWorld, mMeshFolderPath);
mCapsule2 = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mAllShapes.push_back(mCapsule2);
// Set the color
@ -103,7 +103,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Concave Mesh ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mConcaveMesh = new ConcaveMesh(mPhysicsWorld, mMeshFolderPath + "city.obj");
mConcaveMesh = new ConcaveMesh(mPhysicsCommon, mPhysicsWorld, mMeshFolderPath + "city.obj");
mAllShapes.push_back(mConcaveMesh);
// Set the color
@ -114,7 +114,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Box 1 ---------- //
// Create a cylinder and a corresponding collision body in the dynamics world
mBox1 = new Box(BOX_SIZE, mPhysicsWorld, mMeshFolderPath);
mBox1 = new Box(BOX_SIZE, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mAllShapes.push_back(mBox1);
// Set the color
@ -125,7 +125,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Box 2 ---------- //
// Create a cylinder and a corresponding collision body in the dynamics world
mBox2 = new Box(openglframework::Vector3(3, 2, 5), mPhysicsWorld, mMeshFolderPath);
mBox2 = new Box(openglframework::Vector3(3, 2, 5), mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mAllShapes.push_back(mBox2);
// Set the color
@ -136,7 +136,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Convex Mesh ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mConvexMesh = new ConvexMesh(mPhysicsWorld, mMeshFolderPath + "convexmesh.obj");
mConvexMesh = new ConvexMesh(mPhysicsCommon, mPhysicsWorld, mMeshFolderPath + "convexmesh.obj");
mAllShapes.push_back(mConvexMesh);
// Set the color
@ -147,7 +147,7 @@ CollisionDetectionScene::CollisionDetectionScene(const std::string& name, Engine
// ---------- Heightfield ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mHeightField = new HeightField(mPhysicsWorld);
mHeightField = new HeightField(mPhysicsCommon, mPhysicsWorld);
// Set the color
mHeightField->setColor(mGreyColorDemo);
@ -212,7 +212,7 @@ CollisionDetectionScene::~CollisionDetectionScene() {
VisualContactPoint::destroyStaticData();
// Destroy the collision world
delete mPhysicsWorld;
mPhysicsCommon.destroyCollisionWorld(mPhysicsWorld);
}
// Take a step for the simulation

View File

@ -49,14 +49,14 @@ CollisionShapesScene::CollisionShapesScene(const std::string& name, EngineSettin
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
rp3d::DynamicsWorld* dynamicsWorld = new rp3d::DynamicsWorld(gravity, worldSettings);
rp3d::DynamicsWorld* dynamicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
dynamicsWorld->setEventListener(this);
mPhysicsWorld = dynamicsWorld;
for (int i=0; i<NB_COMPOUND_SHAPES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
Dumbbell* dumbbell = new Dumbbell(getDynamicsWorld(), meshFolderPath);
Dumbbell* dumbbell = new Dumbbell(mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Set the box color
dumbbell->setColor(mDemoColors[i % mNbDemoColors]);
@ -75,7 +75,7 @@ CollisionShapesScene::CollisionShapesScene(const std::string& name, EngineSettin
for (int i=0; i<NB_BOXES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Box* box = new Box(BOX_SIZE, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
Box* box = new Box(BOX_SIZE, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
box->setColor(mDemoColors[i % mNbDemoColors]);
@ -94,7 +94,7 @@ CollisionShapesScene::CollisionShapesScene(const std::string& name, EngineSettin
for (int i=0; i<NB_SPHERES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, getDynamicsWorld(), meshFolderPath);
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Add some rolling resistance
sphere->getRigidBody()->getMaterial().setRollingResistance(rp3d::decimal(0.08));
@ -117,7 +117,7 @@ CollisionShapesScene::CollisionShapesScene(const std::string& name, EngineSettin
// Create a cylinder and a corresponding rigid in the dynamics world
Capsule* capsule = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, CAPSULE_MASS,
getDynamicsWorld(), meshFolderPath);
mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
capsule->getRigidBody()->getMaterial().setRollingResistance(rp3d::decimal(0.08f));
@ -138,7 +138,7 @@ CollisionShapesScene::CollisionShapesScene(const std::string& name, EngineSettin
for (int i=0; i<NB_MESHES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
// Set the box color
mesh->setColor(mDemoColors[i % mNbDemoColors]);
@ -155,7 +155,7 @@ CollisionShapesScene::CollisionShapesScene(const std::string& name, EngineSettin
// ---------- Create the floor ---------
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, getDynamicsWorld(), mMeshFolderPath);
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mPhysicsObjects.push_back(mFloor);
// Set the box color
@ -195,7 +195,7 @@ CollisionShapesScene::~CollisionShapesScene() {
}
// Destroy the dynamics world
delete mPhysicsWorld;
mPhysicsCommon.destroyDynamicsWorld(static_cast<rp3d::DynamicsWorld*>(mPhysicsWorld));
}
/// Reset the scene

View File

@ -49,7 +49,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
rp3d::DynamicsWorld* dynamicsWorld = new rp3d::DynamicsWorld(gravity, worldSettings);
rp3d::DynamicsWorld* dynamicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
dynamicsWorld->setEventListener(this);
mPhysicsWorld = dynamicsWorld;
@ -57,7 +57,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_COMPOUND_SHAPES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
Dumbbell* dumbbell = new Dumbbell(getDynamicsWorld(), meshFolderPath);
Dumbbell* dumbbell = new Dumbbell(mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Set the box color
dumbbell->setColor(mDemoColors[i % mNbDemoColors]);
@ -76,7 +76,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_BOXES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Box* box = new Box(BOX_SIZE, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
Box* box = new Box(BOX_SIZE, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
box->setColor(mDemoColors[i % mNbDemoColors]);
@ -95,7 +95,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_SPHERES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, getDynamicsWorld(), meshFolderPath);
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Add some rolling resistance
sphere->getRigidBody()->getMaterial().setRollingResistance(rp3d::decimal(0.08));
@ -118,7 +118,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
// Create a cylinder and a corresponding rigid in the dynamics world
Capsule* capsule = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, CAPSULE_MASS,
getDynamicsWorld(), meshFolderPath);
mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
capsule->getRigidBody()->getMaterial().setRollingResistance(rp3d::decimal(0.08));
@ -139,7 +139,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_MESHES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
// Set the box color
mesh->setColor(mDemoColors[i % mNbDemoColors]);
@ -160,7 +160,7 @@ ConcaveMeshScene::ConcaveMeshScene(const std::string& name, EngineSettings& sett
rp3d::decimal mass = 1.0;
// Create a convex mesh and a corresponding rigid in the dynamics world
mConcaveMesh = new ConcaveMesh(mass, getDynamicsWorld(), meshFolderPath + "city.obj");
mConcaveMesh = new ConcaveMesh(mass, mPhysicsCommon, getDynamicsWorld(), meshFolderPath + "city.obj");
// Set the mesh as beeing static
mConcaveMesh->getRigidBody()->setType(rp3d::BodyType::STATIC);
@ -202,7 +202,7 @@ ConcaveMeshScene::~ConcaveMeshScene() {
}
// Destroy the dynamics world
delete getDynamicsWorld();
mPhysicsCommon.destroyDynamicsWorld(getDynamicsWorld());
}
// Reset the scene

View File

@ -47,7 +47,7 @@ CubesScene::CubesScene(const std::string& name, EngineSettings& settings)
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
rp3d::DynamicsWorld* dynamicsWorld = new rp3d::DynamicsWorld(gravity, worldSettings);
rp3d::DynamicsWorld* dynamicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
dynamicsWorld->setEventListener(this);
mPhysicsWorld = dynamicsWorld;
@ -55,7 +55,7 @@ CubesScene::CubesScene(const std::string& name, EngineSettings& settings)
for (int i=0; i<NB_CUBES; i++) {
// Create a cube and a corresponding rigid in the dynamics world
Box* cube = new Box(BOX_SIZE, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
Box* cube = new Box(BOX_SIZE, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
cube->setColor(mDemoColors[i % mNbDemoColors]);
@ -73,7 +73,7 @@ CubesScene::CubesScene(const std::string& name, EngineSettings& settings)
// ------------------------- FLOOR ----------------------- //
// Create the floor
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, getDynamicsWorld(), mMeshFolderPath);
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mFloor->setColor(mGreyColorDemo);
mFloor->setSleepingColor(mGreyColorDemo);
@ -113,7 +113,7 @@ CubesScene::~CubesScene() {
delete mFloor;
// Destroy the dynamics world
delete getDynamicsWorld();
mPhysicsCommon.destroyDynamicsWorld(getDynamicsWorld());
}
// Reset the scene

View File

@ -47,7 +47,7 @@ CubeStackScene::CubeStackScene(const std::string& name, EngineSettings& settings
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
rp3d::DynamicsWorld* dynamicsWorld = new rp3d::DynamicsWorld(gravity, worldSettings);
rp3d::DynamicsWorld* dynamicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
dynamicsWorld->setEventListener(this);
mPhysicsWorld = dynamicsWorld;
@ -57,7 +57,7 @@ CubeStackScene::CubeStackScene(const std::string& name, EngineSettings& settings
for (int j=0; j<i; j++) {
// Create a cube and a corresponding rigid in the dynamics world
Box* cube = new Box(BOX_SIZE, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
Box* cube = new Box(BOX_SIZE, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
cube->setColor(mDemoColors[i % mNbDemoColors]);
@ -76,7 +76,7 @@ CubeStackScene::CubeStackScene(const std::string& name, EngineSettings& settings
// ------------------------- FLOOR ----------------------- //
// Create the floor
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, getDynamicsWorld(), mMeshFolderPath);
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mFloor->setColor(mGreyColorDemo);
mFloor->setSleepingColor(mGreyColorDemo);
@ -116,7 +116,7 @@ CubeStackScene::~CubeStackScene() {
delete mFloor;
// Destroy the dynamics world
delete getDynamicsWorld();
mPhysicsCommon.destroyDynamicsWorld(getDynamicsWorld());
}
// Reset the scene

View File

@ -49,14 +49,14 @@ HeightFieldScene::HeightFieldScene(const std::string& name, EngineSettings& sett
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
rp3d::DynamicsWorld* dynamicsWorld = new rp3d::DynamicsWorld(gravity, worldSettings);
rp3d::DynamicsWorld* dynamicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
dynamicsWorld->setEventListener(this);
mPhysicsWorld = dynamicsWorld;
for (int i = 0; i<NB_COMPOUND_SHAPES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
Dumbbell* dumbbell = new Dumbbell(getDynamicsWorld(), meshFolderPath);
Dumbbell* dumbbell = new Dumbbell(mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Set the box color
dumbbell->setColor(mDemoColors[i % mNbDemoColors]);
@ -75,7 +75,7 @@ HeightFieldScene::HeightFieldScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_BOXES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Box* box = new Box(BOX_SIZE, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
Box* box = new Box(BOX_SIZE, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
box->setColor(mDemoColors[i % mNbDemoColors]);
@ -94,7 +94,7 @@ HeightFieldScene::HeightFieldScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_SPHERES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, getDynamicsWorld(), meshFolderPath);
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Add some rolling resistance
sphere->getRigidBody()->getMaterial().setRollingResistance(0.08f);
@ -117,7 +117,7 @@ HeightFieldScene::HeightFieldScene(const std::string& name, EngineSettings& sett
// Create a cylinder and a corresponding rigid in the dynamics world
Capsule* capsule = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, CAPSULE_MASS,
getDynamicsWorld(), meshFolderPath);
mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
capsule->getRigidBody()->getMaterial().setRollingResistance(0.08f);
@ -138,7 +138,7 @@ HeightFieldScene::HeightFieldScene(const std::string& name, EngineSettings& sett
for (int i = 0; i<NB_MESHES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
// Set the box color
mesh->setColor(mDemoColors[i % mNbDemoColors]);
@ -159,7 +159,7 @@ HeightFieldScene::HeightFieldScene(const std::string& name, EngineSettings& sett
rp3d::decimal mass = 1.0;
// Create a convex mesh and a corresponding rigid in the dynamics world
mHeightField = new HeightField(mass, getDynamicsWorld());
mHeightField = new HeightField(mass, mPhysicsCommon, getDynamicsWorld());
// Set the mesh as beeing static
mHeightField->getRigidBody()->setType(rp3d::BodyType::STATIC);
@ -201,7 +201,7 @@ HeightFieldScene::~HeightFieldScene() {
}
// Destroy the dynamics world
delete getDynamicsWorld();
mPhysicsCommon.destroyDynamicsWorld(getDynamicsWorld());
}
// Reset the scene

View File

@ -48,7 +48,7 @@ JointsScene::JointsScene(const std::string& name, EngineSettings& settings)
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
rp3d::DynamicsWorld* dynamicsWorld = new rp3d::DynamicsWorld(gravity, worldSettings);
rp3d::DynamicsWorld* dynamicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
dynamicsWorld->setEventListener(this);
mPhysicsWorld = dynamicsWorld;
@ -115,7 +115,7 @@ JointsScene::~JointsScene() {
delete mFloor;
// Destroy the dynamics world
delete getDynamicsWorld();
mPhysicsCommon.destroyDynamicsWorld(getDynamicsWorld());
}
// Update the physics world (take a simulation step)
@ -214,7 +214,7 @@ void JointsScene::createBallAndSocketJoints() {
// Create a box and a corresponding rigid in the dynamics world
mBallAndSocketJointChainBoxes[i] = new Box(boxDimension, boxMass,
getDynamicsWorld(), mMeshFolderPath);
mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mBallAndSocketJointChainBoxes[i]->setTransform(rp3d::Transform(positionBox, rp3d::Quaternion::identity()));
// Set the box color
@ -266,7 +266,7 @@ void JointsScene::createSliderJoint() {
// Create a box and a corresponding rigid in the dynamics world
openglframework::Vector3 box1Dimension(2, 4, 2);
mSliderJointBottomBox = new Box(box1Dimension , BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
mSliderJointBottomBox = new Box(box1Dimension , BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mSliderJointBottomBox->setTransform(rp3d::Transform(positionBox1, rp3d::Quaternion::identity()));
// Set the box color
@ -288,7 +288,7 @@ void JointsScene::createSliderJoint() {
// Create a box and a corresponding rigid in the dynamics world
openglframework::Vector3 box2Dimension(1.5f, 4, 1.5f);
mSliderJointTopBox = new Box(box2Dimension, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
mSliderJointTopBox = new Box(box2Dimension, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mSliderJointTopBox->setTransform(rp3d::Transform(positionBox2, rp3d::Quaternion::identity()));
// Set the box color
@ -330,7 +330,7 @@ void JointsScene::createPropellerHingeJoint() {
// Create a box and a corresponding rigid in the dynamics world
openglframework::Vector3 boxDimension(10, 1, 1);
mPropellerBox = new Box(boxDimension, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
mPropellerBox = new Box(boxDimension, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mPropellerBox->setTransform(rp3d::Transform(positionBox1, rp3d::Quaternion::identity()));
// Set the box color
@ -371,7 +371,7 @@ void JointsScene::createFixedJoints() {
// Create a box and a corresponding rigid in the dynamics world
openglframework::Vector3 boxDimension(1.5, 1.5, 1.5);
mFixedJointBox1 = new Box(boxDimension, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
mFixedJointBox1 = new Box(boxDimension, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mFixedJointBox1->setTransform(rp3d::Transform(positionBox1, rp3d::Quaternion::identity()));
// Set the box color
@ -389,7 +389,7 @@ void JointsScene::createFixedJoints() {
rp3d::Vector3 positionBox2(-5, 7, 0);
// Create a box and a corresponding rigid in the dynamics world
mFixedJointBox2 = new Box(boxDimension, BOX_MASS, getDynamicsWorld(), mMeshFolderPath);
mFixedJointBox2 = new Box(boxDimension, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
mFixedJointBox2->setTransform(rp3d::Transform(positionBox2, rp3d::Quaternion::identity()));
// Set the box color
@ -430,7 +430,7 @@ void JointsScene::createFloor() {
// Create the floor
rp3d::Vector3 floorPosition(0, 0, 0);
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, getDynamicsWorld(), mMeshFolderPath);
mFloor = new Box(FLOOR_SIZE, FLOOR_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
mFloor->setColor(mGreyColorDemo);

View File

@ -0,0 +1,272 @@
/********************************************************************************
* ReactPhysics3D physics library, http://www.reactphysics3d.com *
* Copyright (c) 2010-2016 Daniel Chappuis *
*********************************************************************************
* *
* This software is provided 'as-is', without any express or implied warranty. *
* In no event will the authors be held liable for any damages arising from the *
* use of this software. *
* *
* Permission is granted to anyone to use this software for any purpose, *
* including commercial applications, and to alter it and redistribute it *
* freely, subject to the following restrictions: *
* *
* 1. The origin of this software must not be misrepresented; you must not claim *
* that you wrote the original software. If you use this software in a *
* product, an acknowledgment in the product documentation would be *
* appreciated but is not required. *
* *
* 2. Altered source versions must be plainly marked as such, and must not be *
* misrepresented as being the original software. *
* *
* 3. This notice may not be removed or altered from any source distribution. *
* *
********************************************************************************/
// Libraries
#include "PileScene.h"
// Namespaces
using namespace openglframework;
using namespace pilescene;
// Constructor
PileScene::PileScene(const std::string& name, EngineSettings& settings)
: SceneDemo(name, settings, SCENE_RADIUS) {
std::string meshFolderPath("meshes/");
// Compute the radius and the center of the scene
openglframework::Vector3 center(0, 5, 0);
// Set the center of the scene
setScenePosition(center, SCENE_RADIUS);
// Gravity vector in the dynamics world
rp3d::Vector3 gravity(0, -9.81f, 0);
rp3d::WorldSettings worldSettings;
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
mPhysicsWorld = mPhysicsCommon.createDynamicsWorld(gravity, worldSettings);
for (int i=0; i<NB_COMPOUND_SHAPES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
Dumbbell* dumbbell = new Dumbbell(mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Set the box color
dumbbell->setColor(mDemoColors[i % mNbDemoColors]);
dumbbell->setSleepingColor(mRedColorDemo);
// Change the material properties of the rigid body
rp3d::Material& material = dumbbell->getRigidBody()->getMaterial();
material.setBounciness(rp3d::decimal(0.2));
// Add the mesh the list of dumbbells in the scene
mDumbbells.push_back(dumbbell);
mPhysicsObjects.push_back(dumbbell);
}
// Create all the boxes of the scene
for (int i=0; i<NB_BOXES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Box* box = new Box(BOX_SIZE, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), mMeshFolderPath);
// Set the box color
box->setColor(mDemoColors[i % mNbDemoColors]);
box->setSleepingColor(mRedColorDemo);
// Change the material properties of the rigid body
rp3d::Material& material = box->getRigidBody()->getMaterial();
material.setBounciness(rp3d::decimal(0.2));
// Add the sphere the list of sphere in the scene
mBoxes.push_back(box);
mPhysicsObjects.push_back(box);
}
// Create all the spheres of the scene
for (int i=0; i<NB_SPHERES; i++) {
// Create a sphere and a corresponding rigid in the dynamics world
Sphere* sphere = new Sphere(SPHERE_RADIUS, BOX_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
// Add some rolling resistance
sphere->getRigidBody()->getMaterial().setRollingResistance(rp3d::decimal(0.08));
// Set the box color
sphere->setColor(mDemoColors[i % mNbDemoColors]);
sphere->setSleepingColor(mRedColorDemo);
// Change the material properties of the rigid body
rp3d::Material& material = sphere->getRigidBody()->getMaterial();
material.setBounciness(rp3d::decimal(0.2));
// Add the sphere the list of sphere in the scene
mSpheres.push_back(sphere);
mPhysicsObjects.push_back(sphere);
}
// Create all the capsules of the scene
for (int i=0; i<NB_CAPSULES; i++) {
// Create a cylinder and a corresponding rigid in the dynamics world
Capsule* capsule = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, CAPSULE_MASS,
mPhysicsCommon, getDynamicsWorld(), meshFolderPath);
capsule->getRigidBody()->getMaterial().setRollingResistance(rp3d::decimal(0.08f));
// Set the box color
capsule->setColor(mDemoColors[i % mNbDemoColors]);
capsule->setSleepingColor(mRedColorDemo);
// Change the material properties of the rigid body
rp3d::Material& material = capsule->getRigidBody()->getMaterial();
material.setBounciness(rp3d::decimal(0.2));
// Add the cylinder the list of sphere in the scene
mCapsules.push_back(capsule);
mPhysicsObjects.push_back(capsule);
}
// Create all the convex meshes of the scene
for (int i=0; i<NB_MESHES; i++) {
// Create a convex mesh and a corresponding rigid in the dynamics world
ConvexMesh* mesh = new ConvexMesh(MESH_MASS, mPhysicsCommon, getDynamicsWorld(), meshFolderPath + "convexmesh.obj");
// Set the box color
mesh->setColor(mDemoColors[i % mNbDemoColors]);
mesh->setSleepingColor(mRedColorDemo);
// Change the material properties of the rigid body
rp3d::Material& material = mesh->getRigidBody()->getMaterial();
material.setBounciness(rp3d::decimal(0.2));
// Add the mesh the list of sphere in the scene
mConvexMeshes.push_back(mesh);
mPhysicsObjects.push_back(mesh);
}
// ---------- Create the triangular mesh ---------- //
// Position
rp3d::decimal mass = 1.0;
// Create a convex mesh and a corresponding rigid in the dynamics world
mSandbox = new ConcaveMesh(mass, mPhysicsCommon, getDynamicsWorld(), meshFolderPath + "sandbox.obj");
// Set the mesh as beeing static
mSandbox->getRigidBody()->setType(rp3d::BodyType::STATIC);
// Set the box color
mSandbox->setColor(mGreyColorDemo);
mSandbox->setSleepingColor(mGreyColorDemo);
mPhysicsObjects.push_back(mSandbox);
// Change the material properties of the rigid body
rp3d::Material& material = mSandbox->getRigidBody()->getMaterial();
material.setBounciness(rp3d::decimal(0.2));
material.setFrictionCoefficient(rp3d::decimal(0.1));
// Get the physics engine parameters
mEngineSettings.isGravityEnabled = getDynamicsWorld()->isGravityEnabled();
rp3d::Vector3 gravityVector = getDynamicsWorld()->getGravity();
mEngineSettings.gravity = openglframework::Vector3(gravityVector.x, gravityVector.y, gravityVector.z);
mEngineSettings.isSleepingEnabled = getDynamicsWorld()->isSleepingEnabled();
mEngineSettings.sleepLinearVelocity = getDynamicsWorld()->getSleepLinearVelocity();
mEngineSettings.sleepAngularVelocity = getDynamicsWorld()->getSleepAngularVelocity();
mEngineSettings.nbPositionSolverIterations = getDynamicsWorld()->getNbIterationsPositionSolver();
mEngineSettings.nbVelocitySolverIterations = getDynamicsWorld()->getNbIterationsVelocitySolver();
mEngineSettings.timeBeforeSleep = getDynamicsWorld()->getTimeBeforeSleep();
}
// Destructor
PileScene::~PileScene() {
// Destroy all the physics objects of the scene
for (std::vector<PhysicsObject*>::iterator it = mPhysicsObjects.begin(); it != mPhysicsObjects.end(); ++it) {
// Destroy the corresponding rigid body from the dynamics world
getDynamicsWorld()->destroyRigidBody((*it)->getRigidBody());
// Destroy the object
delete (*it);
}
// Destroy the dynamics world
mPhysicsCommon.destroyDynamicsWorld(getDynamicsWorld());
}
/// Reset the scene
void PileScene::reset() {
const float radius = 3.0f;
for (uint i = 0; i<NB_COMPOUND_SHAPES; i++) {
// Position
float angle = i * 30.0f;
rp3d::Vector3 position(radius * std::cos(angle),
125 + i * (DUMBBELL_HEIGHT + 0.3f),
radius * std::sin(angle));
mDumbbells[i]->setTransform(rp3d::Transform(position, rp3d::Quaternion::identity()));
}
// Create all the boxes of the scene
for (uint i = 0; i<NB_BOXES; i++) {
// Position
float angle = i * 30.0f;
rp3d::Vector3 position(radius * std::cos(angle),
85 + i * (BOX_SIZE.y + 0.8f),
radius * std::sin(angle));
mBoxes[i]->setTransform(rp3d::Transform(position, rp3d::Quaternion::identity()));
}
// Create all the spheres of the scene
for (uint i = 0; i<NB_SPHERES; i++) {
// Position
float angle = i * 35.0f;
rp3d::Vector3 position(radius * std::cos(angle),
75 + i * (SPHERE_RADIUS + 0.8f),
radius * std::sin(angle));
mSpheres[i]->setTransform(rp3d::Transform(position, rp3d::Quaternion::identity()));
}
// Create all the capsules of the scene
for (uint i = 0; i<NB_CAPSULES; i++) {
// Position
float angle = i * 45.0f;
rp3d::Vector3 position(radius * std::cos(angle),
40 + i * (CAPSULE_HEIGHT + 0.3f),
radius * std::sin(angle));
mCapsules[i]->setTransform(rp3d::Transform(position, rp3d::Quaternion::identity()));
}
// Create all the convex meshes of the scene
for (uint i = 0; i<NB_MESHES; i++) {
// Position
float angle = i * 30.0f;
rp3d::Vector3 position(radius * std::cos(angle),
30 + i * (CAPSULE_HEIGHT + 0.3f),
radius * std::sin(angle));
mConvexMeshes[i]->setTransform(rp3d::Transform(position, rp3d::Quaternion::identity()));
}
// ---------- Create the triangular mesh ---------- //
mSandbox->setTransform(rp3d::Transform::identity());
}

View File

@ -0,0 +1,106 @@
/********************************************************************************
* ReactPhysics3D physics library, http://www.reactphysics3d.com *
* Copyright (c) 2010-2016 Daniel Chappuis *
*********************************************************************************
* *
* This software is provided 'as-is', without any express or implied warranty. *
* In no event will the authors be held liable for any damages arising from the *
* use of this software. *
* *
* Permission is granted to anyone to use this software for any purpose, *
* including commercial applications, and to alter it and redistribute it *
* freely, subject to the following restrictions: *
* *
* 1. The origin of this software must not be misrepresented; you must not claim *
* that you wrote the original software. If you use this software in a *
* product, an acknowledgment in the product documentation would be *
* appreciated but is not required. *
* *
* 2. Altered source versions must be plainly marked as such, and must not be *
* misrepresented as being the original software. *
* *
* 3. This notice may not be removed or altered from any source distribution. *
* *
********************************************************************************/
#ifndef PILE_SCENE_H
#define PILE_SCENE_H
// Libraries
#include "openglframework.h"
#include "reactphysics3d.h"
#include "SceneDemo.h"
#include "Sphere.h"
#include "Box.h"
#include "Capsule.h"
#include "ConvexMesh.h"
#include "ConcaveMesh.h"
#include "Dumbbell.h"
#include "VisualContactPoint.h"
namespace pilescene {
// Constants
const float SCENE_RADIUS = 30.0f;
const int NB_BOXES = 150;
const int NB_SPHERES = 80;
const int NB_CAPSULES = 5;
const int NB_MESHES = 0;
const int NB_COMPOUND_SHAPES = 0;
const openglframework::Vector3 BOX_SIZE(2, 2, 2);
const float SPHERE_RADIUS = 1.5f;
const float CONE_RADIUS = 2.0f;
const float CONE_HEIGHT = 3.0f;
const float CYLINDER_RADIUS = 1.0f;
const float CYLINDER_HEIGHT = 5.0f;
const float CAPSULE_RADIUS = 1.0f;
const float CAPSULE_HEIGHT = 1.0f;
const float DUMBBELL_HEIGHT = 1.0f;
const openglframework::Vector3 FLOOR_SIZE(50, 0.5f, 50); // Floor dimensions in meters
const float BOX_MASS = 1.0f;
const float CONE_MASS = 1.0f;
const float CYLINDER_MASS = 1.0f;
const float CAPSULE_MASS = 1.0f;
const float MESH_MASS = 1.0f;
const float FLOOR_MASS = 100.0f; // Floor mass in kilograms
// Class PileScene
class PileScene : public SceneDemo {
private :
// -------------------- Attributes -------------------- //
/// All the boxes of the scene
std::vector<Box*> mBoxes;
std::vector<Sphere*> mSpheres;
std::vector<Capsule*> mCapsules;
/// All the convex meshes of the scene
std::vector<ConvexMesh*> mConvexMeshes;
/// All the dumbbell of the scene
std::vector<Dumbbell*> mDumbbells;
/// Sandbox for the floor
ConcaveMesh* mSandbox;
public:
// -------------------- Methods -------------------- //
/// Constructor
PileScene(const std::string& name, EngineSettings& settings);
/// Destructor
virtual ~PileScene() override;
/// Reset the scene
virtual void reset() override;
};
}
#endif

View File

@ -48,12 +48,12 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
worldSettings.worldName = name;
// Create the dynamics world for the physics simulation
mPhysicsWorld = new rp3d::CollisionWorld(worldSettings);
mPhysicsWorld = mPhysicsCommon.createCollisionWorld(worldSettings);
// ---------- Dumbbell ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mDumbbell = new Dumbbell(mPhysicsWorld, mMeshFolderPath);
mDumbbell = new Dumbbell(mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
// Set the box color
mDumbbell->setColor(mGreyColorDemo);
@ -63,7 +63,7 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
// ---------- Box ---------- //
// Create a box and a corresponding collision body in the dynamics world
mBox = new Box(BOX_SIZE, mPhysicsWorld, mMeshFolderPath);
mBox = new Box(BOX_SIZE, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
mBox->getCollisionBody()->setIsActive(false);
// Set the box color
@ -74,7 +74,7 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
// ---------- Sphere ---------- //
// Create a sphere and a corresponding collision body in the dynamics world
mSphere = new Sphere(SPHERE_RADIUS, mPhysicsWorld, mMeshFolderPath);
mSphere = new Sphere(SPHERE_RADIUS, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
// Set the color
mSphere->setColor(mGreyColorDemo);
@ -85,7 +85,7 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
openglframework::Vector3 position6(0, 0, 0);
// Create a cylinder and a corresponding collision body in the dynamics world
mCapsule = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, mPhysicsWorld, mMeshFolderPath);
mCapsule = new Capsule(CAPSULE_RADIUS, CAPSULE_HEIGHT, mPhysicsCommon, mPhysicsWorld, mMeshFolderPath);
// Set the color
mCapsule->setColor(mGreyColorDemo);
@ -95,7 +95,7 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
// ---------- Convex Mesh ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mConvexMesh = new ConvexMesh(mPhysicsWorld, mMeshFolderPath + "convexmesh.obj");
mConvexMesh = new ConvexMesh(mPhysicsCommon, mPhysicsWorld, mMeshFolderPath + "convexmesh.obj");
// Set the color
mConvexMesh->setColor(mGreyColorDemo);
@ -105,7 +105,7 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
// ---------- Concave Mesh ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mConcaveMesh = new ConcaveMesh(mPhysicsWorld, mMeshFolderPath + "city.obj");
mConcaveMesh = new ConcaveMesh(mPhysicsCommon, mPhysicsWorld, mMeshFolderPath + "city.obj");
// Set the color
mConcaveMesh->setColor(mGreyColorDemo);
@ -115,7 +115,7 @@ RaycastScene::RaycastScene(const std::string& name, EngineSettings& settings)
// ---------- Heightfield ---------- //
// Create a convex mesh and a corresponding collision body in the dynamics world
mHeightField = new HeightField(mPhysicsWorld);
mHeightField = new HeightField(mPhysicsCommon, mPhysicsWorld);
// Set the color
mHeightField->setColor(mGreyColorDemo);
@ -251,7 +251,7 @@ RaycastScene::~RaycastScene() {
VisualContactPoint::destroyStaticData();
// Destroy the collision world
delete mPhysicsWorld;
mPhysicsCommon.destroyCollisionWorld(mPhysicsWorld);
// Destroy the lines
for (std::vector<Line*>::iterator it = mLines.begin(); it != mLines.end();

View File

@ -36,12 +36,14 @@ double Gui::mScrollY = 0.0;
double Gui::mTimeSinceLastProfilingDisplay = 0;
double Gui::mCachedFPS = 0;
double Gui::mCachedUpdateTime = 0;
double Gui::mCachedPhysicsUpdateTime = 0;
double Gui::mCachedTotalPhysicsUpdateTime = 0;
double Gui::mCachedPhysicsStepTime = 0;
// Constructor
Gui::Gui(TestbedApplication* app)
: mApp(app), mSimulationPanel(nullptr), mSettingsPanel(nullptr), mPhysicsPanel(nullptr),
mRenderingPanel(nullptr), mFPSLabel(nullptr), mFrameTimeLabel(nullptr), mPhysicsTimeLabel(nullptr)
mRenderingPanel(nullptr), mFPSLabel(nullptr), mFrameTimeLabel(nullptr), mTotalPhysicsTimeLabel(nullptr),
mPhysicsStepTimeLabel(nullptr)
{
}
@ -78,7 +80,8 @@ void Gui::update() {
mTimeSinceLastProfilingDisplay = mApp->mCurrentTime;
mCachedFPS = mApp->mFPS;
mCachedUpdateTime = mApp->mFrameTime;
mCachedPhysicsUpdateTime = mApp->mPhysicsTime;
mCachedTotalPhysicsUpdateTime = mApp->mTotalPhysicsTime;
mCachedPhysicsStepTime = mApp->mPhysicsStepTime;
}
// Framerate (FPS)
@ -87,8 +90,11 @@ void Gui::update() {
// Frame time
mFrameTimeLabel->setCaption(std::string("Frame time : ") + floatToString(mCachedUpdateTime * 1000.0, 1) + std::string(" ms"));
// Physics time
mPhysicsTimeLabel->setCaption(std::string("Physics time : ") + floatToString(mCachedPhysicsUpdateTime * 1000.0, 1) + std::string(" ms"));
// Total Physics time
mTotalPhysicsTimeLabel->setCaption(std::string("Total physics time : ") + floatToString(mCachedTotalPhysicsUpdateTime * 1000.0, 1) + std::string(" ms"));
// Physics step time
mPhysicsStepTimeLabel->setCaption(std::string("Physics step time : ") + floatToString(mCachedPhysicsStepTime * 1000.0, 1) + std::string(" ms"));
}
void Gui::createSimulationPanel() {
@ -447,8 +453,11 @@ void Gui::createProfilingPanel() {
// Update time
mFrameTimeLabel = new Label(profilingPanel, std::string("Frame time : ") + floatToString(mCachedUpdateTime * 1000.0, 1) + std::string(" ms"),"sans-bold");
// Update time
mPhysicsTimeLabel = new Label(profilingPanel, std::string("Physics time : ") + floatToString(mCachedPhysicsUpdateTime * 1000.0, 1) + std::string(" ms"),"sans-bold");
// Total physics time
mTotalPhysicsTimeLabel = new Label(profilingPanel, std::string("Total physics time : ") + floatToString(mCachedTotalPhysicsUpdateTime * 1000.0, 1) + std::string(" ms"),"sans-bold");
// Physics step time
mPhysicsStepTimeLabel = new Label(profilingPanel, std::string("Physics step time : ") + floatToString(mCachedPhysicsStepTime * 1000.0, 1) + std::string(" ms"),"sans-bold");
profilingPanel->setVisible(true);
}

View File

@ -69,7 +69,8 @@ class Gui {
// Profiling panel
Label* mFPSLabel;
Label* mFrameTimeLabel;
Label* mPhysicsTimeLabel;
Label* mTotalPhysicsTimeLabel;
Label* mPhysicsStepTimeLabel;
std::vector<CheckBox*> mCheckboxesScenes;
@ -86,8 +87,11 @@ class Gui {
/// Cached update time
static double mCachedUpdateTime;
// Cached update physics time
static double mCachedPhysicsUpdateTime;
// Cached total update physics time
static double mCachedTotalPhysicsUpdateTime;
// Cached update single physics step time
static double mCachedPhysicsStepTime;
// -------------------- Methods -------------------- //

View File

@ -96,6 +96,8 @@ class SceneDemo : public Scene {
std::string mMeshFolderPath;
rp3d::PhysicsCommon mPhysicsCommon;
std::vector<PhysicsObject*> mPhysicsObjects;
rp3d::CollisionWorld* mPhysicsWorld;

View File

@ -37,6 +37,7 @@
#include "raycast/RaycastScene.h"
#include "concavemesh/ConcaveMeshScene.h"
#include "cubestack/CubeStackScene.h"
#include "pile/PileScene.h"
using namespace openglframework;
using namespace jointsscene;
@ -47,6 +48,7 @@ using namespace trianglemeshscene;
using namespace heightfieldscene;
using namespace collisiondetectionscene;
using namespace cubestackscene;
using namespace pilescene;
// Initialization of static variables
const float TestbedApplication::SCROLL_SENSITIVITY = 0.08f;
@ -57,7 +59,7 @@ TestbedApplication::TestbedApplication(bool isFullscreen)
mIsInitialized(false), mGui(this), mCurrentScene(nullptr),
mEngineSettings(EngineSettings::defaultSettings()),
mFPS(0), mNbFrames(0), mPreviousTime(0),
mLastTimeComputedFPS(0), mFrameTime(0), mPhysicsTime(0),
mLastTimeComputedFPS(0), mFrameTime(0), mTotalPhysicsTime(0), mPhysicsStepTime(0),
mWidth(1280), mHeight(720),
mSinglePhysicsStepEnabled(false), mSinglePhysicsStepDone(false),
mWindowToFramebufferRatio(Vector2(1, 1)), mIsShadowMappingEnabled(true),
@ -125,6 +127,10 @@ void TestbedApplication::createScenes() {
ConcaveMeshScene* concaveMeshScene = new ConcaveMeshScene("Concave Mesh", mEngineSettings);
mScenes.push_back(concaveMeshScene);
// Pile scene
PileScene* pileScene = new PileScene("Pile", mEngineSettings);
mScenes.push_back(pileScene);
assert(mScenes.size() > 0);
const int firstSceneIndex = 0;
@ -139,7 +145,7 @@ void TestbedApplication::destroyScenes() {
delete mScenes[i];
}
mCurrentScene = NULL;
mCurrentScene = nullptr;
}
void TestbedApplication::updateSinglePhysicsStep() {
@ -163,9 +169,13 @@ void TestbedApplication::updatePhysics() {
// While the time accumulator is not empty
while(mTimer.isPossibleToTakeStep(mEngineSettings.timeStep)) {
double currentTime = glfwGetTime();
// Take a physics simulation step
mCurrentScene->updatePhysics();
mPhysicsStepTime = glfwGetTime() - currentTime;
// Update the timer
mTimer.nextStep(mEngineSettings.timeStep);
}
@ -186,7 +196,7 @@ void TestbedApplication::update() {
}
// Compute the physics update time
mPhysicsTime = glfwGetTime() - currentTime;
mTotalPhysicsTime = glfwGetTime() - currentTime;
// Compute the interpolation factor
float factor = mTimer.computeInterpolationFactor(mEngineSettings.timeStep);

View File

@ -83,8 +83,11 @@ class TestbedApplication : public Screen {
/// Update time (in seconds)
double mFrameTime;
/// Physics update time (in seconds)
double mPhysicsTime;
/// Total physics update time (in seconds)
double mTotalPhysicsTime;
/// Time of a single physics step (in seconds)
double mPhysicsStepTime;
/// Width and height of the window
int mWidth, mHeight;