HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
RE_VertexArray.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: RE_VertexArray.h ( RE Library, C++)
7  *
8  * COMMENTS:
9  * These classes provide a GL-indepedent way of specify vertex attributes
10  * in array or constant form. Array attributes use VBOs, whereas constant
11  * attributes use glVertexAttrib*() calls.
12  */
13 #ifndef RE_VERTEX_ARRAY_H
14 #define RE_VERTEX_ARRAY_H
15 
16 class RE_Render;
17 class RE_ElementArray;
18 class RE_OGLConstAttribute;
19 
20 #include "RE_CachedObject.h"
21 #include "RE_Types.h"
22 #include "RE_Texture.h"
23 #include "RE_OGLBuffer.h"
24 #include <UT/UT_StringHolder.h>
25 #include <UT/UT_WorkBuffer.h>
26 #include <iosfwd>
27 
28 // Base class for various array types.
30 {
31 public:
32  // Returns a new vertex array
33  static RE_VertexArray *newAttribArray(const UT_StringHolder &name,
34  int num_elements=0,
35  const char *cachename = nullptr,
37  int capacity = 0);
38 
39  static RE_VertexArray *newElementArray(int num_elements=0,
40  const char *cachename = nullptr,
41  int capacity = 0);
42 
43  // Creates a container RE_VertexArray around the passed array.
44  static RE_VertexArray *newArrayContainer(RE_OGLBufferHandle &array,
45  const char *cachename = nullptr,
47 
48  static RE_VertexArray *newArrayContainer(UT_Array<RE_OGLBufferHandle>&array,
49  const char *cachename = nullptr,
51 
52  // Returns the cache name
53  static void getAttribCacheName(UT_WorkBuffer &str,
54  const char *name,
55  RE_ArrayType attrib_type,
56  const char *cachename);
57 
58  ~RE_VertexArray();
59 
60  // Creates a new RE_VertexArray with exactly the same format and
61  // buffer references.
62  RE_VertexArray *clone() const;
63 
64  /// Returns the amount of main memory (NOT graphics memory!)
65  /// owned by this RE_VertexArray.
66  int64 getMemoryUsage(bool inclusive) const;
67 
68  // add this buffer to the GL cache using a tag of 'name'/attribname
69  void cacheBuffer(const UT_StringHolder &name)
70  { myCacheName = name; }
71  const char *getCacheName() const { return myCacheName; }
72 
73  // Set the version number on the cached buffer.
74  void setCacheVersion(RE_CacheVersion v);
75  RE_CacheVersion getCacheVersion() const;
76 
77  void allowShared(bool shared) { myAllowShared = shared; }
78 
79  // Indicate if this array is actively in use by the cache.
80  void markAsUsed();
81  void markAsUnused(bool move_to_unused_cache = true);
82  bool isUsed() const { return myInUse; }
83 
84  // sets the cache tag on underlying arrays. The cache tag is used to notify
85  // other entities when the array is evicted from the cache.
86  void setCacheTag(RE_CacheTagHandle h);
87 
88  /// Hint to the GL driver how this buffer will be used. May only be set
89  /// before the buffer is created (initialize(), setArray(), etc).
90  void setUsage(RE_BufferUsageHint h);
91 
92  /// Set the buffer to use persistent mapped buffers, optionally with
93  /// coherent behaviour (writes seen automatically). RE_EXT_BUFFER_STORAGE
94  /// must be supported, or false will be returned and the setting will have
95  /// no effect.
96  void setPersistent(RE_PersistentBufferMode mode);
97 
98  // assigns 'num' buffers to this vertex array, cachable with 'cachename'.
99  void adoptArrays(const UT_Array<RE_OGLBufferHandle> &buffers,
100  const UT_StringHolder &cachename);
101 
102  // Removes all contained arrays, possibly deleting them if not cached.
103  void resetBuffer(bool delete_cached = false,
104  bool mark_as_unused = true);
105 
106  // If the size, type or format of the buffer is changed, this method can
107  // ensure that the underlying array is initialized afterward. 'created'
108  // can be used to query if a new buffer was allocated by this method.
109  bool initialize(RE_Render *r, bool *created = nullptr);
110 
111  // Allows some extra data to be cached with the buffer. Caching must be
112  // enabled, and this can't be a constant attribute (no buffer).
113  // Owndership of the data is always given up, and it will be deleted when
114  // the buffer is.
115  bool setExtraBufferData(RE_CachedExtraData *data);
116  RE_CachedExtraDataHandle getExtraBufferData() const;
117 
118  // Setup
119  // standard GL attributes use the buffer types
120  void setBufferType(RE_BufferType type);
121 
122  // custom attributes are referenced by name.
123  void setAttributeName(const char *attrib);
124 
125  // Sets the data type for the array. This type is one array 'element'.
126  // If normalized is true, fixed formats will be normalized to [0,1]
127  void setFormat(RE_GPUType type, int vectorsize,
128  bool normalized = true);
129 
130  // Sets the length of the array, in elements (a fp32 vec3 is 1 element)
131  void setLength(int len);
132 
133  // Sets the total capacity of the array, in elements (a fp32 vec3 is 1
134  // element). Length may be less than this.
135  bool setCapacity(int cap);
136 
137  // If non-zero, this attribute advances once every 'nprims' number of
138  // primitives instead of once per vertex. RE_EXT_INSTANCED_ARRAYS required.
139  void setInstanceStride(int nprims);
140 
141  // if non-negative, specifies an instance draw group to which this belongs
142  void setInstanceGroup(int instance_group)
143  { myInstanceGroup = instance_group; }
144 
145  // Sets the sampling frequency of this array - either per point, vertex,
146  // primitive, instance or randomly accessed.
147  void setArrayType(RE_ArrayType t) { myArrayType = t; }
148 
149  // Array data methods
150 
151  // Specifies all the data at once, or a subrange of the data if sublen!=0.
152  // offset and sublen are specified in elements, not bytes.
153  bool setArray(RE_Render *r,
154  const void *data,
155  int offset = 0,
156  int sublen = 0,
157  int array_index = 0);
158 
160  const void *data,
161  int array_index = 0)
162  { return setArray(r,data, 0,myLength, array_index); }
163 
165  const void *data,
166  int offset,
167  int length,
168  int array_index)
169  { return setArray(r, data, offset, length, array_index); }
170 
171 
172  // fetch data from a buffer, starting at element 'offset' for 'sublen'
173  // elements (the size of an element depends on the format & type). If
174  // sublen is zero, it will fetch to the end of the buffer.
175  bool getArray(RE_Render *r,
176  void *data,
177  int offset = 0,
178  int sublen = 0,
179  int array_index = 0) const;
180 
181  // Cuts loose the current buffer and recreates a new one. Will still
182  // maintain the same buffer ID, but the underlying chunk of memory will be
183  // handed off to the driver.
184  void orphan(RE_Render *r);
185 
186  // The attribute is constant-valued. Data must be big enough to fill one
187  // element, and the data is always FP. Constant values cannot be mapped.
188  void setConstant(const fpreal32 *data);
189  void setConstant(const fpreal64 *data);
190 
191  // Ensure that a constant is created without assigning any data.
192  void createConstant();
193 
194  // Internally constant data is stored as double.
195  fpreal64 *getConstant();
196  const fpreal64 *getConstant() const;
197 
198  // Indicate that the vertex array is a default value placeholder.
199  void markAsDefaultValue(bool def) { myDefaultValue = def; }
200  bool isDefaultValue() const { return myDefaultValue; }
201 
202  // Returns a pointer to the array so it can be modified. must call unmap()
203  // when finished, before attempting to use the array again. This maps the
204  // entire buffer, so in some instances it may be better to use setArray()
205  // with a subrange.
206  // NOTE: map()/unmap() is generally slower than setArray(), so use only
207  // for reading or persistent buffers.
208  void *map(RE_Render *r,
210  int array_index = 0);
211  void *mapRange(RE_Render *r, int start, int length,
213  int array_index = 0);
214  void unmap(RE_Render *r, int array_index = 0);
215 
216  // For persistent mapped buffers, this returns the currently mapped data.
217  // Will only return a value if mapped, persisent is set, and
218  // RE_EXT_BUFFER_STORAGE is supported.
219  void *getPersistentMap(int array_index = 0) const;
220 
221  // Returns true if this is a persistently mapped buffer
222  bool isPersistentMap() const;
223 
224  // Zero the buffer.
225  void zero(RE_Render *r);
226 
227  // Attach a texture buffer object to a VERTEX, PRIM or RANDOM array type.
228  bool attachTexBuffer(RE_Render *r,
229  RE_Texture *tex);
230 
231  // Return the TBO attached to a VERTEX, PRIM or RANDOM array type.
232  RE_Texture *getTextureBufferObject() const; // inlined below
233 
234  // Binding methods
235 
236  // Binds the array to the given array attribute type for subsequent draw
237  // calls. When drawing with multiple attributes, the first N-1 should be
238  // bound, and the Nth should call draw...Prims().
239  // geo_obj is only true when called from RE_Geometry.
240  bool bind(RE_Render *r, unsigned int stride = 0,
241  bool geo_obj=false,
242  const char *shader_attrib = nullptr);
243  bool unbind(RE_Render *r);
244 
245  // Rebinds an array to a new attribute location due to a shader change.
246  bool rebindAttrib(RE_Render *r, int location);
247  bool unbindAttrib(RE_Render *r);
248 
249  // Bind to a VAO.
250  bool setupForAttribIndex(RE_Render *r, int attrib_location,
251  RE_GPUType t, int stride);
252 
253 
254  // These bind methods bind the buffer to the specificied buffer binding
255  // point, which may be different than the buffer type's default binding
256  // point. Some binding points are indexed (uniform and transform feedback)
257  // while most have a single binding point.
258  bool bindBuffer(RE_Render *r, RE_BufferBinding point, int index=0,
259  int array_index=0);
260  bool unbindBuffer(RE_Render *r, RE_BufferBinding point, int index=0,
261  int array_index=0);
262 
263  // Drawing methods
264 
265  // Draws primitives using every n'th point (where n=stride) in this array
266  // as 'prim' primitive type.
267  void drawPrims(RE_Render *r,
268  RE_PrimType prim,
269  unsigned int stride,
270  int num_instances,
271  bool enable_arrays,
272  int vertices_per_patch);
273 
274  // Draws primitives using a subrange of points in this array
275  void drawSomePrims(RE_Render *r,
276  RE_PrimType prim,
277  int start,
278  int num,
279  int num_instances,
280  bool enable_arrays,
281  int vertices_per_patch);
282 
283  // Draws primitives using some points in this array using a 2nd array as
284  // the indices. The array must be an element array.
285  void drawSomePrims(RE_Render *r,
286  RE_PrimType prim,
287  RE_VertexArray *index_array,
288  int index_offset,
289  int index_num_elements,
290  int num_instances,
291  bool enable_arrays,
292  int vertices_per_patch);
293 
294  // Query
295  RE_BufferType getBufferType() const { return myBufferType; }
296  RE_GPUType getDataType() const { return myType; }
297  int getVectorSize() const { return myVectorSize; }
298  int getLength() const { return myLength; }
299  int getLengthScale() const { return myLengthScale; }
300  int getCapacity() const { return myCapacity; }
301  int getNumBuffers() const { return myArray.entries(); }
302  const RE_OGLBufferHandle &getArrayBuffer(int i=0) const
303  { return (i < myArray.entries()) ? myArray(i) : theNullArray; }
304  const char *getAttributeName() const { return myAttribName; }
305  RE_ArrayType getArrayType() const { return myArrayType; }
306  bool isBufferBound(int array_index=0) const;
307  bool isConstantBuffer() const { return myConstantFlag; }
308  void getHoudiniName(UT_StringHolder &name) const;
309  void getGLName(UT_StringHolder &name) const;
310  int getInstanceStride() const { return myInstanceStride; }
311  int getInstanceGroup() const { return myInstanceGroup; }
312 
313  int64 getSizeBytes() const;
314 
315  // Debugging prints
316  void print(std::ostream *os = nullptr) const;
317  void printValues(RE_Render *r, std::ostream &os,
318  int start=0, int len=0) const;
319 
320  void addRef(void (*callback)(void *), void *data);
321  void removeRef(void (*callback)(void *), void *data);
322 
323  // Some attributes are 'known' types, as listed in RE_GenericAttribID.
324  // Setting the ID can help performance. Do not change the type of an attrib
325  // while bound to an RE_Geometry; this should only be called once.
327  { UT_ASSERT(myGenID == RE_GENATTRIB_UNDEF || myGenID == id);
328  myGenID = id; }
329  RE_GenericAttribID getGenericID() const { return myGenID; }
330 
331 protected:
332  RE_VertexArray(RE_BufferType type, int nelements = 0, int capacity = 0);
333  RE_VertexArray(const UT_StringHolder &name, int nelements = 0,
334  int capacity= 0 );
335  RE_VertexArray(const RE_VertexArray &va);
336 
337  void detachTexBuffer(int index);
338  void generateCacheName(UT_StringHolder &cachename,
339  int index) const;
340 
346  int myLength;
352  RE_OGLConstAttribute *myConstAttrib;
355  bool myInUse;
356 
357  bool myMappedFlag[4];
367 
369  {
370  public:
371  re_VertexArrayCB(void (*cb)(void *),void *d) : callback(cb), data(d) {}
372  void (*callback)(void *);
373  void *data;
374  };
375 
377 };
378 
379 inline RE_Texture *
381 {
382  return (myArray.entries() == 1) ? myArray(0)->getTBO() : nullptr;
383 }
384 
385 /// Shallow reference to an RE_VertexArray. Will be cleared if the
386 /// RE_VertexArray is deleted.
388 {
389 public:
390  RE_VertexArrayRef() : myArray(nullptr) {}
392 
393  bool isValid() { return myArray!=nullptr; }
394  void operator=(RE_VertexArray &va);
395  void clear();
396  RE_VertexArray *get() { return myArray; }
397  const RE_VertexArray *get() const { return myArray; }
399  {
400  UT_ASSERT(myArray);
401  return myArray;
402  }
403  const RE_VertexArray *operator->() const
404  {
405  UT_ASSERT(myArray);
406  return myArray;
407  }
408 
409 private:
410  static void arrayDeleted(void *);
411 
412  RE_VertexArray *myArray;
413 };
414 
415 #endif
bool replaceArrayRange(RE_Render *r, const void *data, int offset, int length, int array_index)
RE_GenericAttribID getGenericID() const
UT_StringHolder myAttribName
int getNumBuffers() const
#define RE_API
Definition: RE_API.h:10
void
Definition: png.h:1083
void setArrayType(RE_ArrayType t)
const RE_VertexArray * operator->() const
const GLdouble * v
Definition: glcorearb.h:837
int getLength() const
GLuint start
Definition: glcorearb.h:475
UT_Array< re_VertexArrayCB > myRefs
void cacheBuffer(const UT_StringHolder &name)
GLuint GLsizei GLsizei * length
Definition: glcorearb.h:795
bool isDefaultValue() const
UT_StringHolder myCacheName
RE_PersistentBufferMode myPersistentBufferMode
RE_ArrayType myArrayType
RE_GenericAttribID myGenID
float fpreal32
Definition: SYS_Types.h:200
RE_OGLConstAttribute * myConstAttrib
double fpreal64
Definition: SYS_Types.h:201
const char * getAttributeName() const
RE_GenericAttribID
Definition: RE_Types.h:348
RE_GPUType
Definition: RE_Types.h:44
RE_BufferType
Definition: RE_Types.h:284
RE_BufferType myBufferType
bool isConstantBuffer() const
GLintptr offset
Definition: glcorearb.h:665
RE_BufferBinding
Definition: RE_Types.h:321
RE_CacheTagHandle myCacheTagHandle
RE_GPUType getDataType() const
GLuint GLint GLboolean GLint GLenum access
Definition: glcorearb.h:2222
void setGenericID(RE_GenericAttribID id)
void allowShared(bool shared)
GLint GLenum GLboolean GLsizei stride
Definition: glcorearb.h:872
const GLuint * buffers
Definition: glcorearb.h:661
Wrapper around hboost::intrusive_ptr.
long long int64
Definition: SYS_Types.h:116
GLint location
Definition: glcorearb.h:805
GLuint id
Definition: glcorearb.h:655
int getLengthScale() const
GLuint const GLchar * name
Definition: glcorearb.h:786
OPENVDB_API void initialize()
Global registration of native Grid, Transform, Metadata and Point attribute types. Also initializes blosc (if enabled).
Definition: logging.h:294
GLint GLenum GLboolean normalized
Definition: glcorearb.h:872
bool replaceArray(RE_Render *r, const void *data, int array_index=0)
int getInstanceStride() const
bool myPersistentMapCopied
GLdouble t
Definition: glad.h:2397
GLenum mode
Definition: glcorearb.h:99
int getCapacity() const
RE_BufferUsageHint myUsage
void markAsDefaultValue(bool def)
static RE_OGLBufferHandle theNullArray
GLfloat GLfloat GLfloat GLfloat h
Definition: glcorearb.h:2002
re_VertexArrayCB(void(*cb)(void *), void *d)
RE_BufferAccess
Definition: RE_Types.h:314
bool isUsed() const
GLuint index
Definition: glcorearb.h:786
const RE_OGLBufferHandle & getArrayBuffer(int i=0) const
RE_VertexArray * operator->()
RE_ArrayType
Definition: RE_Types.h:337
const char * getCacheName() const
RE_ArrayType getArrayType() const
RE_Texture * getTextureBufferObject() const
RE_BufferUsageHint
Definition: RE_Types.h:296
Simple class for a mutli-integer cache tag.
#define UT_ASSERT(ZZ)
Definition: UT_Assert.h:156
RE_GPUType myType
GLboolean r
Definition: glcorearb.h:1222
UT_Array< RE_OGLBufferHandle > myArray
int getInstanceGroup() const
int getVectorSize() const
ImageBuf OIIO_API zero(ROI roi, int nthreads=0)
type
Definition: core.h:1059
FMT_INLINE void print(format_string< T...> fmt, T &&...args)
Definition: core.h:2976
RE_BufferType getBufferType() const
RE_PrimType
Definition: RE_Types.h:193
RE_PersistentBufferMode
Definition: RE_Types.h:541
Definition: format.h:895
void setInstanceGroup(int instance_group)