Loading...
Searching...
No Matches
MultiResGrid.h
Go to the documentation of this file.
// Copyright Contributors to the OpenVDB Project
// SPDX-License-Identifier: MPL-2.0
/// @file MultiResGrid.h
///
/// @author Ken Museth
///
/// @warning This class is fairly new and as such has not seen a lot of
/// use in production. Please report any issues or request for new
/// features directly to ken.museth@dreamworks.com.
///
/// @brief Multi-resolution grid that contains LoD sequences of trees
/// with powers of two refinements.
///
/// @note While this class can arguably be used to implement a sparse
/// Multi-Grid solver it is currently intended as a means to
/// efficiently compute LoD levels for applications like rendering
///
/// @note Prolongation means interpolation from coarse -> fine
/// @note Restriction means interpolation (or remapping) from fine -> coarse
///
/// @todo Add option to define the level of the input grid (currenlty
/// 0) so as to allow for super-sampling.
#ifndef OPENVDB_TOOLS_MULTIRESGRID_HAS_BEEN_INCLUDED
#define OPENVDB_TOOLS_MULTIRESGRID_HAS_BEEN_INCLUDED
#include <openvdb/openvdb.h>
#include <openvdb/Grid.h>
#include <openvdb/math/FiniteDifference.h>
#include <openvdb/math/Math.h>
#include <openvdb/math/Operators.h>
#include <openvdb/math/Stencils.h>
#include <openvdb/Metadata.h>
#include <openvdb/tree/LeafManager.h>
#include <openvdb/tree/NodeManager.h>
#include "Interpolation.h"
#include "Morphology.h"
#include "Prune.h"
#include "SignedFloodFill.h"
#include "ValueTransformer.h"
#include <tbb/blocked_range.h>
#include <tbb/enumerable_thread_specific.h>
#include <tbb/parallel_for.h>
#include <iostream>
#include <sstream>
#include <string>
#include <vector>
namespace openvdb {
OPENVDB_USE_VERSION_NAMESPACE
namespace OPENVDB_VERSION_NAME {
namespace tools {
template<typename TreeType>
class MultiResGrid: public MetaMap
{
public:
using Ptr = SharedPtr<MultiResGrid>;
using ConstPtr = SharedPtr<const MultiResGrid>;
using ValueType = typename TreeType::ValueType;
using ValueOnCIter = typename TreeType::ValueOnCIter;
using ValueOnIter = typename TreeType::ValueOnIter;
using TreePtr = typename TreeType::Ptr;
using ConstTreePtr = typename TreeType::ConstPtr;
using GridPtr = typename Grid<TreeType>::Ptr;
using ConstGridPtr = typename Grid<TreeType>::ConstPtr;
//////////////////////////////////////////////////////////////////////
/// @brief Constructor of empty grids
/// @param levels The number of trees in this MultiResGrid
/// @param background Background value
/// @param voxelSize Size of a (uniform voxel). Defaults to one.
/// @note The multiple grids are all empty.
MultiResGrid(size_t levels, ValueType background, double voxelSize = 1.0);
/// @brief Given an initial high-resolution grid this constructor
/// generates all the coarser grids by means of restriction.
/// @param levels The number of trees in this MultiResGrid
/// @param grid High-resolution input grid
/// @param useInjection Use restriction by injection, vs
/// full-weighting. It defaults to false and should rarely be used.
/// @note This constructor will perform a deep copy of the input
/// grid and use it as the highest level grid.
MultiResGrid(size_t levels, const Grid<TreeType> &grid, bool useInjection = false);
/// @brief Given an initial high-resolution grid this constructor
/// generates all the coarser grids by means of restriction.
/// @param levels The number of trees in this MultiResGrid
/// @param grid High-resolution input grid
/// @param useInjection Use restriction by injection, vs
/// full-weighting. It defaults to false and should rarely be used.
/// @note This constructor will steal the input grid and use it
/// as the highest level grid. On output the grid is empty.
MultiResGrid(size_t levels, GridPtr grid, bool useInjection = false);
//////////////////////////////////////////////////////////////////////
/// @brief Return the number of levels, i.e. trees, in this MultiResGrid
/// @note level 0 is the finest level and numLevels()-1 is the coarsest
/// level.
size_t numLevels() const { return mTrees.size(); }
/// @brief Return the level of the finest grid (always 0)
static size_t finestLevel() { return 0; }
/// @brief Return the level of the coarsest grid, i.e. numLevels()-1
size_t coarsestLevel() const { return mTrees.size()-1; }
//////////////////////////////////////////////////////////////////////
/// @brief Return a reference to the tree at the specified level
/// @param level The level of the tree to be returned
/// @note Level 0 is by definition the finest tree.
TreeType& tree(size_t level);
/// @brief Return a const reference to the tree at the specified level
/// @param level The level of the tree to be returned
/// @note Level 0 is by definition the finest tree.
const TreeType& constTree(size_t level) const;
/// @brief Return a shared pointer to the tree at the specified level
/// @param level The level of the tree to be returned
/// @note Level 0 is by definition the finest tree.
TreePtr treePtr(size_t level);
/// @brief Return a const shared pointer to the tree at the specified level
/// @param level The level of the tree to be returned
/// @note Level 0 is by definition the finest tree.
ConstTreePtr constTreePtr(size_t level) const;
/// @brief Return a reference to the tree at the finest level
TreeType& finestTree() { return *mTrees.front(); }
/// @brief Return a const reference to the tree at the finest level
const TreeType& finestConstTree() const { return *mTrees.front(); }
/// @brief Return a shared pointer to the tree at the finest level
TreePtr finestTreePtr() { return mTrees.front(); }
/// @brief Return a const shared pointer to the tree at the finest level
ConstTreePtr finestConstTreePtr() const { return mTrees.front(); }
/// @brief Return a reference to the tree at the coarsest level
TreeType& coarsestTree() { return *mTrees.back(); }
/// @brief Return a const reference to the tree at the coarsest level
const TreeType& coarsestConstTree() const { return *mTrees.back(); }
/// @brief Return a shared pointer to the tree at the coarsest level
TreePtr coarsestTreePtr() { return mTrees.back(); }
/// @brief Return a const shared pointer to the tree at the coarsest level
ConstTreePtr coarsestConstTreePtr() const { return mTrees.back(); }
//////////////////////////////////////////////////////////////////////
/// @brief Return a shared pointer to the grid at the specified integer level
/// @param level Integer level of the grid to be returned
/// @note Level 0 is by definition the finest grid.
GridPtr grid(size_t level);
/// @brief Return a const shared pointer to the grid at the specified level
/// @param level The level of the grid to be returned
/// @note Level 0 is by definition the finest grid.
ConstGridPtr grid(size_t level) const;
/// @brief Return a shared pointer to a new grid at the specified
/// floating-point level.
/// @param level Floating-point level of the grid to be returned
/// @param grainSize Grain size for the multi-threading
/// @details Interpolation of the specified order is performed
/// between the bracketing integer levels.
/// @note Level 0 is by definition the finest grid.
template<Index Order>
GridPtr createGrid(float level, size_t grainSize = 1) const;
/// @brief Return a shared pointer to a vector of all the base
/// grids in this instance of the MultiResGrid.
/// @brief This method is useful for I/O
GridPtrVecPtr grids();
/// @brief Return a const shared pointer to a vector of all the base
/// grids in this instance of the MultiResGrid.
/// @brief This method is useful for I/O
GridCPtrVecPtr grids() const;
//////////////////////////////////////////////////////////////////////
//@{
/// @brief Return a reference to the finest grid's transform, which might be
/// shared with other grids.
/// @note Calling setTransform() on this grid invalidates all references
/// previously returned by this method.
/// @warning The transform is relative to the finest level (=0) grid!
math::Transform& transform() { return *mTransform; }
const math::Transform& transform() const { return *mTransform; }
const math::Transform& constTransform() const { return *mTransform; }
//@}
//////////////////////////////////////////////////////////////////////
//@{
/// @brief Return the floating-point index coordinate at out_level given
/// the index coordinate in_xyz at in_level.
static Vec3R xyz(const Coord& in_ijk, size_t in_level, size_t out_level);
static Vec3R xyz(const Vec3R& in_xyz, size_t in_level, size_t out_level);
static Vec3R xyz(const Vec3R& in_xyz, double in_level, double out_level);
//@}
//////////////////////////////////////////////////////////////////////
//@{
/// @brief Return the value at the specified coordinate position using
/// interpolation of the specified order into the tree at the out_level.
///
/// @details First in_ijk is mapped from index space at in_level to
/// out_level, and then a value is interpolated from the tree at out_level.
///
/// @param in_ijk Index coordinate position relative to tree at in_level
/// @param in_level Integer level of the input coordinate in_ijk
/// @param out_level Integer level of the interpolated value
template<Index Order>
ValueType sampleValue(const Coord& in_ijk, size_t in_level, size_t out_level) const;
template<Index Order>
ValueType sampleValue(const Vec3R& in_ijk, size_t in_level, size_t out_level) const;
//@}
/// @brief Return the value at the specified integer coordinate position
/// and level using interpolation of the specified order.
/// @param ijk Integer coordinate position relative to the highest level (=0) grid
/// @param level Floating-point level from which to interpolate the value.
/// @brief Non-integer values of the level will use linear-interpolation
/// between the neighboring integer levels.
template<Index Order>
ValueType sampleValue(const Coord& ijk, double level) const;
/// @brief Return the value at the specified floating-point coordinate position
/// and level using interpolation of the specified order.
/// @param xyz Floating-point coordinate position relative to the highest level grid
/// @param level Floating-point level from which to interpolate
/// the value.
/// @brief Non-integer values of the level will use linear-interpolation
/// between the neighboring integer levels.
template<Index Order>
ValueType sampleValue(const Vec3R& xyz, double level) const;
//////////////////////////////////////////////////////////////////////
/// @brief Return the value at coordinate location in @a level tree
/// from the coarser tree at @a level+1 using trilinear interpolation
/// @param coords input coords relative to the fine tree at level
/// @param level The fine level to receive values from the coarser
/// level-1
/// @note Prolongation means to interpolation from coarse -> fine
ValueType prolongateVoxel(const Coord& coords, const size_t level) const;
/// (coarse->fine) Populates all the active voxel values in a fine (@a level) tree
/// from the coarse (@a level+1) tree using linear interpolation
/// This transforms multiple values of the tree in parallel
void prolongateActiveVoxels(size_t destlevel, size_t grainSize = 1);
//////////////////////////////////////////////////////////////////////
/// Populate a coordinate location in @a level (coarse) tree
/// from the @a level-1 (fine) tree using trilinear interpolation
/// input coords are relative to the mTree[level] (coarse)
/// @note Restriction means remapping from fine -> coarse
ValueType restrictVoxel(Coord ijk, const size_t level, bool useInjection = false) const;
/// (fine->coarse) Populates all the active voxel values in the coarse (@a level) tree
/// from the fine (@a level-1) tree using trilinear interpolation.
/// For cell-centered data, this is equivalent to an average
/// For vertex-centered data this is equivalent to transferring the data
/// from the fine vertex directly above the coarse vertex.
/// This transforms multiple values of the tree in parallel
void restrictActiveVoxels(size_t destlevel, size_t grainSize = 1);
/// Output a human-readable description of this MultiResGrid
void print(std::ostream& = std::cout, int verboseLevel = 1) const;
/// @brief Return a string with the name of this MultiResGrid
std::string getName() const
{
if (Metadata::ConstPtr meta = (*this)[GridBase::META_GRID_NAME]) return meta->str();
return "";
}
/// @brief Set the name of this MultiResGrid
void setName(const std::string& name)
{
this->removeMeta(GridBase::META_GRID_NAME);
this->insertMeta(GridBase::META_GRID_NAME, StringMetadata(name));
}
/// Return the class of volumetric data (level set, fog volume, etc.) stored in this grid.
GridClass getGridClass() const
{
typename StringMetadata::ConstPtr s =
this->getMetadata<StringMetadata>(GridBase::META_GRID_CLASS);
return s ? GridBase::stringToGridClass(s->value()) : GRID_UNKNOWN;
}
/// Specify the class of volumetric data (level set, fog volume, etc.) stored in this grid.
void setGridClass(GridClass cls)
{
this->insertMeta(GridBase::META_GRID_CLASS, StringMetadata(GridBase::gridClassToString(cls)));
}
/// Remove the setting specifying the class of this grid's volumetric data.
void clearGridClass() { this->removeMeta(GridBase::META_GRID_CLASS); }
private:
MultiResGrid(const MultiResGrid& other);//disallow copy construction
MultiResGrid& operator=(const MultiResGrid& other);//disallow copy assignment
// For optimal performance we disable registration of the ValueAccessor
using Accessor = tree::ValueAccessor<TreeType, false>;
using ConstAccessor = tree::ValueAccessor<const TreeType, false>;
void topDownRestrict(bool useInjection);
inline void initMeta();
// Private struct that concurrently creates a mask of active voxel
// in a coarse tree from the active voxels in a fine tree
struct MaskOp;
/// Private struct that performs multi-threaded restriction
struct RestrictOp;
/// Private struct that performs multi-threaded prolongation
struct ProlongateOp;
// Private struct that performs multi-threaded computation of grids a fraction levels
template<Index Order>
struct FractionOp;
/// Private template struct that performs the actual multi-threading
template<typename OpType> struct CookOp;
// Array of shared pointer to trees, level 0 has the highest resolution.
std::vector<TreePtr> mTrees;
// Shared pointer to a transform associated with the finest level grid
typename math::Transform::Ptr mTransform;
};// MultiResGrid
template<typename TreeType>
MultiResGrid<TreeType>::
MultiResGrid(size_t levels, ValueType background, double voxelSize)
: mTrees(levels)
, mTransform(math::Transform::createLinearTransform( voxelSize ))
{
this->initMeta();
for (size_t i=0; i<levels; ++i) mTrees[i] = TreePtr(new TreeType(background));
}
template<typename TreeType>
MultiResGrid<TreeType>::
MultiResGrid(size_t levels, const Grid<TreeType> &grid, bool useInjection)
: MetaMap(grid)
, mTrees(levels)
, mTransform( grid.transform().copy() )
{
this->initMeta();
mTrees[0].reset( new TreeType( grid.tree() ) );// deep copy input tree
mTrees[0]->voxelizeActiveTiles();
this->topDownRestrict(useInjection);
}
template<typename TreeType>
MultiResGrid<TreeType>::
MultiResGrid(size_t levels, GridPtr grid, bool useInjection)
: MetaMap(*grid)
, mTrees(levels)
, mTransform( grid->transform().copy() )
{
this->initMeta();
mTrees[0] = grid->treePtr();// steal tree from input grid
mTrees[0]->voxelizeActiveTiles();
grid->newTree();
this->topDownRestrict(useInjection);
}
template<typename TreeType>
inline TreeType& MultiResGrid<TreeType>::
tree(size_t level)
{
assert( level < mTrees.size() );
return *mTrees[level];
}
template<typename TreeType>
inline const TreeType& MultiResGrid<TreeType>::
constTree(size_t level) const
{
assert( level < mTrees.size() );
return *mTrees[level];
}
template<typename TreeType>
inline typename TreeType::Ptr MultiResGrid<TreeType>::
treePtr(size_t level)
{
assert( level < mTrees.size() );
return mTrees[level];
}
template<typename TreeType>
inline typename TreeType::ConstPtr MultiResGrid<TreeType>::
constTreePtr(size_t level) const
{
assert( level < mTrees.size() );
return mTrees[level];
}
template<typename TreeType>
typename Grid<TreeType>::Ptr MultiResGrid<TreeType>::
grid(size_t level)
{
typename Grid<TreeType>::Ptr grid = Grid<TreeType>::create(this->treePtr(level));
math::Transform::Ptr xform = mTransform->copy();
if (level>0) xform->preScale( Real(1 << level) );
grid->setTransform( xform );
grid->insertMeta( *this->copyMeta() );
grid->insertMeta( "MultiResGrid_Level", Int64Metadata(level));
std::stringstream ss;
ss << this->getName() << "_level_" << level;
grid->setName( ss.str() );
return grid;
}
template<typename TreeType>
inline typename Grid<TreeType>::ConstPtr MultiResGrid<TreeType>::
grid(size_t level) const
{
return const_cast<MultiResGrid*>(this)->grid(level);
}
template<typename TreeType>
template<Index Order>
typename Grid<TreeType>::Ptr MultiResGrid<TreeType>::
createGrid(float level, size_t grainSize) const
{
assert( level >= 0.0f && level <= float(mTrees.size()-1) );
typename Grid<TreeType>::Ptr grid(new Grid<TreeType>(this->constTree(0).background()));
math::Transform::Ptr xform = mTransform->copy();
xform->preScale( math::Pow(2.0f, level) );
grid->setTransform( xform );
grid->insertMeta( *(this->copyMeta()) );
grid->insertMeta( "MultiResGrid_Level", FloatMetadata(level) );
std::stringstream ss;
ss << this->getName() << "_level_" << level;
grid->setName( ss.str() );
if ( size_t(floorf(level)) == size_t(ceilf(level)) ) {
grid->setTree( this->constTree( size_t(floorf(level))).copy() );
} else {
FractionOp<Order> tmp(*this, grid->tree(), level, grainSize);
if ( grid->getGridClass() == GRID_LEVEL_SET ) {
signedFloodFill( grid->tree() );
pruneLevelSet( grid->tree() );//only creates inactive tiles
}
}
return grid;
}
template<typename TreeType>
GridPtrVecPtr MultiResGrid<TreeType>::
grids()
{
GridPtrVecPtr grids( new GridPtrVec );
for (size_t level=0; level<mTrees.size(); ++level) grids->push_back(this->grid(level));
return grids;
}
template<typename TreeType>
GridCPtrVecPtr MultiResGrid<TreeType>::
grids() const
{
GridCPtrVecPtr grids( new GridCPtrVec );
for (size_t level=0; level<mTrees.size(); ++level) grids->push_back(this->grid(level));
return grids;
}
template<typename TreeType>
Vec3R MultiResGrid<TreeType>::
xyz(const Coord& in_ijk, size_t in_level, size_t out_level)
{
return Vec3R( in_ijk.data() ) * Real(1 << in_level) / Real(1 << out_level);
}
template<typename TreeType>
Vec3R MultiResGrid<TreeType>::
xyz(const Vec3R& in_xyz, size_t in_level, size_t out_level)
{
return in_xyz * Real(1 << in_level) / Real(1 << out_level);
}
template<typename TreeType>
Vec3R MultiResGrid<TreeType>::
xyz(const Vec3R& in_xyz, double in_level, double out_level)
{
return in_xyz * math::Pow(2.0, in_level - out_level);
}
template<typename TreeType>
template<Index Order>
typename TreeType::ValueType MultiResGrid<TreeType>::
sampleValue(const Coord& in_ijk, size_t in_level, size_t out_level) const
{
assert( in_level < mTrees.size() );
assert( out_level < mTrees.size() );
const ConstAccessor acc(*mTrees[out_level]);// has disabled registration!
return tools::Sampler<Order>::sample( acc, this->xyz(in_ijk, in_level, out_level) );
}
template<typename TreeType>
template<Index Order>
typename TreeType::ValueType MultiResGrid<TreeType>::
sampleValue(const Vec3R& in_xyz, size_t in_level, size_t out_level) const
{
assert( in_level < mTrees.size() );
assert( out_level < mTrees.size() );
const ConstAccessor acc(*mTrees[out_level]);// has disabled registration!
return tools::Sampler<Order>::sample( acc, this->xyz(in_xyz, in_level, out_level) );
}
template<typename TreeType>
template<Index Order>
typename TreeType::ValueType MultiResGrid<TreeType>::
sampleValue(const Coord& ijk, double level) const
{
assert( level >= 0.0 && level <= double(mTrees.size()-1) );
const size_t level0 = size_t(floor(level)), level1 = size_t(ceil(level));
const ValueType v0 = this->template sampleValue<Order>( ijk, 0, level0 );
if ( level0 == level1 ) return v0;
assert( level1 - level0 == 1 );
const ValueType v1 = this->template sampleValue<Order>( ijk, 0, level1 );
OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
const ValueType a = ValueType(level1 - level);
OPENVDB_NO_TYPE_CONVERSION_WARNING_END
return a * v0 + (ValueType(1) - a) * v1;
}
template<typename TreeType>
template<Index Order>
typename TreeType::ValueType MultiResGrid<TreeType>::
sampleValue(const Vec3R& xyz, double level) const
{
assert( level >= 0.0 && level <= double(mTrees.size()-1) );
const size_t level0 = size_t(floor(level)), level1 = size_t(ceil(level));
const ValueType v0 = this->template sampleValue<Order>( xyz, 0, level0 );
if ( level0 == level1 ) return v0;
assert( level1 - level0 == 1 );
const ValueType v1 = this->template sampleValue<Order>( xyz, 0, level1 );
OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
const ValueType a = ValueType(level1 - level);
OPENVDB_NO_TYPE_CONVERSION_WARNING_END
return a * v0 + (ValueType(1) - a) * v1;
}
template<typename TreeType>
typename TreeType::ValueType MultiResGrid<TreeType>::
prolongateVoxel(const Coord& ijk, const size_t level) const
{
assert( level+1 < mTrees.size() );
const ConstAccessor acc(*mTrees[level + 1]);// has disabled registration!
return ProlongateOp::run(ijk, acc);
}
template<typename TreeType>
void MultiResGrid<TreeType>::
prolongateActiveVoxels(size_t destlevel, size_t grainSize)
{
assert( destlevel < mTrees.size()-1 );
TreeType &fineTree = *mTrees[ destlevel ];
const TreeType &coarseTree = *mTrees[ destlevel+1 ];
CookOp<ProlongateOp> tmp( coarseTree, fineTree, grainSize );
}
template<typename TreeType>
typename TreeType::ValueType MultiResGrid<TreeType>::
restrictVoxel(Coord ijk, const size_t destlevel, bool useInjection) const
{
assert( destlevel > 0 && destlevel < mTrees.size() );
const TreeType &fineTree = *mTrees[ destlevel-1 ];
if ( useInjection ) return fineTree.getValue(ijk<<1);
const ConstAccessor acc( fineTree );// has disabled registration!
return RestrictOp::run( ijk, acc);
}
template<typename TreeType>
void MultiResGrid<TreeType>::
restrictActiveVoxels(size_t destlevel, size_t grainSize)
{
assert( destlevel > 0 && destlevel < mTrees.size() );
const TreeType &fineTree = *mTrees[ destlevel-1 ];
TreeType &coarseTree = *mTrees[ destlevel ];
CookOp<RestrictOp> tmp( fineTree, coarseTree, grainSize );
}
template<typename TreeType>
void MultiResGrid<TreeType>::
print(std::ostream& os, int verboseLevel) const
{
os << "MultiResGrid with " << mTrees.size() << " levels\n";
for (size_t i=0; i<mTrees.size(); ++i) {
os << "Level " << i << ": ";
mTrees[i]->print(os, verboseLevel);
}
if ( MetaMap::metaCount() > 0) {
os << "Additional metadata:" << std::endl;
for (ConstMetaIterator it = beginMeta(), end = endMeta(); it != end; ++it) {
os << " " << it->first;
if (it->second) {
const std::string value = it->second->str();
if (!value.empty()) os << ": " << value;
}
os << "\n";
}
}
os << "Transform:" << std::endl;
transform().print(os, /*indent=*/" ");
os << std::endl;
}
template<typename TreeType>
void MultiResGrid<TreeType>::
initMeta()
{
const size_t levels = this->numLevels();
if (levels < 2) {
OPENVDB_THROW(ValueError, "MultiResGrid: at least two levels are required");
}
this->insertMeta("MultiResGrid_Levels", Int64Metadata( levels ) );
}
template<typename TreeType>
void MultiResGrid<TreeType>::
topDownRestrict(bool useInjection)
{
const bool isLevelSet = this->getGridClass() == GRID_LEVEL_SET;
for (size_t n=1; n<mTrees.size(); ++n) {
const TreeType &fineTree = *mTrees[n-1];
mTrees[n] = TreePtr(new TreeType( fineTree.background() ) );// empty tree
TreeType &coarseTree = *mTrees[n];
if (useInjection) {// Restriction by injection
for (ValueOnCIter it = fineTree.cbeginValueOn(); it; ++it) {
const Coord ijk = it.getCoord();
if ( (ijk[0] & 1) || (ijk[1] & 1) || (ijk[2] & 1) ) continue;
coarseTree.setValue( ijk >> 1, *it );
}
} else {// Restriction by full-weighting
MaskOp tmp(fineTree, coarseTree, 128);
this->restrictActiveVoxels(n, 64);
}
if ( isLevelSet ) {
tools::signedFloodFill( coarseTree );
tools::pruneLevelSet( coarseTree );//only creates inactive tiles
}
}// loop over grid levels
}
template<typename TreeType>
struct MultiResGrid<TreeType>::MaskOp
{
using MaskT = typename TreeType::template ValueConverter<ValueMask>::Type;
using PoolType = tbb::enumerable_thread_specific<TreeType>;
using ManagerT = tree::LeafManager<const MaskT>;
using RangeT = typename ManagerT::LeafRange;
using VoxelIterT = typename ManagerT::LeafNodeType::ValueOnCIter;
MaskOp(const TreeType& fineTree, TreeType& coarseTree, size_t grainSize = 1)
: mPool(new PoolType( coarseTree ) )// empty coarse tree acts as examplar
{
assert( coarseTree.empty() );
// Create Mask of restruction performed on fineTree
MaskT mask(fineTree, false, true, TopologyCopy() );
// Multi-threaded dilation which also linearizes the tree to leaf nodes
tools::dilateActiveValues(mask, 1, NN_FACE_EDGE_VERTEX, EXPAND_TILES);
// Restriction by injection using thread-local storage of coarse tree masks
ManagerT leafs( mask );
tbb::parallel_for(leafs.leafRange( grainSize ), *this);
// multithreaded union of thread-local coarse tree masks with the coarse tree
using IterT = typename PoolType::const_iterator;
for (IterT it=mPool->begin(); it!=mPool->end(); ++it) coarseTree.topologyUnion( *it );
delete mPool;
}
void operator()(const RangeT& range) const
{
Accessor coarseAcc( mPool->local() );// disabled registration
for (typename RangeT::Iterator leafIter = range.begin(); leafIter; ++leafIter) {
for (VoxelIterT voxelIter = leafIter->cbeginValueOn(); voxelIter; ++voxelIter) {
Coord ijk = voxelIter.getCoord();
if ( (ijk[2] & 1) || (ijk[1] & 1) || (ijk[0] & 1) ) continue;//no overlap
coarseAcc.setValueOn( ijk >> 1 );//injection from fine to coarse level
}//loop over active voxels in the fine tree
}// loop over leaf nodes in the fine tree
}
PoolType* mPool;
};// MaskOp
template<typename TreeType>
template<Index Order>
struct MultiResGrid<TreeType>::FractionOp
{
using MaskT = typename TreeType::template ValueConverter<ValueMask>::Type;
using PoolType = tbb::enumerable_thread_specific<MaskT>;
using PoolIterT = typename PoolType::iterator;
using Manager1 = tree::LeafManager<const TreeType>;
using Manager2 = tree::LeafManager<TreeType>;
using Range1 = typename Manager1::LeafRange;
using Range2 = typename Manager2::LeafRange;
FractionOp(const MultiResGrid& parent,
TreeType& midTree,
float level,
size_t grainSize = 1)
: mLevel( level )
, mPool(nullptr)
, mTree0( &*(parent.mTrees[size_t(floorf(level))]) )//high-resolution
, mTree1( &*(parent.mTrees[size_t(ceilf(level))]) ) //low-resolution
{
assert( midTree.empty() );
assert( mTree0 != mTree1 );
// Create a pool of thread-local masks
MaskT examplar( false );
mPool = new PoolType( examplar );
{// create mask from re-mapping coarse tree to mid-level tree
tree::LeafManager<const TreeType> manager( *mTree1 );
tbb::parallel_for( manager.leafRange(grainSize), *this );
}
// Multi-threaded dilation of mask
tbb::parallel_for(tbb::blocked_range<PoolIterT>(mPool->begin(),mPool->end(),1), *this);
// Union thread-local coarse tree masks into the coarse tree
for (PoolIterT it=mPool->begin(); it!=mPool->end(); ++it) midTree.topologyUnion( *it );
delete mPool;
{// Interpolate values into the static mid level tree
Manager2 manager( midTree );
tbb::parallel_for(manager.leafRange(grainSize), *this);
}
}
void operator()(const Range1& range) const
{
using VoxelIter = typename Manager1::LeafNodeType::ValueOnCIter;
// Let mLevel = level + frac, where
// level is integer part of mLevel and frac is the fractional part
// low-res voxel size in world units = dx1 = 2^(level + 1)
// mid-res voxel size in world units = dx = 2^(mLevel) = 2^(level + frac)
// low-res index -> world: ijk * dx1
// world -> mid-res index: world / dx
// low-res index -> mid-res index: (ijk * dx1) / dx = ijk * scale where
// scale = dx1/dx = 2^(level+1)/2^(level+frac) = 2^(1-frac)
const float scale = math::Pow(2.0f, 1.0f - math::FractionalPart(mLevel));
tree::ValueAccessor<MaskT, false> acc( mPool->local() );// disabled registration
for (typename Range1::Iterator leafIter = range.begin(); leafIter; ++leafIter) {
for (VoxelIter voxelIter = leafIter->cbeginValueOn(); voxelIter; ++voxelIter) {
Coord ijk = voxelIter.getCoord();
OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
const auto value0 = ijk[0] * scale;
const auto value1 = ijk[1] * scale;
const auto value2 = ijk[2] * scale;
OPENVDB_NO_TYPE_CONVERSION_WARNING_END
ijk[0] = int(math::Round(value0));
ijk[1] = int(math::Round(value1));
ijk[2] = int(math::Round(value2));
acc.setValueOn( ijk );
}//loop over active voxels in the fine tree
}// loop over leaf nodes in the fine tree
}
void operator()(const tbb::blocked_range<PoolIterT>& range) const
{
for (PoolIterT it=range.begin(); it!=range.end(); ++it) {
tools::dilateActiveValues(*it, 1, tools::NN_FACE_EDGE_VERTEX, tools::IGNORE_TILES);
}
}
void operator()(const Range2 &r) const
{
using VoxelIter = typename TreeType::LeafNodeType::ValueOnIter;
// Let mLevel = level + frac, where
// level is integer part of mLevel and frac is the fractional part
// high-res voxel size in world units = dx0 = 2^(level)
// low-res voxel size in world units = dx1 = 2^(level+1)
// mid-res voxel size in world units = dx = 2^(mLevel) = 2^(level + frac)
// mid-res index -> world: ijk * dx
// world -> high-res index: world / dx0
// world -> low-res index: world / dx1
// mid-res index -> high-res index: (ijk * dx) / dx0 = ijk * scale0 where
// scale0 = dx/dx0 = 2^(level+frac)/2^(level) = 2^(frac)
// mid-res index -> low-res index: (ijk * dx) / dx1 = ijk * scale1 where
// scale1 = dx/dx1 = 2^(level+frac)/2^(level+1) = 2^(frac-1)
const float b = math::FractionalPart(mLevel), a = 1.0f - b;
const float scale0 = math::Pow( 2.0f, b );
const float scale1 = math::Pow( 2.0f,-a );
ConstAccessor acc0( *mTree0 ), acc1( *mTree1 );
for (typename Range2::Iterator leafIter = r.begin(); leafIter; ++leafIter) {
for (VoxelIter voxelIter = leafIter->beginValueOn(); voxelIter; ++voxelIter) {
const Vec3R xyz = Vec3R( voxelIter.getCoord().data() );// mid level coord
const ValueType v0 = tools::Sampler<Order>::sample( acc0, xyz * scale0 );
const ValueType v1 = tools::Sampler<Order>::sample( acc1, xyz * scale1 );
OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
const auto value0 = a*v0;
const auto value1 = b*v1;
OPENVDB_NO_TYPE_CONVERSION_WARNING_END
voxelIter.setValue( ValueType(value0 + value1) );
}
}
}
const float mLevel;
PoolType* mPool;
const TreeType *mTree0, *mTree1;
};// FractionOp
template<typename TreeType>
template<typename OperatorType>
struct MultiResGrid<TreeType>::CookOp
{
using ManagerT = tree::LeafManager<TreeType>;
using RangeT = typename ManagerT::LeafRange;
CookOp(const TreeType& srcTree, TreeType& dstTree, size_t grainSize): acc(srcTree)
{
ManagerT leafs(dstTree);
tbb::parallel_for(leafs.leafRange(grainSize), *this);
}
CookOp(const CookOp &other): acc(other.acc.tree()) {}
void operator()(const RangeT& range) const
{
for (auto leafIt = range.begin(); leafIt; ++leafIt) {
auto& phi = leafIt.buffer(0);
for (auto voxelIt = leafIt->beginValueOn(); voxelIt; ++voxelIt) {
phi.setValue(voxelIt.pos(), OperatorType::run(voxelIt.getCoord(), acc));
}
}
}
const ConstAccessor acc;
};// CookOp
template<typename TreeType>
struct MultiResGrid<TreeType>::RestrictOp
{
/// @brief Static method that performs restriction by full weighting
/// @param ijk Coordinate location on the coarse tree
/// @param acc ValueAccessor to the fine tree
static ValueType run(Coord ijk, const ConstAccessor &acc)
{
ijk <<= 1;
// Overlapping grid point
ValueType v = 8*acc.getValue(ijk);
// neighbors in one axial direction
v += 4*(acc.getValue(ijk.offsetBy(-1, 0, 0)) + acc.getValue(ijk.offsetBy( 1, 0, 0)) +// x
acc.getValue(ijk.offsetBy( 0,-1, 0)) + acc.getValue(ijk.offsetBy( 0, 1, 0)) +// y
acc.getValue(ijk.offsetBy( 0, 0,-1)) + acc.getValue(ijk.offsetBy( 0, 0, 1)));// z
// neighbors in two axial directions
v += 2*(acc.getValue(ijk.offsetBy(-1,-1, 0)) + acc.getValue(ijk.offsetBy(-1, 1, 0)) +// xy
acc.getValue(ijk.offsetBy( 1,-1, 0)) + acc.getValue(ijk.offsetBy( 1, 1, 0)) +// xy
acc.getValue(ijk.offsetBy(-1, 0,-1)) + acc.getValue(ijk.offsetBy(-1, 0, 1)) +// xz
acc.getValue(ijk.offsetBy( 1, 0,-1)) + acc.getValue(ijk.offsetBy( 1, 0, 1)) +// xz
acc.getValue(ijk.offsetBy( 0,-1,-1)) + acc.getValue(ijk.offsetBy( 0,-1, 1)) +// yz
acc.getValue(ijk.offsetBy( 0, 1,-1)) + acc.getValue(ijk.offsetBy( 0, 1, 1)));// yz
// neighbors in three axial directions
for (int i=-1; i<=1; i+=2) {
for (int j=-1; j<=1; j+=2) {
for (int k=-1; k<=1; k+=2) v += acc.getValue(ijk.offsetBy(i,j,k));// xyz
}
}
v *= ValueType(1.0f/64.0f);
return v;
}
};// RestrictOp
template<typename TreeType>
struct MultiResGrid<TreeType>::ProlongateOp
{
/// @brief Interpolate values from a coarse grid (acc) into the index space (ijk) of a fine grid
/// @param ijk Coordinate location on the fine tree
/// @param acc ValueAccessor to the coarse tree
static ValueType run(const Coord& ijk, const ConstAccessor &acc)
{
switch ( (ijk[0] & 1) | ((ijk[1] & 1) << 1) | ((ijk[2] & 1) << 2) ) {
case 0:// all even
return acc.getValue(ijk>>1);
case 1:// x is odd
return ValueType(0.5)*(acc.getValue(ijk.offsetBy(-1,0,0)>>1) +
acc.getValue(ijk.offsetBy( 1,0,0)>>1));
case 2:// y is odd
return ValueType(0.5)*(acc.getValue(ijk.offsetBy(0,-1,0)>>1) +
acc.getValue(ijk.offsetBy(0, 1,0)>>1));
case 3:// x&y are odd
return ValueType(0.25)*(acc.getValue(ijk.offsetBy(-1,-1,0)>>1) +
acc.getValue(ijk.offsetBy(-1, 1,0)>>1) +
acc.getValue(ijk.offsetBy( 1,-1,0)>>1) +
acc.getValue(ijk.offsetBy( 1, 1,0)>>1));
case 4:// z is odd
return ValueType(0.5)*(acc.getValue(ijk.offsetBy(0,0,-1)>>1) +
acc.getValue(ijk.offsetBy(0,0, 1)>>1));
case 5:// x&z are odd
return ValueType(0.25)*(acc.getValue(ijk.offsetBy(-1,0,-1)>>1) +
acc.getValue(ijk.offsetBy(-1,0, 1)>>1) +
acc.getValue(ijk.offsetBy( 1,0,-1)>>1) +
acc.getValue(ijk.offsetBy( 1,0, 1)>>1));
case 6:// y&z are odd
return ValueType(0.25)*(acc.getValue(ijk.offsetBy(0,-1,-1)>>1) +
acc.getValue(ijk.offsetBy(0,-1, 1)>>1) +
acc.getValue(ijk.offsetBy(0, 1,-1)>>1) +
acc.getValue(ijk.offsetBy(0, 1, 1)>>1));
}
// all are odd
ValueType v = zeroVal<ValueType>();
for (int i=-1; i<=1; i+=2) {
for (int j=-1; j<=1; j+=2) {
for (int k=-1; k<=1; k+=2) v += acc.getValue(ijk.offsetBy(i,j,k)>>1);// xyz
}
}
return ValueType(0.125) * v;
}
};// ProlongateOp
////////////////////////////////////////
// Explicit Template Instantiation
#ifdef OPENVDB_USE_EXPLICIT_INSTANTIATION
#ifdef OPENVDB_INSTANTIATE_MULTIRESGRID
#include <openvdb/util/ExplicitInstantiation.h>
#endif
OPENVDB_INSTANTIATE_CLASS MultiResGrid<FloatTree>;
OPENVDB_INSTANTIATE_CLASS MultiResGrid<DoubleTree>;
#endif // OPENVDB_USE_EXPLICIT_INSTANTIATION
} // namespace tools
} // namespace OPENVDB_VERSION_NAME
} // namespace openvdb
#endif // OPENVDB_TOOLS_MULTIRESGRID_HAS_BEEN_INCLUDED
OPENVDB_THROW
#define OPENVDB_THROW(exception, message)
Definition Exceptions.h:74
ExplicitInstantiation.h
FiniteDifference.h
Grid.h
Interpolation.h
LeafManager.h
A LeafManager manages a linear array of pointers to a given tree's leaf nodes, as well as optional au...
Math.h
General-purpose arithmetic and comparison routines, most of which accept arbitrary value types (or at...
Metadata.h
Morphology.h
Implementation of morphological dilation and erosion.
Operators.h
OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
#define OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN
Bracket code with OPENVDB_NO_TYPE_CONVERSION_WARNING_BEGIN/_END, to inhibit warnings about type conve...
Definition Platform.h:227
OPENVDB_NO_TYPE_CONVERSION_WARNING_END
#define OPENVDB_NO_TYPE_CONVERSION_WARNING_END
Definition Platform.h:228
Prune.h
Defined various multi-threaded utility functions for trees.
SignedFloodFill.h
Propagate the signs of distance values from the active voxels in the narrow band to the inactive valu...
ValueTransformer.h
openvdb::v11_0::GridBase::META_GRID_NAME
static const char *const META_GRID_NAME
Definition Grid.h:353
openvdb::v11_0::GridBase::META_GRID_CLASS
static const char *const META_GRID_CLASS
Definition Grid.h:351
openvdb::v11_0::GridBase::stringToGridClass
static GridClass stringToGridClass(const std::string &)
Return the class of volumetric data specified by the given string.
openvdb::v11_0::GridBase::gridClassToString
static std::string gridClassToString(GridClass)
Return the metadata string value for the given class of volumetric data.
openvdb::v11_0::Grid
Container class that associates a tree with a transform and metadata.
Definition Grid.h:571
openvdb::v11_0::Grid::ConstPtr
SharedPtr< const Grid > ConstPtr
Definition Grid.h:574
openvdb::v11_0::Grid::Ptr
SharedPtr< Grid > Ptr
Definition Grid.h:573
openvdb::v11_0::Grid::create
static Ptr create()
Return a new grid with background value zero.
Definition Grid.h:1308
openvdb::v11_0::MetaMap::copyMeta
MetaMap::Ptr copyMeta() const
Return a copy of this map whose fields are shared with this map.
openvdb::v11_0::MetaMap::getMetadata
T::Ptr getMetadata(const Name &)
Return a pointer to a TypedMetadata object of type T and with the given name. If no such field exists...
Definition MetaMap.h:138
openvdb::v11_0::MetaMap::metaCount
size_t metaCount() const
Definition MetaMap.h:91
openvdb::v11_0::MetaMap::beginMeta
MetaIterator beginMeta()
Definition MetaMap.h:84
openvdb::v11_0::MetaMap::ConstMetaIterator
MetadataMap::const_iterator ConstMetaIterator
Definition MetaMap.h:27
openvdb::v11_0::MetaMap::removeMeta
void removeMeta(const Name &)
Remove the given metadata field if it exists.
openvdb::v11_0::MetaMap::endMeta
MetaIterator endMeta()
Definition MetaMap.h:85
openvdb::v11_0::MetaMap::MetaMap
MetaMap()
Definition MetaMap.h:30
openvdb::v11_0::MetaMap::insertMeta
void insertMeta(const Name &, const Metadata &value)
Insert a new metadata field or overwrite the value of an existing field.
openvdb::v11_0::Metadata::ConstPtr
SharedPtr< const Metadata > ConstPtr
Definition Metadata.h:27
openvdb::v11_0::TopologyCopy
Tag dispatch class that distinguishes topology copy constructors from deep copy constructors.
Definition Types.h:683
openvdb::v11_0::TypedMetadata< std::string >::ConstPtr
SharedPtr< const TypedMetadata< std::string > > ConstPtr
Definition Metadata.h:125
openvdb::v11_0::ValueError
Definition Exceptions.h:65
openvdb::v11_0::math::Coord
Signed (x, y, z) 32-bit integer coordinates.
Definition Coord.h:25
openvdb::v11_0::math::Coord::offsetBy
Coord offsetBy(Int32 dx, Int32 dy, Int32 dz) const
Definition Coord.h:91
openvdb::v11_0::math::Coord::data
const Int32 * data() const
Definition Coord.h:139
openvdb::v11_0::math::Transform
Definition Transform.h:40
openvdb::v11_0::math::Transform::Ptr
SharedPtr< Transform > Ptr
Definition Transform.h:42
openvdb::v11_0::tools::MultiResGrid
Definition MultiResGrid.h:61
openvdb::v11_0::tools::MultiResGrid::restrictVoxel
ValueType restrictVoxel(Coord ijk, const size_t level, bool useInjection=false) const
Definition MultiResGrid.h:597
openvdb::v11_0::tools::MultiResGrid::setGridClass
void setGridClass(GridClass cls)
Specify the class of volumetric data (level set, fog volume, etc.) stored in this grid.
Definition MultiResGrid.h:314
openvdb::v11_0::tools::MultiResGrid::ValueOnIter
typename TreeType::ValueOnIter ValueOnIter
Definition MultiResGrid.h:68
openvdb::v11_0::tools::MultiResGrid::prolongateActiveVoxels
void prolongateActiveVoxels(size_t destlevel, size_t grainSize=1)
Definition MultiResGrid.h:587
openvdb::v11_0::tools::MultiResGrid::sampleValue
ValueType sampleValue(const Coord &in_ijk, size_t in_level, size_t out_level) const
Return the value at the specified coordinate position using interpolation of the specified order into...
openvdb::v11_0::tools::MultiResGrid::coarsestConstTreePtr
ConstTreePtr coarsestConstTreePtr() const
Return a const shared pointer to the tree at the coarsest level.
Definition MultiResGrid.h:160
openvdb::v11_0::tools::MultiResGrid::ValueType
typename TreeType::ValueType ValueType
Definition MultiResGrid.h:66
openvdb::v11_0::tools::MultiResGrid::print
void print(std::ostream &=std::cout, int verboseLevel=1) const
Output a human-readable description of this MultiResGrid.
Definition MultiResGrid.h:618
openvdb::v11_0::tools::MultiResGrid::constTransform
const math::Transform & constTransform() const
Definition MultiResGrid.h:204
openvdb::v11_0::tools::MultiResGrid::grid
GridPtr grid(size_t level)
Return a shared pointer to the grid at the specified integer level.
Definition MultiResGrid.h:429
openvdb::v11_0::tools::MultiResGrid::clearGridClass
void clearGridClass()
Remove the setting specifying the class of this grid's volumetric data.
Definition MultiResGrid.h:320
openvdb::v11_0::tools::MultiResGrid::Ptr
SharedPtr< MultiResGrid > Ptr
Definition MultiResGrid.h:63
openvdb::v11_0::tools::MultiResGrid::tree
TreeType & tree(size_t level)
Return a reference to the tree at the specified level.
Definition MultiResGrid.h:397
openvdb::v11_0::tools::MultiResGrid::grids
GridPtrVecPtr grids()
Return a shared pointer to a vector of all the base grids in this instance of the MultiResGrid.
Definition MultiResGrid.h:482
openvdb::v11_0::tools::MultiResGrid::MultiResGrid
MultiResGrid(size_t levels, ValueType background, double voxelSize=1.0)
Constructor of empty grids.
Definition MultiResGrid.h:360
openvdb::v11_0::tools::MultiResGrid::transform
math::Transform & transform()
Return a reference to the finest grid's transform, which might be shared with other grids.
Definition MultiResGrid.h:202
openvdb::v11_0::tools::MultiResGrid::coarsestTree
TreeType & coarsestTree()
Return a reference to the tree at the coarsest level.
Definition MultiResGrid.h:151
openvdb::v11_0::tools::MultiResGrid::finestLevel
static size_t finestLevel()
Return the level of the finest grid (always 0)
Definition MultiResGrid.h:111
openvdb::v11_0::tools::MultiResGrid::coarsestLevel
size_t coarsestLevel() const
Return the level of the coarsest grid, i.e. numLevels()-1.
Definition MultiResGrid.h:114
openvdb::v11_0::tools::MultiResGrid::numLevels
size_t numLevels() const
Return the number of levels, i.e. trees, in this MultiResGrid.
Definition MultiResGrid.h:108
openvdb::v11_0::tools::MultiResGrid::constTreePtr
ConstTreePtr constTreePtr(size_t level) const
Return a const shared pointer to the tree at the specified level.
Definition MultiResGrid.h:421
openvdb::v11_0::tools::MultiResGrid::sampleValue
ValueType sampleValue(const Vec3R &in_ijk, size_t in_level, size_t out_level) const
openvdb::v11_0::tools::MultiResGrid::getName
std::string getName() const
Return a string with the name of this MultiResGrid.
Definition MultiResGrid.h:292
openvdb::v11_0::tools::MultiResGrid::sampleValue
ValueType sampleValue(const Coord &ijk, double level) const
Return the value at the specified integer coordinate position and level using interpolation of the sp...
openvdb::v11_0::tools::MultiResGrid::ConstPtr
SharedPtr< const MultiResGrid > ConstPtr
Definition MultiResGrid.h:64
openvdb::v11_0::tools::MultiResGrid::getGridClass
GridClass getGridClass() const
Return the class of volumetric data (level set, fog volume, etc.) stored in this grid.
Definition MultiResGrid.h:306
openvdb::v11_0::tools::MultiResGrid::ValueOnCIter
typename TreeType::ValueOnCIter ValueOnCIter
Definition MultiResGrid.h:67
openvdb::v11_0::tools::MultiResGrid::setName
void setName(const std::string &name)
Set the name of this MultiResGrid.
Definition MultiResGrid.h:299
openvdb::v11_0::tools::MultiResGrid::GridPtr
typename Grid< TreeType >::Ptr GridPtr
Definition MultiResGrid.h:71
openvdb::v11_0::tools::MultiResGrid::prolongateVoxel
ValueType prolongateVoxel(const Coord &coords, const size_t level) const
Return the value at coordinate location in level tree from the coarser tree at level+1 using trilinea...
Definition MultiResGrid.h:578
openvdb::v11_0::tools::MultiResGrid::ConstGridPtr
typename Grid< TreeType >::ConstPtr ConstGridPtr
Definition MultiResGrid.h:72
openvdb::v11_0::tools::MultiResGrid::transform
const math::Transform & transform() const
Definition MultiResGrid.h:203
openvdb::v11_0::tools::MultiResGrid::restrictActiveVoxels
void restrictActiveVoxels(size_t destlevel, size_t grainSize=1)
Definition MultiResGrid.h:608
openvdb::v11_0::tools::MultiResGrid::constTree
const TreeType & constTree(size_t level) const
Return a const reference to the tree at the specified level.
Definition MultiResGrid.h:405
openvdb::v11_0::tools::MultiResGrid::finestConstTreePtr
ConstTreePtr finestConstTreePtr() const
Return a const shared pointer to the tree at the finest level.
Definition MultiResGrid.h:148
openvdb::v11_0::tools::MultiResGrid::finestTreePtr
TreePtr finestTreePtr()
Return a shared pointer to the tree at the finest level.
Definition MultiResGrid.h:145
openvdb::v11_0::tools::MultiResGrid::TreePtr
typename TreeType::Ptr TreePtr
Definition MultiResGrid.h:69
openvdb::v11_0::tools::MultiResGrid::createGrid
GridPtr createGrid(float level, size_t grainSize=1) const
Return a shared pointer to a new grid at the specified floating-point level.
openvdb::v11_0::tools::MultiResGrid::finestConstTree
const TreeType & finestConstTree() const
Return a const reference to the tree at the finest level.
Definition MultiResGrid.h:142
openvdb::v11_0::tools::MultiResGrid::sampleValue
ValueType sampleValue(const Vec3R &xyz, double level) const
Return the value at the specified floating-point coordinate position and level using interpolation of...
openvdb::v11_0::tools::MultiResGrid::treePtr
TreePtr treePtr(size_t level)
Return a shared pointer to the tree at the specified level.
Definition MultiResGrid.h:413
openvdb::v11_0::tools::MultiResGrid::ConstTreePtr
typename TreeType::ConstPtr ConstTreePtr
Definition MultiResGrid.h:70
openvdb::v11_0::tools::MultiResGrid::coarsestConstTree
const TreeType & coarsestConstTree() const
Return a const reference to the tree at the coarsest level.
Definition MultiResGrid.h:154
openvdb::v11_0::tools::MultiResGrid::xyz
static Vec3R xyz(const Coord &in_ijk, size_t in_level, size_t out_level)
Return the floating-point index coordinate at out_level given the index coordinate in_xyz at in_level...
Definition MultiResGrid.h:500
openvdb::v11_0::tools::MultiResGrid::coarsestTreePtr
TreePtr coarsestTreePtr()
Return a shared pointer to the tree at the coarsest level.
Definition MultiResGrid.h:157
openvdb::v11_0::tools::MultiResGrid::finestTree
TreeType & finestTree()
Return a reference to the tree at the finest level.
Definition MultiResGrid.h:139
openvdb::v11_0::tree::LeafManager
This class manages a linear array of pointers to a given tree's leaf nodes, as well as optional auxil...
Definition LeafManager.h:85
openvdb::v11_0::tree::LeafManager::leafRange
LeafRange leafRange(size_t grainsize=1) const
Return a TBB-compatible LeafRange.
Definition LeafManager.h:345
openvdb::v11_0::tree::ValueAccessorImpl::setValueOn
void setValueOn(const Coord &xyz, const ValueType &value)
Definition ValueAccessor.h:569
openvdb::v11_0::tree::ValueAccessorImpl::getValue
const ValueType & getValue(const Coord &xyz) const
Return the value of the voxel at the given coordinates.
Definition ValueAccessor.h:455
openvdb::v11_0::math
Definition Types.h:28
openvdb::v11_0::math::Pow
Type Pow(Type x, int n)
Return xn.
Definition Math.h:561
openvdb::v11_0::math::Round
float Round(float x)
Return x rounded to the nearest integer.
Definition Math.h:819
openvdb::v11_0::math::FractionalPart
Type FractionalPart(Type x)
Return the fractional part of x.
Definition Math.h:843
openvdb::v11_0::tools::NN_FACE_EDGE_VERTEX
@ NN_FACE_EDGE_VERTEX
Definition Morphology.h:59
openvdb::v11_0::tools::pruneLevelSet
void pruneLevelSet(TreeT &tree, bool threaded=true, size_t grainSize=1)
Reduce the memory footprint of a tree by replacing nodes whose values are all inactive with inactive ...
Definition Prune.h:390
openvdb::v11_0::tools::dilateActiveValues
void dilateActiveValues(TreeOrLeafManagerT &tree, const int iterations=1, const NearestNeighbors nn=NN_FACE, const TilePolicy mode=PRESERVE_TILES, const bool threaded=true)
Topologically dilate all active values (i.e. both voxels and tiles) in a tree using one of three near...
Definition Morphology.h:1056
openvdb::v11_0::tools::signedFloodFill
void signedFloodFill(TreeOrLeafManagerT &tree, bool threaded=true, size_t grainSize=1, Index minLevel=0)
Set the values of all inactive voxels and tiles of a narrow-band level set from the signs of the acti...
Definition SignedFloodFill.h:267
openvdb::v11_0::tools::EXPAND_TILES
@ EXPAND_TILES
Definition Morphology.h:81
openvdb::v11_0::tools::IGNORE_TILES
@ IGNORE_TILES
Definition Morphology.h:81
openvdb::v11_0::tree
Definition PointDataGrid.h:169
openvdb::v11_0::tree::ValueAccessor
ValueAccessorImpl< TreeType, IsSafe, MutexType, openvdb::make_index_sequence< CacheLevels > > ValueAccessor
Default alias for a ValueAccessor. This is simply a helper alias for the generic definition but takes...
Definition ValueAccessor.h:86
openvdb::v11_0::GridPtrVec
std::vector< GridBase::Ptr > GridPtrVec
Definition Grid.h:508
openvdb::v11_0::FloatMetadata
TypedMetadata< float > FloatMetadata
Definition Metadata.h:360
openvdb::v11_0::Real
double Real
Definition Types.h:60
openvdb::v11_0::GridClass
GridClass
Definition Types.h:453
openvdb::v11_0::GRID_LEVEL_SET
@ GRID_LEVEL_SET
Definition Types.h:455
openvdb::v11_0::GRID_UNKNOWN
@ GRID_UNKNOWN
Definition Types.h:454
openvdb::v11_0::GridCPtrVecPtr
SharedPtr< GridCPtrVec > GridCPtrVecPtr
Definition Grid.h:516
openvdb::v11_0::zeroVal
constexpr T zeroVal()
Return the value of type T that corresponds to zero.
Definition Math.h:70
openvdb::v11_0::GridPtrVecPtr
SharedPtr< GridPtrVec > GridPtrVecPtr
Definition Grid.h:511
openvdb::v11_0::StringMetadata
TypedMetadata< std::string > StringMetadata
Definition Metadata.h:363
openvdb::v11_0::Vec3R
math::Vec3< Real > Vec3R
Definition Types.h:72
openvdb::v11_0::SharedPtr
std::shared_ptr< T > SharedPtr
Definition Types.h:114
openvdb::v11_0::Int64Metadata
TypedMetadata< int64_t > Int64Metadata
Definition Metadata.h:362
openvdb::v11_0::GridCPtrVec
std::vector< GridBase::ConstPtr > GridCPtrVec
Definition Grid.h:513
openvdb
Definition Exceptions.h:13
Stencils.h
Defines various finite difference stencils by means of the "curiously recurring template pattern" on ...
NodeManager.h
NodeManager produces linear arrays of all tree nodes allowing for efficient threading and bottom-up p...
openvdb.h
openvdb::v11_0::tools::MultiResGrid::MaskOp
Definition MultiResGrid.h:682
openvdb::v11_0::tools::MultiResGrid::MaskOp::VoxelIterT
typename ManagerT::LeafNodeType::ValueOnCIter VoxelIterT
Definition MultiResGrid.h:687
openvdb::v11_0::tools::MultiResGrid::MaskOp::ManagerT
tree::LeafManager< const MaskT > ManagerT
Definition MultiResGrid.h:685
openvdb::v11_0::tools::MultiResGrid::MaskOp::MaskOp
MaskOp(const TreeType &fineTree, TreeType &coarseTree, size_t grainSize=1)
Definition MultiResGrid.h:689
openvdb::v11_0::tools::MultiResGrid::MaskOp::PoolType
tbb::enumerable_thread_specific< TreeType > PoolType
Definition MultiResGrid.h:684
openvdb::v11_0::tools::MultiResGrid::MaskOp::mPool
PoolType * mPool
Definition MultiResGrid.h:720
openvdb::v11_0::tools::MultiResGrid::MaskOp::operator()
void operator()(const RangeT &range) const
Definition MultiResGrid.h:709
openvdb::v11_0::tools::MultiResGrid::MaskOp::RangeT
typename ManagerT::LeafRange RangeT
Definition MultiResGrid.h:686
openvdb::v11_0::tools::MultiResGrid::MaskOp::MaskT
typename TreeType::template ValueConverter< ValueMask >::Type MaskT
Definition MultiResGrid.h:683
openvdb::v11_0::tools::MultiResGrid::ProlongateOp
Definition MultiResGrid.h:904
openvdb::v11_0::tools::MultiResGrid::ProlongateOp::run
static ValueType run(const Coord &ijk, const ConstAccessor &acc)
Interpolate values from a coarse grid (acc) into the index space (ijk) of a fine grid.
Definition MultiResGrid.h:908
openvdb::v11_0::tools::MultiResGrid::RestrictOp
Definition MultiResGrid.h:871
openvdb::v11_0::tools::MultiResGrid::RestrictOp::run
static ValueType run(Coord ijk, const ConstAccessor &acc)
Static method that performs restriction by full weighting.
Definition MultiResGrid.h:875
openvdb::v11_0::tools::Sampler::sample
static bool sample(const TreeT &inTree, const Vec3R &inCoord, typename TreeT::ValueType &result)
Sample inTree at the floating-point index coordinate inCoord and store the result in result.
OPENVDB_VERSION_NAME
#define OPENVDB_VERSION_NAME
The version namespace name for this library version.
Definition version.h.in:121
OPENVDB_USE_VERSION_NAMESPACE
#define OPENVDB_USE_VERSION_NAMESPACE
Definition version.h.in:212
OPENVDB_INSTANTIATE_CLASS
#define OPENVDB_INSTANTIATE_CLASS
Definition version.h.in:153