add serialize for RigidbodyComponent linear/angular drag and gravity, change the physx API for c++ and c#, fixed rotate bug(using radians to storage), some little code tweaks

This commit is contained in:
2026-01-12 18:58:11 +08:00
parent f857d8e791
commit bed57f18d3
17 changed files with 531 additions and 239 deletions

View File

@ -10,6 +10,7 @@
#include "glm/gtx/matrix_decompose.hpp" #include "glm/gtx/matrix_decompose.hpp"
#include "Prism/Core/Input.h" #include "Prism/Core/Input.h"
#include "Prism/Core/Math/Math.h"
#include "Prism/Editor/PhysicsSettingsWindow.h" #include "Prism/Editor/PhysicsSettingsWindow.h"
#include "Prism/Physics/Physics3D.h" #include "Prism/Physics/Physics3D.h"
#include "Prism/Renderer/Renderer2D.h" #include "Prism/Renderer/Renderer2D.h"
@ -22,16 +23,6 @@ namespace Prism
None = 0, ColorProperty = 1, SliderProperty = 2, DragProperty = 4 None = 0, ColorProperty = 1, SliderProperty = 2, DragProperty = 4
}; };
static std::tuple<glm::vec3, glm::quat, glm::vec3> GetTransformDecomposition(const glm::mat4& transform)
{
glm::vec3 scale, translation, skew;
glm::vec4 perspective;
glm::quat orientation;
glm::decompose(transform, scale, orientation, translation, skew, perspective);
return { translation, orientation, scale };
}
bool Property(const std::string& name, bool& value) bool Property(const std::string& name, bool& value)
{ {
ImGui::Text(name.c_str()); ImGui::Text(name.c_str());
@ -236,13 +227,12 @@ namespace Prism
if (selection.Entity.HasComponent<BoxCollider2DComponent>()) if (selection.Entity.HasComponent<BoxCollider2DComponent>())
{ {
const auto& size = selection.Entity.GetComponent<BoxCollider2DComponent>().Size; const auto& size = selection.Entity.GetComponent<BoxCollider2DComponent>().Size;
auto [translation, rotationQuat, scale] = GetTransformDecomposition(selection.Entity.GetComponent<TransformComponent>().GetTransform()); const auto& transform = selection.Entity.GetComponent<TransformComponent>();
const glm::vec3 rotation = glm::eulerAngles(rotationQuat);
Renderer::BeginRenderPass(SceneRenderer::GetFinalRenderPass(), false); Renderer::BeginRenderPass(SceneRenderer::GetFinalRenderPass(), false);
const auto viewProj = m_EditorCamera.GetViewProjection(); const auto viewProj = m_EditorCamera.GetViewProjection();
Renderer2D::BeginScene(viewProj, false); Renderer2D::BeginScene(viewProj, false);
Renderer2D::DrawRotatedQuad({ translation.x, translation.y }, size * 2.0f, glm::degrees(rotation.z), { 1.0f, 0.0f, 1.0f, 1.0f }); Renderer2D::DrawRotatedQuad({ transform.Translation.x, transform.Translation.y }, size * 2.0f, transform.Rotation.z, { 1.0f, 0.0f, 1.0f, 1.0f });
Renderer2D::EndScene(); Renderer2D::EndScene();
Renderer::EndRenderPass(); Renderer::EndRenderPass();
} }
@ -802,10 +792,18 @@ namespace Prism
nullptr, nullptr,
snap ? snapValues : nullptr); snap ? snapValues : nullptr);
auto [translation, rotation, scale] = GetTransformDecomposition(transform); if (ImGuizmo::IsUsing())
{
glm::vec3 translation, rotation, scale;
Math::DecomposeTransform(transform, translation,rotation,scale);
entityTransform.Translation = translation; entityTransform.Translation = translation;
entityTransform.Rotation = glm::degrees(glm::eulerAngles(rotation));
glm::vec3 deltaRotation = rotation - entityTransform.Rotation;
entityTransform.Rotation += deltaRotation;
entityTransform.Scale = scale; entityTransform.Scale = scale;
}
}else }else
{ {
glm::mat4 transformBase = entityTransform.GetTransform() * selection.Mesh->Transform; glm::mat4 transformBase = entityTransform.GetTransform() * selection.Mesh->Transform;
@ -817,9 +815,12 @@ namespace Prism
nullptr, nullptr,
snap ? snapValues : nullptr); snap ? snapValues : nullptr);
if (ImGuizmo::IsUsing())
{
selection.Mesh->Transform = glm::inverse(entityTransform.GetTransform()) * transformBase; selection.Mesh->Transform = glm::inverse(entityTransform.GetTransform()) * transformBase;
} }
} }
}
ImGui::End(); ImGui::End();
ImGui::PopStyleVar(); ImGui::PopStyleVar();

View File

@ -0,0 +1,88 @@
//
// Created by Atdunbg on 2026/1/12.
//
#include "Math.h"
#define GLM_ENABLE_EXPERIMENTAL
#include <glm/gtx/matrix_decompose.hpp>
#include <glm/gtx/norm.hpp>
#include <glm/gtx/quaternion.hpp>
namespace Prism::Math
{
bool DecomposeTransform(const glm::mat4& transform, glm::vec3& translation, glm::vec3& rotation, glm::vec3& scale)
{
using namespace glm;
using T = float;
mat4 LocalMatrix(transform);
// Normalize the matrix.
if (epsilonEqual(LocalMatrix[3][3], static_cast<float>(0), epsilon<T>()))
return false;
// First, isolate perspective. This is the messiest.
if (
epsilonNotEqual(LocalMatrix[0][3], static_cast<T>(0), epsilon<T>()) ||
epsilonNotEqual(LocalMatrix[1][3], static_cast<T>(0), epsilon<T>()) ||
epsilonNotEqual(LocalMatrix[2][3], static_cast<T>(0), epsilon<T>()))
{
// Clear the perspective partition
LocalMatrix[0][3] = LocalMatrix[1][3] = LocalMatrix[2][3] = static_cast<T>(0);
LocalMatrix[3][3] = static_cast<T>(1);
}
// Next take care of translation (easy).
translation = vec3(LocalMatrix[3]);
LocalMatrix[3] = vec4(0, 0, 0, LocalMatrix[3].w);
vec3 Row[3];
// Now get scale and shear.
for (length_t i = 0; i < 3; ++i)
for (length_t j = 0; j < 3; ++j)
Row[i][j] = LocalMatrix[i][j];
// Compute X scale factor and normalize first row.
scale.x = length(Row[0]);
Row[0] = detail::scale(Row[0], static_cast<T>(1));
scale.y = length(Row[1]);
Row[1] = detail::scale(Row[1], static_cast<T>(1));
scale.z = length(Row[2]);
Row[2] = detail::scale(Row[2], static_cast<T>(1));
// At this point, the matrix (in rows[]) is orthonormal.
// Check for a coordinate system flip. If the determinant
// is -1, then negate the matrix and the scaling factors.
#if 0
vec3 Pdum3;
Pdum3 = cross(Row[1], Row[2]); // v3Cross(row[1], row[2], Pdum3);
if (dot(Row[0], Pdum3) < 0)
{
for (length_t i = 0; i < 3; i++)
{
scale[i] *= static_cast<T>(-1);
Row[i] *= static_cast<T>(-1);
}
}
#endif
rotation.y = asin(-Row[0][2]);
if (cos(rotation.y) != 0) {
rotation.x = atan2(Row[1][2], Row[2][2]);
rotation.z = atan2(Row[0][1], Row[0][0]);
}
else {
rotation.x = atan2(-Row[2][0], Row[1][1]);
rotation.z = 0;
}
return true;
}
}

View File

@ -0,0 +1,16 @@
//
// Created by Atdunbg on 2026/1/12.
//
#ifndef PRISM_MATH_H
#define PRISM_MATH_H
#include "glm/fwd.hpp"
#include "Prism/Core/Core.h"
namespace Prism::Math
{
PRISM_API bool DecomposeTransform(const glm::mat4& transform, glm::vec3& translation, glm::vec3& rotation, glm::vec3& scale);
}
#endif //PRISM_MATH_H

View File

@ -462,7 +462,11 @@ namespace Prism
{ {
DrawVec3Control("Translation", transform.Translation); DrawVec3Control("Translation", transform.Translation);
DrawVec3Control("Rotation", transform.Rotation);
glm::vec3 rotation = glm::degrees(transform.Rotation);
if (DrawVec3Control("Rotation", rotation))
transform.Rotation = glm::radians(rotation);
DrawVec3Control("Scale", transform.Scale, 1.0f); DrawVec3Control("Scale", transform.Scale, 1.0f);
ImGui::TreePop(); ImGui::TreePop();
@ -908,9 +912,9 @@ namespace Prism
{ {
mcc.CollisionMesh = Ref<Mesh>::Create(file); mcc.CollisionMesh = Ref<Mesh>::Create(file);
if (mcc.IsConvex) if (mcc.IsConvex)
PhysicsWrappers::CreateConvexMesh(mcc, true); PhysicsWrappers::CreateConvexMesh(mcc);
else else
PhysicsWrappers::CreateTriangleMesh(mcc, true); PhysicsWrappers::CreateTriangleMesh(mcc);
} }
} }
ImGui::EndColumns(); ImGui::EndColumns();
@ -921,9 +925,9 @@ namespace Prism
if (mcc.CollisionMesh) if (mcc.CollisionMesh)
{ {
if (mcc.IsConvex) if (mcc.IsConvex)
PhysicsWrappers::CreateConvexMesh(mcc, true); PhysicsWrappers::CreateConvexMesh(mcc);
else else
PhysicsWrappers::CreateTriangleMesh(mcc, true); PhysicsWrappers::CreateTriangleMesh(mcc);
} }
} }

View File

@ -5,8 +5,6 @@
#include "Physics3D.h" #include "Physics3D.h"
#define GLM_ENABLE_EXPERIMENTAL #define GLM_ENABLE_EXPERIMENTAL
#include <glm/gtx/quaternion.hpp>
#include "glm/gtx/matrix_decompose.hpp"
#include "Prism/Scene/Entity.h" #include "Prism/Scene/Entity.h"
#include "PhysicsLayer.h" #include "PhysicsLayer.h"
@ -17,11 +15,7 @@
namespace Prism namespace Prism
{ {
static physx::PxScene* s_Scene; static physx::PxScene* s_Scene;
static std::vector<Ref<PhysicsActor>> s_SimulatedActors; static std::vector<Ref<PhysicsActor>> s_Actors;
static std::vector<Ref<PhysicsActor>> s_StaticActors;
static Entity* s_EntityStorageBuffer;
static uint32_t s_EntityBufferCount;
static int s_EntityStorageBufferPosition;
static float s_SimulationTime = 0.0f; static float s_SimulationTime = 0.0f;
static PhysicsSettings s_Settings; static PhysicsSettings s_Settings;
@ -68,41 +62,28 @@ namespace Prism
} }
} }
void Physics3D::CreateActor(Entity e) Ref<PhysicsActor> Physics3D::CreateActor(Entity e)
{ {
PM_CORE_ASSERT(s_Scene); PM_CORE_ASSERT(s_Scene);
if (!e.HasComponent<RigidBodyComponent>())
{
PM_CORE_WARN("Trying to create PhysX actor from a non-rigidbody actor!");
return;
}
if (!e.HasComponent<PhysicsMaterialComponent>())
{
PM_CORE_WARN("Trying to create PhysX actor without a PhysicsMaterialComponent!");
return;
}
RigidBodyComponent& rigidbody = e.GetComponent<RigidBodyComponent>();
const auto transform = e.Transform();
Ref<PhysicsActor> actor = Ref<PhysicsActor>::Create(e); Ref<PhysicsActor> actor = Ref<PhysicsActor>::Create(e);
s_Actors.push_back(actor);
if (actor->IsDynamic()) actor->Spawn();
s_SimulatedActors.push_back(actor); return actor;
else
s_StaticActors.push_back(actor);
Entity* entityStorage = &s_EntityStorageBuffer[s_EntityStorageBufferPosition];
*entityStorage = e;
actor->SetRuntimeDataInternal((void *)entityStorage, s_EntityStorageBufferPosition);
s_EntityStorageBufferPosition++;
} }
void Physics3D::Simulate(TimeStep ts) Ref<PhysicsActor> Physics3D::GetActorForEntity(const Entity entity)
{
for (auto& actor : s_Actors)
{
if (actor->GetEntity() == entity)
return actor;
}
return nullptr;
}
void Physics3D::Simulate(const TimeStep ts)
{ {
// TODO: Allow projects to control the fixed step amount // TODO: Allow projects to control the fixed step amount
@ -113,13 +94,13 @@ namespace Prism
s_SimulationTime -= s_Settings.FixedTimestep; s_SimulationTime -= s_Settings.FixedTimestep;
for (auto& actor : s_SimulatedActors) for (auto& actor : s_Actors)
actor->Update(s_Settings.FixedTimestep); actor->Update(s_Settings.FixedTimestep);
s_Scene->simulate(s_Settings.FixedTimestep); s_Scene->simulate(s_Settings.FixedTimestep);
s_Scene->fetchResults(true); s_Scene->fetchResults(true);
for (auto& actor : s_SimulatedActors) for (auto& actor : s_Actors)
actor->SynchronizeTransform(); actor->SynchronizeTransform();
} }
@ -127,12 +108,7 @@ namespace Prism
{ {
PM_CORE_ASSERT(s_Scene); PM_CORE_ASSERT(s_Scene);
delete[] s_EntityStorageBuffer; s_Actors.clear();
s_EntityStorageBuffer = nullptr;
s_EntityStorageBufferPosition = 0;
s_SimulatedActors.clear();
s_StaticActors.clear();
s_Scene->release(); s_Scene->release();
s_Scene = nullptr; s_Scene = nullptr;
} }
@ -160,6 +136,7 @@ namespace Prism
PhysicsWrappers::DisconnectPVD(); PhysicsWrappers::DisconnectPVD();
} }
/*
void Physics3D::ExpandEntityBuffer(const uint32_t entityCount) void Physics3D::ExpandEntityBuffer(const uint32_t entityCount)
{ {
PM_CORE_ASSERT(s_Scene); PM_CORE_ASSERT(s_Scene);
@ -174,11 +151,16 @@ namespace Prism
Entity& e = s_EntityStorageBuffer[i]; Entity& e = s_EntityStorageBuffer[i];
const auto& rb = e.GetComponent<RigidBodyComponent>(); const auto& rb = e.GetComponent<RigidBodyComponent>();
Ref<PhysicsActor> actor = GetActorForEntity(e);
actor->SetUserData(&temp[rb.EntityBufferIndex]);
/*
if (rb.RuntimeActor) if (rb.RuntimeActor)
{ {
auto* actor = static_cast<physx::PxRigidActor*>(rb.RuntimeActor); auto* actor = static_cast<physx::PxRigidActor*>(rb.RuntimeActor);
actor->userData = &temp[rb.EntityBufferIndex]; actor->userData = &temp[rb.EntityBufferIndex];
} }
#1#
} }
delete[] s_EntityStorageBuffer; delete[] s_EntityStorageBuffer;
@ -191,5 +173,6 @@ namespace Prism
s_EntityBufferCount = entityCount; s_EntityBufferCount = entityCount;
} }
} }
*/
} }

View File

@ -11,6 +11,8 @@
namespace Prism namespace Prism
{ {
class PhysicsActor;
enum class ForceMode : uint16_t enum class ForceMode : uint16_t
{ {
Force = 0, Force = 0,
@ -70,10 +72,12 @@ namespace Prism
static void Shutdown(); static void Shutdown();
static PhysicsSettings& GetSettings(); static PhysicsSettings& GetSettings();
static void ExpandEntityBuffer(uint32_t entityCount); // static void ExpandEntityBuffer(uint32_t entityCount);
static void CreateScene(); static void CreateScene();
static void CreateActor(Entity e); static Ref<PhysicsActor> CreateActor(Entity e);
static Ref<PhysicsActor> GetActorForEntity(Entity entity);
static void Simulate(TimeStep ts); static void Simulate(TimeStep ts);

View File

@ -9,24 +9,179 @@
#include "PhysicsWrappers.h" #include "PhysicsWrappers.h"
#include "PxRigidActor.h" #include "PxRigidActor.h"
#include "Prism/Script/ScriptEngine.h" #include "Prism/Script/ScriptEngine.h"
#include <glm/gtx/compatibility.hpp>
namespace Prism namespace Prism
{ {
PhysicsActor::PhysicsActor(Entity entity) PhysicsActor::PhysicsActor(Entity entity)
: m_Entity(entity), m_RigidBody(entity.GetComponent<RigidBodyComponent>()) : m_Entity(entity), m_RigidBody(entity.GetComponent<RigidBodyComponent>())
{
if (!m_Entity.HasComponent<PhysicsMaterialComponent>())
{
m_Material.StaticFriction = 1.0f;
m_Material.DynamicFriction = 1.0f;
m_Material.Bounciness = 0.0f;
}
else
{ {
m_Material = entity.GetComponent<PhysicsMaterialComponent>(); m_Material = entity.GetComponent<PhysicsMaterialComponent>();
}
Create(); Initialize();
} }
PhysicsActor::~PhysicsActor() PhysicsActor::~PhysicsActor()
{
if (m_ActorInternal && m_ActorInternal->isReleasable())
{ {
m_ActorInternal->release(); m_ActorInternal->release();
m_ActorInternal = nullptr; m_ActorInternal = nullptr;
} }
}
void PhysicsActor::Create() glm::vec3 PhysicsActor::GetPosition() const
{
return FromPhysXVector(m_ActorInternal->getGlobalPose().p);
}
glm::quat PhysicsActor::GetRotation() const
{
return FromPhysXQuat(m_ActorInternal->getGlobalPose().q);
}
void PhysicsActor::Rotate(const glm::vec3& rotation) const
{
physx::PxTransform transform = m_ActorInternal->getGlobalPose();
const auto r = glm::radians(rotation);
transform.q *= physx::PxQuat(r.x, { 1.0f, 0.0f, 0.0f }) *
physx::PxQuat(r.y, { 0.0f, 1.0f, 0.0f }) *
physx::PxQuat(r.z, { 0.0f, 0.0f, 1.0f });
m_ActorInternal->setGlobalPose(transform);
}
float PhysicsActor::GetMass() const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to set mass of non-dynamic PhysicsActor.");
return 0.0f;
}
const auto actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
return actor->getMass();
}
void PhysicsActor::SetMass(const float mass) const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to set mass of non-dynamic PhysicsActor.");
return;
}
const auto actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
physx::PxRigidBodyExt::setMassAndUpdateInertia(*actor, mass);
m_RigidBody.Mass = mass;
}
void PhysicsActor::AddForce(const glm::vec3& force, ForceMode forceMode) const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to add force to non-dynamic PhysicsActor.");
return;
}
auto* actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
actor->addForce(ToPhysXVector(force), static_cast<physx::PxForceMode::Enum>(forceMode));
}
void PhysicsActor::AddTorque(const glm::vec3& torque, ForceMode forceMode) const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to add torque to non-dynamic PhysicsActor.");
return;
}
const auto actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
actor->addTorque(ToPhysXVector(torque), static_cast<physx::PxForceMode::Enum>(forceMode));
}
glm::vec3 PhysicsActor::GetLinearVelocity() const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to get velocity of non-dynamic PhysicsActor.");
return glm::vec3(0.0f);
}
const auto actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
return FromPhysXVector(actor->getLinearVelocity());
}
void PhysicsActor::SetLinearVelocity(const glm::vec3& velocity) const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to set velocity of non-dynamic PhysicsActor.");
return;
}
if (!glm::all(glm::isfinite(velocity)))
return;
auto* actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
actor->setLinearVelocity(ToPhysXVector(velocity));
}
glm::vec3 PhysicsActor::GetAngularVelocity() const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to get angular velocity of non-dynamic PhysicsActor.");
return glm::vec3(0.0f);
}
const auto* actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
return FromPhysXVector(actor->getAngularVelocity());
}
void PhysicsActor::SetAngularVelocity(const glm::vec3& velocity) const
{
if (!IsDynamic())
{
PM_CORE_WARN("Trying to set angular velocity of non-dynamic PhysicsActor.");
return;
}
if (!glm::all(glm::isfinite(velocity)))
return;
auto* actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
actor->setAngularVelocity(ToPhysXVector(velocity));
}
void PhysicsActor::SetLinearDrag(const float drag) const
{
if (!IsDynamic())
return;
auto* actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
actor->setLinearDamping(drag);
}
void PhysicsActor::SetAngularDrag(const float drag) const
{
if (!IsDynamic())
return;
const auto actor = static_cast<physx::PxRigidDynamic*>(m_ActorInternal);
actor->setAngularDamping(drag);
}
void PhysicsActor::Initialize()
{ {
physx::PxPhysics& physics = PhysicsWrappers::GetPhysics(); physx::PxPhysics& physics = PhysicsWrappers::GetPhysics();
@ -51,11 +206,11 @@ namespace Prism
actor->setActorFlag(physx::PxActorFlag::eDISABLE_GRAVITY, m_RigidBody.DisableGravity); actor->setActorFlag(physx::PxActorFlag::eDISABLE_GRAVITY, m_RigidBody.DisableGravity);
actor->setSolverIterationCounts(settings.SolverIterations, settings.SolverVelocityIterations); actor->setSolverIterationCounts(settings.SolverIterations, settings.SolverVelocityIterations);
physx::PxRigidBodyExt::updateMassAndInertia(*actor, m_RigidBody.Mass); physx::PxRigidBodyExt::setMassAndUpdateInertia(*actor, m_RigidBody.Mass);
m_ActorInternal = actor; m_ActorInternal = actor;
} }
physx::PxMaterial* physicsMat = physics.createMaterial(m_Material.StaticFriction, m_Material.DynamicFriction, m_Material.Bounciness); const physx::PxMaterial* physicsMat = physics.createMaterial(m_Material.StaticFriction, m_Material.DynamicFriction, m_Material.Bounciness);
if (m_Entity.HasComponent<BoxColliderComponent>()) PhysicsWrappers::AddBoxCollider(*this, *physicsMat); if (m_Entity.HasComponent<BoxColliderComponent>()) PhysicsWrappers::AddBoxCollider(*this, *physicsMat);
if (m_Entity.HasComponent<SphereColliderComponent>()) PhysicsWrappers::AddSphereCollider(*this, *physicsMat); if (m_Entity.HasComponent<SphereColliderComponent>()) PhysicsWrappers::AddSphereCollider(*this, *physicsMat);
if (m_Entity.HasComponent<CapsuleColliderComponent>()) PhysicsWrappers::AddCapsuleCollider(*this, *physicsMat); if (m_Entity.HasComponent<CapsuleColliderComponent>()) PhysicsWrappers::AddCapsuleCollider(*this, *physicsMat);
@ -65,18 +220,15 @@ namespace Prism
m_RigidBody.Layer = 0; m_RigidBody.Layer = 0;
SetLayer(m_RigidBody.Layer); SetLayer(m_RigidBody.Layer);
m_ActorInternal->userData = &m_Entity;
}
void PhysicsActor::Spawn() const
{
static_cast<physx::PxScene*>(Physics3D::GetPhysicsScene())->addActor(*m_ActorInternal); static_cast<physx::PxScene*>(Physics3D::GetPhysicsScene())->addActor(*m_ActorInternal);
} }
void PhysicsActor::SetRuntimeDataInternal(void* entityStorage, int storageBufferPosition) void PhysicsActor::Update(const float fixedTimestep) const
{
m_ActorInternal->userData = entityStorage;
m_RigidBody.RuntimeActor = m_ActorInternal;
m_RigidBody.EntityBufferIndex = storageBufferPosition;
}
void PhysicsActor::Update(float fixedTimestep)
{ {
if (!ScriptEngine::IsEntityModuleValid(m_Entity)) if (!ScriptEngine::IsEntityModuleValid(m_Entity))
return; return;
@ -85,15 +237,47 @@ namespace Prism
} }
void PhysicsActor::SynchronizeTransform() void PhysicsActor::SynchronizeTransform()
{
if (IsDynamic())
{ {
TransformComponent& transform = m_Entity.Transform(); TransformComponent& transform = m_Entity.Transform();
physx::PxRigidActor* actor = static_cast<physx::PxRigidActor*>(m_RigidBody.RuntimeActor); const physx::PxTransform actorPose = m_ActorInternal->getGlobalPose();
physx::PxTransform actorPose = actor->getGlobalPose();
transform.Translation = FromPhysXVector(actorPose.p); transform.Translation = FromPhysXVector(actorPose.p);
transform.Rotation = glm::eulerAngles(FromPhysXQuat(actorPose.q)); transform.Rotation = glm::eulerAngles(FromPhysXQuat(actorPose.q));
const auto& a = transform.Rotation;
}
else
{
// Synchronize Physics Actor with static Entity
m_ActorInternal->setGlobalPose(ToPhysXTransform(m_Entity.Transform()));
}
} }
void PhysicsActor::SetLayer(uint32_t layer) void PhysicsActor::AddCollisionShape(physx::PxShape* shape)
{
const int shapeType = shape->getGeometry().getType();
if (m_Shapes.find(shapeType) == m_Shapes.end())
{
m_Shapes[shapeType] = std::vector<physx::PxShape*>();
}
m_Shapes[shapeType].push_back(shape);
}
void PhysicsActor::RemoveCollisionsShapes(const int type)
{
if (m_Shapes.find(type) != m_Shapes.end())
{
for (const auto shape : m_Shapes[type])
shape->release();
m_Shapes[type].clear();
m_Shapes.erase(type);
}
}
void PhysicsActor::SetLayer(const uint32_t layer) const
{ {
physx::PxAllocatorCallback& allocator = PhysicsWrappers::GetAllocator(); physx::PxAllocatorCallback& allocator = PhysicsWrappers::GetAllocator();
@ -108,7 +292,7 @@ namespace Prism
const physx::PxU32 numShapes = m_ActorInternal->getNbShapes(); const physx::PxU32 numShapes = m_ActorInternal->getNbShapes();
physx::PxShape** shapes = (physx::PxShape**)allocator.allocate(sizeof(physx::PxShape*) * numShapes, "", "", 0); physx::PxShape** shapes = static_cast<physx::PxShape**>(allocator.allocate(sizeof(physx::PxShape*) * numShapes, "", "", 0));
m_ActorInternal->getShapes(shapes, numShapes); m_ActorInternal->getShapes(shapes, numShapes);
for (physx::PxU32 i = 0; i < numShapes; i++) for (physx::PxU32 i = 0; i < numShapes; i++)

View File

@ -4,45 +4,70 @@
#ifndef PRISM_PHYSICSACTOR_H #ifndef PRISM_PHYSICSACTOR_H
#define PRISM_PHYSICSACTOR_H #define PRISM_PHYSICSACTOR_H
#include "Physics3D.h"
#include "Prism/Core/Ref.h" #include "Prism/Core/Ref.h"
#include "Prism/Scene/Entity.h" #include "Prism/Scene/Entity.h"
namespace physx namespace physx
{ {
class PxRigidActor; class PxRigidActor;
class PxShape;
} }
namespace Prism namespace Prism
{ {
class PhysicsActor : public RefCounted class PRISM_API PhysicsActor : public RefCounted
{ {
public: public:
PhysicsActor(Entity entity); PhysicsActor(Entity entity);
~PhysicsActor(); ~PhysicsActor();
void Update(float fixedTimestep); glm::vec3 GetPosition() const;
void SynchronizeTransform(); glm::quat GetRotation() const;
void SetLayer(uint32_t layer); void Rotate(const glm::vec3& rotation) const;
float GetMass() const;
void SetMass(float mass) const;
void AddForce(const glm::vec3& force, ForceMode forceMode) const;
void AddTorque(const glm::vec3& torque, ForceMode forceMode) const;
glm::vec3 GetLinearVelocity() const;
void SetLinearVelocity(const glm::vec3& velocity) const;
glm::vec3 GetAngularVelocity() const;
void SetAngularVelocity(const glm::vec3& velocity) const;
void SetLinearDrag(float drag) const;
void SetAngularDrag(float drag) const;
void SetLayer(uint32_t layer) const;
bool IsDynamic() const { return m_RigidBody.BodyType == RigidBodyComponent::Type::Dynamic; } bool IsDynamic() const { return m_RigidBody.BodyType == RigidBodyComponent::Type::Dynamic; }
Entity& GetEntity() { return m_Entity; } Entity& GetEntity() { return m_Entity; }
private: private:
void Create(); void Initialize();
void Spawn() const;
void SetRuntimeDataInternal(void* entityStorage, int storageBufferPosition); void Update(float fixedTimestep) const;
void SynchronizeTransform();
void AddCollisionShape(physx::PxShape* shape);
void RemoveCollisionsShapes(int type);
private: private:
Entity m_Entity; Entity m_Entity;
RigidBodyComponent& m_RigidBody; RigidBodyComponent& m_RigidBody;
PhysicsMaterialComponent m_Material; PhysicsMaterialComponent m_Material;
physx::PxRigidActor* m_ActorInternal; physx::PxRigidActor* m_ActorInternal{};
friend class Physics3D; friend class Physics3D;
friend class PhysicsWrappers; friend class PhysicsWrappers;
std::unordered_map<int, std::vector<physx::PxShape*>> m_Shapes;
}; };
} }

View File

@ -179,6 +179,8 @@ namespace Prism
void PhysicsWrappers::AddBoxCollider(PhysicsActor& actor, const physx::PxMaterial& material) void PhysicsWrappers::AddBoxCollider(PhysicsActor& actor, const physx::PxMaterial& material)
{ {
actor.RemoveCollisionsShapes(physx::PxGeometryType::eBOX);
const auto& collider = actor.m_Entity.GetComponent<BoxColliderComponent>(); const auto& collider = actor.m_Entity.GetComponent<BoxColliderComponent>();
const glm::vec3 scale = actor.m_Entity.Transform().Scale; const glm::vec3 scale = actor.m_Entity.Transform().Scale;
glm::vec3 colliderSize = collider.Size; glm::vec3 colliderSize = collider.Size;
@ -195,10 +197,14 @@ namespace Prism
shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger);
shape->setLocalPose(ToPhysXTransform(glm::translate(glm::mat4(1.0F), collider.Offset))); shape->setLocalPose(ToPhysXTransform(glm::translate(glm::mat4(1.0F), collider.Offset)));
actor.AddCollisionShape(shape);
} }
void PhysicsWrappers::AddSphereCollider(PhysicsActor& actor, const physx::PxMaterial& material) void PhysicsWrappers::AddSphereCollider(PhysicsActor& actor, const physx::PxMaterial& material)
{ {
actor.RemoveCollisionsShapes(physx::PxGeometryType::eSPHERE);
const auto& collider = actor.m_Entity.GetComponent<SphereColliderComponent>(); const auto& collider = actor.m_Entity.GetComponent<SphereColliderComponent>();
const glm::vec3 scale = actor.m_Entity.Transform().Scale; const glm::vec3 scale = actor.m_Entity.Transform().Scale;
float colliderRadius = collider.Radius; float colliderRadius = collider.Radius;
@ -211,10 +217,14 @@ namespace Prism
// physx::PxShape* shape = physx::PxRigidActorExt::createExclusiveShape(actor, sphereGeometry, material); // physx::PxShape* shape = physx::PxRigidActorExt::createExclusiveShape(actor, sphereGeometry, material);
shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger);
shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger);
actor.AddCollisionShape(shape);
} }
void PhysicsWrappers::AddCapsuleCollider(PhysicsActor& actor, const physx::PxMaterial& material) void PhysicsWrappers::AddCapsuleCollider(PhysicsActor& actor, const physx::PxMaterial& material)
{ {
actor.RemoveCollisionsShapes(physx::PxGeometryType::eCAPSULE);
const auto& collider = actor.m_Entity.GetComponent<CapsuleColliderComponent>(); const auto& collider = actor.m_Entity.GetComponent<CapsuleColliderComponent>();
const glm::vec3 scale = actor.m_Entity.Transform().Scale; const glm::vec3 scale = actor.m_Entity.Transform().Scale;
float colliderRadius = collider.Radius; float colliderRadius = collider.Radius;
@ -230,7 +240,7 @@ namespace Prism
shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger);
shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger);
// shape->setLocalPose(physx::PxTransform(physx::PxQuat(physx::PxHalfPi, physx::PxVec3(0, 0, 1)))); actor.AddCollisionShape(shape);
} }
void PhysicsWrappers::AddMeshCollider(PhysicsActor& actor, const physx::PxMaterial& material) void PhysicsWrappers::AddMeshCollider(PhysicsActor& actor, const physx::PxMaterial& material)
@ -240,7 +250,9 @@ namespace Prism
if (collider.IsConvex) if (collider.IsConvex)
{ {
std::vector<physx::PxConvexMesh*> meshes = CreateConvexMesh(collider, true); actor.RemoveCollisionsShapes(physx::PxGeometryType::eTRIANGLEMESH);
const std::vector<physx::PxConvexMesh*> meshes = CreateConvexMesh(collider, true);
for (const auto mesh : meshes) for (const auto mesh : meshes)
{ {
@ -249,11 +261,15 @@ namespace Prism
physx::PxShape* shape = physx::PxRigidActorExt::createExclusiveShape(*actor.m_ActorInternal, convexGeometry, material); physx::PxShape* shape = physx::PxRigidActorExt::createExclusiveShape(*actor.m_ActorInternal, convexGeometry, material);
shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger);
shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger);
actor.AddCollisionShape(shape);
} }
} }
else else
{ {
std::vector<physx::PxTriangleMesh*> meshes = CreateTriangleMesh(collider, true); actor.RemoveCollisionsShapes(physx::PxGeometryType::eCONVEXMESH);
const std::vector<physx::PxTriangleMesh*> meshes = CreateTriangleMesh(collider);
for (const auto mesh : meshes) for (const auto mesh : meshes)
{ {
@ -261,11 +277,13 @@ namespace Prism
physx::PxShape* shape = physx::PxRigidActorExt::createExclusiveShape(*actor.m_ActorInternal, convexGeometry, material); physx::PxShape* shape = physx::PxRigidActorExt::createExclusiveShape(*actor.m_ActorInternal, convexGeometry, material);
shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eSIMULATION_SHAPE, !collider.IsTrigger);
shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger); shape->setFlag(physx::PxShapeFlag::eTRIGGER_SHAPE, collider.IsTrigger);
actor.AddCollisionShape(shape);
} }
} }
} }
std::vector<physx::PxTriangleMesh*> PhysicsWrappers::CreateTriangleMesh(MeshColliderComponent& collider, bool invalidateOld) std::vector<physx::PxTriangleMesh*> PhysicsWrappers::CreateTriangleMesh(MeshColliderComponent& collider)
{ {
std::vector<physx::PxTriangleMesh*> meshes; std::vector<physx::PxTriangleMesh*> meshes;
@ -279,7 +297,7 @@ namespace Prism
const std::vector<Vertex>& vertices = collider.CollisionMesh->GetStaticVertices(); const std::vector<Vertex>& vertices = collider.CollisionMesh->GetStaticVertices();
const std::vector<Index>& indices = collider.CollisionMesh->GetIndices(); const std::vector<Index>& indices = collider.CollisionMesh->GetIndices();
// 提取顶点位置(如果需要) // 提取顶点位置
std::vector<glm::vec3> vertexPositions; std::vector<glm::vec3> vertexPositions;
if (vertices[0].Position != glm::vec3()) { if (vertices[0].Position != glm::vec3()) {
vertexPositions.reserve(vertices.size()); vertexPositions.reserve(vertices.size());
@ -288,10 +306,8 @@ namespace Prism
} }
} }
// 清空旧的处理网格(如果需要) // 清空旧的处理网格
if (invalidateOld) {
collider.ProcessedMeshes.clear(); collider.ProcessedMeshes.clear();
}
// 处理每个子网格 // 处理每个子网格
for (const auto& submesh : collider.CollisionMesh->GetSubmeshes()) for (const auto& submesh : collider.CollisionMesh->GetSubmeshes())
@ -332,8 +348,8 @@ namespace Prism
meshes.push_back(triangleMesh); meshes.push_back(triangleMesh);
// 为可视化生成渲染网格(如果需要) // 为可视化生成渲染网格
if (collider.ProcessedMeshes.empty() || invalidateOld) if (collider.ProcessedMeshes.empty())
{ {
const uint32_t nbVerts = triangleMesh->getNbVertices(); const uint32_t nbVerts = triangleMesh->getNbVertices();
const physx::PxVec3* meshVertices = triangleMesh->getVertices(); const physx::PxVec3* meshVertices = triangleMesh->getVertices();
@ -388,32 +404,34 @@ namespace Prism
return meshes; return meshes;
} }
std::vector<physx::PxConvexMesh*> PhysicsWrappers::CreateConvexMesh(MeshColliderComponent& collider, bool invalidateOld) std::vector<physx::PxConvexMesh*> PhysicsWrappers::CreateConvexMesh(MeshColliderComponent& collider, const bool rotatedX)
{ {
std::vector<physx::PxConvexMesh*> meshes; std::vector<physx::PxConvexMesh*> meshes;
// 设置烹饪参数,保持与原始版本相同的配置
physx::PxCookingParams cookingParams(s_Physics->getTolerancesScale()); physx::PxCookingParams cookingParams(s_Physics->getTolerancesScale());
cookingParams.planeTolerance = 0.0F; cookingParams.planeTolerance = 0.0F;
cookingParams.meshPreprocessParams = physx::PxMeshPreprocessingFlags(physx::PxMeshPreprocessingFlag::eWELD_VERTICES); cookingParams.meshPreprocessParams = physx::PxMeshPreprocessingFlags(physx::PxMeshPreprocessingFlag::eWELD_VERTICES);
cookingParams.meshWeldTolerance = 0.01f; cookingParams.meshWeldTolerance = 0.01f;
// 获取顶点数据
const std::vector<Vertex>& vertices = collider.CollisionMesh->GetStaticVertices(); const std::vector<Vertex>& vertices = collider.CollisionMesh->GetStaticVertices();
const std::vector<Index>& indices = collider.CollisionMesh->GetIndices(); const std::vector<Index>& indices = collider.CollisionMesh->GetIndices();
// 准备顶点位置数组(如果需要的话) // prepare vertices
std::vector<glm::vec3> vertexPositions; std::vector<glm::vec3> position;
if (vertices[0].Position != glm::vec3()) {
vertexPositions.reserve(vertices.size()); if (rotatedX)
for (const auto& vertex : vertices) { {
vertexPositions.push_back(vertex.Position); for (auto& vertex : vertices)
} position.push_back(glm::rotate(vertex.Position, glm::radians(90.0f), { -1.0f, 0.0f, 0.0f }));
}else
{
for (auto& vertex : vertices)
position.push_back(vertex.Position);
} }
if (invalidateOld) {
// clear old meshes
collider.ProcessedMeshes.clear(); collider.ProcessedMeshes.clear();
}
// 处理每个子网格 // 处理每个子网格
@ -425,15 +443,14 @@ namespace Prism
convexDesc.points.stride = sizeof(glm::vec3); convexDesc.points.stride = sizeof(glm::vec3);
// 使用顶点位置数组或原始顶点数据 // 使用顶点位置数组或原始顶点数据
if (!vertexPositions.empty()) { convexDesc.points.data = &position[submesh.BaseVertex];
convexDesc.points.data = &vertexPositions[submesh.BaseVertex];
} else { convexDesc.indices.count = submesh.IndexCount / 3;
convexDesc.points.stride = sizeof(Vertex); convexDesc.indices.data = &indices[submesh.BaseIndex / 3];
convexDesc.points.data = &vertices[submesh.BaseVertex]; convexDesc.indices.stride = sizeof(Index);
}
convexDesc.flags = physx::PxConvexFlag::eCOMPUTE_CONVEX | convexDesc.flags = physx::PxConvexFlag::eCOMPUTE_CONVEX |
physx::PxConvexFlag::eCHECK_ZERO_AREA_TRIANGLES | // physx::PxConvexFlag::eCHECK_ZERO_AREA_TRIANGLES |
physx::PxConvexFlag::eSHIFT_VERTICES; physx::PxConvexFlag::eSHIFT_VERTICES;
// 创建凸包网格 // 创建凸包网格
@ -452,8 +469,8 @@ namespace Prism
meshes.push_back(convexMesh); meshes.push_back(convexMesh);
// 为可视化生成渲染网格(如果需要) // 为可视化生成渲染网格
if (collider.ProcessedMeshes.empty() || invalidateOld) if (collider.ProcessedMeshes.empty())
{ {
const uint32_t nbPolygons = convexMesh->getNbPolygons(); const uint32_t nbPolygons = convexMesh->getNbPolygons();
const physx::PxVec3* convexVertices = convexMesh->getVertices(); const physx::PxVec3* convexVertices = convexMesh->getVertices();
@ -466,7 +483,7 @@ namespace Prism
for (uint32_t i = 0; i < nbPolygons; i++) for (uint32_t i = 0; i < nbPolygons; i++)
{ {
physx::PxHullPolygon polygon; physx::PxHullPolygon polygon{};
convexMesh->getPolygonData(i, polygon); convexMesh->getPolygonData(i, polygon);
const uint32_t vI0 = vertCounter; const uint32_t vI0 = vertCounter;
@ -474,7 +491,7 @@ namespace Prism
// 收集当前多边形的所有顶点 // 收集当前多边形的所有顶点
for (uint32_t vI = 0; vI < polygon.mNbVerts; vI++) for (uint32_t vI = 0; vI < polygon.mNbVerts; vI++)
{ {
Vertex vertex; Vertex vertex{};
vertex.Position = FromPhysXVector( vertex.Position = FromPhysXVector(
convexVertices[convexIndices[polygon.mIndexBase + vI]] convexVertices[convexIndices[polygon.mIndexBase + vI]]
); );
@ -488,7 +505,7 @@ namespace Prism
// 为当前多边形生成三角形索引(扇形三角剖分) // 为当前多边形生成三角形索引(扇形三角剖分)
for (auto vI = 1; vI < polygon.mNbVerts - 1; vI++) for (auto vI = 1; vI < polygon.mNbVerts - 1; vI++)
{ {
Index index; Index index{};
index.V1 = vI0; index.V1 = vI0;
index.V2 = vI0 + vI + 1; index.V2 = vI0 + vI + 1;
index.V3 = vI0 + vI; index.V3 = vI0 + vI;
@ -497,7 +514,6 @@ namespace Prism
} }
} }
// 为当前子网格创建渲染网格
collider.ProcessedMeshes.push_back(Ref<Mesh>::Create(collisionVertices, collisionIndices)); collider.ProcessedMeshes.push_back(Ref<Mesh>::Create(collisionVertices, collisionIndices));
} }
} }

View File

@ -51,8 +51,8 @@ namespace Prism
// static void AddMeshCollider(::physx::PxRigidActor& actor, const ::physx::PxMaterial& material, ::Prism::MeshColliderComponent& collider, const glm::vec3& scale = glm::vec3(0.0f)); // static void AddMeshCollider(::physx::PxRigidActor& actor, const ::physx::PxMaterial& material, ::Prism::MeshColliderComponent& collider, const glm::vec3& scale = glm::vec3(0.0f));
static std::vector<physx::PxTriangleMesh*> CreateTriangleMesh(MeshColliderComponent& collider, bool invalidateOld = false); static std::vector<physx::PxTriangleMesh*> CreateTriangleMesh(MeshColliderComponent& collider);
static std::vector<physx::PxConvexMesh*> CreateConvexMesh(MeshColliderComponent& collider, bool invalidateOld = false); static std::vector<physx::PxConvexMesh*> CreateConvexMesh(MeshColliderComponent& collider, bool rotatedX = false);
// static physx::PxMaterial* CreateMaterial(const PhysicsMaterialComponent& material); // static physx::PxMaterial* CreateMaterial(const PhysicsMaterialComponent& material);

View File

@ -369,12 +369,12 @@ namespace Prism
s_Data.Stats.QuadCount++; s_Data.Stats.QuadCount++;
} }
void Renderer2D::DrawRotatedQuad(const glm::vec2& position, const glm::vec2& size, float rotation, const glm::vec4& color) void Renderer2D::DrawRotatedQuad(const glm::vec2& position, const glm::vec2& size, const float rotation, const glm::vec4& color)
{ {
DrawRotatedQuad({ position.x, position.y, 0.0f }, size, rotation, color); DrawRotatedQuad({ position.x, position.y, 0.0f }, size, rotation, color);
} }
void Renderer2D::DrawRotatedQuad(const glm::vec3& position, const glm::vec2& size, float rotation, const glm::vec4& color) void Renderer2D::DrawRotatedQuad(const glm::vec3& position, const glm::vec2& size, const float rotation, const glm::vec4& color)
{ {
if (s_Data.QuadIndexCount >= Renderer2DData::MaxIndices) if (s_Data.QuadIndexCount >= Renderer2DData::MaxIndices)
FlushAndReset(); FlushAndReset();
@ -383,7 +383,7 @@ namespace Prism
const float tilingFactor = 1.0f; const float tilingFactor = 1.0f;
glm::mat4 transform = glm::translate(glm::mat4(1.0f), position) glm::mat4 transform = glm::translate(glm::mat4(1.0f), position)
* glm::rotate(glm::mat4(1.0f), glm::radians(rotation), { 0.0f, 0.0f, 1.0f }) * glm::rotate(glm::mat4(1.0f), rotation, { 0.0f, 0.0f, 1.0f })
* glm::scale(glm::mat4(1.0f), { size.x, size.y, 1.0f }); * glm::scale(glm::mat4(1.0f), { size.x, size.y, 1.0f });
for (uint32_t i = 0; i < 4; i++) for (uint32_t i = 0; i < 4; i++)

View File

@ -505,7 +505,7 @@ namespace Prism
Renderer::SubmitMesh(dc.mesh, dc.Transform, overrideMaterial); Renderer::SubmitMesh(dc.mesh, dc.Transform, overrideMaterial);
} }
if (outline) if (collider || outline)
{ {
Renderer::Submit([]() Renderer::Submit([]()
{ {

View File

@ -17,6 +17,7 @@
#include <glm/glm.hpp> #include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp> #include <glm/gtc/matrix_transform.hpp>
#include <glm/gtx/quaternion.hpp> #include <glm/gtx/quaternion.hpp>
#include <utility>
#include "Prism/Renderer/SceneEnvironment.h" #include "Prism/Renderer/SceneEnvironment.h"
@ -33,8 +34,8 @@ namespace Prism
TagComponent() = default; TagComponent() = default;
TagComponent(const TagComponent& other) = default; TagComponent(const TagComponent& other) = default;
TagComponent(const std::string& tag) TagComponent(std::string tag)
: Tag(tag) {} : Tag(std::move(tag)) {}
explicit operator std::string& () { return Tag; } explicit operator std::string& () { return Tag; }
explicit operator const std::string& () const { return Tag; } explicit operator const std::string& () const { return Tag; }
@ -56,7 +57,7 @@ namespace Prism
glm::mat4 GetTransform() const glm::mat4 GetTransform() const
{ {
return glm::translate(glm::mat4(1.0f), Translation) return glm::translate(glm::mat4(1.0f), Translation)
* glm::toMat4(glm::quat(glm::radians(Rotation))) * glm::toMat4(glm::quat((Rotation)))
* glm::scale(glm::mat4(1.0f), Scale); * glm::scale(glm::mat4(1.0f), Scale);
} }
}; };
@ -166,7 +167,7 @@ namespace Prism
struct RigidBodyComponent struct RigidBodyComponent
{ {
enum class Type { Static, Dynamic}; enum class Type { Static, Dynamic};
Type BodyType; Type BodyType = Type::Static;
float Mass = 1.0f; float Mass = 1.0f;
float LinearDrag = 0.0F; float LinearDrag = 0.0F;
float AngularDrag = 0.05F; float AngularDrag = 0.05F;
@ -181,8 +182,8 @@ namespace Prism
bool LockRotationY = false; bool LockRotationY = false;
bool LockRotationZ = false; bool LockRotationZ = false;
void* RuntimeActor = nullptr; // void* RuntimeActor = nullptr;
int32_t EntityBufferIndex = -1; // int32_t EntityBufferIndex = -1;
RigidBodyComponent() = default; RigidBodyComponent() = default;
RigidBodyComponent(const RigidBodyComponent& other) = default; RigidBodyComponent(const RigidBodyComponent& other) = default;

View File

@ -15,6 +15,7 @@
#include <glm/gtx/matrix_decompose.hpp> #include <glm/gtx/matrix_decompose.hpp>
#include "Prism/Physics/Physics3D.h" #include "Prism/Physics/Physics3D.h"
#include "Prism/Physics/PhysicsActor.h"
#define PX_PHYSX_STATIC_LIB #define PX_PHYSX_STATIC_LIB
#include <PxPhysicsAPI.h> #include <PxPhysicsAPI.h>
@ -219,12 +220,12 @@ namespace Prism
// Process lights // Process lights
{ {
m_LightEnvironment = LightEnvironment(); m_LightEnvironment = LightEnvironment();
auto lights = m_Registry.group<DirectionalLightComponent>(entt::get<TransformComponent>); const auto lights = m_Registry.group<DirectionalLightComponent>(entt::get<TransformComponent>);
uint32_t directionalLightIndex = 0; uint32_t directionalLightIndex = 0;
for (auto entity : lights) for (const auto entity : lights)
{ {
auto [transformComponent, lightComponent] = lights.get<TransformComponent, DirectionalLightComponent>(entity); auto [transformComponent, lightComponent] = lights.get<TransformComponent, DirectionalLightComponent>(entity);
glm::vec3 direction = -glm::normalize(glm::mat3(transformComponent.GetTransform()) * glm::vec3(1.0f)); const glm::vec3 direction = -glm::normalize(glm::mat3(transformComponent.GetTransform()) * glm::vec3(1.0f));
m_LightEnvironment.DirectionalLights[directionalLightIndex++] = m_LightEnvironment.DirectionalLights[directionalLightIndex++] =
{ {
direction, direction,
@ -238,8 +239,8 @@ namespace Prism
// TODO: only one sky light at the moment! // TODO: only one sky light at the moment!
{ {
m_Environment = Environment(); m_Environment = Environment();
auto lights = m_Registry.group<SkyLightComponent>(entt::get<TransformComponent>); const auto lights = m_Registry.group<SkyLightComponent>(entt::get<TransformComponent>);
for (auto entity : lights) for (const auto entity : lights)
{ {
auto [transformComponent, skyLightComponent] = lights.get<TransformComponent, SkyLightComponent>(entity); auto [transformComponent, skyLightComponent] = lights.get<TransformComponent, SkyLightComponent>(entity);
m_Environment = skyLightComponent.SceneEnvironment; m_Environment = skyLightComponent.SceneEnvironment;
@ -532,11 +533,12 @@ namespace Prism
{ {
auto view = m_Registry.view<RigidBodyComponent>(); auto view = m_Registry.view<RigidBodyComponent>();
Physics3D::ExpandEntityBuffer(static_cast<uint32_t>(view.size())); // Physics3D::ExpandEntityBuffer(static_cast<uint32_t>(view.size()));
for (auto entity : view) for (auto entity : view)
{ {
Entity e = { entity, this }; Entity e = { entity, this };
Physics3D::CreateActor(e); Physics3D::CreateActor(e);
// Physics3D::CreateActor(e);
} }
} }

View File

@ -187,10 +187,10 @@ namespace Prism
out << YAML::Key << "ScriptComponent"; out << YAML::Key << "ScriptComponent";
out << YAML::BeginMap; // ScriptComponent out << YAML::BeginMap; // ScriptComponent
auto& moduleName = entity.GetComponent<ScriptComponent>().ModuleName; const auto& moduleName = entity.GetComponent<ScriptComponent>().ModuleName;
out << YAML::Key << "ModuleName" << YAML::Value << moduleName; out << YAML::Key << "ModuleName" << YAML::Value << moduleName;
EntityInstanceData& data = ScriptEngine::GetEntityInstanceData(entity.GetSceneUUID(), uuid); const EntityInstanceData& data = ScriptEngine::GetEntityInstanceData(entity.GetSceneUUID(), uuid);
const auto& moduleFieldMap = data.ModuleFieldMap; const auto& moduleFieldMap = data.ModuleFieldMap;
if (moduleFieldMap.find(moduleName) != moduleFieldMap.end()) if (moduleFieldMap.find(moduleName) != moduleFieldMap.end())
{ {
@ -201,7 +201,7 @@ namespace Prism
{ {
out << YAML::BeginMap; // Field out << YAML::BeginMap; // Field
out << YAML::Key << "Name" << YAML::Value << name; out << YAML::Key << "Name" << YAML::Value << name;
out << YAML::Key << "Type" << YAML::Value << (uint32_t)field.Type; out << YAML::Key << "Type" << YAML::Value << static_cast<uint32_t>(field.Type);
out << YAML::Key << "Data" << YAML::Value; out << YAML::Key << "Data" << YAML::Value;
switch (field.Type) switch (field.Type)
@ -238,7 +238,7 @@ namespace Prism
out << YAML::Key << "MeshComponent"; out << YAML::Key << "MeshComponent";
out << YAML::BeginMap; // MeshComponent out << YAML::BeginMap; // MeshComponent
auto mesh = entity.GetComponent<MeshComponent>().Mesh; const auto mesh = entity.GetComponent<MeshComponent>().Mesh;
out << YAML::Key << "AssetPath" << YAML::Value << mesh->GetFilePath(); out << YAML::Key << "AssetPath" << YAML::Value << mesh->GetFilePath();
out << YAML::EndMap; // MeshComponent out << YAML::EndMap; // MeshComponent
@ -249,7 +249,7 @@ namespace Prism
out << YAML::Key << "DirectionalLightComponent"; out << YAML::Key << "DirectionalLightComponent";
out << YAML::BeginMap; // DirectionalLightComponent out << YAML::BeginMap; // DirectionalLightComponent
auto& directionalLightComponent = entity.GetComponent<DirectionalLightComponent>(); const auto& directionalLightComponent = entity.GetComponent<DirectionalLightComponent>();
out << YAML::Key << "Radiance" << YAML::Value << directionalLightComponent.Radiance; out << YAML::Key << "Radiance" << YAML::Value << directionalLightComponent.Radiance;
out << YAML::Key << "CastShadows" << YAML::Value << directionalLightComponent.CastShadows; out << YAML::Key << "CastShadows" << YAML::Value << directionalLightComponent.CastShadows;
out << YAML::Key << "SoftShadows" << YAML::Value << directionalLightComponent.SoftShadows; out << YAML::Key << "SoftShadows" << YAML::Value << directionalLightComponent.SoftShadows;
@ -263,7 +263,7 @@ namespace Prism
out << YAML::Key << "SkyLightComponent"; out << YAML::Key << "SkyLightComponent";
out << YAML::BeginMap; // SkyLightComponent out << YAML::BeginMap; // SkyLightComponent
auto& skyLightComponent = entity.GetComponent<SkyLightComponent>(); const auto& skyLightComponent = entity.GetComponent<SkyLightComponent>();
out << YAML::Key << "EnvironmentAssetPath" << YAML::Value << skyLightComponent.SceneEnvironment.FilePath; out << YAML::Key << "EnvironmentAssetPath" << YAML::Value << skyLightComponent.SceneEnvironment.FilePath;
out << YAML::Key << "Intensity" << YAML::Value << skyLightComponent.Intensity; out << YAML::Key << "Intensity" << YAML::Value << skyLightComponent.Intensity;
out << YAML::Key << "Angle" << YAML::Value << skyLightComponent.Angle; out << YAML::Key << "Angle" << YAML::Value << skyLightComponent.Angle;
@ -342,9 +342,14 @@ namespace Prism
out << YAML::Key << "RigidBodyComponent"; out << YAML::Key << "RigidBodyComponent";
out << YAML::BeginMap; // RigidBodyComponent out << YAML::BeginMap; // RigidBodyComponent
auto& rigidbodyComponent = entity.GetComponent<RigidBodyComponent>(); const auto& rigidbodyComponent = entity.GetComponent<RigidBodyComponent>();
out << YAML::Key << "BodyType" << YAML::Value << (int)rigidbodyComponent.BodyType; out << YAML::Key << "BodyType" << YAML::Value << static_cast<int>(rigidbodyComponent.BodyType);
out << YAML::Key << "Mass" << YAML::Value << rigidbodyComponent.Mass; out << YAML::Key << "Mass" << YAML::Value << rigidbodyComponent.Mass;
out << YAML::Key << "LinearDrag" << YAML::Value << rigidbodyComponent.LinearDrag;
out << YAML::Key << "AngularDrag" << YAML::Value << rigidbodyComponent.AngularDrag;
out << YAML::Key << "DisableGravity" << YAML::Value << rigidbodyComponent.DisableGravity;
out << YAML::Key << "IsKinematic" << YAML::Value << rigidbodyComponent.IsKinematic; out << YAML::Key << "IsKinematic" << YAML::Value << rigidbodyComponent.IsKinematic;
out << YAML::Key << "Layer" << YAML::Value << rigidbodyComponent.Layer; out << YAML::Key << "Layer" << YAML::Value << rigidbodyComponent.Layer;
@ -709,6 +714,11 @@ namespace Prism
auto& component = deserializedEntity.AddComponent<RigidBodyComponent>(); auto& component = deserializedEntity.AddComponent<RigidBodyComponent>();
component.BodyType = (RigidBodyComponent::Type)rigidBodyComponent["BodyType"].as<int>(); component.BodyType = (RigidBodyComponent::Type)rigidBodyComponent["BodyType"].as<int>();
component.Mass = rigidBodyComponent["Mass"].as<float>(); component.Mass = rigidBodyComponent["Mass"].as<float>();
component.LinearDrag = rigidBodyComponent["LinearDrag"] ? rigidBodyComponent["LinearDrag"].as<float>() : 0.0f;
component.AngularDrag = rigidBodyComponent["AngularDrag"] ? rigidBodyComponent["AngularDrag"].as<float>() : 0.05f;
component.DisableGravity = rigidBodyComponent["DisableGravity"] ? rigidBodyComponent["DisableGravity"].as<bool>() : false;
component.IsKinematic = rigidBodyComponent["IsKinematic"] ? rigidBodyComponent["IsKinematic"].as<bool>() : false; component.IsKinematic = rigidBodyComponent["IsKinematic"] ? rigidBodyComponent["IsKinematic"].as<bool>() : false;
component.Layer = rigidBodyComponent["Layer"] ? rigidBodyComponent["Layer"].as<uint32_t>() : 0; component.Layer = rigidBodyComponent["Layer"] ? rigidBodyComponent["Layer"].as<uint32_t>() : 0;

View File

@ -378,13 +378,13 @@ namespace Prism { namespace Script {
Entity entity = entityMap.at(entityID); Entity entity = entityMap.at(entityID);
const auto& transform = entity.GetComponent<TransformComponent>(); const auto& transform = entity.GetComponent<TransformComponent>();
const glm::quat rotation = glm::quat(glm::radians(transform.Rotation)); const glm::quat rotation = glm::quat(transform.Rotation);
const glm::vec3 right = glm::normalize(glm::rotate(rotation, glm::vec3(1.0f, 0.0f, 0.0f))); const glm::vec3 right = glm::normalize(glm::rotate(rotation, glm::vec3(1.0f, 0.0f, 0.0f)));
const glm::vec3 up = glm::normalize(glm::rotate(rotation, glm::vec3(0.0f, 1.0f, 0.0f))); const glm::vec3 up = glm::normalize(glm::rotate(rotation, glm::vec3(0.0f, 1.0f, 0.0f)));
const glm::vec3 forward = glm::normalize(glm::rotate(rotation, glm::vec3(0.0f, 0.0f, -1.0f))); const glm::vec3 forward = glm::normalize(glm::rotate(rotation, glm::vec3(0.0f, 0.0f, -1.0f)));
*outTransform = { *outTransform = {
transform.Translation, transform.Rotation, transform.Scale, transform.Translation, glm::degrees(transform.Rotation), transform.Scale,
up, right, forward up, right, forward
}; };
} }
@ -400,7 +400,7 @@ namespace Prism { namespace Script {
auto& transform = entity.GetComponent<TransformComponent>(); auto& transform = entity.GetComponent<TransformComponent>();
transform.Translation = inTransform->Translation; transform.Translation = inTransform->Translation;
transform.Rotation = inTransform->Rotation; transform.Rotation = glm::radians(inTransform->Rotation);
transform.Scale = inTransform->Scale; transform.Scale = inTransform->Scale;
} }
@ -441,7 +441,7 @@ namespace Prism { namespace Script {
const b2BodyId body = component.RuntimeBodyID; const b2BodyId body = component.RuntimeBodyID;
b2Body_ApplyLinearImpulse(body, *(const b2Vec2*)impulse, b2Body_GetWorldCenterOfMass(body) + *(const b2Vec2*)offset, wake); b2Body_ApplyLinearImpulse(body, *reinterpret_cast<const b2Vec2*>(impulse), b2Body_GetWorldCenterOfMass(body) + *reinterpret_cast<const b2Vec2*>(offset), wake);
} }
void Prism_RigidBody2DComponent_GetLinearVelocity(const uint64_t entityID, glm::vec2 *outVelocity) void Prism_RigidBody2DComponent_GetLinearVelocity(const uint64_t entityID, glm::vec2 *outVelocity)
@ -489,7 +489,7 @@ namespace Prism { namespace Script {
return component.BodyType; return component.BodyType;
} }
void Prism_RigidBodyComponent_AddForce(const uint64_t entityID, glm::vec3* force, ForceMode forceMode) void Prism_RigidBodyComponent_AddForce(const uint64_t entityID, const glm::vec3* force, const ForceMode forceMode)
{ {
Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext(); Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext();
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
@ -505,15 +505,11 @@ namespace Prism { namespace Script {
return; return;
} }
auto* actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
auto* dynamicActor = actor->is<physx::PxRigidDynamic>(); actor->AddForce(*force, forceMode);
PM_CORE_ASSERT(dynamicActor);
PM_CORE_ASSERT(force);
dynamicActor->addForce({ force->x, force->y, force->z }, (physx::PxForceMode::Enum)forceMode);
} }
void Prism_RigidBodyComponent_AddTorque(const uint64_t entityID, glm::vec3* torque, ForceMode forceMode) void Prism_RigidBodyComponent_AddTorque(const uint64_t entityID, const glm::vec3* torque, const ForceMode forceMode)
{ {
Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext(); Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext();
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
@ -529,12 +525,8 @@ namespace Prism { namespace Script {
return; return;
} }
const auto actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
auto* dynamicActor = actor->is<physx::PxRigidDynamic>(); actor->AddTorque(*torque, forceMode);
PM_CORE_ASSERT(dynamicActor);
PM_CORE_ASSERT(torque);
dynamicActor->addTorque({ torque->x, torque->y, torque->z }, (physx::PxForceMode::Enum)forceMode);
} }
void Prism_RigidBodyComponent_GetLinearVelocity(const uint64_t entityID, glm::vec3* outVelocity) void Prism_RigidBodyComponent_GetLinearVelocity(const uint64_t entityID, glm::vec3* outVelocity)
@ -553,17 +545,12 @@ namespace Prism { namespace Script {
return; return;
} }
const auto actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor);
const physx::PxRigidDynamic* dynamicActor = actor->is<physx::PxRigidDynamic>();
PM_CORE_ASSERT(dynamicActor);
PM_CORE_ASSERT(outVelocity); PM_CORE_ASSERT(outVelocity);
physx::PxVec3 velocity = dynamicActor->getLinearVelocity(); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
*outVelocity = { velocity.x, velocity.y, velocity.z }; *outVelocity = actor->GetLinearVelocity();
} }
void Prism_RigidBodyComponent_SetLinearVelocity(const uint64_t entityID, glm::vec3* velocity) void Prism_RigidBodyComponent_SetLinearVelocity(const uint64_t entityID, const glm::vec3* velocity)
{ {
Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext(); Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext();
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
@ -579,16 +566,12 @@ namespace Prism { namespace Script {
return; return;
} }
const auto actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor);
auto* dynamicActor = actor->is<physx::PxRigidDynamic>();
PM_CORE_ASSERT(dynamicActor);
PM_CORE_ASSERT(velocity); PM_CORE_ASSERT(velocity);
PM_CORE_INFO("Hazel_RigidBodyComponent_SetLinearVelocity - {0}, {1}, {2}", velocity->x, velocity->y, velocity->z); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
dynamicActor->setLinearVelocity({ velocity->x, velocity->y, velocity->z }); actor->SetLinearVelocity(*velocity);
} }
void Prism_RigidBodyComponent_GetAngularVelocity(uint64_t entityID, glm::vec3* outVelocity) void Prism_RigidBodyComponent_GetAngularVelocity(const uint64_t entityID, glm::vec3* outVelocity)
{ {
Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext(); Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext();
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
@ -599,16 +582,12 @@ namespace Prism { namespace Script {
PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>()); PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>());
const auto& component = entity.GetComponent<RigidBodyComponent>(); const auto& component = entity.GetComponent<RigidBodyComponent>();
const auto actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor);
const auto* dynamicActor = actor->is<physx::PxRigidDynamic>();
PM_CORE_ASSERT(dynamicActor);
PM_CORE_ASSERT(outVelocity); PM_CORE_ASSERT(outVelocity);
physx::PxVec3 velocity = dynamicActor->getAngularVelocity(); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
*outVelocity = { velocity.x, velocity.y, velocity.z }; *outVelocity = actor->GetAngularVelocity();
} }
void Prism_RigidBodyComponent_SetAngularVelocity(uint64_t entityID, glm::vec3* velocity) void Prism_RigidBodyComponent_SetAngularVelocity(const uint64_t entityID, const glm::vec3* velocity)
{ {
Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext(); Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext();
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
@ -619,15 +598,12 @@ namespace Prism { namespace Script {
PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>()); PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>());
const auto& component = entity.GetComponent<RigidBodyComponent>(); const auto& component = entity.GetComponent<RigidBodyComponent>();
auto* actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor);
auto* dynamicActor = actor->is<physx::PxRigidDynamic>();
PM_CORE_ASSERT(dynamicActor);
PM_CORE_ASSERT(velocity); PM_CORE_ASSERT(velocity);
dynamicActor->setAngularVelocity({ velocity->x, velocity->y, velocity->z }); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
actor->SetAngularVelocity(*velocity);
} }
void Prism_RigidBodyComponent_Rotate(uint64_t entityID, glm::vec3* rotation) void Prism_RigidBodyComponent_Rotate(const uint64_t entityID, const glm::vec3* rotation)
{ {
Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext(); Ref<Scene> scene = ScriptEngine::GetCurrentSceneContext();
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
@ -638,16 +614,8 @@ namespace Prism { namespace Script {
PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>()); PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>());
const auto& component = entity.GetComponent<RigidBodyComponent>(); const auto& component = entity.GetComponent<RigidBodyComponent>();
const auto actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
auto* dynamicActor = actor->is<physx::PxRigidDynamic>(); actor->Rotate(*rotation);
PM_CORE_ASSERT(dynamicActor);
physx::PxTransform transform = dynamicActor->getGlobalPose();
transform.q *= (physx::PxQuat(glm::radians(rotation->x), { 1.0f, 0.0f, 0.0f })
* physx::PxQuat(glm::radians(rotation->y), { 0.0f, 1.0f, 0.0f })
* physx::PxQuat(glm::radians(rotation->z), { 0.0f, 0.0f, 1.0f }));
dynamicActor->setGlobalPose(transform);
} }
uint32_t Prism_RigidBodyComponent_GetLayer(const uint64_t entityID) uint32_t Prism_RigidBodyComponent_GetLayer(const uint64_t entityID)
@ -672,13 +640,9 @@ namespace Prism { namespace Script {
Entity entity = entityMap.at(entityID); Entity entity = entityMap.at(entityID);
PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>()); PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>());
const auto& component = entity.GetComponent<RigidBodyComponent>();
const auto actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
const physx::PxRigidDynamic* dynamicActor = actor->is<physx::PxRigidDynamic>(); return actor->GetMass();
PM_CORE_ASSERT(dynamicActor);
return dynamicActor->getMass();
} }
void Prism_RigidBodyComponent_SetMass(const uint64_t entityID, const float mass) void Prism_RigidBodyComponent_SetMass(const uint64_t entityID, const float mass)
@ -687,17 +651,11 @@ namespace Prism { namespace Script {
PM_CORE_ASSERT(scene, "No active scene!"); PM_CORE_ASSERT(scene, "No active scene!");
const auto& entityMap = scene->GetEntityMap(); const auto& entityMap = scene->GetEntityMap();
PM_CORE_ASSERT(entityMap.find(entityID) != entityMap.end(), "Invalid entity ID or entity doesn't exist in scene!"); PM_CORE_ASSERT(entityMap.find(entityID) != entityMap.end(), "Invalid entity ID or entity doesn't exist in scene!");
Entity entity = entityMap.at(entityID); Entity entity = entityMap.at(entityID);
PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>()); PM_CORE_ASSERT(entity.HasComponent<RigidBodyComponent>());
auto& component = entity.GetComponent<RigidBodyComponent>();
auto* actor = static_cast<physx::PxRigidActor*>(component.RuntimeActor); Ref<PhysicsActor> actor = Physics3D::GetActorForEntity(entity);
auto* dynamicActor = actor->is<physx::PxRigidDynamic>(); actor->SetMass(mass);
PM_CORE_ASSERT(dynamicActor);
component.Mass = mass;
physx::PxRigidBodyExt::updateMassAndInertia(*dynamicActor, mass);
} }
@ -731,7 +689,7 @@ namespace Prism { namespace Script {
{ {
Ref<Mesh>& mesh = *inMesh; Ref<Mesh>& mesh = *inMesh;
const auto& materials = mesh->GetMaterials(); const auto& materials = mesh->GetMaterials();
return (int)materials.size(); return static_cast<int>(materials.size());
} }
void* Prism_Texture2D_Constructor(const uint32_t width, const uint32_t height) void* Prism_Texture2D_Constructor(const uint32_t width, const uint32_t height)

View File

@ -67,13 +67,13 @@ namespace Prism { namespace Script {
// 3D Physic // 3D Physic
RigidBodyComponent::Type Prism_RigidBodyComponent_GetBodyType(uint64_t entityID); RigidBodyComponent::Type Prism_RigidBodyComponent_GetBodyType(uint64_t entityID);
void Prism_RigidBodyComponent_AddForce(uint64_t entityID, glm::vec3* force, ForceMode forceMode); void Prism_RigidBodyComponent_AddForce(uint64_t entityID, const glm::vec3* force, ForceMode forceMode);
void Prism_RigidBodyComponent_AddTorque(uint64_t entityID, glm::vec3* torque, ForceMode forceMode); void Prism_RigidBodyComponent_AddTorque(uint64_t entityID, const glm::vec3* torque, ForceMode forceMode);
void Prism_RigidBodyComponent_GetLinearVelocity(uint64_t entityID, glm::vec3* outVelocity); void Prism_RigidBodyComponent_GetLinearVelocity(uint64_t entityID, glm::vec3* outVelocity);
void Prism_RigidBodyComponent_SetLinearVelocity(uint64_t entityID, glm::vec3* velocity); void Prism_RigidBodyComponent_SetLinearVelocity(uint64_t entityID, const glm::vec3* velocity);
void Prism_RigidBodyComponent_GetAngularVelocity(uint64_t entityID, glm::vec3* outVelocity); void Prism_RigidBodyComponent_GetAngularVelocity(uint64_t entityID, glm::vec3* outVelocity);
void Prism_RigidBodyComponent_SetAngularVelocity(uint64_t entityID, glm::vec3* velocity); void Prism_RigidBodyComponent_SetAngularVelocity(uint64_t entityID, const glm::vec3* velocity);
void Prism_RigidBodyComponent_Rotate(uint64_t entityID, glm::vec3* rotation); void Prism_RigidBodyComponent_Rotate(uint64_t entityID, const glm::vec3* rotation);
uint32_t Prism_RigidBodyComponent_GetLayer(uint64_t entityID); uint32_t Prism_RigidBodyComponent_GetLayer(uint64_t entityID);
float Prism_RigidBodyComponent_GetMass(uint64_t entityID); float Prism_RigidBodyComponent_GetMass(uint64_t entityID);
void Prism_RigidBodyComponent_SetMass(uint64_t entityID, float mass); void Prism_RigidBodyComponent_SetMass(uint64_t entityID, float mass);