94 lines
3.8 KiB
C++
94 lines
3.8 KiB
C++
#include "HydraTransformSystem.h"
|
|
#include "../../engine/HydraEngine.h"
|
|
#include "../HydraECS.h"
|
|
#include "../components/HydraPositionComponent.h"
|
|
#include "../../scheduler/HydraTaskScheduler.h"
|
|
#include "../../task/buffer/HydraCreateGPUBufferTask.hpp"
|
|
#include "../../task/buffer/HydraUpdateWholeGPUBufferTask.hpp"
|
|
#include "../../actor/HydraActorManager.h"
|
|
|
|
void HydraTransformSystem::UpdateTransform(HydraID actor_id)
|
|
{
|
|
|
|
HydraECS *ecs = GetEngine()->ECS();
|
|
HydraPositionComponent &pos_comp = ecs->GetComponent<HydraPositionComponent>(actor_id);
|
|
pos_comp.needs_update = true;
|
|
m_entities_to_update.push(actor_id);
|
|
}
|
|
|
|
void HydraTransformSystem::Initialise()
|
|
{
|
|
HydraTaskScheduler *task_scheduler = GetEngine()->TaskScheduler();
|
|
HydraID create_gpu_buffer_task_id = task_scheduler->CreateTask<HydraCreateGPUBufferTask>(HydraThreadAffinity::Render);
|
|
HydraCreateGPUBufferTask *task = static_cast<HydraCreateGPUBufferTask *>(task_scheduler->GetTask(create_gpu_buffer_task_id));
|
|
task->Intialise("PositionsBuffer", 1, MAX_ACTORS * sizeof(glm::mat4),
|
|
&m_transform_buffer_id, HYDRA_BUFFER_TYPE::HYDRA_SSBO_BUFFER);
|
|
task_scheduler->WaitForTask(create_gpu_buffer_task_id);
|
|
m_model_matrix.resize(MAX_ACTORS);
|
|
}
|
|
|
|
void HydraTransformSystem::UpdateSystem(float delta_t_seconds)
|
|
{
|
|
HydraECS *ecs = GetEngine()->ECS();
|
|
|
|
while(m_entities_to_update.size() > 0)
|
|
{
|
|
HydraID actor_id = m_entities_to_update.front();
|
|
m_entities_to_update.pop();
|
|
HydraPositionComponent &pos_comp = ecs->GetComponent<HydraPositionComponent>(actor_id);
|
|
if(pos_comp.needs_update)
|
|
{
|
|
HydraID parent_id = GetEngine()->ActorManager()->GetRoot(actor_id);
|
|
glm::mat4 identity = glm::mat4(1);
|
|
_UpdateChild(INVALID_HYDRA_ID, parent_id, identity);
|
|
}
|
|
}
|
|
_WriteToGPU();
|
|
}
|
|
|
|
void HydraTransformSystem::InitialiseComponent(HydraID actor_id)
|
|
{
|
|
HydraECS *ecs = GetEngine()->ECS();
|
|
|
|
HydraPositionComponent &pos_comp = ecs->GetComponent<HydraPositionComponent>(actor_id);
|
|
if (pos_comp.needs_update)
|
|
{
|
|
glm::mat4 identity = glm::mat4(1);
|
|
_UpdateChild(INVALID_HYDRA_ID, actor_id, identity);
|
|
}
|
|
}
|
|
|
|
void HydraTransformSystem::_UpdateChild(HydraID parent_id, HydraID actor_id, glm::mat4 parent_transform)
|
|
{
|
|
HydraECS *ecs = GetEngine()->ECS();
|
|
std::vector<HydraID> &child_ids = GetEngine()->ActorManager()->GetChildren(actor_id);
|
|
glm::mat4 trans = parent_transform;
|
|
|
|
if (ecs->HasComponent<HydraPositionComponent>(actor_id))
|
|
{
|
|
HydraPositionComponent &pos_comp = ecs->GetComponent<HydraPositionComponent>(actor_id);
|
|
glm::mat4 trans_matrix = glm::translate(glm::vec3(pos_comp.position.x, pos_comp.position.y, pos_comp.position.z));
|
|
glm::mat4 rot_matrix = glm::toMat4(glm::quat(pos_comp.orientation));
|
|
glm::mat4 scale_matrix = glm::scale(pos_comp.scale);
|
|
glm::mat4 model_matrix = trans_matrix * rot_matrix * scale_matrix;
|
|
|
|
pos_comp.transform = trans * model_matrix;
|
|
pos_comp.needs_update = false;
|
|
m_model_matrix[actor_id] = pos_comp.transform;
|
|
trans = pos_comp.transform;
|
|
}
|
|
for (uint32_t child_idx = 0; child_idx < child_ids.size(); child_idx++)
|
|
{
|
|
_UpdateChild(actor_id, child_ids[child_idx], trans);
|
|
}
|
|
}
|
|
|
|
void HydraTransformSystem::_WriteToGPU()
|
|
{
|
|
HydraTaskScheduler *task_scheduler = GetEngine()->TaskScheduler();
|
|
HydraID update_buffer_task_id = task_scheduler->CreateTask<HydraUpdateWholeGPUBufferTask>(HydraThreadAffinity::Render);
|
|
HydraUpdateWholeGPUBufferTask *task = static_cast<HydraUpdateWholeGPUBufferTask *>(task_scheduler->GetTask(update_buffer_task_id));
|
|
task->Intialise(m_transform_buffer_id, &m_model_matrix[0]);
|
|
task_scheduler->WaitForTask(update_buffer_task_id);
|
|
}
|