HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
GT_AttributeList.h
Go to the documentation of this file.
1 /*
2  * PROPRIETARY INFORMATION. This software is proprietary to
3  * Side Effects Software Inc., and is not to be reproduced,
4  * transmitted, or disclosed in any way without written permission.
5  *
6  * NAME: GT_AttributeList.h ( GT Library, C++)
7  *
8  * COMMENTS:
9  */
10 
11 #ifndef __GT_AttributeList__
12 #define __GT_AttributeList__
13 
14 #include "GT_API.h"
15 #include "GT_AttributeMap.h"
16 #include "GT_DataArray.h"
17 #include "GT_Handles.h"
18 #include "GT_Types.h"
19 
20 #include <UT/UT_Assert.h>
21 #include <UT/UT_IntrusivePtr.h>
22 #include <UT/UT_StringHolder.h>
23 #include <SYS/SYS_Inline.h>
24 
25 #include <utility>
26 
27 
28 class GT_DataArray;
29 class GT_AttributeMerge;
30 class UT_JSONWriter;
31 class GU_Detail;
32 
34  : public UT_IntrusiveRefCounter<GT_AttributeList>
35 {
36 public:
37  /// An attribute list stores a list of GT_DataArray values for each
38  /// attribute defined in the map. @c motion_segments specifies the number
39  /// of different motion segments.
40  GT_AttributeList(const GT_AttributeMapHandle &map, int motion_segments=1);
43 
44  /// Create an attribute list using varying number of
45  /// (const UT_StringHolder &name, const GT_DataArrayHandle &data) pairs.
46  /// For example: @code
47  /// GT_AttributeList::createAttributeList(
48  /// "P", new GT_Real32Array(...),
49  /// "N", new GT_Real32Array(...),
50  /// "uv", new GT_Real32Array(...));
51  /// @endcode
52  template <typename... Pairs>
54  {
55  int n = gt_CountAttribs(std::forward<Pairs>(pairs)...);
57  list(new GT_AttributeList(n, new GT_AttributeMap(n), 1));
58  gt_CreateAttributeList(*list, *list->getMap(),
59  std::forward<Pairs>(pairs)...);
60  return list;
61  }
62 
63  /// Test whether two attribute lists match in their definition. If both
64  /// attribute lists are empty, this will count as a match.
65  static bool matchDefinition(const GT_AttributeListHandle &a,
66  const GT_AttributeListHandle &b);
67 
68 
69  /// Create a new attribute list, adding a new attribute in the process.
70  GT_AttributeListHandle addAttribute(const UT_StringHolder &name,
71  const GT_DataArrayHandle &h,
72  bool replace_existing) const;
73 
74  /// Remove an attribute from this list, returning a new attribute list.
75  GT_AttributeListHandle removeAttribute(const UT_StringRef &name) const;
76 
77  /// Remove multiple attributes from this, returning a new attribute list.
78  GT_AttributeListHandle removeAttributes(const UT_StringArray &name) const;
79 
80 
81  /// Harden all the attribute lists
82  void harden();
83 
84  /// Harden a single attribute
85  void harden(int idx);
86 
87  /// Get a handle to the name map for this list.
88  const GT_AttributeMapHandle &getMap() const { return myMap; }
89 
90  /// Return the number of attributes in the list.
91  int entries() const
92  { return myMap->entries(); }
93 
94  /// Return the approximate memory usage. Because data can be shared, this
95  /// may not reflect the usage accurately.
96  int64 getMemoryUsage() const;
97 
98  /// Return the number of motion segements
99  int getSegments() const
100  { return myMotionSegments; }
101 
102  /// Return the list of names
103  const UT_StringArray &getNames() const
104  { return myMap->getNames(); }
105 
106  /// Return the data for the named array
108  int segment=0) const
109  {
110  return get(myMap->get(name), segment);
111  }
112  /// Return the data for a given index
113  const GT_DataArrayHandle &get(int index, int motion_segment=0) const;
114 
115  /// Return the name for a given index
116  const UT_StringHolder &getName(int index) const
117  { return myMap->getName(index); }
118 
119  /// Return the export name for a given index.
121  { return myMap->getExportName(index); }
122 
123  /// Get original attribute owner for the given attribute.
124  GT_Owner getOriginalOwner(int idx) const
125  { return myMap->getOriginalOwner(idx); }
126 
127  /// Return the index for a given name (returns -1 if miss)
128  int getIndex(const UT_StringRef &name) const
129  { return myMap->get(name); }
130 
131  /// Test of an attribute name exists
132  bool hasName(const UT_StringRef &name) const
133  { return myMap->hasName(name); }
134 
135  /// Assign an array to a given index in the list.
136  void set(int idx, const GT_DataArrayHandle &h,
137  int motion_segment=0);
138 
139  /// Assign an array to a given index in the list for @b all motion segments
140  void setAllSegments(int idx,
141  const GT_DataArrayHandle &h);
142 
143  /// Copies an entire segment of data arrays from a source list to this list.
144  /// This is useful when combining multiple primitives into a single motion
145  /// blurred primitive for example.
146  /// @param dest_segment @n
147  /// Data arrays are copied to this segment in this list
148  /// @param source_list @n
149  /// Data arrays are copied from this source list
150  /// @param source_segment @n
151  /// Data arrays are copied from this segment in the source_list
152  /// @warning The source attribute list @b must have the same maps. The
153  /// code does @b not verify that the maps are the same.
154  bool copySegment(int dest_segment,
155  const GT_AttributeListHandle &source_list,
156  int source_segment=0);
157 
158  /// Create a transformed version of the attributes
160 
161  /// Create a new attribute list containing
162  GT_AttributeListHandle createConstant(GT_Offset offset,
163  GT_Size size) const;
164 
165  /// Create an attribute list of a subset of the contents
166  GT_AttributeListHandle createSubArray(GT_Offset start,
167  GT_Size size) const;
168 
169  /// Create a new attribute list based on the indirect indicies in the
170  /// @c list
171  GT_AttributeListHandle createIndirect(
173  bool flatten_nested = true) const;
174 
175  /// Merge attributes which don't already exist in this attribute list
176  GT_AttributeListHandle mergeNewAttributes(
177  const GT_AttributeListHandle &s) const;
178 
179  /// Create the "s" and "t" attributes for the given u/v vertex count.
180  /// The attributes will only be created if @c nu or @c nv is greater than 0
181  GT_AttributeListHandle createUV(int nu, int nv,
182  fpreal64 s0=0, fpreal64 s1=1,
183  fpreal64 t0=0, fpreal64 t1=1) const;
184 
185  /// Create a merged list of the two lists. This will merge a sub-array of
186  /// the first list and an indirect mapping of the second list.
187  /// This is used to merge a vertex list (l0) with a point list (l1)
188  static GT_AttributeListHandle createMerged(
189  const GT_AttributeMerge &map,
190  const GT_AttributeListHandle &l0,
191  GT_Offset l0_offset, GT_Size l0_size,
192  const GT_AttributeListHandle &l1,
193  const GT_DataArrayHandle &l1_indirect);
194 
195  /// Merge two lists, expanding the constant list to have arrays matching
196  /// the length of the varying array.
197  static GT_AttributeListHandle expandConstantMerge(
198  const GT_AttributeMerge &map,
199  const GT_AttributeListHandle &varying,
200  const GT_AttributeListHandle &constant,
201  GT_Offset const_index=0);
202 
203  /// Merge two lists, creating a constant value list, selecting a single
204  /// element from a varying list.
205  static GT_AttributeListHandle createConstantMerge(
206  const GT_AttributeMerge &map,
207  const GT_AttributeListHandle &varying,
209  const GT_AttributeListHandle &constant);
210 
211  /// Merge an array of N lists to form a single attribute list. All the
212  /// data is concatenated in order.
213  ///
214  /// This method will fail (return an empty list) if any lists don't have
215  /// matching attributes (including motion segments & order of attributes)
216  ///
217  /// The list may have NULL handles.
218  static GT_AttributeListHandle concatenateLists(
219  const UT_Array<GT_AttributeListHandle> &lists);
220 
221  /// Get a 64b hash of all data ids in the list. Return false if any attribs
222  /// have an invalid data id (-1)
223  bool getDataIdHash(int64 &hash, int segment=0) const;
224 
225  /// Refresh the any detail references and data IDs on all data arrays.
226  void updateGeoDetail(const GU_ConstDetailHandle &dtl,
227  GT_Owner scope) const;
228 
229  /// Debug method to dump the list to stdout
230  void dumpList(const char *label="", bool data_too = true);
231 
232  /// Save to a JSON stream
233  bool save(UT_JSONWriter &w) const;
234 
236  {
237  public:
239  : myList(NULL), myCurr(0), mySize(0), mySegment(0) {}
240  iterator(const iterator &src)
241  { *this = src; }
243 
245  {
246  return myList->get(myCurr,
247  mySegment);
248  }
249  const UT_StringHolder &getName() const
250  {
251  return myList->getName(myCurr);
252  }
253 
254  void rewind() { myCurr = 0; }
255  void advance() { myCurr++; }
256  bool atEnd() const { return myCurr >= mySize; }
257 
258  iterator &operator++() { advance(); return *this; }
259  // No post increment as it is dangerous.
260  const iterator &operator=(const iterator &src)
261  {
262  myList = src.myList;
263  myCurr = src.myCurr;
264  mySize = src.mySize;
265  return *this;
266  }
267 
268  private:
269  iterator(const GT_AttributeList *list, int segment)
270  : myList(list),
271  mySegment(segment),
272  myCurr(0),
273  mySize(list->entries()) {}
274 
275  const GT_AttributeList *myList;
276  int myCurr, mySize, mySegment;
277  friend class GT_AttributeList;
278  };
279  /// Traverse over all attributes for a given motion segment
280  iterator begin(int segment=0) const { return iterator(this, segment); }
281 
282  // Forward declare nested class (and make it a friend)
283  class gt_CreateIndirectTask;
284  friend class gt_CreateIndirectTask;
285 
286 private:
287 
288  // Private constructor for createAttributeList() only
290  int motion_segments);
291 
292  static SYS_FORCE_INLINE int
293  gt_CountAttribs()
294  {
295  return 0;
296  }
297  template <typename DataT, typename... Pairs>
298  static int
299  gt_CountAttribs(const UT_StringRef &name, DataT&& data,
300  Pairs&&... pairs)
301  {
302  return (data ? 1 : 0) + gt_CountAttribs(std::forward<Pairs>(pairs)...);
303  }
304 
305  static SYS_FORCE_INLINE void
306  gt_CreateAttributeList(GT_AttributeList &, GT_AttributeMap &)
307  {
308  }
309  template <typename DataT, typename... Pairs>
310  static void
311  gt_CreateAttributeList(
312  GT_AttributeList &list, GT_AttributeMap &map,
313  const UT_StringHolder &name, DataT&& data,
314  Pairs&&... pairs)
315  {
316  // Ignore NULL data arrays. Makes it easier to make lists where it's
317  // not known if some of the data arrays are valid at compile time.
318  if (data)
319  {
320  int i = map.add(name, /*replace*/false);
321  UT_ASSERT_MSG(i >= 0, "Should not have duplicates!");
322  list.set(i, data);
323  }
324  gt_CreateAttributeList(list, map, std::forward<Pairs>(pairs)...);
325  }
326 
327 private:
328  /// Create a new constant data array for the i'th element
329  const GT_DataArrayHandle createConstant(int idx, GT_Offset offset,
330  GT_Size size,
331  int segment) const;
332 
333  /// Create a new sub-array data array for the i'th element
334  const GT_DataArrayHandle createSubArray(int idx, GT_Offset start,
335  GT_Size size,
336  int segment) const;
337 
338  /// Create a new sub-array data array for the i'th element
339  const GT_DataArrayHandle createIndirect(
340  int idx,
342  int segment,
343  bool flatten_nested) const;
344 
345  inline int getSegmentIndex(int index, int segment) const
346  { return index + segment*entries(); }
347 
348  // Keep the 32 bit int first in the structure. Since we inherit from
349  // GA_IntrusiveRefCounter, this alignment makes the object smaller.
350  int myMotionSegments;
351  const GT_AttributeMapHandle myMap;
352  GT_DataArrayHandle *myData;
353 
354  // For threading of creating indirect arrays
355 };
356 
357 #endif
Keep track of merging of attribute maps.
GLuint GLsizei const GLchar * label
Definition: glcorearb.h:2544
void set(int idx, const GT_DataArrayHandle &h, int motion_segment=0)
Assign an array to a given index in the list.
A symbol table for attribute data.
png_voidp s1
Definition: png.h:2193
const GT_DataArrayHandle & getData() const
GLuint start
Definition: glcorearb.h:474
#define GT_API
Definition: GT_API.h:11
int getIndex(const UT_StringRef &name) const
Return the index for a given name (returns -1 if miss)
GLboolean GLboolean GLboolean GLboolean a
Definition: glcorearb.h:1221
const GT_AttributeMapHandle & getMap() const
Get a handle to the name map for this list.
Class which writes ASCII or binary JSON streams.
Definition: UT_JSONWriter.h:32
A reference counter base class for use with UT_IntrusivePtr.
png_uint_32 i
Definition: png.h:2877
const UT_StringHolder & getName(int index) const
Return the name for a given index.
int add(const UT_StringHolder &name, bool replace_existing)
GLsizeiptr size
Definition: glcorearb.h:663
iterator(const iterator &src)
const UT_StringArray & getNames() const
Return the list of names.
const UT_StringHolder & getExportName(int index) const
Return the export name for a given index.
long long int64
Definition: SYS_Types.h:107
GLdouble n
Definition: glcorearb.h:2007
Abstract data class for an array of float, int or string data.
Definition: GT_DataArray.h:38
double fpreal64
Definition: SYS_Types.h:192
#define SYS_FORCE_INLINE
Definition: SYS_Inline.h:45
GLintptr offset
Definition: glcorearb.h:664
static GT_AttributeListHandle createAttributeList(Pairs &&...pairs)
GLboolean * data
Definition: glcorearb.h:130
int entries() const
Return the number of attributes in the list.
GLuint const GLchar * name
Definition: glcorearb.h:785
GLboolean GLboolean GLboolean b
Definition: glcorearb.h:1221
GA_API const UT_StringHolder transform
const UT_StringHolder & getName() const
GT_Owner
Definition: GT_Types.h:75
GLfloat GLfloat GLfloat GLfloat h
Definition: glcorearb.h:2001
png_infop png_sPLT_tpp entries
Definition: png.h:2481
#define UT_ASSERT_MSG(ZZ, MM)
Definition: UT_Assert.h:129
GLuint index
Definition: glcorearb.h:785
GLint GLenum GLint x
Definition: glcorearb.h:408
const void * indirect
Definition: glcorearb.h:1794
int getSegments() const
Return the number of motion segements.
iterator begin(int segment=0) const
Traverse over all attributes for a given motion segment.
GT_Owner getOriginalOwner(int idx) const
Get original attribute owner for the given attribute.
GLubyte GLubyte GLubyte GLubyte w
Definition: glcorearb.h:856
int64 GT_Offset
Definition: GT_Types.h:113
int64 GT_Size
Definition: GT_Types.h:112
const iterator & operator=(const iterator &src)
bool hasName(const UT_StringRef &name) const
Test of an attribute name exists.
GLenum src
Definition: glcorearb.h:1792