MayaFlux 0.4.0
Digital-First Multimedia Processing Framework
Loading...
Searching...
No Matches
MeshProcessor.cpp
Go to the documentation of this file.
1#include "MeshProcessor.hpp"
2#include "MeshBuffer.hpp"
3
8
9namespace MayaFlux::Buffers {
10
16
17// =============================================================================
18// on_attach
19// =============================================================================
20
21void MeshProcessor::on_attach(const std::shared_ptr<Buffer>& buffer)
22{
23 if (!m_buffer_service) {
26 }
27
28 if (!m_buffer_service) {
29 error<std::runtime_error>(
32 std::source_location::current(),
33 "MeshProcessor requires a valid BufferService");
34 }
35
36 auto mesh_buf = std::dynamic_pointer_cast<MeshBuffer>(buffer);
37 if (!mesh_buf) {
39 "MeshProcessor: attached to non-MeshBuffer — detaching");
40 return;
41 }
42
43 if (!mesh_buf->m_mesh_data.is_valid()) {
45 "MeshProcessor: MeshData is not valid on attach — no GPU resources allocated");
46 return;
47 }
48
49 m_mesh_buffer = mesh_buf;
50
51 ensure_initialized(mesh_buf);
52
53 allocate_gpu_buffers(mesh_buf);
54 upload_vertices(mesh_buf);
55 upload_indices(mesh_buf);
57
58 mesh_buf->clear_vertices_dirty();
59 mesh_buf->clear_indices_dirty();
60
61 mesh_buf->set_vertex_layout(mesh_buf->m_mesh_data.layout);
62
64 "MeshProcessor: initialised — {} vertices, {} indices ({} faces), stride {}",
65 mesh_buf->get_vertex_count(),
66 mesh_buf->get_index_count(),
67 mesh_buf->get_face_count(),
68 mesh_buf->m_mesh_data.layout.stride_bytes);
69}
70
71void MeshProcessor::on_detach(const std::shared_ptr<Buffer>& /*buffer*/)
72{
73 m_mesh_buffer.reset();
74 m_gpu_index_buffer.reset();
75 m_vertex_staging.reset();
76 m_index_staging.reset();
77}
78
79// =============================================================================
80// processing_function — per-cycle dirty check
81// =============================================================================
82
83void MeshProcessor::processing_function(const std::shared_ptr<Buffer>& /*buffer*/)
84{
85 if (!m_mesh_buffer) {
86 return;
87 }
88
89 if (m_mesh_buffer->vertices_dirty()) {
91 m_mesh_buffer->clear_vertices_dirty();
92
94 "MeshProcessor: re-uploaded vertex data ({} bytes)",
95 m_mesh_buffer->get_size_bytes());
96 }
97
98 if (m_mesh_buffer->indices_dirty()) {
101 m_mesh_buffer->clear_indices_dirty();
102
104 "MeshProcessor: re-uploaded index data ({} indices)",
105 m_mesh_buffer->get_index_count());
106 }
107}
108
109// =============================================================================
110// Private helpers
111// =============================================================================
112
113void MeshProcessor::allocate_gpu_buffers(const std::shared_ptr<MeshBuffer>& buf)
114{
115 const auto* vb = std::get_if<std::vector<uint8_t>>(
116 &buf->m_mesh_data.vertex_variant);
117 const auto* ib = std::get_if<std::vector<uint32_t>>(
118 &buf->m_mesh_data.index_variant);
119
120 if (!vb || vb->empty() || !ib || ib->empty()) {
122 "MeshProcessor::allocate_gpu_buffers: empty vertex or index data");
123 return;
124 }
125
126 if (!buf->is_host_visible()) {
128 }
129
130 const size_t idx_bytes = ib->size() * sizeof(uint32_t);
131 m_gpu_index_buffer = std::make_shared<VKBuffer>(
132 idx_bytes,
135
138
140 "MeshProcessor: allocated vertex buffer ({} bytes) + index buffer ({} bytes)",
141 vb->size(), idx_bytes);
142}
143
144void MeshProcessor::upload_vertices(const std::shared_ptr<MeshBuffer>& buf)
145{
146 const auto* vb = std::get_if<std::vector<uint8_t>>(
147 &buf->m_mesh_data.vertex_variant);
148 if (!vb || vb->empty()) {
149 return;
150 }
151
153 vb->data(),
154 vb->size(),
155 std::dynamic_pointer_cast<VKBuffer>(buf),
156 buf->is_host_visible() ? nullptr : m_vertex_staging);
157}
158
159void MeshProcessor::upload_indices(const std::shared_ptr<MeshBuffer>& buf)
160{
161 const auto* ib = std::get_if<std::vector<uint32_t>>(
162 &buf->m_mesh_data.index_variant);
163 if (!ib || ib->empty() || !m_gpu_index_buffer) {
164 return;
165 }
166
168 ib->data(),
169 ib->size() * sizeof(uint32_t),
172}
173
175{
177 return;
178 }
179
180 m_mesh_buffer->set_index_resources(
181 m_gpu_index_buffer->get_buffer(),
182 m_gpu_index_buffer->get_buffer_resources().memory,
183 m_gpu_index_buffer->get_size_bytes());
184}
185
186} // namespace MayaFlux::Buffers
#define MF_INFO(comp, ctx,...)
#define MF_ERROR(comp, ctx,...)
#define MF_DEBUG(comp, ctx,...)
void processing_function(const std::shared_ptr< Buffer > &buffer) override
The core processing function that must be implemented by derived classes.
std::shared_ptr< VKBuffer > m_vertex_staging
void allocate_gpu_buffers(const std::shared_ptr< MeshBuffer > &buf)
void upload_vertices(const std::shared_ptr< MeshBuffer > &buf)
std::shared_ptr< VKBuffer > m_index_staging
std::shared_ptr< MeshBuffer > m_mesh_buffer
std::shared_ptr< VKBuffer > m_gpu_index_buffer
void upload_indices(const std::shared_ptr< MeshBuffer > &buf)
void on_attach(const std::shared_ptr< Buffer > &buffer) override
Called when this processor is attached to a buffer.
void on_detach(const std::shared_ptr< Buffer > &buffer) override
Called when this processor is detached from a buffer.
Registry::Service::BufferService * m_buffer_service
Definition VKBuffer.hpp:651
void ensure_initialized(const std::shared_ptr< VKBuffer > &buffer)
Definition VKBuffer.cpp:462
Interface * get_service()
Query for a backend service.
static BackendRegistry & instance()
Get the global registry instance.
void upload_resizing(const void *data, size_t size, const std::shared_ptr< VKBuffer > &target, const std::shared_ptr< VKBuffer > &staging, float growth_factor)
Upload size bytes to target, growing both buffers first if needed.
@ GRAPHICS_BACKEND
Standard graphics processing backend configuration.
std::shared_ptr< VKBuffer > create_staging_buffer(size_t size)
Create staging buffer for transfers.
@ BufferProcessing
Buffer processing (Buffers::BufferManager, processing chains)
@ Buffers
Buffers, Managers, processors and processing chains.
@ UNKNOWN
Unknown or undefined modality.
Backend buffer management service interface.