Named Array Collections
From K-3D
Overview
Many K-3D data structures, particularly including the Geometric Primitive Data Structures store collections of arrays. In particular, all of the geometric primitives store primitive-specific data "components", such as per-vertex, per-face, and per-edge data. To manage storage of these arrays, K-3D provides several collection objects:
- k3d::named_arrays - stores a collection of named arrays with unrelated lengths.
- Implemented as a std::map<k3d::string_t, k3d::pipeline_data<k3d::array> >. This means that named_array assignment automatically shallow-copies arrays.
- k3d::table - stores a collection of named arrays, all-of-which must have identical lengths. Used to store mesh primitive structure and attributes such as per-vertex or per-face data.
- Also implemented as a std::map<k3d::string_t, k3d::pipeline_data<k3d::array> >.
- k3d::named_tables - stores a collection of named k3d::table objects. Used to store the components (structure and attributes) in a generic geometric primitive.
- Implemented as a std::map<k3d::string_t, k3d::table>. Note that storing each k3d::table using pipeline_data would have been redundant.
Note the subtle distinction between k3d::named_arrays and k3d::table - k3d::named_arrays stores an arbitrary collection of arrays that may be completely unrelated to one-another, while k3d::table stores a collection of arrays that share cardinality - i.e. attributes must be defined for every entity in a set (every point, every edge, every face, etc) Thus, every array in k3d::table must have the same length at all times.
API
Both named_arrays and table provide similar methods for manipulating arrays:
- Overloaded T& create() methods make it easy to create a new array and assign it to a local variable for immediate use, and are intentionally modeled to be similar to the Pipeline Data API:
k3d::mesh::colors_t& color = Output.vertex_data.create<k3d::mesh::colors_t>("Cs"); k3d::mesh::doubles_t& weight = Output.vertex_data.create("weight", new k3d::mesh::doubles_t(vertex_count, 1.0));
- Overloaded const T* lookup() methods handle the most common cases searching for a read-only input array:
const k3d::array* const abstract_array = Input.point_attributes.lookup("label"); const k3d::mesh::colors_t* const color = Input.point_attributes.lookup<k3d::mesh::colors_t>("Cs");
- Overloaded T* writable() methods handle searches for writable output arrays, and again are modeled on the Pipeline Data API:
k3d::array* const abstract_array = Input.point_attributes.writable("label"); k3d::mesh::colors_t* const color = Input.point_attributes.writable<k3d::mesh::colors_t>("Cs");
Note that lookup() and writable() may fail: an array with the given name or given type may not exist. This is why they return arrays by-pointer instead of by-reference - as always, you must test for NULL pointers before dereferencing them!
- The k3d::table API provides a resize() method that resizes every array in the collection.
- The k3d::named_table class provides a const table* lookup() method that can be used to search for a table by-name.