mirror of
https://gitlab.kitware.com/vtk/vtk-m
synced 2024-10-05 01:49:02 +00:00
Merge topic 'amrFilter'
11d770659 add worklet include 7139a1c8c add amr capability as filter Acked-by: Kitware Robot <kwrobot@kitware.com> Acked-by: Kenneth Moreland <morelandkd@ornl.gov> Merge-request: !2646
This commit is contained in:
commit
557055b9cc
3
data/baseline/filter/amrArrays2D.png
Normal file
3
data/baseline/filter/amrArrays2D.png
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
version https://git-lfs.github.com/spec/v1
|
||||||
|
oid sha256:0994e1747beaddba1ab6e97a48e17956e64a12ebfdffac1c2ae8734f3578956f
|
||||||
|
size 20716
|
3
data/baseline/filter/amrArrays3D.png
Normal file
3
data/baseline/filter/amrArrays3D.png
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
version https://git-lfs.github.com/spec/v1
|
||||||
|
oid sha256:6a610fe2de049c6a2402f7b19ea5a03f2e637e90d62a6df38832e62b89a691bb
|
||||||
|
size 25953
|
@ -102,6 +102,42 @@ struct Bounds
|
|||||||
return (this->X.Contains(point[0]) && this->Y.Contains(point[1]) && this->Z.Contains(point[2]));
|
return (this->X.Contains(point[0]) && this->Y.Contains(point[1]) && this->Z.Contains(point[2]));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// \b Returns the volume of the bounds.
|
||||||
|
///
|
||||||
|
/// \c Volume computes the product of the lengths of the ranges in each dimension. If the bounds
|
||||||
|
/// are empty, 0 is returned.
|
||||||
|
///
|
||||||
|
VTKM_EXEC_CONT
|
||||||
|
vtkm::Float64 Volume() const
|
||||||
|
{
|
||||||
|
if (this->IsNonEmpty())
|
||||||
|
{
|
||||||
|
return (this->X.Length() * this->Y.Length() * this->Z.Length());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return 0.0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// \b Returns the area of the bounds in the X-Y-plane.
|
||||||
|
///
|
||||||
|
/// \c Area computes the product of the lengths of the ranges in dimensions X and Y. If the bounds
|
||||||
|
/// are empty, 0 is returned.
|
||||||
|
///
|
||||||
|
VTKM_EXEC_CONT
|
||||||
|
vtkm::Float64 Area() const
|
||||||
|
{
|
||||||
|
if (this->IsNonEmpty())
|
||||||
|
{
|
||||||
|
return (this->X.Length() * this->Y.Length());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return 0.0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// \b Returns the center of the range.
|
/// \b Returns the center of the range.
|
||||||
///
|
///
|
||||||
/// \c Center computes the point at the middle of the bounds. If the bounds
|
/// \c Center computes the point at the middle of the bounds. If the bounds
|
||||||
@ -152,6 +188,16 @@ struct Bounds
|
|||||||
return unionBounds;
|
return unionBounds;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// \b Return the intersection of this and another range.
|
||||||
|
///
|
||||||
|
VTKM_EXEC_CONT
|
||||||
|
vtkm::Bounds Intersection(const vtkm::Bounds& otherBounds) const
|
||||||
|
{
|
||||||
|
return vtkm::Bounds(this->X.Intersection(otherBounds.X),
|
||||||
|
this->Y.Intersection(otherBounds.Y),
|
||||||
|
this->Z.Intersection(otherBounds.Z));
|
||||||
|
}
|
||||||
|
|
||||||
/// \b Operator for union
|
/// \b Operator for union
|
||||||
///
|
///
|
||||||
VTKM_EXEC_CONT
|
VTKM_EXEC_CONT
|
||||||
|
@ -19,7 +19,7 @@ enum CellClassification : vtkm::UInt8
|
|||||||
GHOST = 1 << 0, //Ghost cell
|
GHOST = 1 << 0, //Ghost cell
|
||||||
INVALID = 1 << 1, //Cell is invalid
|
INVALID = 1 << 1, //Cell is invalid
|
||||||
UNUSED0 = 1 << 2,
|
UNUSED0 = 1 << 2,
|
||||||
UNUSED1 = 1 << 3,
|
BLANKED = 1 << 3, //Blanked cell in AMR
|
||||||
UNUSED3 = 1 << 4,
|
UNUSED3 = 1 << 4,
|
||||||
UNUSED4 = 1 << 5,
|
UNUSED4 = 1 << 5,
|
||||||
UNUSED5 = 1 << 6,
|
UNUSED5 = 1 << 6,
|
||||||
|
@ -153,6 +153,14 @@ struct Range
|
|||||||
return unionRange;
|
return unionRange;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// \b Return the intersection of this and another range.
|
||||||
|
///
|
||||||
|
VTKM_EXEC_CONT
|
||||||
|
vtkm::Range Intersection(const vtkm::Range& otherRange) const
|
||||||
|
{
|
||||||
|
return vtkm::Range(vtkm::Max(this->Min, otherRange.Min), vtkm::Min(this->Max, otherRange.Max));
|
||||||
|
}
|
||||||
|
|
||||||
/// \b Operator for union
|
/// \b Operator for union
|
||||||
///
|
///
|
||||||
VTKM_EXEC_CONT
|
VTKM_EXEC_CONT
|
||||||
|
86
vtkm/filter/AmrArrays.h
Normal file
86
vtkm/filter/AmrArrays.h
Normal file
@ -0,0 +1,86 @@
|
|||||||
|
//============================================================================
|
||||||
|
// Copyright (c) Kitware, Inc.
|
||||||
|
// All rights reserved.
|
||||||
|
// See LICENSE.txt for details.
|
||||||
|
//
|
||||||
|
// This software is distributed WITHOUT ANY WARRANTY; without even
|
||||||
|
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||||
|
// PURPOSE. See the above copyright notice for more information.
|
||||||
|
//============================================================================
|
||||||
|
#ifndef vtk_m_filter_AmrArrays_h
|
||||||
|
#define vtk_m_filter_AmrArrays_h
|
||||||
|
|
||||||
|
#include <vtkm/filter/FilterDataSet.h>
|
||||||
|
|
||||||
|
namespace vtkm
|
||||||
|
{
|
||||||
|
namespace filter
|
||||||
|
{
|
||||||
|
|
||||||
|
class AmrArrays : public vtkm::filter::FilterDataSet<AmrArrays>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
using SupportedTypes = vtkm::List<vtkm::UInt8>;
|
||||||
|
|
||||||
|
VTKM_CONT
|
||||||
|
AmrArrays();
|
||||||
|
|
||||||
|
template <typename DerivedPolicy>
|
||||||
|
vtkm::cont::PartitionedDataSet PrepareForExecution(
|
||||||
|
const vtkm::cont::PartitionedDataSet& input,
|
||||||
|
const vtkm::filter::PolicyBase<DerivedPolicy>&);
|
||||||
|
|
||||||
|
template <typename DerivedPolicy>
|
||||||
|
VTKM_CONT bool MapFieldOntoOutput(vtkm::cont::DataSet& result,
|
||||||
|
const vtkm::cont::Field& field,
|
||||||
|
const vtkm::filter::PolicyBase<DerivedPolicy>&)
|
||||||
|
{
|
||||||
|
result.AddField(field);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
/// the list of ids contains all amrIds of the level above/below that have an overlap
|
||||||
|
VTKM_CONT
|
||||||
|
void GenerateParentChildInformation();
|
||||||
|
|
||||||
|
/// the corresponding template function based on the dimension of this dataset
|
||||||
|
VTKM_CONT
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
void ComputeGenerateParentChildInformation();
|
||||||
|
|
||||||
|
/// generate the vtkGhostType array based on the overlap analogously to vtk
|
||||||
|
/// blanked cells: 8 normal cells: 0
|
||||||
|
VTKM_CONT
|
||||||
|
void GenerateGhostType();
|
||||||
|
|
||||||
|
/// the corresponding template function based on the dimension of this dataset
|
||||||
|
VTKM_CONT
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
void ComputeGenerateGhostType();
|
||||||
|
|
||||||
|
/// Add helper arrays like in ParaView
|
||||||
|
VTKM_CONT
|
||||||
|
void GenerateIndexArrays();
|
||||||
|
|
||||||
|
/// the input partitioned dataset
|
||||||
|
vtkm::cont::PartitionedDataSet AmrDataSet;
|
||||||
|
|
||||||
|
/// per level
|
||||||
|
/// contains the index where the PartitionIds start for each level
|
||||||
|
std::vector<std::vector<vtkm::Id>> PartitionIds;
|
||||||
|
|
||||||
|
/// per partitionId
|
||||||
|
/// contains all PartitonIds of the level above that have an overlap
|
||||||
|
std::vector<std::vector<vtkm::Id>> ParentsIdsVector;
|
||||||
|
|
||||||
|
/// per partitionId
|
||||||
|
/// contains all PartitonIds of the level below that have an overlap
|
||||||
|
std::vector<std::vector<vtkm::Id>> ChildrenIdsVector;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
} // namespace vtkm::filter
|
||||||
|
|
||||||
|
#include <vtkm/filter/AmrArrays.hxx>
|
||||||
|
|
||||||
|
#endif //vtk_m_filter_AmrArrays_h
|
307
vtkm/filter/AmrArrays.hxx
Normal file
307
vtkm/filter/AmrArrays.hxx
Normal file
@ -0,0 +1,307 @@
|
|||||||
|
//============================================================================
|
||||||
|
// Copyright (c) Kitware, Inc.
|
||||||
|
// All rights reserved.
|
||||||
|
// See LICENSE.txt for details.
|
||||||
|
//
|
||||||
|
// This software is distributed WITHOUT ANY WARRANTY; without even
|
||||||
|
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||||
|
// PURPOSE. See the above copyright notice for more information.
|
||||||
|
//============================================================================
|
||||||
|
#ifndef vtk_m_filter_AmrArrays_hxx
|
||||||
|
#define vtk_m_filter_AmrArrays_hxx
|
||||||
|
|
||||||
|
#include <vtkm/CellClassification.h>
|
||||||
|
#include <vtkm/RangeId.h>
|
||||||
|
#include <vtkm/RangeId2.h>
|
||||||
|
#include <vtkm/RangeId3.h>
|
||||||
|
#include <vtkm/Types.h>
|
||||||
|
#include <vtkm/cont/ArrayCopy.h>
|
||||||
|
#include <vtkm/cont/ArrayHandle.h>
|
||||||
|
#include <vtkm/cont/BoundsCompute.h>
|
||||||
|
#include <vtkm/worklet/WorkletMapTopology.h>
|
||||||
|
|
||||||
|
|
||||||
|
namespace vtkm
|
||||||
|
{
|
||||||
|
namespace worklet
|
||||||
|
{
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
struct GenerateGhostTypeWorklet : vtkm::worklet::WorkletVisitCellsWithPoints
|
||||||
|
{
|
||||||
|
using ControlSignature = void(CellSetIn cellSet,
|
||||||
|
FieldInPoint pointArray,
|
||||||
|
FieldInOutCell ghostArray);
|
||||||
|
using ExecutionSignature = void(PointCount, _2, _3);
|
||||||
|
using InputDomain = _1;
|
||||||
|
|
||||||
|
GenerateGhostTypeWorklet(vtkm::Bounds boundsChild)
|
||||||
|
: BoundsChild(boundsChild)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename pointArrayType, typename cellArrayType>
|
||||||
|
VTKM_EXEC void operator()(vtkm::IdComponent numPoints,
|
||||||
|
const pointArrayType pointArray,
|
||||||
|
cellArrayType& ghostArray) const
|
||||||
|
{
|
||||||
|
vtkm::Bounds boundsCell = vtkm::Bounds();
|
||||||
|
for (vtkm::IdComponent pointId = 0; pointId < numPoints; pointId++)
|
||||||
|
{
|
||||||
|
boundsCell.Include(pointArray[pointId]);
|
||||||
|
}
|
||||||
|
vtkm::Bounds boundsIntersection = boundsCell.Intersection(BoundsChild);
|
||||||
|
if ((Dim == 2 && boundsIntersection.Area() > 0.5 * boundsCell.Area()) ||
|
||||||
|
(Dim == 3 && boundsIntersection.Volume() > 0.5 * boundsCell.Volume()))
|
||||||
|
{
|
||||||
|
// std::cout<<boundsCell<<" is (partly) contained in "<<BoundsChild<<" "<<boundsIntersection<<" "<<boundsIntersection.Area()<<std::endl;
|
||||||
|
ghostArray = ghostArray + vtkm::CellClassification::BLANKED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
vtkm::Bounds BoundsChild;
|
||||||
|
};
|
||||||
|
} // worklet
|
||||||
|
} // vtkm
|
||||||
|
|
||||||
|
namespace vtkm
|
||||||
|
{
|
||||||
|
namespace filter
|
||||||
|
{
|
||||||
|
|
||||||
|
inline VTKM_CONT AmrArrays::AmrArrays() {}
|
||||||
|
|
||||||
|
VTKM_CONT
|
||||||
|
void AmrArrays::GenerateParentChildInformation()
|
||||||
|
{
|
||||||
|
vtkm::Bounds bounds = vtkm::cont::BoundsCompute(this->AmrDataSet);
|
||||||
|
if (bounds.Z.Max - bounds.Z.Min < vtkm::Epsilon<vtkm::FloatDefault>())
|
||||||
|
{
|
||||||
|
ComputeGenerateParentChildInformation<2>();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ComputeGenerateParentChildInformation<3>();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template void AmrArrays::ComputeGenerateParentChildInformation<2>();
|
||||||
|
|
||||||
|
template void AmrArrays::ComputeGenerateParentChildInformation<3>();
|
||||||
|
|
||||||
|
VTKM_CONT
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
void AmrArrays::ComputeGenerateParentChildInformation()
|
||||||
|
{
|
||||||
|
// read out spacings in decreasing order to infer levels
|
||||||
|
std::set<FloatDefault, std::greater<FloatDefault>> spacings;
|
||||||
|
for (vtkm::Id p = 0; p < this->AmrDataSet.GetNumberOfPartitions(); p++)
|
||||||
|
{
|
||||||
|
vtkm::cont::ArrayHandleUniformPointCoordinates uniformCoords =
|
||||||
|
this->AmrDataSet.GetPartition(p)
|
||||||
|
.GetCoordinateSystem()
|
||||||
|
.GetData()
|
||||||
|
.AsArrayHandle<vtkm::cont::ArrayHandleUniformPointCoordinates>();
|
||||||
|
spacings.insert(uniformCoords.GetSpacing()[0]);
|
||||||
|
}
|
||||||
|
std::set<FloatDefault, std::greater<FloatDefault>>::iterator itr;
|
||||||
|
// for (itr = spacings.begin(); itr != spacings.end(); itr++)
|
||||||
|
// {
|
||||||
|
// std::cout << *itr << "\n";
|
||||||
|
// }
|
||||||
|
|
||||||
|
/// contains the partitionIds of each level and blockId
|
||||||
|
this->PartitionIds.resize(spacings.size());
|
||||||
|
for (vtkm::Id p = 0; p < this->AmrDataSet.GetNumberOfPartitions(); p++)
|
||||||
|
{
|
||||||
|
vtkm::cont::ArrayHandleUniformPointCoordinates uniformCoords =
|
||||||
|
this->AmrDataSet.GetPartition(p)
|
||||||
|
.GetCoordinateSystem()
|
||||||
|
.GetData()
|
||||||
|
.AsArrayHandle<vtkm::cont::ArrayHandleUniformPointCoordinates>();
|
||||||
|
int index = -1;
|
||||||
|
for (itr = spacings.begin(); itr != spacings.end(); itr++)
|
||||||
|
{
|
||||||
|
index++;
|
||||||
|
if (*itr == uniformCoords.GetSpacing()[0])
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
this->PartitionIds.at(index).push_back(p);
|
||||||
|
// std::cout <<p<<" "<< index << "\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
// compute parent and child relations
|
||||||
|
this->ParentsIdsVector.resize(this->AmrDataSet.GetNumberOfPartitions());
|
||||||
|
this->ChildrenIdsVector.resize(this->AmrDataSet.GetNumberOfPartitions());
|
||||||
|
for (unsigned int l = 0; l < this->PartitionIds.size() - 1; l++)
|
||||||
|
{
|
||||||
|
for (unsigned int bParent = 0; bParent < this->PartitionIds.at(l).size(); bParent++)
|
||||||
|
{
|
||||||
|
// std::cout << std::endl << "level " << l << " block " << bParent << std::endl;
|
||||||
|
vtkm::Bounds boundsParent =
|
||||||
|
this->AmrDataSet.GetPartition(this->PartitionIds.at(l).at(bParent))
|
||||||
|
.GetCoordinateSystem()
|
||||||
|
.GetBounds();
|
||||||
|
|
||||||
|
// compute size of a cell to compare overlap against
|
||||||
|
auto coords = this->AmrDataSet.GetPartition(this->PartitionIds.at(l).at(bParent))
|
||||||
|
.GetCoordinateSystem()
|
||||||
|
.GetDataAsMultiplexer();
|
||||||
|
vtkm::cont::CellSetStructured<Dim> cellset;
|
||||||
|
vtkm::Id ptids[8];
|
||||||
|
this->AmrDataSet.GetPartition(this->PartitionIds.at(l).at(bParent))
|
||||||
|
.GetCellSet()
|
||||||
|
.CopyTo(cellset);
|
||||||
|
cellset.GetCellPointIds(0, ptids);
|
||||||
|
vtkm::Bounds boundsCell = vtkm::Bounds();
|
||||||
|
for (vtkm::IdComponent pointId = 0; pointId < cellset.GetNumberOfPointsInCell(0); pointId++)
|
||||||
|
{
|
||||||
|
boundsCell.Include(coords.ReadPortal().Get(ptids[pointId]));
|
||||||
|
}
|
||||||
|
|
||||||
|
// see if there is overlap of at least one half of a cell
|
||||||
|
for (unsigned int bChild = 0; bChild < this->PartitionIds.at(l + 1).size(); bChild++)
|
||||||
|
{
|
||||||
|
vtkm::Bounds boundsChild =
|
||||||
|
this->AmrDataSet.GetPartition(this->PartitionIds.at(l + 1).at(bChild))
|
||||||
|
.GetCoordinateSystem()
|
||||||
|
.GetBounds();
|
||||||
|
vtkm::Bounds boundsIntersection = boundsParent.Intersection(boundsChild);
|
||||||
|
if ((Dim == 2 && boundsIntersection.Area() > 0.5 * boundsCell.Area()) ||
|
||||||
|
(Dim == 3 && boundsIntersection.Volume() >= 0.5 * boundsCell.Volume()))
|
||||||
|
{
|
||||||
|
this->ParentsIdsVector.at(this->PartitionIds.at(l + 1).at(bChild))
|
||||||
|
.push_back(this->PartitionIds.at(l).at(bParent));
|
||||||
|
this->ChildrenIdsVector.at(this->PartitionIds.at(l).at(bParent))
|
||||||
|
.push_back(this->PartitionIds.at(l + 1).at(bChild));
|
||||||
|
// std::cout << " overlaps with level " << l + 1 << " block " << bChild << " "
|
||||||
|
// << boundsParent << " " << boundsChild << " " << boundsIntersection << " "
|
||||||
|
// << boundsIntersection.Area() << " " << boundsIntersection.Volume() << std::endl;
|
||||||
|
}
|
||||||
|
// else
|
||||||
|
// {
|
||||||
|
// std::cout << " does not overlap with level " << l + 1 << " block " << bChild << " "
|
||||||
|
// << boundsParent << " " << boundsChild << " " << boundsIntersection << " "
|
||||||
|
// << boundsIntersection.Area() << " " << boundsIntersection.Volume() << std::endl;
|
||||||
|
// }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
VTKM_CONT
|
||||||
|
void AmrArrays::GenerateGhostType()
|
||||||
|
{
|
||||||
|
vtkm::Bounds bounds = vtkm::cont::BoundsCompute(this->AmrDataSet);
|
||||||
|
if (bounds.Z.Max - bounds.Z.Min < vtkm::Epsilon<vtkm::FloatDefault>())
|
||||||
|
{
|
||||||
|
ComputeGenerateGhostType<2>();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ComputeGenerateGhostType<3>();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template void AmrArrays::ComputeGenerateGhostType<2>();
|
||||||
|
|
||||||
|
template void AmrArrays::ComputeGenerateGhostType<3>();
|
||||||
|
|
||||||
|
VTKM_CONT
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
void AmrArrays::ComputeGenerateGhostType()
|
||||||
|
{
|
||||||
|
for (unsigned int l = 0; l < this->PartitionIds.size(); l++)
|
||||||
|
{
|
||||||
|
for (unsigned int bParent = 0; bParent < this->PartitionIds.at(l).size(); bParent++)
|
||||||
|
{
|
||||||
|
// std::cout<<std::endl<<"level "<<l<<" block "<<bParent<<" has "<<this->ChildrenIdsVector.at(this->PartitionIds.at(l).at(bParent)).size()<<" children"<<std::endl;
|
||||||
|
|
||||||
|
vtkm::cont::DataSet partition =
|
||||||
|
this->AmrDataSet.GetPartition(this->PartitionIds.at(l).at(bParent));
|
||||||
|
vtkm::cont::CellSetStructured<Dim> cellset;
|
||||||
|
partition.GetCellSet().CopyTo(cellset);
|
||||||
|
vtkm::cont::ArrayHandle<vtkm::UInt8> ghostField;
|
||||||
|
if (!partition.HasField("vtkGhostType", vtkm::cont::Field::Association::CELL_SET))
|
||||||
|
{
|
||||||
|
vtkm::cont::ArrayCopy(
|
||||||
|
vtkm::cont::ArrayHandleConstant<vtkm::UInt8>(0, partition.GetNumberOfCells()),
|
||||||
|
ghostField);
|
||||||
|
}
|
||||||
|
// leave field unchanged if it is the highest level
|
||||||
|
if (l < this->PartitionIds.size() - 1)
|
||||||
|
{
|
||||||
|
auto pointField = partition.GetCoordinateSystem().GetDataAsMultiplexer();
|
||||||
|
|
||||||
|
for (unsigned int bChild = 0;
|
||||||
|
bChild < this->ChildrenIdsVector.at(this->PartitionIds.at(l).at(bParent)).size();
|
||||||
|
bChild++)
|
||||||
|
{
|
||||||
|
vtkm::Bounds boundsChild =
|
||||||
|
this->AmrDataSet
|
||||||
|
.GetPartition(
|
||||||
|
this->ChildrenIdsVector.at(this->PartitionIds.at(l).at(bParent)).at(bChild))
|
||||||
|
.GetCoordinateSystem()
|
||||||
|
.GetBounds();
|
||||||
|
// std::cout<<" is (partly) contained in level "<<l + 1<<" block "<<bChild<<" which is partition "<<this->ChildrenIdsVector.at(this->PartitionIds.at(l).at(bParent)).at(bChild)<<" with bounds "<<boundsChild<<std::endl;
|
||||||
|
|
||||||
|
vtkm::cont::Invoker invoke;
|
||||||
|
invoke(vtkm::worklet::GenerateGhostTypeWorklet<Dim>{ boundsChild },
|
||||||
|
cellset,
|
||||||
|
pointField,
|
||||||
|
ghostField);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
partition.AddCellField("vtkGhostType", ghostField);
|
||||||
|
this->AmrDataSet.ReplacePartition(this->PartitionIds.at(l).at(bParent), partition);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add helper arrays like in ParaView
|
||||||
|
VTKM_CONT
|
||||||
|
void AmrArrays::GenerateIndexArrays()
|
||||||
|
{
|
||||||
|
for (unsigned int l = 0; l < this->PartitionIds.size(); l++)
|
||||||
|
{
|
||||||
|
for (unsigned int b = 0; b < this->PartitionIds.at(l).size(); b++)
|
||||||
|
{
|
||||||
|
vtkm::cont::DataSet partition = this->AmrDataSet.GetPartition(this->PartitionIds.at(l).at(b));
|
||||||
|
|
||||||
|
vtkm::cont::ArrayHandle<vtkm::Id> fieldAmrLevel;
|
||||||
|
vtkm::cont::ArrayCopy(
|
||||||
|
vtkm::cont::ArrayHandleConstant<vtkm::Id>(l, partition.GetNumberOfCells()), fieldAmrLevel);
|
||||||
|
partition.AddCellField("vtkAmrLevel", fieldAmrLevel);
|
||||||
|
|
||||||
|
vtkm::cont::ArrayHandle<vtkm::Id> fieldBlockId;
|
||||||
|
vtkm::cont::ArrayCopy(
|
||||||
|
vtkm::cont::ArrayHandleConstant<vtkm::Id>(b, partition.GetNumberOfCells()), fieldBlockId);
|
||||||
|
partition.AddCellField("vtkAmrIndex", fieldBlockId);
|
||||||
|
|
||||||
|
vtkm::cont::ArrayHandle<vtkm::Id> fieldPartitionIndex;
|
||||||
|
vtkm::cont::ArrayCopy(vtkm::cont::ArrayHandleConstant<vtkm::Id>(
|
||||||
|
this->PartitionIds.at(l).at(b), partition.GetNumberOfCells()),
|
||||||
|
fieldPartitionIndex);
|
||||||
|
partition.AddCellField("vtkCompositeIndex", fieldPartitionIndex);
|
||||||
|
|
||||||
|
this->AmrDataSet.ReplacePartition(this->PartitionIds.at(l).at(b), partition);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename DerivedPolicy>
|
||||||
|
vtkm::cont::PartitionedDataSet AmrArrays::PrepareForExecution(
|
||||||
|
const vtkm::cont::PartitionedDataSet& input,
|
||||||
|
const vtkm::filter::PolicyBase<DerivedPolicy>&)
|
||||||
|
{
|
||||||
|
this->AmrDataSet = input;
|
||||||
|
this->GenerateParentChildInformation();
|
||||||
|
this->GenerateGhostType();
|
||||||
|
this->GenerateIndexArrays();
|
||||||
|
return this->AmrDataSet;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
@ -77,6 +77,7 @@ set(common_sources_device
|
|||||||
)
|
)
|
||||||
|
|
||||||
set(extra_headers
|
set(extra_headers
|
||||||
|
AmrArrays.h
|
||||||
CellSetConnectivity.h
|
CellSetConnectivity.h
|
||||||
ClipWithField.h
|
ClipWithField.h
|
||||||
ClipWithImplicitFunction.h
|
ClipWithImplicitFunction.h
|
||||||
@ -134,6 +135,7 @@ set(extra_headers
|
|||||||
)
|
)
|
||||||
|
|
||||||
set(extra_header_template_sources
|
set(extra_header_template_sources
|
||||||
|
AmrArrays.hxx
|
||||||
CellSetConnectivity.hxx
|
CellSetConnectivity.hxx
|
||||||
ClipWithField.hxx
|
ClipWithField.hxx
|
||||||
ClipWithImplicitFunction.hxx
|
ClipWithImplicitFunction.hxx
|
||||||
|
@ -98,6 +98,7 @@ if (VTKm_ENABLE_RENDERING)
|
|||||||
list(APPEND libraries vtkm_rendering)
|
list(APPEND libraries vtkm_rendering)
|
||||||
|
|
||||||
list(APPEND unit_tests
|
list(APPEND unit_tests
|
||||||
|
RegressionTestAmrArrays.cxx
|
||||||
RegressionTestContourFilter.cxx
|
RegressionTestContourFilter.cxx
|
||||||
RegressionTestPointTransform.cxx
|
RegressionTestPointTransform.cxx
|
||||||
RegressionTestSliceFilter.cxx
|
RegressionTestSliceFilter.cxx
|
||||||
|
78
vtkm/filter/testing/RegressionTestAmrArrays.cxx
Normal file
78
vtkm/filter/testing/RegressionTestAmrArrays.cxx
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
//============================================================================
|
||||||
|
// Copyright (c) Kitware, Inc.
|
||||||
|
// All rights reserved.
|
||||||
|
// See LICENSE.txt for details.
|
||||||
|
//
|
||||||
|
// This software is distributed WITHOUT ANY WARRANTY; without even
|
||||||
|
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||||
|
// PURPOSE. See the above copyright notice for more information.
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
#include <vtkm/cont/MergePartitionedDataSet.h>
|
||||||
|
#include <vtkm/filter/ExternalFaces.h>
|
||||||
|
#include <vtkm/filter/Threshold.h>
|
||||||
|
#include <vtkm/source/Amr.h>
|
||||||
|
|
||||||
|
#include <vtkm/rendering/CanvasRayTracer.h>
|
||||||
|
#include <vtkm/rendering/MapperRayTracer.h>
|
||||||
|
#include <vtkm/rendering/View3D.h>
|
||||||
|
#include <vtkm/rendering/testing/RenderTest.h>
|
||||||
|
#include <vtkm/rendering/testing/Testing.h>
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
|
||||||
|
void TestAmrArraysExecute(int dim, int numberOfLevels, int cellsPerDimension)
|
||||||
|
{
|
||||||
|
std::cout << "Generate Image for AMR" << std::endl;
|
||||||
|
|
||||||
|
using M = vtkm::rendering::MapperRayTracer;
|
||||||
|
using C = vtkm::rendering::CanvasRayTracer;
|
||||||
|
using V3 = vtkm::rendering::View3D;
|
||||||
|
|
||||||
|
// Generate AMR
|
||||||
|
vtkm::source::Amr source(dim, cellsPerDimension, numberOfLevels);
|
||||||
|
vtkm::cont::PartitionedDataSet amrDataSet = source.Execute();
|
||||||
|
// std::cout << "amr " << std::endl;
|
||||||
|
// amrDataSet.PrintSummary(std::cout);
|
||||||
|
|
||||||
|
// Remove blanked cells
|
||||||
|
vtkm::filter::Threshold threshold;
|
||||||
|
threshold.SetLowerThreshold(0);
|
||||||
|
threshold.SetUpperThreshold(1);
|
||||||
|
threshold.SetActiveField("vtkGhostType");
|
||||||
|
vtkm::cont::PartitionedDataSet derivedDataSet = threshold.Execute(amrDataSet);
|
||||||
|
// std::cout << "derived " << std::endl;
|
||||||
|
// derivedDataSet.PrintSummary(std::cout);
|
||||||
|
|
||||||
|
// Extract surface for efficient 3D pipeline
|
||||||
|
vtkm::filter::ExternalFaces surface;
|
||||||
|
surface.SetFieldsToPass("RTDataCells");
|
||||||
|
derivedDataSet = surface.Execute(derivedDataSet);
|
||||||
|
|
||||||
|
// Merge dataset
|
||||||
|
vtkm::cont::DataSet result = vtkm::cont::MergePartitionedDataSet(derivedDataSet);
|
||||||
|
// std::cout << "merged " << std::endl;
|
||||||
|
// result.PrintSummary(std::cout);
|
||||||
|
|
||||||
|
vtkm::rendering::testing::RenderAndRegressionTest<M, C, V3>(result,
|
||||||
|
"RTDataCells",
|
||||||
|
vtkm::cont::ColorTable("inferno"),
|
||||||
|
"filter/amrArrays" +
|
||||||
|
std::to_string(dim) + "D.png",
|
||||||
|
false);
|
||||||
|
}
|
||||||
|
|
||||||
|
void TestAmrArrays()
|
||||||
|
{
|
||||||
|
int numberOfLevels = 5;
|
||||||
|
int cellsPerDimension = 6;
|
||||||
|
TestAmrArraysExecute(2, numberOfLevels, cellsPerDimension);
|
||||||
|
TestAmrArraysExecute(3, numberOfLevels, cellsPerDimension);
|
||||||
|
}
|
||||||
|
} // namespace
|
||||||
|
|
||||||
|
int RegressionTestAmrArrays(int argc, char* argv[])
|
||||||
|
{
|
||||||
|
return vtkm::cont::testing::Testing::Run(TestAmrArrays, argc, argv);
|
||||||
|
}
|
111
vtkm/source/Amr.cxx
Normal file
111
vtkm/source/Amr.cxx
Normal file
@ -0,0 +1,111 @@
|
|||||||
|
//============================================================================
|
||||||
|
// Copyright (c) Kitware, Inc.
|
||||||
|
// All rights reserved.
|
||||||
|
// See LICENSE.txt for details.
|
||||||
|
//
|
||||||
|
// This software is distributed WITHOUT ANY WARRANTY; without even
|
||||||
|
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||||
|
// PURPOSE. See the above copyright notice for more information.
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
|
||||||
|
#include <vtkm/cont/PartitionedDataSet.h>
|
||||||
|
#include <vtkm/filter/AmrArrays.h>
|
||||||
|
#include <vtkm/filter/CellAverage.h>
|
||||||
|
#include <vtkm/source/Amr.h>
|
||||||
|
#include <vtkm/source/Wavelet.h>
|
||||||
|
|
||||||
|
|
||||||
|
namespace vtkm
|
||||||
|
{
|
||||||
|
namespace source
|
||||||
|
{
|
||||||
|
|
||||||
|
Amr::Amr(vtkm::IdComponent dimension,
|
||||||
|
vtkm::IdComponent cellsPerDimension,
|
||||||
|
vtkm::IdComponent numberOfLevels)
|
||||||
|
: Dimension(dimension)
|
||||||
|
, CellsPerDimension(cellsPerDimension)
|
||||||
|
, NumberOfLevels(numberOfLevels)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
Amr::~Amr() = default;
|
||||||
|
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
vtkm::cont::DataSet Amr::GenerateDataSet(unsigned int level, unsigned int amrIndex) const
|
||||||
|
{
|
||||||
|
vtkm::Id3 extent = { vtkm::Id(this->CellsPerDimension / 2) };
|
||||||
|
vtkm::Id3 dimensions = { this->CellsPerDimension + 1 };
|
||||||
|
vtkm::Vec3f origin = { float(1. / pow(2, level) * amrIndex) };
|
||||||
|
vtkm::Vec3f spacing = { float(1. / this->CellsPerDimension / pow(2, level)) };
|
||||||
|
vtkm::Vec3f center = 0.5f - (origin + spacing * extent);
|
||||||
|
vtkm::Vec3f frequency = { 60.f, 30.f, 40.f };
|
||||||
|
frequency = frequency * this->CellsPerDimension;
|
||||||
|
vtkm::FloatDefault deviation = 0.5f / this->CellsPerDimension;
|
||||||
|
|
||||||
|
if (Dim == 2)
|
||||||
|
{
|
||||||
|
extent[2] = 0;
|
||||||
|
dimensions[2] = 1;
|
||||||
|
origin[2] = 0;
|
||||||
|
spacing[2] = 1;
|
||||||
|
center[2] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
vtkm::source::Wavelet waveletSource(-extent, extent);
|
||||||
|
waveletSource.SetOrigin(origin);
|
||||||
|
waveletSource.SetSpacing(spacing);
|
||||||
|
waveletSource.SetCenter(center);
|
||||||
|
waveletSource.SetFrequency(frequency);
|
||||||
|
waveletSource.SetStandardDeviation(deviation);
|
||||||
|
vtkm::cont::DataSet wavelet = waveletSource.Execute();
|
||||||
|
|
||||||
|
vtkm::filter::CellAverage cellAverage;
|
||||||
|
cellAverage.SetActiveField("RTData", vtkm::cont::Field::Association::POINTS);
|
||||||
|
cellAverage.SetOutputFieldName("RTDataCells");
|
||||||
|
return cellAverage.Execute(wavelet);
|
||||||
|
}
|
||||||
|
|
||||||
|
vtkm::cont::PartitionedDataSet Amr::Execute() const
|
||||||
|
{
|
||||||
|
assert(this->CellsPerDimension > 1);
|
||||||
|
assert(this->CellsPerDimension % 2 == 0);
|
||||||
|
|
||||||
|
// Generate AMR
|
||||||
|
std::vector<std::vector<vtkm::Id>> blocksPerLevel(this->NumberOfLevels);
|
||||||
|
unsigned int counter = 0;
|
||||||
|
for (unsigned int l = 0; l < blocksPerLevel.size(); l++)
|
||||||
|
{
|
||||||
|
for (unsigned int b = 0; b < pow(2, l); b++)
|
||||||
|
{
|
||||||
|
blocksPerLevel.at(l).push_back(counter++);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
vtkm::cont::PartitionedDataSet amrDataSet;
|
||||||
|
|
||||||
|
// Fill AMR with data from the wavelet
|
||||||
|
for (unsigned int l = 0; l < blocksPerLevel.size(); l++)
|
||||||
|
{
|
||||||
|
for (unsigned int b = 0; b < blocksPerLevel.at(l).size(); b++)
|
||||||
|
{
|
||||||
|
if (this->Dimension == 2)
|
||||||
|
{
|
||||||
|
amrDataSet.AppendPartition(this->GenerateDataSet<2>(l, b));
|
||||||
|
}
|
||||||
|
else if (this->Dimension == 3)
|
||||||
|
{
|
||||||
|
amrDataSet.AppendPartition(this->GenerateDataSet<3>(l, b));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Generate helper arrays
|
||||||
|
vtkm::filter::AmrArrays amrArrays;
|
||||||
|
amrDataSet = amrArrays.Execute(amrDataSet);
|
||||||
|
|
||||||
|
return amrDataSet;
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace source
|
||||||
|
} // namespace vtkm
|
81
vtkm/source/Amr.h
Normal file
81
vtkm/source/Amr.h
Normal file
@ -0,0 +1,81 @@
|
|||||||
|
//============================================================================
|
||||||
|
// Copyright (c) Kitware, Inc.
|
||||||
|
// All rights reserved.
|
||||||
|
// See LICENSE.txt for details.
|
||||||
|
//
|
||||||
|
// This software is distributed WITHOUT ANY WARRANTY; without even
|
||||||
|
// the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||||
|
// PURPOSE. See the above copyright notice for more information.
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
#ifndef vtk_m_source_Amr_h
|
||||||
|
#define vtk_m_source_Amr_h
|
||||||
|
|
||||||
|
#include <vtkm/cont/PartitionedDataSet.h>
|
||||||
|
#include <vtkm/source/vtkm_source_export.h>
|
||||||
|
|
||||||
|
namespace vtkm
|
||||||
|
{
|
||||||
|
namespace source
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @brief The Amr source creates a dataset similar to VTK's
|
||||||
|
* vtkRTAnalyticSource.
|
||||||
|
*
|
||||||
|
* This class generates a predictable structured dataset with a smooth yet
|
||||||
|
* interesting set of scalars, which is useful for testing and benchmarking.
|
||||||
|
*
|
||||||
|
* The Execute method creates a complete structured dataset that have a
|
||||||
|
* point field names 'scalars'
|
||||||
|
*
|
||||||
|
* The scalars are computed as:
|
||||||
|
*
|
||||||
|
* ```
|
||||||
|
* MaxVal * Gauss + MagX * sin(FrqX*x) + MagY * sin(FrqY*y) + MagZ * cos(FrqZ*z)
|
||||||
|
* ```
|
||||||
|
*
|
||||||
|
* The dataset properties are determined by:
|
||||||
|
* - `Minimum/MaximumExtent`: The logical point extents of the dataset.
|
||||||
|
* - `Spacing`: The distance between points of the dataset.
|
||||||
|
* - `Center`: The center of the dataset.
|
||||||
|
*
|
||||||
|
* The scalar functions is control via:
|
||||||
|
* - `Center`: The center of a Gaussian contribution to the scalars.
|
||||||
|
* - `StandardDeviation`: The unscaled width of a Gaussian contribution.
|
||||||
|
* - `MaximumValue`: Upper limit of the scalar range.
|
||||||
|
* - `Frequency`: The Frq[XYZ] parameters of the periodic contributions.
|
||||||
|
* - `Magnitude`: The Mag[XYZ] parameters of the periodic contributions.
|
||||||
|
*
|
||||||
|
* By default, the following parameters are used:
|
||||||
|
* - `Extents`: { -10, -10, -10 } `-->` { 10, 10, 10 }
|
||||||
|
* - `Spacing`: { 1, 1, 1 }
|
||||||
|
* - `Center`: { 0, 0, 0 }
|
||||||
|
* - `StandardDeviation`: 0.5
|
||||||
|
* - `MaximumValue`: 255
|
||||||
|
* - `Frequency`: { 60, 30, 40 }
|
||||||
|
* - `Magnitude`: { 10, 18, 5 }
|
||||||
|
*/
|
||||||
|
class VTKM_SOURCE_EXPORT Amr
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
VTKM_CONT
|
||||||
|
Amr(vtkm::IdComponent dimension = 2,
|
||||||
|
vtkm::IdComponent cellsPerDimension = 6,
|
||||||
|
vtkm::IdComponent numberOfLevels = 4);
|
||||||
|
VTKM_CONT
|
||||||
|
~Amr();
|
||||||
|
|
||||||
|
vtkm::cont::PartitionedDataSet Execute() const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
vtkm::cont::DataSet GenerateDataSet(unsigned int level, unsigned int amrIndex) const;
|
||||||
|
|
||||||
|
vtkm::IdComponent Dimension;
|
||||||
|
vtkm::IdComponent CellsPerDimension;
|
||||||
|
vtkm::IdComponent NumberOfLevels;
|
||||||
|
};
|
||||||
|
} //namespace source
|
||||||
|
} //namespace vtkm
|
||||||
|
|
||||||
|
#endif //vtk_m_source_Amr_h
|
@ -9,6 +9,7 @@
|
|||||||
##============================================================================
|
##============================================================================
|
||||||
|
|
||||||
set(headers
|
set(headers
|
||||||
|
Amr.h
|
||||||
Oscillator.h
|
Oscillator.h
|
||||||
Source.h
|
Source.h
|
||||||
Tangle.h
|
Tangle.h
|
||||||
@ -17,6 +18,7 @@ set(headers
|
|||||||
)
|
)
|
||||||
|
|
||||||
set(device_sources
|
set(device_sources
|
||||||
|
Amr.cxx
|
||||||
Oscillator.cxx
|
Oscillator.cxx
|
||||||
Source.cxx
|
Source.cxx
|
||||||
Tangle.cxx
|
Tangle.cxx
|
||||||
@ -25,11 +27,12 @@ set(device_sources
|
|||||||
)
|
)
|
||||||
|
|
||||||
vtkm_library(NAME vtkm_source
|
vtkm_library(NAME vtkm_source
|
||||||
|
SOURCES ${sources}
|
||||||
DEVICE_SOURCES ${device_sources}
|
DEVICE_SOURCES ${device_sources}
|
||||||
HEADERS ${headers}
|
HEADERS ${headers}
|
||||||
)
|
)
|
||||||
|
|
||||||
target_link_libraries(vtkm_source PUBLIC vtkm_cont)
|
target_link_libraries(vtkm_source PUBLIC vtkm_cont vtkm_filter)
|
||||||
|
|
||||||
#-----------------------------------------------------------------------------
|
#-----------------------------------------------------------------------------
|
||||||
if (VTKm_ENABLE_TESTING)
|
if (VTKm_ENABLE_TESTING)
|
||||||
|
@ -98,6 +98,7 @@ struct WaveletField : public vtkm::worklet::WorkletVisitPointsWithCells
|
|||||||
|
|
||||||
Wavelet::Wavelet(vtkm::Id3 minExtent, vtkm::Id3 maxExtent)
|
Wavelet::Wavelet(vtkm::Id3 minExtent, vtkm::Id3 maxExtent)
|
||||||
: Center{ minExtent - ((minExtent - maxExtent) / 2) }
|
: Center{ minExtent - ((minExtent - maxExtent) / 2) }
|
||||||
|
, Origin{ minExtent }
|
||||||
, Spacing{ 1. }
|
, Spacing{ 1. }
|
||||||
, Frequency{ 60., 30., 40. }
|
, Frequency{ 60., 30., 40. }
|
||||||
, Magnitude{ 10., 18., 5. }
|
, Magnitude{ 10., 18., 5. }
|
||||||
@ -108,17 +109,16 @@ Wavelet::Wavelet(vtkm::Id3 minExtent, vtkm::Id3 maxExtent)
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
vtkm::cont::DataSet Wavelet::Execute() const
|
template <vtkm::IdComponent Dim>
|
||||||
|
vtkm::cont::DataSet Wavelet::GenerateDataSet(vtkm::cont::CoordinateSystem coords) const
|
||||||
{
|
{
|
||||||
VTKM_LOG_SCOPE_FUNCTION(vtkm::cont::LogLevel::Perf);
|
|
||||||
|
|
||||||
// Create points:
|
|
||||||
const vtkm::Id3 dims{ this->MaximumExtent - this->MinimumExtent + vtkm::Id3{ 1 } };
|
|
||||||
const vtkm::Vec3f origin{ this->MinimumExtent };
|
|
||||||
vtkm::cont::CoordinateSystem coords{ "coordinates", dims, origin, this->Spacing };
|
|
||||||
|
|
||||||
// And cells:
|
// And cells:
|
||||||
vtkm::cont::CellSetStructured<3> cellSet;
|
vtkm::Vec<vtkm::Id, Dim> dims;
|
||||||
|
for (unsigned int d = 0; d < Dim; d++)
|
||||||
|
{
|
||||||
|
dims[d] = this->MaximumExtent[d] - this->MinimumExtent[d] + 1;
|
||||||
|
}
|
||||||
|
vtkm::cont::CellSetStructured<Dim> cellSet;
|
||||||
cellSet.SetPointDimensions(dims);
|
cellSet.SetPointDimensions(dims);
|
||||||
|
|
||||||
// Compile the dataset:
|
// Compile the dataset:
|
||||||
@ -133,7 +133,27 @@ vtkm::cont::DataSet Wavelet::Execute() const
|
|||||||
return dataSet;
|
return dataSet;
|
||||||
}
|
}
|
||||||
|
|
||||||
vtkm::cont::Field Wavelet::GeneratePointField(const vtkm::cont::CellSetStructured<3>& cellset,
|
vtkm::cont::DataSet Wavelet::Execute() const
|
||||||
|
{
|
||||||
|
VTKM_LOG_SCOPE_FUNCTION(vtkm::cont::LogLevel::Perf);
|
||||||
|
|
||||||
|
// Create points:
|
||||||
|
const vtkm::Id3 dims{ this->MaximumExtent - this->MinimumExtent + vtkm::Id3{ 1 } };
|
||||||
|
vtkm::cont::CoordinateSystem coords{ "coordinates", dims, this->Origin, this->Spacing };
|
||||||
|
|
||||||
|
// Compile the dataset:
|
||||||
|
if (this->MaximumExtent[2] - this->MinimumExtent[2] < vtkm::Epsilon<vtkm::FloatDefault>())
|
||||||
|
{
|
||||||
|
return this->GenerateDataSet<2>(coords);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return this->GenerateDataSet<3>(coords);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
vtkm::cont::Field Wavelet::GeneratePointField(const vtkm::cont::CellSetStructured<Dim>& cellset,
|
||||||
const std::string& name) const
|
const std::string& name) const
|
||||||
{
|
{
|
||||||
const vtkm::Id3 dims{ this->MaximumExtent - this->MinimumExtent + vtkm::Id3{ 1 } };
|
const vtkm::Id3 dims{ this->MaximumExtent - this->MinimumExtent + vtkm::Id3{ 1 } };
|
||||||
|
@ -53,6 +53,8 @@ namespace source
|
|||||||
* - `MaximumValue`: 255
|
* - `MaximumValue`: 255
|
||||||
* - `Frequency`: { 60, 30, 40 }
|
* - `Frequency`: { 60, 30, 40 }
|
||||||
* - `Magnitude`: { 10, 18, 5 }
|
* - `Magnitude`: { 10, 18, 5 }
|
||||||
|
*
|
||||||
|
* If the extent has zero length in the z-direction, a 2D dataset is generated.
|
||||||
*/
|
*/
|
||||||
class VTKM_SOURCE_EXPORT Wavelet final : public vtkm::source::Source
|
class VTKM_SOURCE_EXPORT Wavelet final : public vtkm::source::Source
|
||||||
{
|
{
|
||||||
@ -62,6 +64,8 @@ public:
|
|||||||
|
|
||||||
VTKM_CONT void SetCenter(const vtkm::Vec<FloatDefault, 3>& center) { this->Center = center; }
|
VTKM_CONT void SetCenter(const vtkm::Vec<FloatDefault, 3>& center) { this->Center = center; }
|
||||||
|
|
||||||
|
VTKM_CONT void SetOrigin(const vtkm::Vec<FloatDefault, 3>& origin) { this->Origin = origin; }
|
||||||
|
|
||||||
VTKM_CONT void SetSpacing(const vtkm::Vec<FloatDefault, 3>& spacing) { this->Spacing = spacing; }
|
VTKM_CONT void SetSpacing(const vtkm::Vec<FloatDefault, 3>& spacing) { this->Spacing = spacing; }
|
||||||
|
|
||||||
VTKM_CONT void SetFrequency(const vtkm::Vec<FloatDefault, 3>& frequency)
|
VTKM_CONT void SetFrequency(const vtkm::Vec<FloatDefault, 3>& frequency)
|
||||||
@ -94,10 +98,15 @@ public:
|
|||||||
vtkm::cont::DataSet Execute() const;
|
vtkm::cont::DataSet Execute() const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
vtkm::cont::Field GeneratePointField(const vtkm::cont::CellSetStructured<3>& cellset,
|
template <vtkm::IdComponent Dim>
|
||||||
|
vtkm::cont::Field GeneratePointField(const vtkm::cont::CellSetStructured<Dim>& cellset,
|
||||||
const std::string& name) const;
|
const std::string& name) const;
|
||||||
|
|
||||||
|
template <vtkm::IdComponent Dim>
|
||||||
|
vtkm::cont::DataSet GenerateDataSet(vtkm::cont::CoordinateSystem coords) const;
|
||||||
|
|
||||||
vtkm::Vec3f Center;
|
vtkm::Vec3f Center;
|
||||||
|
vtkm::Vec3f Origin;
|
||||||
vtkm::Vec3f Spacing;
|
vtkm::Vec3f Spacing;
|
||||||
vtkm::Vec3f Frequency;
|
vtkm::Vec3f Frequency;
|
||||||
vtkm::Vec3f Magnitude;
|
vtkm::Vec3f Magnitude;
|
||||||
|
Loading…
Reference in New Issue
Block a user