20 #ifndef OPENVEB_POINTS_TRANSFER_HAS_BEEN_INCLUDED
21 #define OPENVEB_POINTS_TRANSFER_HAS_BEEN_INCLUDED
30 #include <type_traits>
163 template <
typename PointDataTreeOrGridT,
165 typename FilterT = NullFilter,
166 typename InterrupterT = util::NullInterrupter>
170 const FilterT&
filter = NullFilter(),
171 InterrupterT* interrupter =
nullptr);
184 : mSourceTransform(st)
185 , mTargetTransform(tt) {}
187 template <
typename T>
194 template <
typename T>
213 template <
typename ...TreeTypes>
216 static const size_t Size =
sizeof...(TreeTypes);
230 : mTreeArray(other.mTreeArray)
234 mBuffers.fill(
nullptr);
235 mMasks.fill(
nullptr);
242 template <
size_t Idx>
248 template <
size_t Idx>
254 template <
size_t Idx>
258 template <
size_t Idx>
260 inline const NodeMaskT*
mask(
const size_t idx)
const {
return mMasks[idx]; }
262 template <
typename FunctorT>
263 inline void foreach(
const FunctorT& functor);
267 std::array<void*, Size> mBuffers;
268 std::array<NodeMaskT*, Size> mMasks;
273 template <
typename TreeT>
278 using NodeMaskT =
typename TreeType::LeafNodeType::NodeMaskType;
281 "One or more template arguments to VolumeTransfer "
282 "are not a valid openvdb::Tree type.");
304 if (
auto leaf = mTree->probeLeaf(origin)) {
305 mBuffer = leaf->buffer().data();
306 mMask = &(leaf->getValueMask());
331 namespace transfer_internal
333 template<
typename T,
typename F,
size_t... Is>
334 void foreach(T&&
t,
const F&
func, std::integer_sequence<size_t, Is...>)
336 auto init = { (
func(std::get<Is>(
t), Is), 0)... };
340 template<
typename T,
typename F,
size_t... Is>
341 void foreach(
void**
buffers,
const F& func, std::integer_sequence<size_t, Is...>)
343 int init[
sizeof...(Is)] = {
345 (*(buffers + Is)), Is), 0)...
349 template<
typename T,
template <
typename>
class R,
typename F,
size_t... Is>
350 void foreach(
void** buffers,
const F& func, std::integer_sequence<size_t, Is...>)
352 int init[
sizeof...(Is)] = {
354 (*(buffers + Is)), Is), 0)...
359 template <
typename ...TreeTypes>
361 : mTreeArray({ trees... })
368 "One or more template arguments to VolumeTransfer "
369 "are not a valid openvdb::Tree type.");
371 }, std::make_integer_sequence<size_t, Size>());
377 template <
typename ...TreeTypes>
381 [&](
auto&& tree,
const size_t i) {
383 if (
auto leaf = tree->probeLeaf(origin)) {
384 mBuffers[i] =
static_cast<void*
>(leaf->buffer().data());
385 mMasks[i] = &(leaf->getValueMask());
391 }, std::make_integer_sequence<size_t, Size>());
394 template <
typename ...TreeTypes>
395 template <
typename FunctorT>
398 transfer_internal::foreach<TreeTupleT, TypeResolver>(
mBuffers.data(), functor,
399 std::make_integer_sequence<size_t, Size>());
402 namespace transfer_internal
404 template <
typename TransferT,
406 typename PointFilterT = points::NullFilter,
413 static const Index DIM = TopologyT::LeafNodeType::DIM;
418 const TransferT& transfer,
419 const PointFilterT&
filter = PointFilterT(),
420 InterrupterT* interrupter =
nullptr)
421 : mPointAccessor(tree)
422 , mTransfer(transfer)
424 , mInterrupter(interrupter) {}
429 thread::cancelGroupExecution();
433 const Coord& origin = leaf.origin();
434 auto&
mask = leaf.getValueMask();
439 if (
mask.isConstant(state)) {
441 else bounds = leaf.getNodeBoundingBox();
446 leaf.evalActiveBoundingBox(bounds);
447 assert(!bounds.empty());
450 mTransfer.initialize(origin, idx, bounds);
453 this->transform<>(
search);
456 const Coord
min = (search.min() & ~(
DIM-1));
457 const Coord&
max = search.max();
458 PointFilterT localFilter(mFilter);
462 for (leafOrigin[0] = min[0]; leafOrigin[0] <= max[0]; leafOrigin[0]+=
DIM32) {
463 for (leafOrigin[1] = min[1]; leafOrigin[1] <= max[1]; leafOrigin[1]+=
DIM32) {
464 for (leafOrigin[2] = min[2]; leafOrigin[2] <= max[2]; leafOrigin[2]+=
DIM32) {
468 pbox.intersect(search);
469 if (pbox.empty())
continue;
472 const auto* pointLeaf = mPointAccessor.probeConstLeaf(leafOrigin);
473 if (!pointLeaf)
continue;
474 if (!mTransfer.startPointLeaf(*pointLeaf))
continue;
475 localFilter.reset(*pointLeaf);
478 const Coord& pmin(pbox.min());
479 const Coord& pmax(pbox.max());
480 for (Coord ijk = pmin; ijk.x() <= pmax.x(); ++ijk.x()) {
482 for (ijk.y() = pmin.y(); ijk.y() <= pmax.y(); ++ijk.y()) {
484 for (ijk.z() = pmin.z(); ijk.z() <= pmax.z(); ++ijk.z()) {
486 assert((ijk & ~(
DIM-1u)) == leafOrigin);
488 const Index end = pointLeaf->getValue(index);
489 Index id = (index == 0) ? 0 :
Index(pointLeaf->getValue(index - 1));
490 for (;
id <
end; ++
id) {
491 if (!localFilter.valid(&
id))
continue;
492 mTransfer.rasterizePoint(ijk,
id, bounds);
498 if (!mTransfer.endPointLeaf(*pointLeaf)) {
500 if (!mTransfer.finalize(origin, idx)) {
510 if (!mTransfer.finalize(origin, idx)) {
517 for (
auto leaf = range.
begin(); leaf; ++leaf) {
518 (*this)(*leaf, leaf.pos());
524 template <
typename EnableT = TransferT>
530 const BBoxd bbox(bounds.min().asVec3d(), bounds.max().asVec3d());
535 template <
typename EnableT = TransferT>
540 const PointDataGrid::ConstAccessor mPointAccessor;
541 mutable TransferT mTransfer;
542 const PointFilterT& mFilter;
543 InterrupterT* mInterrupter;
551 template <
typename PointDataTreeOrGridT,
554 typename InterrupterT>
559 InterrupterT* interrupter)
563 "Provided points to rasterize is not a derived TreeBase type.");
567 auto&
topology = transfer.topology();
571 raster(tree, transfer, filter, interrupter);
579 #endif //OPENVEB_POINTS_TRANSFER_HAS_BEEN_INCLUDED
VolumeTransfer(const VolumeTransfer &other)
const NodeMaskT * mask(const size_t idx) const
typename TreeType< 0 >::LeafNodeType::NodeMaskType NodeMaskT
VolumeTransfer(const VolumeTransfer &other)
GLdouble GLdouble GLint GLint const GLdouble * points
void rasterize(const PointDataTreeOrGridT &points, TransferT &transfer, const FilterT &filter=NullFilter(), InterrupterT *interrupter=nullptr)
Perform potentially complex rasterization from a user defined transfer scheme.
typename T::ValueType Type
typename LeafManagerT::LeafNodeType LeafNodeT
GLsizei const GLfloat * value
const ValueType * buffer() const
typename TreeType::LeafNodeType::NodeMaskType NodeMaskT
void foreach(const FunctorT &functor)
#define OPENVDB_USE_VERSION_NAMESPACE
ImageBuf OIIO_API min(Image_or_Const A, Image_or_Const B, ROI roi={}, int nthreads=0)
**But if you need a result
Base class for interrupters.
NodeMaskT * mask(const size_t idx)
void initialize(const Coord &origin, const size_t, const CoordBBox &)
GT_API const UT_StringHolder topology
const NodeMaskT * mask() const
VolumeTransfer(TreeType &tree)
std::tuple< TreeTypes *...> TreeTupleT
void initialize(const Coord &origin, const size_t, const CoordBBox &)
This class manages a linear array of pointers to a given tree's leaf nodes, as well as optional auxil...
HUSD_API const char * raster()
GridTypes::Transform< internal::ToTreeType > TreeTypes
static TreeType & tree(TreeType &t)
void foreach(const LeafOp &op, bool threaded=true, size_t grainSize=1)
Threaded method that applies a user-supplied functor to each leaf node in the LeafManager.
auto search(const T &set, const V &val) -> std::pair< bool, decltype(std::begin(detail::smart_deref(set)))>
A search function.
const ValueType< Idx > * buffer() const
GT_API const UT_StringHolder st
typename std::tuple_element< Idx, std::tuple< TreeTypes...>>::type TreeType
ValueType< Idx > * buffer()
TreeType< 0 > & topology()
void foreach(T &&t, const F &func, std::integer_sequence< size_t, Is...>)
void operator()(LeafNodeT &leaf, const size_t idx) const
ImageBuf OIIO_API max(Image_or_Const A, Image_or_Const B, ROI roi={}, int nthreads=0)
VolumeTransfer(TreeType *tree)
void operator()(const typename LeafManagerT::LeafRange &range) const
const ValueType * buffer() const
The VolumeTransfer module provides methods to automatically setup and access destination buffers for ...
tree::Tree< tree::RootNode< tree::InternalNode< tree::InternalNode< PointDataLeafNode< PointDataIndex32, 3 >, 4 >, 5 >>> PointDataTree
Point index tree configured to match the default VDB configurations.
const NodeMaskT * mask() const
typename TreeType< Idx >::ValueType ValueType
VolumeTransfer(TreeTypes &...trees)
bool wasInterrupted(T *i, int percent=-1)
const NodeMaskT * mask() const
#define OPENVDB_VERSION_NAME
The version namespace name for this library version.
VolumeTransfer(TreeTypes *...trees)
typename TreeType::ValueType ValueType
RasterizePoints(const points::PointDataTree &tree, const TransferT &transfer, const PointFilterT &filter=PointFilterT(), InterrupterT *interrupter=nullptr)
GLint GLint GLint GLint GLint GLint GLint GLbitfield GLenum filter
static const Index LOG2DIM