HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
GEO_PrimVDB.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: GEO_PrimVDB.h ( GEO Library, C++)
7  *
8  * COMMENTS: Custom VDB primitive.
9  */
10 
11 #ifndef __GEO_PrimVDB__
12 #define __GEO_PrimVDB__
13 
14 #include "GEO_API.h"
15 #include "GEO_Primitive.h"
16 #include "GEO_VolumeOptions.h"
17 
18 #include <GA/GA_Defines.h>
19 
20 #include <SYS/SYS_AtomicInt.h> // for SYS_AtomicCounter
21 
22 #include <UT/UT_BoundingBox.h>
23 #include <UT/UT_VDBUtils.h>
24 
25 #include <openvdb/Platform.h>
26 #include <openvdb/openvdb.h>
27 
28 
29 class GEO_Detail;
30 class GEO_PrimVolume;
32 class UT_MemoryCounter;
33 
34 class CE_VDBGrid;
35 
37 {
38 public:
39  typedef uint64 UniqueId;
40 
41 protected:
42  /// NOTE: The constructor should only be called from subclass
43  /// constructors.
45 
46  ~GEO_PrimVDB() override;
47 public:
49  { return GA_FAMILY_NONE; }
50 
51  /// @{
52  /// Required interface methods
53  bool isDegenerate() const override;
54  int getBBox(UT_BoundingBox *bbox) const override;
55  void reverse() override;
56  UT_Vector3 computeNormal() const override;
57  void copyPrimitive(const GEO_Primitive *src) override;
58  void copySubclassData(const GA_Primitive *source) override;
59 
60  /// Acquire a CE grid and cache it on the GPU. If marked for
61  /// writing, the CPU version will be overwritten.
62  /// Note that the getVoxelHandle does *NOT* auto-flush these!
63  /// NOTE: If someone else fetches a non-read grid, and you fetch it
64  /// as a read grid, you will not get any copied data.
65  CE_VDBGrid *getCEGrid(bool read, bool write) const;
66 
67  /// Any modified CE cache on the GPU will be copied back to the
68  /// CPU. Will leave result on GPU.
69  void flushCEWriteCaches() override;
70 
71  /// Remove all CE caches from the GPU, possibly writing back
72  /// if necessary.
73  void flushCECaches() override;
74 
75 
83  { return getVertexOffset(0); }
86  { return getPointOffset(0); }
89  { setPointOffset(0, pt); }
92  { return getPos3(0); }
94  void setPos3(const UT_Vector3 &pos)
95  { setPos3(0, pos); }
96 
97  /// Convert an index in the voxel array into the corresponding worldspace
98  /// location
99  void indexToPos(int x, int y, int z, UT_Vector3 &pos) const;
100  void findexToPos(UT_Vector3 index, UT_Vector3 &pos) const;
101  void indexToPos(exint x, exint y, exint z, UT_Vector3D &pos) const;
102  void findexToPos(UT_Vector3D index, UT_Vector3D &pos) const;
103 
104  /// Convert a 3d position into the closest index value.
105  void posToIndex(UT_Vector3 pos, int &x, int &y, int &z) const;
106  void posToIndex(UT_Vector3 pos, UT_Vector3 &index) const;
107  void posToIndex(UT_Vector3D pos, exint &x, exint &y, exint &z) const;
108  void posToIndex(UT_Vector3D pos, UT_Vector3D &index) const;
109 
110  /// Evaluate the voxel value at the given world space position.
111  /// Note that depending on the underlying VDB type, this may not
112  /// be sensible, in which case a zero will silently be returned
113  fpreal getValueF(const UT_Vector3 &pos) const;
114  fpreal getValueAtIndexF(int ix, int iy, int iz) const;
115  UT_Vector3D getValueV3(const UT_Vector3 &pos) const;
116  UT_Vector3D getValueAtIndexV3(int ix, int iy, int iz) const;
117 
118  void getValues(float *f, int stride, const UT_Vector3 *pos, int num) const;
119  void getValues(int *f, int stride, const UT_Vector3 *pos, int num) const;
120  void getValuesAtIndices(float *f, int stride, const int *ix, const int *iy, const int *iz, int num) const;
121  void getValuesAtIndices(int *f, int stride, const int *ix, const int *iy, const int *iz, int num) const;
122 
123  /// Vector grid variants.
124  void getValues(UT_Vector3 *f, int stride, const UT_Vector3 *pos, int num) const;
125  void getValuesAtIndices(UT_Vector3 *f, int stride, const int *ix, const int *iy, const int *iz, int num) const;
126 
127  void getValues(double *f, int stride, const UT_Vector3D *pos, int num) const;
128  void getValues(exint *f, int stride, const UT_Vector3D *pos, int num) const;
129  void getValuesAtIndices(double *f, int stride, const exint *ix, const exint *iy, const exint *iz, int num) const;
130  void getValuesAtIndices(exint *f, int stride, const exint *ix, const exint *iy, const exint *iz, int num) const;
131 
132  /// Vector grid variants.
133  void getValues(UT_Vector3D *f, int stride, const UT_Vector3D *pos, int num) const;
134  void getValuesAtIndices(UT_Vector3D *f, int stride, const exint *ix, const exint *iy, const exint *iz, int num) const;
135 
136  // Worldspace gradient at the given position
137  UT_Vector3 getGradient(const UT_Vector3 &pos) const;
138 
139  /// Evaluate this grid's gradients at the given world space positions.
140  /// Does nothing and returns false if grid is non-scalar.
141  /// If normalize is true, then the gradients will be normalized to be unit
142  /// length.
143  bool evalGradients(
144  UT_Vector3 *gradients,
145  int gradients_stride,
146  const UT_Vector3 *positions,
147  int num_positions,
148  bool normalize = false) const;
149 
150  /// Get the storage type of the grid
153  { return myGridAccessor.getStorageType(); }
154  /// Get the tuple size, usually 1 or 3
156  int getTupleSize() const
157  { return UTvdbGetGridTupleSize(getStorageType()); }
158 
159  bool isSDF() const;
160 
161  /// True if the two volumes map the same indices to the same positions.
162  bool isAligned(const GEO_PrimVDB *vdb) const;
163  /// True if the two volumes have the same active regions
164  bool isActiveRegionMatched(const GEO_PrimVDB *vdb) const;
165 
166  /// True if we are aligned with the world axes. Ie, all our
167  /// off diagonals are zero and our diagonal is positive.
168  bool isWorldAxisAligned() const;
169 
170  // Transform the matrix associated with this primitive. Translate is
171  // ignored.
172  void transform(const UT_Matrix4 &mat) override;
173 
174  /// Accessors for the 4x4 matrix representing the affine transform that
175  /// converts from index space voxel coordinates to world space. For frustum
176  /// maps, this will be transform as if the taper value is set to 1.
177  /// @{
178  void setTransform4(const UT_DMatrix4 &xform4);
179  void setTransform4(const UT_Matrix4 &xform4);
180  UT_Matrix4D getTransform4() const;
181  /// @}
182 
183  // Take the whole set of points into consideration when applying the
184  // point removal operation to this primitive. The method returns 0 if
185  // successful, -1 if it failed because it would have become degenerate,
186  // and -2 if it failed because it would have had to remove the primitive
187  // altogether.
188  int detachPoints(GA_PointGroup &grp) override;
189  /// Before a point is deleted, all primitives using the point will be
190  /// notified. The method should return "false" if it's impossible to
191  /// delete the point. Otherwise, the vertices should be removed.
192  GA_DereferenceStatus dereferencePoint(GA_Offset point,
193  bool dry_run=false) override;
194  GA_DereferenceStatus dereferencePoints(const GA_RangeMemberQuery &pt_q,
195  bool dry_run=false) override;
196  const GA_PrimitiveJSON *getJSON() const override;
197 
198  /// This method assigns a preallocated vertex to the quadric, optionally
199  /// creating the topological link between the primitive and new vertex.
200  void assignVertex(GA_Offset new_vtx, bool update_topology);
201 
202  /// Evalaute a point given a u,v coordinate (with derivatives)
203  bool evaluatePointRefMap(
204  GA_Offset result_vtx,
205  GA_AttributeRefMap &hlist,
206  fpreal u, fpreal v,
207  uint du, uint dv) const override;
208  /// Evalaute position given a u,v coordinate (with derivatives)
210  UT_Vector4 &pos,
211  float u, float v = 0,
212  unsigned du=0, unsigned dv=0) const override
213  {
214  return GEO_Primitive::evaluatePointV4(pos, u, v,
215  du, dv);
216  }
217  /// @}
218 
219  /// Convert transforms between native volumes and VDBs
220  /// @{
221 
222  /// Get a GEO_PrimVolumeXform which represent's the grid's full transform.
223  /// The returned space's fromVoxelSpace() method will convert index space
224  /// voxel coordinates to world space positions (and the vice versa for
225  /// toVoxelSpace()).
226  GEO_PrimVolumeXform getIndexSpaceTransform() const;
227 
228  /// Equivalent to getSpaceTransform(getGrid().evalActiveVoxelBoundingBox()).
229  /// The returned space's fromVoxelSpace() method will convert 0-1
230  /// coordinates over the active voxel bounding box to world space (and vice
231  /// versa for toVoxelSpace()).
232  GEO_PrimVolumeXform getSpaceTransform() const;
233 
234  /// Gives the equivalent to GEO_PrimVolume's getSpaceTransform() by using
235  /// the given bounding box to determine the bounds of the transform.
236  /// The resulting world space sample points will be offset by half a voxel
237  /// so that they match GEO_PrimVolume.
238  /// The returned space's fromVoxelSpace() method will convert 0-1
239  /// coordinates over the bbox extents to world space (and vice versa for
240  /// toVoxelSpace()).
241  GEO_PrimVolumeXform getSpaceTransform(const UT_BoundingBoxD &bbox) const;
242 
243  /// Sets the transform from a GEO_PrimVolume's getSpaceTransform() by using
244  /// the index space [(0,0,0), resolution] bbox. If force_taper is true,
245  /// then the resulting transform will always be a NonlinearFrustumMap even
246  /// if there is no tapering.
247  void setSpaceTransform(const GEO_PrimVolumeXform &space,
248  const UT_Vector3R &resolution,
249  bool force_taper = false);
250 
251  /// @}
252 
253  fpreal getTaper() const;
254 
255  /// Returns the resolution of the active voxel array.
256  /// Does *not* mean the indices go from 0..rx, however!
257  void getRes(int &rx, int &ry, int &rz) const;
258 
259  /// Computes the voxel diameter by taking a step in x, y, and z
260  /// converting to world space and taking the length of that vector.
261  fpreal getVoxelDiameter() const;
262 
263  /// Returns the length of the voxel when you take an x, y, and z step
264  UT_Vector3 getVoxelSize() const;
265 
266  /// Compute useful aggregate properties of the volume.
267  fpreal calcMinimum() const;
268  fpreal calcMaximum() const;
269  fpreal calcAverage() const;
270 
271  /// VDBs may either be unbounded, or created with a specific frustum
272  /// range. The latter is important for tapered VDBs that otherwise
273  /// have a singularity at the camera location. Tools can use the
274  /// presence of an idxbox as a clipping box in index space.
275  /// This does *NOT* relate to getRes - it may be much larger or
276  /// even in some cases smaller.
277  bool getFrustumBounds(UT_BoundingBox &idxbox) const;
278 
280  {
281  ACTIVATE_UNION, // Activate anything in source
282  ACTIVATE_INTERSECT, // Deactivate anything not in source
283  ACTIVATE_SUBTRACT, // Deactivate anything in source
284  ACTIVATE_COPY // Set our activation to match source
285  };
286 
287  /// Activates voxels given an *index* space bounding box. This
288  /// is an inclusive box.
289  /// If this is Frustum VDB, the activation will be clipped by that.
290  /// Setting the value only takes effect if the voxels are activated,
291  /// deactivated voxels are set to the background.
293  const openvdb::CoordBBox& bbox,
294  ActivateOperation operation,
295  bool setvalue, fpreal value)
296  {
297  activateIndexBBoxAdapter(
298  &bbox, operation, setvalue, value);
299  }
300 
301  /// Activates all of the voxels in this VDB that are touched
302  /// by active voxels in the source.
303  /// If ignore_transform is true, voxels will be activated
304  /// by grid index instead of world space position.
305  void activateByVDB(const GEO_PrimVDB *vdb,
306  ActivateOperation operation,
307  bool setvalue, fpreal value,
308  bool ignore_transform=false);
309 
310  /// @{
311  /// Though not strictly required (i.e. not pure virtual), these methods
312  /// should be implemented for proper behaviour.
313  GEO_Primitive *copy(int preserve_shared_pts = 0) const override;
314 
315  // Have we been deactivated and stashed?
316  void stashed(bool beingstashed,
318 
319  /// @}
320 
321  /// @{
322  /// Optional interface methods. Though not required, implementing these
323  /// will give better behaviour for the new primitive.
324  UT_Vector3 baryCenter() const override;
325  fpreal calcVolume(const UT_Vector3 &refpt) const override;
326  /// Calculate the surface area of the active voxels where
327  /// a voxel face contributes if it borders an inactive voxel.
328  fpreal calcArea() const override;
329  /// @}
330 
331  /// @{
332  /// Enlarge a bounding box by the bounding box of the primitive. A
333  /// return value of false indicates an error in the operation, most
334  /// likely an invalid P. For any attribute other than the position
335  /// these methods simply enlarge the bounding box based on the vertex.
336  bool enlargeBoundingBox(
338  const GA_Attribute *P) const override;
339  bool enlargeBoundingBox(
340  UT_BoundingBox &b,
341  const GA_Attribute *P) const override;
342  void enlargePointBounds(UT_BoundingBox &e) const override;
343  /// @}
344  /// Enlarge a bounding sphere to encompass the primitive. A return value
345  /// of false indicates an error in the operation, most likely an invalid
346  /// P. For any attribute other than the position this method simply
347  /// enlarges the sphere based on the vertex.
350  const GA_Attribute *P) const override;
351 
352  /// Accessor for the local 3x3 affine transform matrix for the primitive.
353  /// For frustum maps, this will be transform as if the taper value is set
354  /// to 1.
355  /// @{
356  void getLocalTransform(UT_Matrix3D &result) const override;
357  void setLocalTransform(const UT_Matrix3D &new_mat3) override;
358  /// @}
359 
360  /// @internal Hack to condition 4x4 matrices that we avoid creating what
361  /// OpenVDB erroneously thinks are singular matrices. Returns true if mat4
362  /// was modified.
363  static bool conditionMatrix(UT_Matrix4D &mat4);
364 
365  /// Visualization accessors
366  /// @{
367  const GEO_VolumeOptions &getVisOptions() const { return myVis; }
369  { setVisualization(vis.myMode, vis.myIso, vis.myDensity, vis.myLod); }
370 
372  GEO_VolumeVis vismode,
373  fpreal iso,
374  fpreal density,
376  {
377  myVis.myMode = vismode;
378  myVis.myIso = iso;
379  myVis.myDensity = density;
380  myVis.myLod = lod;
381  }
382  GEO_VolumeVis getVisualization() const { return myVis.myMode; }
383  fpreal getVisIso() const { return myVis.myIso; }
384  fpreal getVisDensity() const { return myVis.myDensity; }
385  GEO_VolumeVisLod getVisLod() const { return myVis.myLod; }
386  /// @}
387 
388  /// Load the order from a JSON value
389  bool loadOrder(const UT_JSONValue &p);
390 
391  /// @{
392  /// Save/Load vdb to a JSON stream
393  bool saveVDB(UT_JSONWriter &w, const GA_SaveMap &sm,
394  bool as_shmem = false) const;
395  bool loadVDB(UT_JSONParser &p,
396  bool as_shmem = false);
397  /// @}
398 
399  bool saveVisualization(
400  UT_JSONWriter &w,
401  const GA_SaveMap &map) const;
402  bool loadVisualization(
403  UT_JSONParser &p,
404  const GA_LoadMap &map);
405 
406  /// Method to perform quick lookup of vertex without the virtual call
408  {
409  UT_ASSERT_P(index < 1);
410  return getVertexOffset();
411  }
412 
413  void setVertexPoint(int i, GA_Offset pt)
414  {
415  if (i == 0)
416  setPointOffset(pt);
417  }
418 
419  /// @brief Computes the total density of the volume, scaled by
420  /// the volume's size. Negative values will be ignored.
421  fpreal calcPositiveDensity() const;
422 
424  bool hasGrid() const { return myGridAccessor.hasGrid(); }
425 
426  /// @brief If this primitive's grid's voxel data (i.e., its tree)
427  /// is shared, replace the tree with a deep copy of itself that is
428  /// not shared with anyone else.
431  { myGridAccessor.makeGridUnique(); }
432 
433  /// @brief Returns true if the tree is not shared. If it is not shared,
434  /// one can make destructive edits without makeGridUnique.
435  bool isGridUnique() const
436  { return myGridAccessor.isGridUnique(); }
437 
438  /// @brief Return a reference to this primitive's grid.
439  /// @note Calling setGrid() invalidates all references previously returned.
441  const openvdb::GridBase & getConstGrid() const
442  { return myGridAccessor.getConstGrid(*this); }
443  /// @brief Return a reference to this primitive's grid.
444  /// @note Calling setGrid() invalidates all references previously returned.
446  const openvdb::GridBase & getGrid() const
447  { return getConstGrid(); }
448  /// @brief Return a reference to this primitive's grid.
449  /// @note Calling setGrid() invalidates all references previously returned.
450  /// @warning Call makeGridUnique() before modifying the grid's voxel data.
452  openvdb::GridBase & getGrid()
453  {
454  incrGridUniqueIds();
455  return myGridAccessor.getGrid(*this);
456  }
457 
458  /// @brief Return a shared pointer to this primitive's grid.
459  /// @note Calling setGrid() causes the grid to which the shared pointer
460  /// refers to be disassociated with this primitive.
462  openvdb::GridBase::ConstPtr getConstGridPtr() const
463  { return myGridAccessor.getConstGridPtr(*this); }
464  /// @brief Return a shared pointer to this primitive's grid.
465  /// @note Calling setGrid() causes the grid to which the shared pointer
466  /// refers to be disassociated with this primitive.
468  openvdb::GridBase::ConstPtr getGridPtr() const
469  { return getConstGridPtr(); }
470  /// @brief Return a shared pointer to this primitive's grid.
471  /// @note Calling setGrid() causes the grid to which the shared pointer
472  /// refers to be disassociated with this primitive.
473  /// @warning Call makeGridUnique() before modifying the grid's voxel data.
475  openvdb::GridBase::Ptr getGridPtr()
476  {
477  incrGridUniqueIds();
478  return myGridAccessor.getGridPtr(*this);
479  }
480 
481  /// @brief Set this primitive's grid to a shallow copy of the given grid.
482  /// @note Invalidates all previous getGrid() and getConstGrid() references
484  void setGrid(const openvdb::GridBase &grid, bool copyPosition=true)
485  {
486  incrGridUniqueIds();
487  myGridAccessor.setGrid(grid, *this, copyPosition);
488  }
489 
490  /// @brief Return a reference to this primitive's grid metadata.
491  /// @note Calling setGrid() invalidates all references previously returned.
492  const openvdb::MetaMap& getConstMetadata() const
493  { return getConstGrid(); }
494  /// @brief Return a reference to this primitive's grid metadata.
495  /// @note Calling setGrid() invalidates all references previously returned.
496  const openvdb::MetaMap& getMetadata() const
497  { return getConstGrid(); }
498  /// @brief Return a reference to this primitive's grid metadata.
499  /// @note Calling setGrid() invalidates all references previously returned.
501  openvdb::MetaMap& getMetadata()
502  {
503  incrMetadataUniqueId();
504  return myGridAccessor.getGrid(*this);
505  }
506 
507  /// @brief Return the value of this primitive's "name" attribute
508  /// in the given detail.
509  const char * getGridName() const;
510 
511  /// @brief Return this primitive's serial number.
512  /// @details A primitive's serial number never changes.
514  { return static_cast<UniqueId>(myUniqueId.relaxedLoad()); }
515 
516  /// @brief Return the serial number of this primitive's voxel data.
517  /// @details The serial number is incremented whenever a non-const
518  /// reference or pointer to this primitive's grid is requested
519  /// (whether or not the voxel data is ultimately modified).
521  { return static_cast<UniqueId>(myTreeUniqueId.relaxedLoad()); }
522  /// @brief Return the serial number of this primitive's grid metadata.
523  /// @details The serial number is incremented whenever a non-const
524  /// reference to the metadata or non-const access to the grid is requested
525  /// (whether or not the metadata is ultimately modified).
527  { return static_cast<UniqueId>(myMetadataUniqueId.relaxedLoad()); }
528  /// @brief Return the serial number of this primitive's transform.
529  /// @details The serial number is incremented whenever the transform
530  /// is modified or non-const access to this primitive's grid is requested
531  /// (whether or not the transform is ultimately modified).
533  { return static_cast<UniqueId>(myTransformUniqueId.relaxedLoad()); }
534 
535 
536  /// @brief If this primitive's grid resolves to one of the listed grid types,
537  /// invoke the functor @a op on the resolved grid.
538  /// @return @c true if the functor was invoked, @c false otherwise
539  ///
540  /// @par Example:
541  /// @code
542  /// auto printOp = [](const openvdb::GridBase& grid) { grid.print(); };
543  /// const GEO_PrimVDB* prim = ...;
544  /// using RealGridTypes = openvdb::TypeList<openvdb::FloatGrid, openvdb::DoubleGrid>;
545  /// // Print info about the primitive's grid if it is a floating-point grid.
546  /// prim->apply<RealGridTypes>(printOp);
547  /// @endcode
548  template<typename GridTypeListT, typename OpT>
549  bool apply(OpT& op) const
550  { return hasGrid() ? getConstGrid().apply<GridTypeListT>(op) : false; }
551 
552  /// @brief If this primitive's grid resolves to one of the listed grid types,
553  /// invoke the functor @a op on the resolved grid.
554  /// @return @c true if the functor was invoked, @c false otherwise
555  /// @details If @a makeUnique is true, deep copy the grid's tree before
556  /// invoking the functor if the tree is shared with other grids.
557  ///
558  /// @par Example:
559  /// @code
560  /// auto fillOp = [](const auto& grid) { // C++14
561  /// // Convert voxels in the given bounding box into background voxels.
562  /// grid.fill(openvdb::CoordBBox(openvdb::Coord(0), openvdb::Coord(99)),
563  /// grid.background(), /*active=*/false);
564  /// };
565  /// GEO_PrimVDB* prim = ...;
566  /// // Set background voxels in the primitive's grid if it is a floating-point grid.
567  /// using RealGridTypes = openvdb::TypeList<openvdb::FloatGrid, openvdb::DoubleGrid>;
568  /// prim->apply<RealGridTypes>(fillOp);
569  /// @endcode
570  template<typename GridTypeListT, typename OpT>
571  bool apply(OpT& op, bool makeUnique = true)
572  {
573  if (hasGrid()) {
574  auto& grid = myGridAccessor.getGrid(*this);
575  if (makeUnique) {
576  auto treePtr = grid.baseTreePtr();
577  if (treePtr.use_count() > 2) { // grid + treePtr = 2
578  // If the grid resolves to one of the listed types and its tree
579  // is shared with other grids, replace the tree with a deep copy.
580  grid.apply<GridTypeListT>([this](openvdb::GridBase& baseGrid) {
581  baseGrid.setTree(baseGrid.constBaseTree().copy());
582  this->incrTreeUniqueId();
583  });
584  }
585  }
586  if (grid.apply<GridTypeListT>(op)) {
587  incrGridUniqueIds();
588  return true;
589  }
590  }
591  return false;
592  }
593 
594 protected:
596 
597  /// Register intrinsic attributes
598  GA_DECLARE_INTRINSICS(override)
599 
600  /// Return true if the given metadata token is an intrinsic
601  static bool isIntrinsicMetadata(const char *name);
602 
603  /// @warning vertexPoint() doesn't check the bounds. Use with caution.
604  GA_Offset vertexPoint(GA_Size) const
605  { return getPointOffset(); }
606 
607  /// Report approximate memory usage, excluding sizeof(*this),
608  /// because the subclass doesn't have access to myGridAccessor.
609  int64 getBaseMemoryUsage() const;
610 
611  // This is called by the subclasses to count the
612  // memory used by this, excluding sizeof(*this).
614 
615  /// @brief Return an ID number that is guaranteed to be unique across
616  /// all VDB primitives.
617  static UniqueId nextUniqueId();
618 
620  { myTreeUniqueId.maximum(nextUniqueId()); }
622  { myMetadataUniqueId.maximum(nextUniqueId()); }
624  { myTransformUniqueId.maximum(nextUniqueId()); }
626  {
627  incrTreeUniqueId();
628  incrMetadataUniqueId();
629  incrTransformUniqueId();
630  }
631 
632  /// @brief Replace this primitive's grid with a shallow copy
633  /// of another primitive's grid.
634  void copyGridFrom(const GEO_PrimVDB&, bool copyPosition=true);
635 
636  /// @brief GridAccessor manages access to a GEO_PrimVDB's grid.
637  /// @details In keeping with OpenVDB library conventions, the grid
638  /// is stored internally by shared pointer. However, grid objects
639  /// are never shared among primitives, though their voxel data
640  /// (i.e., their trees) may be shared.
641  /// <p>Among other things, GridAccessor
642  /// - ensures that each primitive's transform and metadata are unique
643  /// (i.e., not shared with anyone else)
644  /// - allows primitives to share voxel data but, via makeGridUnique(),
645  /// provides a way to break the connection
646  /// - ensures that the primitive's transform and the grid's transform
647  /// are in sync (specifically, the translation component, which is
648  /// stored independently as a vertex offset).
650  {
651  public:
653  GridAccessor() : myStorageType(UT_VDB_INVALID)
654  { }
655 
657  void clear()
658  {
659  myGrid.reset();
660  myStorageType = UT_VDB_INVALID;
661  }
662 
664  openvdb::GridBase &
665  getGrid(const GEO_PrimVDB &prim)
666  { updateGridTranslates(prim); return *myGrid; }
667 
669  const openvdb::GridBase &
670  getConstGrid(const GEO_PrimVDB &prim) const
671  { updateGridTranslates(prim); return *myGrid; }
672 
674  openvdb::GridBase::Ptr
675  getGridPtr(const GEO_PrimVDB &prim)
676  { updateGridTranslates(prim); return myGrid; }
677 
679  openvdb::GridBase::ConstPtr
680  getConstGridPtr(const GEO_PrimVDB &prim) const
681  { updateGridTranslates(prim); return myGrid; }
682 
683  // These accessors will ensure the transform's translate is set into
684  // the vertex position.
686  void setGrid(const openvdb::GridBase& grid, GEO_PrimVDB& prim, bool copyPosition=true)
687  { setGridAdapter(&grid, prim, copyPosition); }
690  const openvdb::math::Transform &xform,
691  GEO_PrimVDB &prim)
692  { setTransformAdapter(&xform, prim); }
693 
694  void makeGridUnique();
695  bool isGridUnique() const;
696 
698  UT_VDBType getStorageType() const { return myStorageType; }
699 
701  bool hasGrid() const { return myGrid != 0; }
702 
703  private:
704  void updateGridTranslates(const GEO_PrimVDB &prim) const;
705 
707  void setVertexPosition(
708  const openvdb::math::Transform &xform,
709  GEO_PrimVDB &prim)
710  { setVertexPositionAdapter(&xform, prim); }
711 
712  void setGridAdapter(const void* grid, GEO_PrimVDB&, bool copyPosition);
713  void setTransformAdapter(const void* xform, GEO_PrimVDB&);
714  void setVertexPositionAdapter(const void* xform, GEO_PrimVDB&);
715 
716  private:
717  openvdb::GridBase::Ptr myGrid;
718  UT_VDBType myStorageType;
719  };
720 
721 private:
722  void activateIndexBBoxAdapter(
723  const void* bbox,
724  ActivateOperation,
725  bool setvalue, fpreal value);
726 
727 
728  GridAccessor myGridAccessor;
729 
730  GEO_VolumeOptions myVis;
731 
732  mutable CE_VDBGrid *myCEGrid;
733  mutable bool myCEGridAuthorative;
734  mutable bool myCEGridIsOwned;
735 
736  AtomicUniqueId myUniqueId;
737  AtomicUniqueId myTreeUniqueId;
738  AtomicUniqueId myMetadataUniqueId;
739  AtomicUniqueId myTransformUniqueId;
740 
741 }; // class GEO_PrimVDB
742 
743 
744 #if 0 // ndef SESI_OPENVDB
745 namespace openvdb_houdini {
746 using ::GEO_VolumeOptions;
747 using ::GEO_PrimVDB;
748 }
749 #endif
750 
751 
752 ////////////////////////////////////////
753 
754 
755 namespace UT_VDBUtils {
756 
757 // This overload of UT_VDBUtils::callTypedGrid(), for GridBaseType = GEO_PrimVDB,
758 // calls makeGridUnique() on the primitive just before instantiating and
759 // invoking the functor on the primitive's grid. This delays the call
760 // to makeGridUnique() until it is known to be necessary and thus avoids
761 // making deep copies of grids of types that won't be processed.
762 template<typename GridType, typename OpType>
763 inline void
764 callTypedGrid(GEO_PrimVDB& prim, OpType& op)
765 {
766  prim.makeGridUnique();
767  op.template operator()<GridType>(*(UTverify_cast<GridType*>(&prim.getGrid())));
768 }
769 
770 // Overload of callTypedGrid() for GridBaseType = const GEO_PrimVDB
771 template<typename GridType, typename OpType>
772 inline void
773 callTypedGrid(const GEO_PrimVDB& prim, OpType& op)
774 {
775  op.template operator()<GridType>(*(UTverify_cast<const GridType*>(&prim.getConstGrid())));
776 }
777 
778 } // namespace UT_VDBUtils
779 
780 // Define UTvdbProcessTypedGrid*() (see UT_VDBUtils.h) for grids
781 // belonging to primitives, for various subsets of grid types.
784 
785 
786 ////////////////////////////////////////
787 
788 
789 /// @brief Utility function to process the grid of a const primitive using functor @a op.
790 /// @details It will invoke @code op.operator()<GridT>(const GridT &grid) @endcode
791 /// @{
792 template <typename OpT>
793 inline bool GEOvdbProcessTypedGrid(const GEO_PrimVDB &vdb, OpT &op)
794 {
795  return UTvdbProcessTypedGrid(vdb.getStorageType(), vdb.getGrid(), op);
796 }
797 
798 template <typename OpT>
799 inline bool GEOvdbProcessTypedGridReal(const GEO_PrimVDB &vdb, OpT &op)
800 {
801  return UTvdbProcessTypedGridReal(vdb.getStorageType(), vdb.getGrid(), op);
802 }
803 
804 template <typename OpT>
805 inline bool GEOvdbProcessTypedGridScalar(const GEO_PrimVDB &vdb, OpT &op)
806 {
807  return UTvdbProcessTypedGridScalar(vdb.getStorageType(), vdb.getGrid(), op);
808 }
809 
810 template <typename OpT>
811 inline bool GEOvdbProcessTypedGridTopology(const GEO_PrimVDB &vdb, OpT &op)
812 {
813  return UTvdbProcessTypedGridTopology(vdb.getStorageType(), vdb.getGrid(), op);
814 }
815 
816 template <typename OpT>
817 inline bool GEOvdbProcessTypedGridVec3(const GEO_PrimVDB &vdb, OpT &op)
818 {
819  return UTvdbProcessTypedGridVec3(vdb.getStorageType(), vdb.getGrid(), op);
820 }
821 
822 template <typename OpT>
823 inline bool GEOvdbProcessTypedGridPoint(const GEO_PrimVDB &vdb, OpT &op)
824 {
825  return UTvdbProcessTypedGridPoint(vdb.getStorageType(), vdb.getGrid(), op);
826 }
827 /// @}
828 
829 /// @brief Utility function to process the grid of a primitive using functor @a op.
830 /// @param vdb the primitive whose grid is to be processed
831 /// @param op a functor with a call operator of the form
832 /// @code op.operator()<GridT>(GridT &grid) @endcode
833 /// @param makeUnique if @c true, call <tt>vdb.makeGridUnique()</tt> before
834 /// invoking the functor
835 /// @{
836 template <typename OpT>
837 inline bool GEOvdbProcessTypedGrid(GEO_PrimVDB &vdb, OpT &op, bool makeUnique = true)
838 {
839  if (makeUnique) return UTvdbProcessTypedGrid(vdb.getStorageType(), vdb, op);
840  return UTvdbProcessTypedGrid(vdb.getStorageType(), vdb.getGrid(), op);
841 }
842 
843 template <typename OpT>
844 inline bool GEOvdbProcessTypedGridReal(GEO_PrimVDB &vdb, OpT &op, bool makeUnique = true)
845 {
846  if (makeUnique) return UTvdbProcessTypedGridReal(vdb.getStorageType(), vdb, op);
847  return UTvdbProcessTypedGridReal(vdb.getStorageType(), vdb.getGrid(), op);
848 }
849 
850 template <typename OpT>
851 inline bool GEOvdbProcessTypedGridScalar(GEO_PrimVDB &vdb, OpT &op, bool makeUnique = true)
852 {
853  if (makeUnique) return UTvdbProcessTypedGridScalar(vdb.getStorageType(), vdb, op);
854  return UTvdbProcessTypedGridScalar(vdb.getStorageType(), vdb.getGrid(), op);
855 }
856 
857 template <typename OpT>
858 inline bool GEOvdbProcessTypedGridTopology(GEO_PrimVDB &vdb, OpT &op, bool makeUnique = true)
859 {
860  if (makeUnique) return UTvdbProcessTypedGridTopology(vdb.getStorageType(), vdb, op);
861  return UTvdbProcessTypedGridTopology(vdb.getStorageType(), vdb.getGrid(), op);
862 }
863 
864 template <typename OpT>
865 inline bool GEOvdbProcessTypedGridVec3(GEO_PrimVDB &vdb, OpT &op, bool makeUnique = true)
866 {
867  if (makeUnique) return UTvdbProcessTypedGridVec3(vdb.getStorageType(), vdb, op);
868  return UTvdbProcessTypedGridVec3(vdb.getStorageType(), vdb.getGrid(), op);
869 }
870 
871 template <typename OpT>
872 inline bool GEOvdbProcessTypedGridPoint(GEO_PrimVDB &vdb, OpT &op, bool makeUnique = true)
873 {
874  if (makeUnique) return UTvdbProcessTypedGridPoint(vdb.getStorageType(), vdb, op);
875  return UTvdbProcessTypedGridPoint(vdb.getStorageType(), vdb.getGrid(), op);
876 }
877 /// @}
878 
879 #endif // __GEO_PrimVDB__
virtual void flushCEWriteCaches()
Copy any modified caches from the GPU back to CPU cache.
Definition: GA_Primitive.h:783
virtual void flushCECaches()
Definition: GA_Primitive.h:787
Definition of a geometry attribute.
Definition: GA_Attribute.h:196
GridAccessor manages access to a GEO_PrimVDB's grid.
Definition: GEO_PrimVDB.h:649
virtual GEO_Primitive * copy(int preserve_shared_pts=0) const
SYS_FORCE_INLINE GA_Offset getPointOffset(GA_Size i) const
Definition: GA_Primitive.h:254
virtual UT_Vector3 baryCenter() const
GA_Offset fastVertexOffset(GA_Size UT_IF_ASSERT_P(index)) const
Method to perform quick lookup of vertex without the virtual call.
Definition: GEO_PrimVDB.h:407
GLenum src
Definition: glew.h:2410
virtual void copyPrimitive(const GEO_Primitive *src)=0
SYS_FORCE_INLINE UT_VDBType getStorageType() const
Get the storage type of the grid.
Definition: GEO_PrimVDB.h:152
bool GEOvdbProcessTypedGridTopology(const GEO_PrimVDB &vdb, OpT &op)
Utility function to process the grid of a const primitive using functor op.
Definition: GEO_PrimVDB.h:811
SYS_FORCE_INLINE void setPos3(const UT_Vector3 &pos)
Definition: GEO_PrimVDB.h:94
GLuint const GLchar * name
Definition: glew.h:1814
Used to pass options and map offset values during saving.
Definition: GA_SaveMap.h:48
SYS_FORCE_INLINE openvdb::MetaMap & getMetadata()
Return a reference to this primitive's grid metadata.
Definition: GEO_PrimVDB.h:501
SYS_FORCE_INLINE GridAccessor()
Definition: GEO_PrimVDB.h:653
SYS_FORCE_INLINE void clear()
Definition: GEO_PrimVDB.h:657
GLuint index
Definition: glew.h:1814
SYS_FORCE_INLINE openvdb::GridBase::ConstPtr getConstGridPtr() const
Return a shared pointer to this primitive's grid.
Definition: GEO_PrimVDB.h:462
virtual void copySubclassData(const GA_Primitive *source)
Definition: GA_Primitive.h:484
SYS_AtomicCounter AtomicUniqueId
Definition: GEO_PrimVDB.h:595
const openvdb::MetaMap & getMetadata() const
Return a reference to this primitive's grid metadata.
Definition: GEO_PrimVDB.h:496
fpreal calcVolume(const UT_Vector3 &) const override
SYS_FORCE_INLINE const openvdb::GridBase & getConstGrid() const
Return a reference to this primitive's grid.
Definition: GEO_PrimVDB.h:441
SYS_FORCE_INLINE void setPointOffset(GA_Size i, GA_Offset ptoff)
Definition: GA_Primitive.h:260
int64 exint
Definition: SYS_Types.h:125
UniqueId getUniqueId() const
Return this primitive's serial number.
Definition: GEO_PrimVDB.h:513
GLsizei GLsizei GLchar * source
Definition: glew.h:1832
virtual GA_DereferenceStatus dereferencePoint(GA_Offset point, bool dry_run=false)=0
void incrTransformUniqueId()
Definition: GEO_PrimVDB.h:623
JSON reader class which handles parsing of JSON or bJSON files.
Definition: UT_JSONParser.h:76
void reverse() override=0
Reverse the order of vertices.
#define GA_DECLARE_INTRINSICS(OVERRIDE)
Definition: GA_Primitive.h:80
bool enlargeBoundingBox(UT_BoundingRect &b, const GA_Attribute *P) const override
GEO_VolumeVis myMode
Class which writes ASCII or binary JSON streams.
Definition: UT_JSONWriter.h:34
Abstract base class for a range membership query object.
const GLdouble * v
Definition: glew.h:1391
SYS_FORCE_INLINE TO_T UTverify_cast(FROM_T from)
Definition: UT_Assert.h:208
UT_VDBType
Definition: UT_VDBUtils.h:11
const GEO_VolumeOptions & getVisOptions() const
Definition: GEO_PrimVDB.h:367
unsigned long long uint64
Definition: SYS_Types.h:117
#define UT_IF_ASSERT_P(ZZ)
Definition: UT_Assert.h:161
fpreal calcArea() const override
bool GEOvdbProcessTypedGridPoint(const GEO_PrimVDB &vdb, OpT &op)
Utility function to process the grid of a const primitive using functor op.
Definition: GEO_PrimVDB.h:823
SYS_FORCE_INLINE openvdb::GridBase::ConstPtr getConstGridPtr(const GEO_PrimVDB &prim) const
Definition: GEO_PrimVDB.h:680
void read(T &in, bool &v)
Definition: ImfXdr.h:611
UniqueId getMetadataUniqueId() const
Return the serial number of this primitive's grid metadata.
Definition: GEO_PrimVDB.h:526
void incrGridUniqueIds()
Definition: GEO_PrimVDB.h:625
exint GA_Size
Defines the bit width for index and offset types in GA.
Definition: GA_Types.h:233
SYS_FORCE_INLINE int64 getBaseMemoryUsage() const
Report approximate memory usage for myVertexList for subclasses.
Definition: GA_Primitive.h:813
bool apply(OpT &op) const
If this primitive's grid resolves to one of the listed grid types, invoke the functor op on the resol...
Definition: GEO_PrimVDB.h:549
GA_PrimitiveFamilyMask
void setVisualization(GEO_VolumeVis vismode, fpreal iso, fpreal density, GEO_VolumeVisLod lod=GEO_VOLUMEVISLOD_FULL)
Definition: GEO_PrimVDB.h:371
virtual UT_Vector3 computeNormal() const =0
Return a normal vector for the primitive.
#define GA_INVALID_OFFSET
Definition: GA_Types.h:676
SYS_FORCE_INLINE UT_Vector3 getPos3() const
Definition: GEO_PrimVDB.h:91
bool GEOvdbProcessTypedGridReal(const GEO_PrimVDB &vdb, OpT &op)
Utility function to process the grid of a const primitive using functor op.
Definition: GEO_PrimVDB.h:799
bool GEOvdbProcessTypedGridVec3(const GEO_PrimVDB &vdb, OpT &op)
Utility function to process the grid of a const primitive using functor op.
Definition: GEO_PrimVDB.h:817
GLdouble GLdouble z
Definition: glew.h:1559
uint64 UniqueId
Definition: GEO_PrimVDB.h:39
virtual bool isDegenerate() const =0
Is the primitive degenerate.
GA_Size GA_Offset
Definition: GA_Types.h:639
SYS_FORCE_INLINE bool hasGrid() const
Definition: GEO_PrimVDB.h:701
virtual bool enlargeBoundingSphere(UT_BoundingSphere &b, const GA_Attribute *P) const
SYS_FORCE_INLINE GA_Offset getPointOffset() const
Definition: GEO_PrimVDB.h:85
#define UT_VDB_DECL_PROCESS_TYPED_GRID(GRID_BASE_T)
Utility function that, given a generic grid pointer, calls a functor on the fully-resolved grid...
Definition: UT_VDBUtils.h:237
SYS_FORCE_INLINE UT_VDBType getStorageType() const
Definition: GEO_PrimVDB.h:698
SYS_FORCE_INLINE UT_Vector3 getPos3(GA_Size i) const
Definition: GA_Primitive.h:274
virtual void setLocalTransform(const UT_Matrix3D &matrix)
Set the local transform. The default implementation does nothing.
GLclampf f
Definition: glew.h:3499
GLint GLint GLint GLint GLint x
Definition: glew.h:1252
SYS_FORCE_INLINE openvdb::GridBase::Ptr getGridPtr()
Return a shared pointer to this primitive's grid.
Definition: GEO_PrimVDB.h:475
GLint GLint GLint GLint GLint GLint y
Definition: glew.h:1252
bool GEOvdbProcessTypedGridScalar(const GEO_PrimVDB &vdb, OpT &op)
Utility function to process the grid of a const primitive using functor op.
Definition: GEO_PrimVDB.h:805
GEO_VolumeVisLod myLod
#define UT_ASSERT_P(ZZ)
Definition: UT_Assert.h:134
void incrMetadataUniqueId()
Definition: GEO_PrimVDB.h:621
#define SYS_FORCE_INLINE
Definition: SYS_Inline.h:45
GLubyte GLubyte GLubyte GLubyte w
Definition: glew.h:1890
virtual const GA_PrimitiveJSON * getJSON() const =0
void setVertexPoint(int i, GA_Offset pt)
Definition: GEO_PrimVDB.h:413
Provide a JSON interface to a primitive.
#define GEO_API
Definition: GEO_API.h:14
void activateIndexBBox(const openvdb::CoordBBox &bbox, ActivateOperation operation, bool setvalue, fpreal value)
Definition: GEO_PrimVDB.h:292
SYS_FORCE_INLINE void setTransform(const openvdb::math::Transform &xform, GEO_PrimVDB &prim)
Definition: GEO_PrimVDB.h:689
GEO_VolumeVis
SYS_FORCE_INLINE int getTupleSize() const
Get the tuple size, usually 1 or 3.
Definition: GEO_PrimVDB.h:156
long long int64
Definition: SYS_Types.h:116
A handle to simplify manipulation of multiple attributes.
UniqueId getTreeUniqueId() const
Return the serial number of this primitive's voxel data.
Definition: GEO_PrimVDB.h:520
SYS_FORCE_INLINE bool hasGrid() const
Definition: GEO_PrimVDB.h:424
Options during loading.
Definition: GA_LoadMap.h:42
virtual int getBBox(UT_BoundingBox *bbox) const =0
GridType::Ptr normalize(const GridType &grid, bool threaded, InterruptT *interrupt)
Normalize the vectors of the given vector-valued grid.
SYS_FORCE_INLINE void setGrid(const openvdb::GridBase &grid, GEO_PrimVDB &prim, bool copyPosition=true)
Definition: GEO_PrimVDB.h:686
SYS_FORCE_INLINE openvdb::GridBase & getGrid(const GEO_PrimVDB &prim)
Definition: GEO_PrimVDB.h:665
SYS_FORCE_INLINE openvdb::GridBase::Ptr getGridPtr(const GEO_PrimVDB &prim)
Definition: GEO_PrimVDB.h:675
int evaluatePointV4(UT_Vector4 &pos, float u, float v=0, unsigned du=0, unsigned dv=0) const override
Evalaute position given a u,v coordinate (with derivatives)
Definition: GEO_PrimVDB.h:209
virtual GA_DereferenceStatus dereferencePoints(const GA_RangeMemberQuery &pt_q, bool dry_run=false)=0
SYS_FORCE_INLINE GA_Offset getVertexOffset() const
Definition: GEO_PrimVDB.h:82
SYS_FORCE_INLINE void setGrid(const openvdb::GridBase &grid, bool copyPosition=true)
Set this primitive's grid to a shallow copy of the given grid.
Definition: GEO_PrimVDB.h:484
SYS_FORCE_INLINE void setPos3(GA_Size i, const UT_Vector3 &pos) const
Definition: GA_Primitive.h:280
UniqueId getTransformUniqueId() const
Return the serial number of this primitive's transform.
Definition: GEO_PrimVDB.h:532
GLsizei stride
Definition: glew.h:1523
virtual void transform(const UT_Matrix4 &)
GLdouble GLdouble GLdouble b
Definition: glew.h:9122
virtual void enlargePointBounds(UT_BoundingBox &box) const
GLfloat GLfloat p
Definition: glew.h:16321
SYS_FORCE_INLINE const openvdb::GridBase & getConstGrid(const GEO_PrimVDB &prim) const
Definition: GEO_PrimVDB.h:670
virtual void getLocalTransform(UT_Matrix3D &matrix) const
virtual int detachPoints(GA_PointGroup &grp)=0
GLuint counter
Definition: glew.h:2740
fpreal getVisDensity() const
Definition: GEO_PrimVDB.h:384
SYS_FORCE_INLINE void makeGridUnique()
If this primitive's grid's voxel data (i.e., its tree) is shared, replace the tree with a deep copy o...
Definition: GEO_PrimVDB.h:430
bool isGridUnique() const
Returns true if the tree is not shared. If it is not shared, one can make destructive edits without m...
Definition: GEO_PrimVDB.h:435
GLuint num
Definition: glew.h:2690
int UTvdbGetGridTupleSize(UT_VDBType type)
Returns the tuple size of a grid given its value type.
Definition: UT_VDBUtils.h:108
fpreal64 fpreal
Definition: SYS_Types.h:277
GLint lod
Definition: glew.h:1385
SYS_FORCE_INLINE openvdb::GridBase::ConstPtr getGridPtr() const
Return a shared pointer to this primitive's grid.
Definition: GEO_PrimVDB.h:468
SYS_FORCE_INLINE GA_Offset getVertexOffset(GA_Size primvertexnum) const
Definition: GA_Primitive.h:240
void setVisOptions(const GEO_VolumeOptions &vis)
Definition: GEO_PrimVDB.h:368
Class to store JSON objects as C++ objects.
Definition: UT_JSONValue.h:77
virtual bool evaluatePointRefMap(GA_Offset result_vtx, GA_AttributeRefMap &map, fpreal u, fpreal v=0, uint du=0, uint dv=0) const =0
GEO_VolumeVisLod getVisLod() const
Definition: GEO_PrimVDB.h:385
GLuint64EXT * result
Definition: glew.h:14007
static GA_PrimitiveFamilyMask buildFamilyMask()
Definition: GEO_PrimVDB.h:48
void callTypedGrid(GEO_PrimVDB &prim, OpType &op)
Definition: GEO_PrimVDB.h:764
GEO_VolumeVisLod
#define const
Definition: zconf.h:214
SYS_FORCE_INLINE const openvdb::GridBase & getGrid() const
Return a reference to this primitive's grid.
Definition: GEO_PrimVDB.h:446
fpreal getVisIso() const
Definition: GEO_PrimVDB.h:383
SYS_FORCE_INLINE void setPointOffset(GA_Offset pt)
Definition: GEO_PrimVDB.h:88
void write(T &out, bool v)
Definition: ImfXdr.h:332
void countBaseMemory(UT_MemoryCounter &counter) const
GLsizei const GLfloat * value
Definition: glew.h:1849
unsigned int uint
Definition: SYS_Types.h:45
GEO_VolumeVis getVisualization() const
Definition: GEO_PrimVDB.h:382
SYS_FORCE_INLINE openvdb::GridBase & getGrid()
Return a reference to this primitive's grid.
Definition: GEO_PrimVDB.h:452
bool GEOvdbProcessTypedGrid(const GEO_PrimVDB &vdb, OpT &op)
Utility function to process the grid of a const primitive using functor op.
Definition: GEO_PrimVDB.h:793
void incrTreeUniqueId()
Definition: GEO_PrimVDB.h:619
virtual int evaluatePointV4(UT_Vector4 &pos, float u, float v=0, unsigned du=0, unsigned dv=0) const
virtual void stashed(bool beingstashed, GA_Offset offset=GA_INVALID_OFFSET)
bool apply(OpT &op, bool makeUnique=true)
If this primitive's grid resolves to one of the listed grid types, invoke the functor op on the resol...
Definition: GEO_PrimVDB.h:571
const openvdb::MetaMap & getConstMetadata() const
Return a reference to this primitive's grid metadata.
Definition: GEO_PrimVDB.h:492
GLintptr offset
Definition: glew.h:1682