MayaFlux 1.0.0
Digital-First Multimedia Processing Framework
Loading...
Searching...
No Matches

◆ write_network_geometry_buffer_sample()

MAYAFLUX_API bool MayaFlux::IO::write_network_geometry_buffer_sample ( SpatialCache &  cache,
const std::string &  stream_name,
const std::shared_ptr< Buffers::NetworkGeometryBuffer > &  buffer 
)

Pack a NetworkGeometryBuffer's driving network into one or more SpatialCache streams, choosing CPU or GPU readback depending on whether the network's CPU-side vertex state is still authoritative.

A GpuFieldOperator anywhere in the network's operator chain (detected via OperatorChain::find<GpuFieldOperator>()) means vertex positions are mutated directly on the GPU: the CPU-side GraphicsOperator buffer write_operator_sample() would otherwise read is stale. In that case this downloads the live vertex bytes straight from the buffer itself (it is a VKBuffer, so the same download_from_gpu_async() pattern download_compute_mesh() uses for ComputeMeshBuffer applies directly), using the still-CPU-tracked get_vertex_count()/get_vertex_layout()/ declared_topology() for population size, record schema, and sample shape (these describe the buffer's contract, not its live GPU bytes, so they stay valid regardless of which side owns the vertex data), then reads the downloaded bytes as Kakshya::Vertex records exactly as write_operator_sample() reads them from CPU memory: color, scalar, uv, normal, and tangent all come along with position, since the record schema is unchanged by which side owns the bytes; only the transfer differs. A curve topology chunks on build_cluster_ids() the same way write_operator_sample() does, since graph/path membership is structural and unaffected by what a GpuFieldOperator does to positions. Also attaches the declared hash_cluster_id state field as a "cluster" attribute when present. Written as a single stream named stream_name: once GPU-driven, the buffer is one flat array and no longer separable by originating operator. Velocities and any per-rule state beyond hash_cluster_id are left out deliberately, the same way relaxation_grid_positions() leaves per-cell state to the caller: a GpuFieldOperator's own bespoke state fields have no shape this function can decode generically.

Without a GpuFieldOperator, every GraphicsOperator on the network (its primary operator plus any in get_operator_chain()) is CPU-readable and each is written through write_operator_sample() as its own set: a network with exactly one GraphicsOperator keeps the plain stream_name unchanged, while a network chaining several writes one child stream per operator, named "<stream_name>_<get_type_name()>" (a trailing index appended for a repeated type), the same role multiple named aiMesh entries play for a multi-submesh ModelWriter export. A per-operator "cluster" attribute (from that operator's own build_cluster_ids()) continues to mark distinct populations within one operator, e.g. PhysicsOperator's collections.

Parameters
cacheTarget cache, already open().
stream_nameStream (or stream-name prefix, if the network chains several GraphicsOperators) to write.
bufferSource buffer. Must be non-null, with a non-null network exposing at least one GraphicsOperator.
Returns
False if buffer/network is missing, no GraphicsOperator is found, or any underlying write_operator_sample()/cache.write() call fails.

Definition at line 346 of file SpatialExport.cpp.

350{
351 if (!buffer) {
352 MF_ERROR(Journal::Component::IO, Journal::Context::FileIO,
353 "write_network_geometry_buffer_sample: null buffer");
354 return false;
355 }
356
357 auto network = buffer->get_network();
358 if (!network) {
359 MF_ERROR(Journal::Component::IO, Journal::Context::FileIO,
360 "write_network_geometry_buffer_sample: buffer has no network");
361 return false;
362 }
363
364 auto chain = network->get_operator_chain();
365
366 if (chain && chain->find<Nodes::Network::GpuFieldOperator>()) {
367 auto* graphics_op = dynamic_cast<Nodes::Network::GraphicsOperator*>(network->get_operator());
368 if (!graphics_op) {
369 MF_ERROR(Journal::Component::IO, Journal::Context::FileIO,
370 "write_network_geometry_buffer_sample: network's primary operator is not a GraphicsOperator");
371 return false;
372 }
373 return write_network_geometry_buffer_gpu_sample(cache, stream_name, buffer, graphics_op);
374 }
375
376 std::vector<std::pair<std::string, Nodes::Network::GraphicsOperator*>> graphics_ops;
377 if (auto* primary = dynamic_cast<Nodes::Network::GraphicsOperator*>(network->get_operator())) {
378 graphics_ops.emplace_back(std::string(primary->get_type_name()), primary);
379 }
380 if (chain) {
381 for (const auto& op : chain->operators()) {
382 if (auto* secondary = dynamic_cast<Nodes::Network::GraphicsOperator*>(op.get())) {
383 graphics_ops.emplace_back(std::string(secondary->get_type_name()), secondary);
384 }
385 }
386 }
387
388 if (graphics_ops.empty()) {
389 MF_ERROR(Journal::Component::IO, Journal::Context::FileIO,
390 "write_network_geometry_buffer_sample: network has no GraphicsOperator");
391 return false;
392 }
393
394 if (graphics_ops.size() == 1) {
395 return write_operator_sample(cache, stream_name, graphics_ops.front().second);
396 }
397
398 std::unordered_map<std::string, int> seen;
399 for (const auto& [type_name, op] : graphics_ops) {
400 int& occurrence = seen[type_name];
401 std::string set_name = stream_name;
402 set_name.append("_").append(type_name);
403 if (occurrence != 0) {
404 set_name.append(std::to_string(occurrence));
405 }
406 ++occurrence;
407
408 if (!write_operator_sample(cache, set_name, op)) {
409 return false;
410 }
411 }
412
413 return true;
414}
#define MF_ERROR(comp, ctx,...)
Core::GlobalNetworkConfig network
Definition Config.cpp:43
std::shared_ptr< NetworkGeometryBuffer > buffer
BufferProcessingChain * chain
bool write_operator_sample(SpatialCache &cache, const std::string &stream_name, const Nodes::Network::GraphicsOperator *op)
Pack one GraphicsOperator's current vertex state into a SpatialCache stream, as a Points or Curves sa...
constexpr std::string_view type_name() noexcept
Returns the fully qualified compile-time type name of T.
Definition TypeInfo.hpp:28

References buffer, chain, MayaFlux::Journal::FileIO, MayaFlux::Journal::IO, MF_ERROR, network, and write_operator_sample().

Referenced by make_network_geometry_source().

+ Here is the call graph for this function:
+ Here is the caller graph for this function: