HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
GA_Range.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: GA_Range.h ( GA Library, C++)
7  *
8  * COMMENTS:
9  */
10 
11 #ifndef __GA_Range__
12 #define __GA_Range__
13 
14 #include "GA_API.h"
15 #include "GA_OffsetList.h"
16 #include "GA_RangeTypeInterface.h"
17 #include "GA_Types.h"
18 
19 #include <stddef.h>
20 
21 
22 class GA_Detail;
23 class GA_ElementGroup;
24 class GA_IndexMap;
25 class GA_Iterator;
26 class GA_IteratorState;
29 
30 
31 /// @brief A range of elements in an index-map
32 ///
33 /// A range specifies a selection/collection of elements in an index map
34 /// for iteration. The membership state of individual elements can also
35 /// be queried (@see allocMemberQuery()).
36 ///
37 /// Iteration over a range, performed by instantiating a GA_Iterator, does
38 /// not affect the range object itself. The begin() method can be used to
39 /// initialize a basic iterator.
40 ///
41 /// Custom range types are implemented by subclassing GA_RangeTypeInterface.
43 {
44 public:
47 
48  /// @{
49  /// Constructor/destructors
50  GA_Range();
52  GA_Range(const GA_Range &src);
54  ~GA_Range();
55  /// @}
56 
57  /// @{
58  /// Default iterator
59  GA_Iterator begin() const;
60  GA_Iterator end() const;
61  /// @}
62 
63  /// Determine whether a range is empty
64  bool empty() const
65  { return myRange->isEmpty(); }
66 
67  /// @{
68  /// Classes used to differentiate between different constructors
69  class pointref {};
70  class ordered {};
71  class primitiveref {};
72  class emptyrange {};
74  class safedeletions {};
75  class enditerator {};
76  class ignore_order {};
77  /// @}
78 
79  /// @{
80  /// Interface for making another range into an ordered range.
81  /// @param descending If true, the index order is going to be in
82  /// a descending order. If false, it's ascending.
83  GA_Range(const GA_Range &src, ordered, bool descending = false);
84  /// @}
85  //
86  /// @{
87  /// Interface for making another range into one where deletions
88  /// are safe to perform during the traversal.
90  /// @}
91 
92  /// @{
93  /// An empty range.
94  GA_Range(const GA_IndexMap &map, emptyrange);
95  /// @}
96 
97  /// @{
98  /// Convenience constructor to construct an offset range
99  /// The range includes @c start, but doesn't include @c end.
100  /// @see GA_RTIOffset
101  explicit GA_Range(const GA_IndexMap &map);
103  /// @}
104 
105  /// @{
106  /// Convenience constructor to construct an index range
107  /// @see GA_RTIIndex
110  GA_Size step, ordered);
111  /// @}
112 
113 
114  /// Constructor to create a range containing the offsets in the given list.
115  /// If end < 0, it will be set to the @c offsetlist.entries()
116  /// @see GA_RTIOffsetList
117  GA_Range(const GA_IndexMap &map, const GA_OffsetList &offsetlist,
118  GA_Size start=0, GA_Size end=-1);
119 
120  /// Construct a range of the elements in a given group
121  /// @see GA_RTIElementGroup
122  explicit GA_Range(const GA_ElementGroup &group,
123  bool complement=false);
124 
125  /// Construct a range of the elements in a given group
126  /// @see GA_RTIElementGroup
127  GA_Range(const GA_IndexMap &map, const GA_ElementGroup *group,
128  bool complement=false);
129 
130  /// Construct a range of the elements in a given group, ignoring its order
131  /// even if it is ordered.
132  /// @see GA_RTIElementGroup
133  /// @{
134  GA_Range(const GA_ElementGroup &group, ignore_order, bool complement=false);
135  GA_Range(const GA_IndexMap &map, const GA_ElementGroup *group,
136  ignore_order, bool complement=false);
137  /// @}
138 
139  /// Construct a range of all the elements referencing a given point. The
140  /// harden argument determines whether it is safe to use this range after
141  /// the point has been deleted. If the point will exist for the lifetime
142  /// of the range, harden can be false and thus more efficient.
143  ///
144  /// For example, to find all the vertices which reference point number 3:
145  /// @code
146  /// GA_Range(geo, 3, GA_ATTRIB_VERTEX, GA_Range::pointref, false);
147  /// @endcode
148  /// @see GA_RTIPointRef
149  GA_Range(const GA_Detail &geo, GA_Offset point, GA_AttributeOwner owner,
150  pointref, bool harden);
151 
152  /// Construct a range of all primitives/vertices referenced by the points
153  /// in the given range. The harden argument determines whether it is safe
154  /// to use this range after the point has been deleted. If the point will
155  /// exist for the lifetime of the range, harden can be false and thus more
156  /// efficient.
157  /// @code
158  /// GA_Range(geo, geo.getPointRange(), GA_ATTRIB_PRIMITIVE, false);
159  /// GA_Range(geo, geo.getPointRange(), GA_ATTRIB_VERTEX, false);
160  /// @endcode
161  /// @see GA_RTIPointComprehension
162  GA_Range(const GA_Detail &geo, const GA_Range &point_range,
163  GA_AttributeOwner type, pointref, bool harden);
164 
165 
166  /// Construct a range of all the elements used by a given primitive. The
167  /// harden argument determines whether it is safe to use this range after
168  /// the primitive has been deleted. If the primitive will exist for the
169  /// lifetime of the range, harden can be false, and thus more efficient.
170  /// If vertices are added or removed during traversal and harden is true,
171  /// only the original vertices will be traversed, but behaviour is
172  /// undefined if harden is false.
173  ///
174  /// For example, to find all the points which referenced by primitive 3:
175  /// @code
176  /// GA_Range(geo, 3, GA_ATTRIB_VERTEX, GA_Range::primitiveref);
177  /// @endcode
178  /// @see GA_RTIPrimitiveRef
179  GA_Range(const GA_Detail &geo, GA_Offset prim, GA_AttributeOwner owner,
180  primitiveref, bool harden);
181 
182  /// Construct a range of all points/vertices referenced by the primitives
183  /// in the given range. The harden argument determines whether it is safe
184  /// to use this range after the primitive has been deleted. If the
185  /// primitive will exist for the lifetime of the range, harden can be false
186  /// and thus more efficient.
187  /// @code
188  /// GA_Range(geo, geo.getPrimitiveRange(), GA_ATTRIB_POINT);
189  /// GA_Range(geo, geo.getPrimitiveRange(), GA_ATTRIB_VERTEX);
190  /// @endcode
191  /// @see GA_RTIPrimitiveComprehension
192  GA_Range(const GA_Detail &geo, const GA_Range &primitive_range,
193  GA_AttributeOwner type, primitiveref, bool harden);
194 
195  /// Construct a range of all points/vertices referenced by the primitives
196  /// in the given range. The harden argument determines whether it is safe
197  /// to use this range after the primitive has been deleted. If the
198  /// primitive will exist for the lifetime of the range, harden can be false
199  /// and thus more efficient.
200  ///
201  /// This version delivers the points/vertices in the order imposed by the
202  /// @c primitive_range. This is equivalent to traversing the vertices of
203  /// each primitive with a GA_Primitive::const_iterator as it is visited.
204  /// @code
205  /// GA_Range(geo, geo.getPrimitiveRange(), GA_ATTRIB_POINT);
206  /// GA_Range(geo, geo.getPrimitiveRange(), GA_ATTRIB_VERTEX);
207  /// @endcode
208  /// @see GA_RTIPrimitiveComprehension
209  GA_Range(const GA_Detail &geo, const GA_Range &primitive_range,
210  GA_AttributeOwner type, primitiveref, ordered, bool harden);
211 
212  /// Iterate over all elements in the index map, including any temporary
213  /// elements. This should be used within ATI's when changing data for all
214  /// elements (including temporaries).
216 
217  /// @{
218  /// Operators
220  {
221  setRange(src.myRange);
222  return *this;
223  }
225  {
226  if (myRange)
227  myRange->decref();
228  myRange = src.myRange;
229  src.myRange = nullptr;
230  return *this;
231  }
232  bool operator==(const GA_Range &src) const;
233  /// @}
234 
235  /// Take ownership of the given GA_RangeTypeInterface. This is used to
236  /// avoid unnecessary calls to GA_RangeTypeInterface::copy().
237  void adopt(GA_RangeTypeInterface *r) { setRange(r); }
238 
239  /// Check whether range is valid (i.e. has an implementation)
240  bool isValid() const { return myRange != NULL; }
241 
242  /// Query type of element
243  GA_AttributeOwner getOwner() const { return myRange->getOwner(); }
244 
245  /// Check whether the range is empty
246  bool isEmpty() const { return myRange->isEmpty(); }
247 
248  /// Get an upper bound on the range
249  GA_Size getMaxEntries() const { return myRange->getMaxEntries(); }
250  /// Get an accurate count of the entries in the range
251  GA_Size getEntries() const { return myRange->getEntries(); }
252 
253  /// Query if it is safe to delete an element during traversal. If not,
254  /// you can build an equivalent range by calling:
255  /// GA_Range(initial_range, GA_Range::safedeletions)
257  {
258  return !getRTI() ||
259  getRTI()->areTraversalDeletionsSafe();
260  }
261 
262  /// Query if the range contains duplicates. If it cannot, then
263  /// optimizations can be made assuming that there are no duplicates in the
264  /// range. This defaults to true.
265  bool canContainDuplicates() const
266  { return myRange->canContainDuplicates(); }
267 
268 
269  /// Allocate an object for testing the membership of individual elements
270  /// to this range. The caller is responsible for deleting this object,
271  /// which should not outlive the allocating range.
272  ///
273  /// Behaviour of this object is undefined for any elements that have been
274  /// deleted or moved since its creation.
275  const GA_RangeMemberQuery *allocMemberQuery() const;
276 
277  /// @cond INTERNAL
278  /// Interface used by iterators to perform iteration
279  void iterateCreate(GA_IteratorState &state) const
280  { myRange->iterateCreate(state); }
281  void iterateDestroy(GA_IteratorState &state) const
282  { myRange->iterateDestroy(state); }
283  void iterateRewind(GA_IteratorState &state,
284  GA_Offset &start, GA_Offset &end) const
285  { myRange->iterateRewind(state, start, end); }
286  void iterateNext(GA_IteratorState &state,
287  GA_Offset &start, GA_Offset &end) const
288  { myRange->iterateNext(state, start, end); }
289  void iterateCopy(GA_IteratorState &dest,
290  const GA_IteratorState &src) const
291  { myRange->iterateCopy(dest, src); }
292  /// @endcond
293 
294  /// Accessor for RTI
295  const GA_RangeTypeInterface *getRTI() const { return myRange; }
296 
297 private:
298  void setRange(GA_RangeTypeInterface *r)
299  {
300  if (r != myRange)
301  {
302  if (r)
303  r->incref();
304  if (myRange)
305  myRange->decref();
306  myRange = r;
307  }
308  }
309  GA_RangeTypeInterface *myRange;
310 
311  friend class GA_RangeTypeInterface; // For splitting
312  friend class GA_SplittableRange; // For splitting
313 };
314 
315 #endif
A class to manage an ordered array which has fixed offset handles.
Definition: GA_IndexMap.h:63
GLenum GLint * range
Definition: glew.h:3500
GLenum src
Definition: glew.h:2410
Iteration over a range of elements.
Definition: GA_Iterator.h:28
FMT_CONSTEXPR auto begin(const C &c) -> decltype(c.begin())
Definition: format.h:251
GA_Iterator const_iterator
Definition: GA_Range.h:45
bool isValid() const
Check whether range is valid (i.e. has an implementation)
Definition: GA_Range.h:240
bool areTraversalDeletionsSafe() const
Definition: GA_Range.h:256
#define GA_API
Definition: GA_API.h:12
Abstract base class for a range membership query object.
exint GA_Size
Defines the bit width for index and offset types in GA.
Definition: GA_Types.h:231
void incref() const
A range of elements in an index-map.
Definition: GA_Range.h:42
GA_Iterator iterator
Definition: GA_Range.h:46
GA_Size GA_Offset
Definition: GA_Types.h:637
bool operator==(const BaseDimensions< T > &a, const BaseDimensions< Y > &b)
Definition: Dimensions.h:137
bool canContainDuplicates() const
Definition: GA_Range.h:265
GLuint GLuint end
Definition: glew.h:1253
GA_Size getMaxEntries() const
Get an upper bound on the range.
Definition: GA_Range.h:249
const GA_RangeTypeInterface * getRTI() const
Accessor for RTI.
Definition: GA_Range.h:295
GA_Size GA_Index
Define the strictness of GA_Offset/GA_Index.
Definition: GA_Types.h:631
GLuint GLuint GLsizei GLenum type
Definition: glew.h:1253
GLuint start
Definition: glew.h:1253
Abstract implementation of a range.
bool isEmpty() const
Check whether the range is empty.
Definition: GA_Range.h:246
bool empty() const
Determine whether a range is empty.
Definition: GA_Range.h:64
const GA_Range & operator=(const GA_Range &src)
Definition: GA_Range.h:219
GA_AttributeOwner
Definition: GA_Types.h:33
GA_Size getEntries() const
Get an accurate count of the entries in the range.
Definition: GA_Range.h:251
GLdouble GLdouble GLdouble r
Definition: glew.h:1406
Container class for all geometry.
Definition: GA_Detail.h:95
void adopt(GA_RangeTypeInterface *r)
Definition: GA_Range.h:237
GA_AttributeOwner getOwner() const
Query type of element.
Definition: GA_Range.h:243
const GA_Range & operator=(GA_Range &&src)
Definition: GA_Range.h:224
GLboolean GLuint group
Definition: glew.h:2745