Push the current work on the Physics2D module
This commit is contained in:
parent
080db76ac1
commit
9a7767867b
|
|
@ -0,0 +1,6 @@
|
|||
MODULE.Name = "Physics2D"
|
||||
|
||||
MODULE.Libraries = {
|
||||
"NazaraCore",
|
||||
"chipmunk-s"
|
||||
}
|
||||
|
|
@ -0,0 +1,105 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 2D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_COLLIDER2D_HPP
|
||||
#define NAZARA_COLLIDER2D_HPP
|
||||
|
||||
#include <Nazara/Prerequesites.hpp>
|
||||
#include <Nazara/Core/ObjectRef.hpp>
|
||||
#include <Nazara/Core/ObjectLibrary.hpp>
|
||||
#include <Nazara/Core/Signal.hpp>
|
||||
#include <Nazara/Math/Vector2.hpp>
|
||||
#include <Nazara/Physics2D/Config.hpp>
|
||||
#include <Nazara/Physics2D/Enums.hpp>
|
||||
#include <vector>
|
||||
|
||||
struct cpShape;
|
||||
struct cpSpace;
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
class Collider2D;
|
||||
class RigidBody2D;
|
||||
|
||||
using Collider2DConstRef = ObjectRef<const Collider2D>;
|
||||
using Collider2DLibrary = ObjectLibrary<Collider2D>;
|
||||
using Collider2DRef = ObjectRef<Collider2D>;
|
||||
|
||||
class NAZARA_PHYSICS2D_API Collider2D : public RefCounted
|
||||
{
|
||||
friend Collider2DLibrary;
|
||||
friend RigidBody2D;
|
||||
|
||||
public:
|
||||
Collider2D() = default;
|
||||
Collider2D(const Collider2D&) = delete;
|
||||
Collider2D(Collider2D&&) = delete;
|
||||
virtual ~Collider2D();
|
||||
|
||||
virtual float ComputeInertialMatrix(float mass) const = 0;
|
||||
|
||||
virtual ColliderType2D GetType() const = 0;
|
||||
|
||||
Collider2D& operator=(const Collider2D&) = delete;
|
||||
Collider2D& operator=(Collider2D&&) = delete;
|
||||
|
||||
// Signals:
|
||||
NazaraSignal(OnColliderRelease, const Collider2D* /*collider*/);
|
||||
|
||||
protected:
|
||||
virtual std::vector<cpShape*> CreateShapes(RigidBody2D* body) const = 0;
|
||||
|
||||
static Collider2DLibrary::LibraryMap s_library;
|
||||
};
|
||||
|
||||
class CircleCollider2D;
|
||||
|
||||
using CircleCollider2DConstRef = ObjectRef<const CircleCollider2D>;
|
||||
using CircleCollider2DRef = ObjectRef<CircleCollider2D>;
|
||||
|
||||
class NAZARA_PHYSICS2D_API CircleCollider2D : public Collider2D
|
||||
{
|
||||
public:
|
||||
CircleCollider2D(float radius, const Vector2f& offset = Vector2f::Zero());
|
||||
|
||||
float ComputeInertialMatrix(float mass) const override;
|
||||
|
||||
inline float GetRadius() const;
|
||||
ColliderType2D GetType() const override;
|
||||
|
||||
template<typename... Args> static CircleCollider2DRef New(Args&&... args);
|
||||
|
||||
private:
|
||||
std::vector<cpShape*> CreateShapes(RigidBody2D* body) const override;
|
||||
|
||||
Vector2f m_offset;
|
||||
float m_radius;
|
||||
};
|
||||
|
||||
class NullCollider2D;
|
||||
|
||||
using NullCollider2DConstRef = ObjectRef<const NullCollider2D>;
|
||||
using NullCollider2DRef = ObjectRef<NullCollider2D>;
|
||||
|
||||
class NAZARA_PHYSICS2D_API NullCollider2D : public Collider2D
|
||||
{
|
||||
public:
|
||||
NullCollider2D() = default;
|
||||
|
||||
float ComputeInertialMatrix(float mass) const override;
|
||||
|
||||
ColliderType2D GetType() const override;
|
||||
|
||||
template<typename... Args> static NullCollider2DRef New(Args&&... args);
|
||||
|
||||
private:
|
||||
std::vector<cpShape*> CreateShapes(RigidBody2D* body) const override;
|
||||
};
|
||||
}
|
||||
|
||||
#include <Nazara/Physics2D/Collider2D.inl>
|
||||
|
||||
#endif // NAZARA_COLLIDER2D_HPP
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <memory>
|
||||
#include <Nazara/Physics2D/Debug.hpp>
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
inline float CircleCollider2D::GetRadius() const
|
||||
{
|
||||
return m_radius;
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
CircleCollider2DRef CircleCollider2D::New(Args&&... args)
|
||||
{
|
||||
std::unique_ptr<CircleCollider2D> object(new CircleCollider2D(std::forward<Args>(args)...));
|
||||
object->SetPersistent(false);
|
||||
|
||||
return object.release();
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
NullCollider2DRef NullCollider2D::New(Args&&... args)
|
||||
{
|
||||
std::unique_ptr<NullCollider2D> object(new NullCollider2D(std::forward<Args>(args)...));
|
||||
object->SetPersistent(false);
|
||||
|
||||
return object.release();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include <Nazara/Physics2D/DebugOff.hpp>
|
||||
|
|
@ -0,0 +1,51 @@
|
|||
/*
|
||||
Nazara Engine - Physics 3D module
|
||||
|
||||
Copyright (C) 2015 Jérôme "Lynix" Leclercq (Lynix680@gmail.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
this software and associated documentation files (the "Software"), to deal in
|
||||
the Software without restriction, including without limitation the rights to
|
||||
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
|
||||
of the Software, and to permit persons to whom the Software is furnished to do
|
||||
so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_CONFIG_PHYSICS2D_HPP
|
||||
#define NAZARA_CONFIG_PHYSICS2D_HPP
|
||||
|
||||
/// Chaque modification d'un paramètre du module nécessite une recompilation de celui-ci
|
||||
|
||||
// Utilise un manager de mémoire pour gérer les allocations dynamiques (détecte les leaks au prix d'allocations/libérations dynamiques plus lentes)
|
||||
#define NAZARA_PHYSICS2D_MANAGE_MEMORY 0
|
||||
|
||||
// Active les tests de sécurité basés sur le code (Conseillé pour le développement)
|
||||
#define NAZARA_PHYSICS2D_SAFE 1
|
||||
|
||||
/// Vérification des valeurs et types de certaines constantes
|
||||
#include <Nazara/Physics2D/ConfigCheck.hpp>
|
||||
|
||||
#if defined(NAZARA_STATIC)
|
||||
#define NAZARA_PHYSICS2D_API
|
||||
#else
|
||||
#ifdef NAZARA_PHYSICS2D_BUILD
|
||||
#define NAZARA_PHYSICS2D_API NAZARA_EXPORT
|
||||
#else
|
||||
#define NAZARA_PHYSICS2D_API NAZARA_IMPORT
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#endif // NAZARA_CONFIG_PHYSICS3D_HPP
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_CONFIG_CHECK_PHYSICS_HPP
|
||||
#define NAZARA_CONFIG_CHECK_PHYSICS_HPP
|
||||
|
||||
/// Ce fichier sert à vérifier la valeur des constantes du fichier Config.hpp
|
||||
|
||||
// On force la valeur de MANAGE_MEMORY en mode debug
|
||||
#if defined(NAZARA_DEBUG) && !NAZARA_PHYSICS_MANAGE_MEMORY
|
||||
#undef NAZARA_PHYSICS_MANAGE_MEMORY
|
||||
#define NAZARA_PHYSICS3D_MANAGE_MEMORY 0
|
||||
#endif
|
||||
|
||||
#endif // NAZARA_CONFIG_CHECK_PHYSICS_HPP
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <Nazara/Physics3D/Config.hpp>
|
||||
#if NAZARA_PHYSICS_MANAGE_MEMORY
|
||||
#include <Nazara/Core/Debug/NewRedefinition.hpp>
|
||||
#endif
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
// On suppose que Debug.hpp a déjà été inclus, tout comme Config.hpp
|
||||
#if NAZARA_PHYSICS_MANAGE_MEMORY
|
||||
#undef delete
|
||||
#undef new
|
||||
#endif
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 2D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_ENUMS_PHYSICS2D_HPP
|
||||
#define NAZARA_ENUMS_PHYSICS2D_HPP
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
enum ColliderType2D
|
||||
{
|
||||
ColliderType2D_Box,
|
||||
ColliderType2D_Convex,
|
||||
ColliderType2D_Circle,
|
||||
ColliderType2D_Null,
|
||||
ColliderType2D_Segment,
|
||||
|
||||
ColliderType2D_Max = ColliderType2D_Segment
|
||||
};
|
||||
}
|
||||
|
||||
#endif // NAZARA_ENUMS_PHYSICS2D_HPP
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_PHYSWORLD2D_HPP
|
||||
#define NAZARA_PHYSWORLD2D_HPP
|
||||
|
||||
#include <Nazara/Prerequesites.hpp>
|
||||
#include <Nazara/Math/Vector2.hpp>
|
||||
#include <Nazara/Physics2D/Config.hpp>
|
||||
|
||||
struct cpSpace;
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
class NAZARA_PHYSICS2D_API PhysWorld2D
|
||||
{
|
||||
public:
|
||||
PhysWorld2D();
|
||||
PhysWorld2D(const PhysWorld2D&) = delete;
|
||||
PhysWorld2D(PhysWorld2D&&) = delete; ///TODO
|
||||
~PhysWorld2D();
|
||||
|
||||
Vector2f GetGravity() const;
|
||||
cpSpace* GetHandle() const;
|
||||
float GetStepSize() const;
|
||||
|
||||
void SetGravity(const Vector2f& gravity);
|
||||
void SetSolverModel(unsigned int model);
|
||||
void SetStepSize(float stepSize);
|
||||
|
||||
void Step(float timestep);
|
||||
|
||||
PhysWorld2D& operator=(const PhysWorld2D&) = delete;
|
||||
PhysWorld2D& operator=(PhysWorld2D&&) = delete; ///TODO
|
||||
|
||||
private:
|
||||
cpSpace* m_handle;
|
||||
float m_stepSize;
|
||||
float m_timestepAccumulator;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // NAZARA_PHYSWORLD2D_HPP
|
||||
|
|
@ -0,0 +1,33 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_PHYSICS2D_HPP
|
||||
#define NAZARA_PHYSICS2D_HPP
|
||||
|
||||
#include <Nazara/Prerequesites.hpp>
|
||||
#include <Nazara/Core/Initializer.hpp>
|
||||
#include <Nazara/Physics2D/Config.hpp>
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
class NAZARA_PHYSICS2D_API Physics2D
|
||||
{
|
||||
public:
|
||||
Physics2D() = delete;
|
||||
~Physics2D() = delete;
|
||||
|
||||
static bool Initialize();
|
||||
|
||||
static bool IsInitialized();
|
||||
|
||||
static void Uninitialize();
|
||||
|
||||
private:
|
||||
static unsigned int s_moduleReferenceCounter;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // NAZARA_PHYSICS2D_HPP
|
||||
|
|
@ -0,0 +1,76 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef NAZARA_RIGIDBODY2D_HPP
|
||||
#define NAZARA_RIGIDBODY2D_HPP
|
||||
|
||||
#include <Nazara/Prerequesites.hpp>
|
||||
#include <Nazara/Core/Enums.hpp>
|
||||
#include <Nazara/Math/Matrix4.hpp>
|
||||
#include <Nazara/Math/Quaternion.hpp>
|
||||
#include <Nazara/Math/Rect.hpp>
|
||||
#include <Nazara/Math/Vector3.hpp>
|
||||
#include <Nazara/Physics2D/Config.hpp>
|
||||
#include <Nazara/Physics2D/Collider2D.hpp>
|
||||
|
||||
struct cpBody;
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
class PhysWorld2D;
|
||||
|
||||
class NAZARA_PHYSICS2D_API RigidBody2D
|
||||
{
|
||||
public:
|
||||
RigidBody2D(PhysWorld2D* world, float mass);
|
||||
RigidBody2D(PhysWorld2D* world, float mass, Collider2DRef geom);
|
||||
RigidBody2D(const RigidBody2D& object);
|
||||
RigidBody2D(RigidBody2D&& object);
|
||||
~RigidBody2D();
|
||||
|
||||
void AddForce(const Vector2f& force, CoordSys coordSys = CoordSys_Global);
|
||||
void AddForce(const Vector2f& force, const Vector2f& point, CoordSys coordSys = CoordSys_Global);
|
||||
void AddTorque(float torque);
|
||||
|
||||
Rectf GetAABB() const;
|
||||
float GetAngularVelocity() const;
|
||||
Vector2f GetCenterOfGravity(CoordSys coordSys = CoordSys_Local) const;
|
||||
const Collider2DRef& GetGeom() const;
|
||||
float GetGravityFactor() const;
|
||||
cpBody* GetHandle() const;
|
||||
float GetMass() const;
|
||||
Vector2f GetPosition() const;
|
||||
float GetRotation() const;
|
||||
Vector2f GetVelocity() const;
|
||||
|
||||
bool IsMoveable() const;
|
||||
bool IsSleeping() const;
|
||||
|
||||
void SetAngularVelocity(float angularVelocity);
|
||||
void SetGeom(Collider2DRef geom);
|
||||
void SetGravityFactor(float gravityFactor);
|
||||
void SetMass(float mass);
|
||||
void SetMassCenter(const Vector2f& center);
|
||||
void SetPosition(const Vector2f& position);
|
||||
void SetRotation(float rotation);
|
||||
void SetVelocity(const Vector2f& velocity);
|
||||
|
||||
RigidBody2D& operator=(const RigidBody2D& object);
|
||||
RigidBody2D& operator=(RigidBody2D&& object);
|
||||
|
||||
private:
|
||||
std::vector<cpShape*> m_shapes;
|
||||
Collider2DRef m_geom;
|
||||
Vector3f m_forceAccumulator;
|
||||
Vector3f m_torqueAccumulator;
|
||||
cpBody* m_handle;
|
||||
PhysWorld2D* m_world;
|
||||
float m_gravityFactor;
|
||||
float m_mass;
|
||||
};
|
||||
}
|
||||
|
||||
#endif // NAZARA_RIGIDBODY3D_HPP
|
||||
|
|
@ -0,0 +1,56 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <Nazara/Physics2D/Collider2D.hpp>
|
||||
#include <Nazara/Physics2D/RigidBody2D.hpp>
|
||||
#include <chipmunk/chipmunk.h>
|
||||
#include <Nazara/Physics3D/Debug.hpp>
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
Collider2D::~Collider2D() = default;
|
||||
|
||||
/******************************** CircleCollider2D *********************************/
|
||||
|
||||
CircleCollider2D::CircleCollider2D(float radius, const Vector2f& offset) :
|
||||
m_offset(offset),
|
||||
m_radius(radius)
|
||||
{
|
||||
}
|
||||
|
||||
float CircleCollider2D::ComputeInertialMatrix(float mass) const
|
||||
{
|
||||
return cpMomentForCircle(mass, 0.f, m_radius, cpv(m_offset.x, m_offset.y));
|
||||
}
|
||||
|
||||
ColliderType2D CircleCollider2D::GetType() const
|
||||
{
|
||||
return ColliderType2D_Circle;
|
||||
}
|
||||
|
||||
std::vector<cpShape*> CircleCollider2D::CreateShapes(RigidBody2D* body) const
|
||||
{
|
||||
std::vector<cpShape*> shapes;
|
||||
shapes.push_back(cpCircleShapeNew(body->GetHandle(), m_radius, cpv(m_offset.x, m_offset.y)));
|
||||
|
||||
return shapes;
|
||||
}
|
||||
|
||||
/********************************* NullCollider2D **********************************/
|
||||
|
||||
ColliderType2D NullCollider2D::GetType() const
|
||||
{
|
||||
return ColliderType2D_Null;
|
||||
}
|
||||
|
||||
float NullCollider2D::ComputeInertialMatrix(float mass) const
|
||||
{
|
||||
return 0.f;
|
||||
}
|
||||
|
||||
std::vector<cpShape*> NullCollider2D::CreateShapes(RigidBody2D* body) const
|
||||
{
|
||||
return std::vector<cpShape*>();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <Nazara/Physics3D/Config.hpp>
|
||||
#if NAZARA_PHYSICS_MANAGE_MEMORY
|
||||
|
||||
#include <Nazara/Core/MemoryManager.hpp>
|
||||
#include <new> // Nécessaire ?
|
||||
|
||||
void* operator new(std::size_t size)
|
||||
{
|
||||
return Nz::MemoryManager::Allocate(size, false);
|
||||
}
|
||||
|
||||
void* operator new[](std::size_t size)
|
||||
{
|
||||
return Nz::MemoryManager::Allocate(size, true);
|
||||
}
|
||||
|
||||
void operator delete(void* pointer) noexcept
|
||||
{
|
||||
Nz::MemoryManager::Free(pointer, false);
|
||||
}
|
||||
|
||||
void operator delete[](void* pointer) noexcept
|
||||
{
|
||||
Nz::MemoryManager::Free(pointer, true);
|
||||
}
|
||||
|
||||
#endif // NAZARA_PHYSICS_MANAGE_MEMORY
|
||||
|
|
@ -0,0 +1,60 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <Nazara/Physics2D/PhysWorld2D.hpp>
|
||||
#include <chipmunk/chipmunk.h>
|
||||
#include <Nazara/Physics2D/Debug.hpp>
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
PhysWorld2D::PhysWorld2D() :
|
||||
m_stepSize(0.005f),
|
||||
m_timestepAccumulator(0.f)
|
||||
{
|
||||
m_handle = cpSpaceNew();
|
||||
cpSpaceSetUserData(m_handle, this);
|
||||
}
|
||||
|
||||
PhysWorld2D::~PhysWorld2D()
|
||||
{
|
||||
cpSpaceFree(m_handle);
|
||||
}
|
||||
|
||||
Vector2f PhysWorld2D::GetGravity() const
|
||||
{
|
||||
cpVect gravity = cpSpaceGetGravity(m_handle);
|
||||
return Vector2f(gravity.x, gravity.y);
|
||||
}
|
||||
|
||||
cpSpace* PhysWorld2D::GetHandle() const
|
||||
{
|
||||
return m_handle;
|
||||
}
|
||||
|
||||
float PhysWorld2D::GetStepSize() const
|
||||
{
|
||||
return m_stepSize;
|
||||
}
|
||||
|
||||
void PhysWorld2D::SetGravity(const Vector2f& gravity)
|
||||
{
|
||||
cpSpaceSetGravity(m_handle, cpv(gravity.x, gravity.y));
|
||||
}
|
||||
|
||||
void PhysWorld2D::SetStepSize(float stepSize)
|
||||
{
|
||||
m_stepSize = stepSize;
|
||||
}
|
||||
|
||||
void PhysWorld2D::Step(float timestep)
|
||||
{
|
||||
m_timestepAccumulator += timestep;
|
||||
|
||||
while (m_timestepAccumulator >= m_stepSize)
|
||||
{
|
||||
cpSpaceStep(m_handle, m_stepSize);
|
||||
m_timestepAccumulator -= m_stepSize;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,59 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <Nazara/Physics2D/Physics2D.hpp>
|
||||
#include <Nazara/Core/Core.hpp>
|
||||
#include <Nazara/Core/Log.hpp>
|
||||
#include <Nazara/Physics2D/Debug.hpp>
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
bool Physics2D::Initialize()
|
||||
{
|
||||
if (s_moduleReferenceCounter > 0)
|
||||
{
|
||||
s_moduleReferenceCounter++;
|
||||
return true; // Déjà initialisé
|
||||
}
|
||||
|
||||
// Initialisation des dépendances
|
||||
if (!Core::Initialize())
|
||||
{
|
||||
NazaraError("Failed to initialize core module");
|
||||
return false;
|
||||
}
|
||||
|
||||
s_moduleReferenceCounter++;
|
||||
|
||||
NazaraNotice("Initialized: Physics2D module");
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Physics2D::IsInitialized()
|
||||
{
|
||||
return s_moduleReferenceCounter != 0;
|
||||
}
|
||||
|
||||
void Physics2D::Uninitialize()
|
||||
{
|
||||
if (s_moduleReferenceCounter != 1)
|
||||
{
|
||||
// Le module est soit encore utilisé, soit pas initialisé
|
||||
if (s_moduleReferenceCounter > 1)
|
||||
s_moduleReferenceCounter--;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// Libération du module
|
||||
s_moduleReferenceCounter = 0;
|
||||
|
||||
NazaraNotice("Uninitialized: Physics2D module");
|
||||
|
||||
// Libération des dépendances
|
||||
Core::Uninitialize();
|
||||
}
|
||||
|
||||
unsigned int Physics2D::s_moduleReferenceCounter = 0;
|
||||
}
|
||||
|
|
@ -0,0 +1,266 @@
|
|||
// Copyright (C) 2015 Jérôme Leclercq
|
||||
// This file is part of the "Nazara Engine - Physics 3D module"
|
||||
// For conditions of distribution and use, see copyright notice in Config.hpp
|
||||
|
||||
#include <Nazara/Physics2D/RigidBody2D.hpp>
|
||||
#include <Nazara/Math/Algorithm.hpp>
|
||||
#include <Nazara/Physics2D/Config.hpp>
|
||||
#include <Nazara/Physics2D/PhysWorld2D.hpp>
|
||||
#include <chipmunk/chipmunk.h>
|
||||
#include <chipmunk/chipmunk_private.h>
|
||||
#include <algorithm>
|
||||
#include <Nazara/Physics3D/Debug.hpp>
|
||||
|
||||
namespace Nz
|
||||
{
|
||||
RigidBody2D::RigidBody2D(PhysWorld2D* world, float mass) :
|
||||
RigidBody2D(world, mass, nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
RigidBody2D::RigidBody2D(PhysWorld2D* world, float mass, Collider2DRef geom) :
|
||||
m_geom(),
|
||||
m_forceAccumulator(Vector3f::Zero()),
|
||||
m_torqueAccumulator(Vector3f::Zero()),
|
||||
m_world(world),
|
||||
m_gravityFactor(1.f),
|
||||
m_mass(0.f)
|
||||
{
|
||||
NazaraAssert(m_world, "Invalid world");
|
||||
|
||||
m_handle = cpBodyNew(0.f, 0.f);
|
||||
cpBodySetUserData(m_handle, this);
|
||||
cpSpaceAddBody(m_world->GetHandle(), m_handle);
|
||||
|
||||
SetGeom(geom);
|
||||
SetMass(mass);
|
||||
}
|
||||
|
||||
RigidBody2D::RigidBody2D(const RigidBody2D& object) :
|
||||
m_geom(object.m_geom),
|
||||
m_forceAccumulator(Vector3f::Zero()),
|
||||
m_torqueAccumulator(Vector3f::Zero()),
|
||||
m_world(object.m_world),
|
||||
m_gravityFactor(object.m_gravityFactor),
|
||||
m_mass(0.f)
|
||||
{
|
||||
NazaraAssert(m_world, "Invalid world");
|
||||
NazaraAssert(m_geom, "Invalid geometry");
|
||||
|
||||
m_handle = cpBodyNew(0.f, 0.f);
|
||||
cpBodySetUserData(m_handle, this);
|
||||
cpSpaceAddBody(m_world->GetHandle(), m_handle);
|
||||
|
||||
SetGeom(object.GetGeom());
|
||||
SetMass(object.GetMass());
|
||||
}
|
||||
|
||||
RigidBody2D::RigidBody2D(RigidBody2D&& object) :
|
||||
m_geom(std::move(object.m_geom)),
|
||||
m_forceAccumulator(std::move(object.m_forceAccumulator)),
|
||||
m_torqueAccumulator(std::move(object.m_torqueAccumulator)),
|
||||
m_handle(object.m_handle),
|
||||
m_world(object.m_world),
|
||||
m_gravityFactor(object.m_gravityFactor),
|
||||
m_mass(object.m_mass)
|
||||
{
|
||||
object.m_handle = nullptr;
|
||||
}
|
||||
|
||||
RigidBody2D::~RigidBody2D()
|
||||
{
|
||||
if (m_handle)
|
||||
cpBodyFree(m_handle);
|
||||
}
|
||||
|
||||
void RigidBody2D::AddForce(const Vector2f& force, CoordSys coordSys)
|
||||
{
|
||||
return AddForce(force, GetCenterOfGravity(coordSys), coordSys);
|
||||
}
|
||||
|
||||
void RigidBody2D::AddForce(const Vector2f& force, const Vector2f& point, CoordSys coordSys)
|
||||
{
|
||||
switch (coordSys)
|
||||
{
|
||||
case CoordSys_Global:
|
||||
cpBodyApplyForceAtWorldPoint(m_handle, cpv(force.x, force.y), cpv(force.x, force.y));
|
||||
break;
|
||||
|
||||
case CoordSys_Local:
|
||||
cpBodyApplyForceAtLocalPoint(m_handle, cpv(force.x, force.y), cpv(point.x, point.y));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void RigidBody2D::AddTorque(float torque)
|
||||
{
|
||||
cpBodySetTorque(m_handle, cpBodyGetTorque(m_handle) + torque);
|
||||
}
|
||||
|
||||
Rectf RigidBody2D::GetAABB() const
|
||||
{
|
||||
cpBB bb = cpBBNew(0.f, 0.f, 0.f, 0.f);
|
||||
for (cpShape* shape : m_shapes)
|
||||
bb = cpBBMerge(bb, cpShapeGetBB(shape));
|
||||
|
||||
return Rectf(bb.l, bb.t, bb.r - bb.l, bb.b - bb.t);
|
||||
}
|
||||
|
||||
float RigidBody2D::GetAngularVelocity() const
|
||||
{
|
||||
return cpBodyGetAngularVelocity(m_handle);
|
||||
}
|
||||
|
||||
const Collider2DRef& RigidBody2D::GetGeom() const
|
||||
{
|
||||
return m_geom;
|
||||
}
|
||||
|
||||
float RigidBody2D::GetGravityFactor() const
|
||||
{
|
||||
return m_gravityFactor;
|
||||
}
|
||||
|
||||
cpBody* RigidBody2D::GetHandle() const
|
||||
{
|
||||
return m_handle;
|
||||
}
|
||||
|
||||
float RigidBody2D::GetMass() const
|
||||
{
|
||||
return m_mass;
|
||||
}
|
||||
|
||||
Vector2f RigidBody2D::GetCenterOfGravity(CoordSys coordSys) const
|
||||
{
|
||||
cpVect cog = cpBodyGetCenterOfGravity(m_handle);
|
||||
|
||||
switch (coordSys)
|
||||
{
|
||||
case CoordSys_Global:
|
||||
cog = cpBodyLocalToWorld(m_handle, cog);
|
||||
break;
|
||||
|
||||
case CoordSys_Local:
|
||||
break; // Nothing to do
|
||||
}
|
||||
|
||||
return Vector2f(cog.x, cog.y);
|
||||
}
|
||||
|
||||
Vector2f RigidBody2D::GetPosition() const
|
||||
{
|
||||
cpVect pos = cpBodyGetPosition(m_handle);
|
||||
return Vector2f(pos.x, pos.y);
|
||||
}
|
||||
|
||||
float RigidBody2D::GetRotation() const
|
||||
{
|
||||
return cpBodyGetAngle(m_handle);
|
||||
}
|
||||
|
||||
Vector2f RigidBody2D::GetVelocity() const
|
||||
{
|
||||
cpVect vel = cpBodyGetVelocity(m_handle);
|
||||
return Vector2f(vel.x, vel.y);
|
||||
}
|
||||
|
||||
bool RigidBody2D::IsMoveable() const
|
||||
{
|
||||
return m_mass > 0.f;
|
||||
}
|
||||
|
||||
bool RigidBody2D::IsSleeping() const
|
||||
{
|
||||
return cpBodyIsSleeping(m_handle) != 0;
|
||||
}
|
||||
|
||||
void RigidBody2D::SetAngularVelocity(float angularVelocity)
|
||||
{
|
||||
cpBodySetAngularVelocity(m_handle, angularVelocity);
|
||||
}
|
||||
|
||||
void RigidBody2D::SetGeom(Collider2DRef geom)
|
||||
{
|
||||
if (m_geom.Get() != geom)
|
||||
{
|
||||
for (cpShape* shape : m_shapes)
|
||||
cpBodyRemoveShape(m_handle, shape);
|
||||
|
||||
if (geom)
|
||||
m_geom = geom;
|
||||
else
|
||||
m_geom = NullCollider2D::New();
|
||||
|
||||
m_shapes = m_geom->CreateShapes(this);
|
||||
}
|
||||
}
|
||||
|
||||
void RigidBody2D::SetGravityFactor(float gravityFactor)
|
||||
{
|
||||
m_gravityFactor = gravityFactor;
|
||||
}
|
||||
|
||||
void RigidBody2D::SetMass(float mass)
|
||||
{
|
||||
if (m_mass > 0.f)
|
||||
{
|
||||
if (mass > 0.f)
|
||||
cpBodySetMass(m_handle, mass);
|
||||
else
|
||||
cpBodySetType(m_handle, CP_BODY_TYPE_STATIC);
|
||||
}
|
||||
else if (mass > 0.f)
|
||||
{
|
||||
if (cpBodyGetType(m_handle) == CP_BODY_TYPE_STATIC)
|
||||
cpBodySetType(m_handle, CP_BODY_TYPE_DYNAMIC);
|
||||
}
|
||||
|
||||
m_mass = mass;
|
||||
}
|
||||
|
||||
void RigidBody2D::SetMassCenter(const Vector2f& center)
|
||||
{
|
||||
if (m_mass > 0.f)
|
||||
cpBodySetCenterOfGravity(m_handle, cpv(center.x, center.y));
|
||||
}
|
||||
|
||||
void RigidBody2D::SetPosition(const Vector2f& position)
|
||||
{
|
||||
cpBodySetPosition(m_handle, cpv(position.x, position.y));
|
||||
}
|
||||
|
||||
void RigidBody2D::SetRotation(float rotation)
|
||||
{
|
||||
cpBodySetAngle(m_handle, rotation);
|
||||
}
|
||||
|
||||
void RigidBody2D::SetVelocity(const Vector2f& velocity)
|
||||
{
|
||||
cpBodySetVelocity(m_handle, cpv(velocity.x, velocity.y));
|
||||
}
|
||||
|
||||
RigidBody2D& RigidBody2D::operator=(const RigidBody2D& object)
|
||||
{
|
||||
RigidBody2D physObj(object);
|
||||
return operator=(std::move(physObj));
|
||||
}
|
||||
|
||||
RigidBody2D& RigidBody2D::operator=(RigidBody2D&& object)
|
||||
{
|
||||
if (m_handle)
|
||||
cpBodyFree(m_handle);
|
||||
|
||||
m_handle = object.m_handle;
|
||||
m_forceAccumulator = std::move(object.m_forceAccumulator);
|
||||
m_geom = std::move(object.m_geom);
|
||||
m_gravityFactor = object.m_gravityFactor;
|
||||
m_mass = object.m_mass;
|
||||
m_torqueAccumulator = std::move(object.m_torqueAccumulator);
|
||||
m_world = object.m_world;
|
||||
|
||||
object.m_handle = nullptr;
|
||||
|
||||
return *this;
|
||||
}
|
||||
}
|
||||
Loading…
Reference in New Issue