Added 90% of transform component & transform system.

This commit is contained in:
Cocoa 2022-09-21 00:49:52 +08:00
parent cc6d1dd95b
commit 9c69d41a4e
8 changed files with 239 additions and 55 deletions

View File

@ -211,6 +211,7 @@ xcopy /s /r /y /q "$(SolutionDir)/Dependencies/dotnet/bin" "$(OutDir)"</Command
<ClInclude Include="src\Math\SHQuaternion.h" />
<ClInclude Include="src\Math\Transform\SHTransform.h" />
<ClInclude Include="src\Math\Transform\SHTransformComponent.h" />
<ClInclude Include="src\Math\Transform\SHTransformSystem.h" />
<ClInclude Include="src\Math\Vector\SHVec2.h" />
<ClInclude Include="src\Math\Vector\SHVec3.h" />
<ClInclude Include="src\Math\Vector\SHVec4.h" />
@ -307,6 +308,7 @@ xcopy /s /r /y /q "$(SolutionDir)/Dependencies/dotnet/bin" "$(OutDir)"</Command
<ClCompile Include="src\Math\SHQuaternion.cpp" />
<ClCompile Include="src\Math\Transform\SHTransform.cpp" />
<ClCompile Include="src\Math\Transform\SHTransformComponent.cpp" />
<ClCompile Include="src\Math\Transform\SHTransformSystem.cpp" />
<ClCompile Include="src\Math\Vector\SHVec2.cpp" />
<ClCompile Include="src\Math\Vector\SHVec3.cpp" />
<ClCompile Include="src\Math\Vector\SHVec4.cpp" />

View File

@ -499,6 +499,7 @@
<Filter>Tools</Filter>
</ClInclude>
<ClInclude Include="src\Math\Transform\SHTransformComponent.h" />
<ClInclude Include="src\Math\Transform\SHTransformSystem.h" />
</ItemGroup>
<ItemGroup>
<ClCompile Include="src\ECS_Base\Components\SHComponent.cpp">
@ -740,5 +741,6 @@
<Filter>Tools</Filter>
</ClCompile>
<ClCompile Include="src\Math\Transform\SHTransformComponent.cpp" />
<ClCompile Include="src\Math\Transform\SHTransformSystem.cpp" />
</ItemGroup>
</Project>

View File

@ -51,15 +51,6 @@ namespace SHADE
return (position != rhs.position || rotation != rhs.rotation || scale != rhs.scale);
}
/*-----------------------------------------------------------------------------------*/
/* Getter Function Definitions */
/*-----------------------------------------------------------------------------------*/
const SHMatrix& SHTransform::GetTRS() const
{
return trs;
}
/*-----------------------------------------------------------------------------------*/
/* Public Function Member Definitions */
/*-----------------------------------------------------------------------------------*/

View File

@ -29,9 +29,11 @@ namespace SHADE
static const SHTransform Identity;
SHVec3 position;
SHVec3 rotation;
SHVec3 scale;
SHVec3 position;
SHVec3 rotation;
SHVec3 scale;
SHMatrix trs;
/*---------------------------------------------------------------------------------*/
/* Constructors & Destructor */
@ -54,24 +56,12 @@ namespace SHADE
[[nodiscard]] bool operator==(const SHTransform& rhs) const noexcept;
[[nodiscard]] bool operator!=(const SHTransform& rhs) const noexcept;
/*---------------------------------------------------------------------------------*/
/* Getter Functions */
/*---------------------------------------------------------------------------------*/
[[nodiscard]] const SHMatrix& GetTRS() const;
/*---------------------------------------------------------------------------------*/
/* Function Members */
/*---------------------------------------------------------------------------------*/
const SHMatrix& ComputeTRS();
private:
/*---------------------------------------------------------------------------------*/
/* Data Members */
/*---------------------------------------------------------------------------------*/
SHMatrix trs;
};
} // namespace SHADE

View File

@ -21,16 +21,15 @@ namespace SHADE
SHTransformComponent::SHTransformComponent() noexcept
: SHComponent {}
, parent { nullptr }
{}
/*-----------------------------------------------------------------------------------*/
/* Getter Function Definitions */
/*-----------------------------------------------------------------------------------*/
const SHTransform* SHTransformComponent::GetParent() const noexcept
bool SHTransformComponent::HasChanged() const noexcept
{
return parent;
return dirty;
}
const SHVec3& SHTransformComponent::GetLocalPosition() const noexcept
@ -63,65 +62,83 @@ namespace SHADE
return world.scale;
}
SHMatrix SHTransformComponent::GetLocalToWorld() const noexcept
const SHMatrix& SHTransformComponent::GetLocalToWorld() const noexcept
{
return parent != nullptr ? parent->GetTRS() : SHMatrix::Identity;
return local.trs;
}
SHMatrix SHTransformComponent::GetWorldToLocal() const noexcept
{
return parent != nullptr ? SHMatrix::Inverse(parent->GetTRS()) : SHMatrix::Identity;
return SHMatrix::Inverse(local.trs);
}
const SHMatrix& SHTransformComponent::GetTRS() const noexcept
{
return world.GetTRS();
return world.trs;
}
/*-----------------------------------------------------------------------------------*/
/* Setter Function Definitions */
/*-----------------------------------------------------------------------------------*/
void SHTransformComponent::SetParent(const SHTransform* parentTransform) noexcept
{
if (parent == nullptr)
SHLOG_WARNING("Removing parent transform from Entity {}", GetEID())
parent = parentTransform;
}
void SHTransformComponent::SetLocalPosition(const SHVec3& newLocalPosition) noexcept
{
dirty = true;
local.position = newLocalPosition;
updateQueue.push({ UpdateCommandType::LOCAL_POSITION, newLocalPosition });
}
void SHTransformComponent::SetLocalRotation(const SHVec3& newLocalRotation) noexcept
{
dirty = true;
local.rotation = newLocalRotation;
updateQueue.push({ UpdateCommandType::LOCAL_ROTATION, newLocalRotation });
}
void SHTransformComponent::SetLocalRotation(float pitch, float yaw, float roll) noexcept
{
dirty = true;
local.rotation.x = pitch;
local.rotation.y = yaw;
local.rotation.z = roll;
}
void SHTransformComponent::SetLocalScale(const SHVec3& newLocalScale) noexcept
{
dirty = true;
local.scale = newLocalScale;
updateQueue.push({ UpdateCommandType::LOCAL_SCALE, newLocalScale });
}
void SHTransformComponent::SetWorldPosition(const SHVec3& newWorldPosition) noexcept
{
dirty = true;
world.position = newWorldPosition;
updateQueue.push({ UpdateCommandType::WORLD_POSITION, newWorldPosition });
}
void SHTransformComponent::SetWorldRotation(const SHVec3& newWorldRotation) noexcept
{
dirty = true;
world.rotation = newWorldRotation;
updateQueue.push({ UpdateCommandType::WORLD_ROTATION, newWorldRotation });
}
void SHTransformComponent::SetWorldRotation(float pitch, float yaw, float roll) noexcept
{
dirty = true;
world.rotation.x = pitch;
world.rotation.y = yaw;
world.rotation.z = roll;
updateQueue.push({ UpdateCommandType::WORLD_ROTATION, SHVec3{ pitch, yaw, roll} });
}
void SHTransformComponent::SetWorldScale(const SHVec3& newWorldScale) noexcept
{
dirty = true;
world.scale = newWorldScale;
updateQueue.push({ UpdateCommandType::WORLD_SCALE, newWorldScale });
}

View File

@ -25,8 +25,14 @@ namespace SHADE
class SH_API SHTransformComponent : public SHComponent
{
public:
private:
/*---------------------------------------------------------------------------------*/
/* Friends */
/*---------------------------------------------------------------------------------*/
friend class SHTransformSystem;
public:
/*---------------------------------------------------------------------------------*/
/* Constructors & Destructor */
/*---------------------------------------------------------------------------------*/
@ -45,7 +51,7 @@ namespace SHADE
/* Getter Functions */
/*---------------------------------------------------------------------------------*/
[[nodiscard]] const SHTransform* GetParent () const noexcept;
[[nodiscard]] bool HasChanged () const noexcept;
[[nodiscard]] const SHVec3& GetLocalPosition () const noexcept;
[[nodiscard]] const SHVec3& GetLocalRotation () const noexcept;
@ -54,7 +60,7 @@ namespace SHADE
[[nodiscard]] const SHVec3& GetWorldRotation () const noexcept;
[[nodiscard]] const SHVec3& GetWorldScale () const noexcept;
[[nodiscard]] SHMatrix GetLocalToWorld () const noexcept;
[[nodiscard]] const SHMatrix& GetLocalToWorld () const noexcept;
[[nodiscard]] SHMatrix GetWorldToLocal () const noexcept;
[[nodiscard]] const SHMatrix& GetTRS () const noexcept;
@ -63,13 +69,13 @@ namespace SHADE
/* Setter Functions */
/*---------------------------------------------------------------------------------*/
void SetParent (const SHTransform* parentTransform) noexcept;
void SetLocalPosition (const SHVec3& newLocalPosition) noexcept;
void SetLocalRotation (const SHVec3& newLocalRotation) noexcept;
void SetLocalRotation (float pitch, float yaw, float roll) noexcept;
void SetLocalScale (const SHVec3& newLocalScale) noexcept;
void SetWorldPosition (const SHVec3& newWorldPosition) noexcept;
void SetWorldRotation (const SHVec3& newWorldRotation) noexcept;
void SetWorldRotation (float pitch, float yaw, float roll) noexcept;
void SetWorldScale (const SHVec3& newWorldScale) noexcept;
private:
@ -79,10 +85,7 @@ namespace SHADE
enum class UpdateCommandType
{
LOCAL_POSITION
, LOCAL_ROTATION
, LOCAL_SCALE
, WORLD_POSITION
WORLD_POSITION
, WORLD_ROTATION
, WORLD_SCALE
};
@ -104,11 +107,12 @@ namespace SHADE
/* Data Members */
/*---------------------------------------------------------------------------------*/
const SHTransform* parent;
SHTransform local;
SHTransform world;
bool dirty;
UpdateQueue updateQueue;
SHTransform local; // Local TRS holds Local To World Transform
SHTransform world;
UpdateQueue updateQueue;
};

View File

@ -0,0 +1,121 @@
/****************************************************************************************
* \file SHTransformSystem.cpp
* \author Diren D Bharwani, diren.dbharwani, 390002520
* \brief Implementation for the Transform System
*
* \copyright Copyright (C) 2022 DigiPen Institute of Technology. Reproduction or
* disclosure of this file or its contents without the prior written consent
* of DigiPen Institute of Technology is prohibited.
****************************************************************************************/
#include <SHpch.h>
// Primary Header
#include "SHTransformSystem.h"
// Project Headers
#include "Scene/SHSceneManager.h"
#include "ECS_Base/Managers/SHComponentManager.h"
namespace SHADE
{
/*-----------------------------------------------------------------------------------*/
/* Constructors & Destructor Definitions */
/*-----------------------------------------------------------------------------------*/
SHTransformSystem::SHTransformSystem()
: SHSystemRoutine { "Transform Routine", false }
{}
/*-----------------------------------------------------------------------------------*/
/* Public Function Member Definitions */
/*-----------------------------------------------------------------------------------*/
void SHTransformSystem::Execute(double dt) noexcept
{
// Get the current scene graph to traverse and update
auto& sceneGraph = SHSceneManager::GetCurrentSceneGraph();
UpdateEntity(sceneGraph.GetRoot());
// Clear all dirty flags
}
/*-----------------------------------------------------------------------------------*/
/* Private Function Member Definitions */
/*-----------------------------------------------------------------------------------*/
void SHTransformSystem::UpdateEntity(const SHSceneNode* node)
{
const auto* NODE_TRANSFORM = SHComponentManager::GetComponent_s<SHTransformComponent>(node->GetEntityID());
const bool HAS_PARENT_CHANGED = NODE_TRANSFORM && NODE_TRANSFORM->dirty;
for (const auto* child : node->GetChildren())
{
const bool HAS_TRANSFORM = SHComponentManager::HasComponent<SHTransformComponent>(child->GetEntityID());
if (!HAS_TRANSFORM)
continue;
auto* childTransform = SHComponentManager::GetComponent<SHTransformComponent>(child->GetEntityID());
if (childTransform->dirty || HAS_PARENT_CHANGED)
UpdateTransform(*childTransform, NODE_TRANSFORM);
UpdateEntity(child);
}
}
void SHTransformSystem::UpdateTransform(SHTransformComponent& tf, const SHTransformComponent* parent)
{
SHMatrix localToWorld = SHMatrix::Identity;
SHMatrix worldToLocal = SHMatrix::Identity;
if (parent)
{
localToWorld = parent->GetTRS();
worldToLocal = SHMatrix::Inverse(tf.local.trs);
}
while (!tf.updateQueue.empty())
{
const auto& UPDATE_COMMAND = tf.updateQueue.front();
switch (UPDATE_COMMAND.type)
{
case SHTransformComponent::UpdateCommandType::WORLD_POSITION:
{
tf.local.position = SHVec3::Transform(UPDATE_COMMAND.data, worldToLocal);
break;
}
case SHTransformComponent::UpdateCommandType::WORLD_ROTATION:
{
tf.local.rotation = tf.world.rotation;
if (parent)
tf.local.rotation -= parent->GetLocalRotation();
break;
}
case SHTransformComponent::UpdateCommandType::WORLD_SCALE:
{
tf.local.scale = tf.world.scale;
if (parent)
tf.local.scale /= parent->GetLocalScale();
break;
}
default: break; // Redundant
}
tf.updateQueue.pop();
}
tf.local.trs = localToWorld;
tf.world.position = SHVec3::Transform(tf.local.position, localToWorld);
tf.world.rotation = tf.local.rotation + (parent ? parent->GetLocalRotation() : SHVec3::Zero);
tf.world.scale = tf.local.scale * (parent ? parent->GetLocalScale() : SHVec3::One);
tf.world.ComputeTRS();
}
} // namespace SHADE

View File

@ -0,0 +1,57 @@
/****************************************************************************************
* \file SHTransformSystem.h
* \author Diren D Bharwani, diren.dbharwani, 390002520
* \brief Interface for the Transform System
*
* \copyright Copyright (C) 2022 DigiPen Institute of Technology. Reproduction or
* disclosure of this file or its contents without the prior written consent
* of DigiPen Institute of Technology is prohibited.
****************************************************************************************/
#pragma once
// Project Headers
#include "SHTransformComponent.h"
#include "Scene/SHSceneGraph.h"
#include "ECS_Base/System/SHSystemRoutine.h"
namespace SHADE
{
/*-----------------------------------------------------------------------------------*/
/* Type Definitions */
/*-----------------------------------------------------------------------------------*/
class SH_API SHTransformSystem : public SHSystemRoutine
{
public:
/*---------------------------------------------------------------------------------*/
/* Constructors & Destructor */
/*---------------------------------------------------------------------------------*/
SHTransformSystem ();
~SHTransformSystem () = default;
SHTransformSystem (const SHTransformSystem&) = delete;
SHTransformSystem (SHTransformSystem&&) = delete;
SHTransformSystem& operator= (const SHTransformSystem&) = delete;
SHTransformSystem& operator= (SHTransformSystem&&) = delete;
/*---------------------------------------------------------------------------------*/
/* Function Members */
/*---------------------------------------------------------------------------------*/
void Execute(double dt) noexcept override;
private:
/*---------------------------------------------------------------------------------*/
/* Function Members */
/*---------------------------------------------------------------------------------*/
static void UpdateEntity (const SHSceneNode* node);
static void UpdateTransform(SHTransformComponent& tf, const SHTransformComponent* parent = nullptr);
};
} // namespace SHADE