Commit 4c781374 authored by Abhishek Yenpure's avatar Abhishek Yenpure
Browse files

Removing virtuals v1

-- Remove virtuals from Integrators, Fields, Particles
-- Remaining virtuals are in the CellInterpolationHelpers
parent 91d13bdf
......@@ -25,9 +25,9 @@
#include <vtkm/worklet/WorkletMapField.h>
#include <vtkm/worklet/particleadvection/Field.h>
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
#include <vtkm/worklet/particleadvection/Particles.h>
#include <vtkm/worklet/particleadvection/RK4Integrator.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
#include <cstring>
#include <sstream>
......@@ -279,12 +279,14 @@ inline VTKM_CONT vtkm::cont::DataSet Lagrangian::DoExecute(
using FieldType = vtkm::worklet::particleadvection::VelocityField<FieldHandle>;
using GridEvalType = vtkm::worklet::particleadvection::GridEvaluator<FieldType>;
using RK4Type = vtkm::worklet::particleadvection::RK4Integrator<GridEvalType>;
using Stepper = vtkm::worklet::particleadvection::Stepper<RK4Type, GridEvalType>;
vtkm::worklet::ParticleAdvection particleadvection;
vtkm::worklet::ParticleAdvectionResult<vtkm::Particle> res;
FieldType velocities(field);
GridEvalType gridEval(coords, cells, velocities);
RK4Type rk4(gridEval, static_cast<vtkm::Float32>(this->stepSize));
Stepper rk4(gridEval, static_cast<vtkm::Float32>(this->stepSize));
res = particleadvection.Run(rk4, basisParticleArray, 1); // Taking a single step
auto particles = res.Particles;
......
......@@ -17,7 +17,7 @@
#include <vtkm/worklet/ParticleAdvection.h>
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
namespace vtkm
{
......
......@@ -16,9 +16,9 @@
#include <vtkm/cont/Invoker.h>
#include <vtkm/worklet/particleadvection/Field.h>
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
#include <vtkm/worklet/particleadvection/Particles.h>
#include <vtkm/worklet/particleadvection/RK4Integrator.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
#include <vtkm/worklet/LagrangianStructures.h>
......@@ -86,7 +86,8 @@ inline VTKM_CONT vtkm::cont::DataSet LagrangianStructures::DoExecute(
using FieldHandle = vtkm::cont::ArrayHandle<vtkm::Vec<T, 3>, StorageType>;
using FieldType = vtkm::worklet::particleadvection::VelocityField<FieldHandle>;
using GridEvaluator = vtkm::worklet::particleadvection::GridEvaluator<FieldType>;
using Integrator = vtkm::worklet::particleadvection::RK4Integrator<GridEvaluator>;
using IntegratorType = vtkm::worklet::particleadvection::RK4Integrator<GridEvaluator>;
using Stepper = vtkm::worklet::particleadvection::Stepper<IntegratorType, GridEvaluator>;
vtkm::FloatDefault stepSize = this->GetStepSize();
vtkm::Id numberOfSteps = this->GetNumberOfSteps();
......@@ -138,7 +139,7 @@ inline VTKM_CONT vtkm::cont::DataSet LagrangianStructures::DoExecute(
FieldType velocities(field);
GridEvaluator evaluator(input.GetCoordinateSystem(), input.GetCellSet(), velocities);
Integrator integrator(evaluator, stepSize);
Stepper integrator(evaluator, stepSize);
vtkm::worklet::ParticleAdvection particles;
vtkm::worklet::ParticleAdvectionResult<vtkm::Particle> advectionResult;
vtkm::cont::ArrayHandle<vtkm::Particle> advectionPoints;
......
......@@ -14,7 +14,7 @@
#include <vtkm/filter/FilterDataSetWithField.h>
#include <vtkm/worklet/ParticleAdvection.h>
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
namespace vtkm
{
......
......@@ -15,7 +15,7 @@
#include <vtkm/worklet/ParticleAdvection.h>
#include <vtkm/worklet/StreamSurface.h>
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
namespace vtkm
{
......
......@@ -21,6 +21,7 @@
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/Particles.h>
#include <vtkm/worklet/particleadvection/RK4Integrator.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
namespace vtkm
{
......@@ -57,11 +58,12 @@ inline VTKM_CONT vtkm::cont::DataSet StreamSurface::DoExecute(
using FieldType = vtkm::worklet::particleadvection::VelocityField<FieldHandle>;
using GridEvalType = vtkm::worklet::particleadvection::GridEvaluator<FieldType>;
using RK4Type = vtkm::worklet::particleadvection::RK4Integrator<GridEvalType>;
using Stepper = vtkm::worklet::particleadvection::Stepper<RK4Type, GridEvalType>;
//compute streamlines
FieldType velocities(field);
GridEvalType eval(coords, cells, velocities);
RK4Type rk4(eval, this->StepSize);
Stepper rk4(eval, this->StepSize);
vtkm::worklet::Streamline streamline;
......
......@@ -15,6 +15,7 @@
#include <vtkm/cont/DataSet.h>
#include <vtkm/worklet/ParticleAdvection.h>
#include <vtkm/worklet/particleadvection/RK4Integrator.h>
#include <vtkm/worklet/particleadvection/Stepper.h>
#include <vtkm/worklet/particleadvection/TemporalGridEvaluators.h>
#include <memory>
......@@ -51,17 +52,18 @@ public:
{
auto copyFlag = (this->CopySeedArray ? vtkm::CopyFlag::On : vtkm::CopyFlag::Off);
auto seedArray = vtkm::cont::make_ArrayHandle(v, copyFlag);
RK4Type rk4(*this->Eval, stepSize);
Stepper rk4(*this->Eval, stepSize);
this->DoAdvect(seedArray, rk4, maxSteps, result);
}
protected:
using RK4Type = vtkm::worklet::particleadvection::RK4Integrator<GridEvalType>;
using Stepper = vtkm::worklet::particleadvection::Stepper<RK4Type, GridEvalType>;
using FieldHandleType = vtkm::cont::ArrayHandle<vtkm::Vec3f>;
template <typename ResultType>
inline void DoAdvect(vtkm::cont::ArrayHandle<vtkm::Particle>& seeds,
const RK4Type& rk4,
const Stepper& rk4,
vtkm::Id maxSteps,
ResultType& result) const;
......
......@@ -23,7 +23,10 @@ using GridEvalType = vtkm::worklet::particleadvection::GridEvaluator<
using TemporalGridEvalType = vtkm::worklet::particleadvection::TemporalGridEvaluator<
vtkm::worklet::particleadvection::VelocityField<vtkm::cont::ArrayHandle<vtkm::Vec3f>>>;
using RK4Type = vtkm::worklet::particleadvection::RK4Integrator<GridEvalType>;
using Stepper = vtkm::worklet::particleadvection::Stepper<RK4Type, GridEvalType>;
using TemporalRK4Type = vtkm::worklet::particleadvection::RK4Integrator<TemporalGridEvalType>;
using TemporalStepper =
vtkm::worklet::particleadvection::Stepper<TemporalRK4Type, TemporalGridEvalType>;
//-----
// Specialization for ParticleAdvection worklet
......@@ -31,7 +34,7 @@ template <>
template <>
inline void DataSetIntegratorBase<GridEvalType>::DoAdvect(
vtkm::cont::ArrayHandle<vtkm::Particle>& seeds,
const RK4Type& rk4,
const Stepper& rk4,
vtkm::Id maxSteps,
vtkm::worklet::ParticleAdvectionResult<vtkm::Particle>& result) const
{
......@@ -45,7 +48,7 @@ template <>
template <>
inline void DataSetIntegratorBase<GridEvalType>::DoAdvect(
vtkm::cont::ArrayHandle<vtkm::Particle>& seeds,
const RK4Type& rk4,
const Stepper& rk4,
vtkm::Id maxSteps,
vtkm::worklet::StreamlineResult<vtkm::Particle>& result) const
{
......@@ -59,7 +62,7 @@ template <>
template <>
inline void DataSetIntegratorBase<TemporalGridEvalType>::DoAdvect(
vtkm::cont::ArrayHandle<vtkm::Particle>& seeds,
const TemporalRK4Type& rk4,
const TemporalStepper& rk4,
vtkm::Id maxSteps,
vtkm::worklet::StreamlineResult<vtkm::Particle>& result) const
{
......
......@@ -14,7 +14,7 @@ set(headers
Field.h
GridEvaluators.h
GridEvaluatorStatus.h
IntegratorBase.h
Stepper.h
IntegratorStatus.h
Particles.h
ParticleAdvectionWorklets.h
......
......@@ -13,8 +13,6 @@
#ifndef vtk_m_worklet_particleadvection_EulerIntegrator_h
#define vtk_m_worklet_particleadvection_EulerIntegrator_h
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
namespace vtkm
{
namespace worklet
......@@ -22,73 +20,56 @@ namespace worklet
namespace particleadvection
{
template <typename FieldEvaluateType>
class EulerIntegrator : public IntegratorBase
template <typename EvaluatorType>
class ExecEulerIntegrator
{
public:
EulerIntegrator() = default;
VTKM_CONT
EulerIntegrator(const FieldEvaluateType& evaluator, const vtkm::FloatDefault stepLength)
: IntegratorBase(stepLength)
, Evaluator(evaluator)
VTKM_EXEC_CONT
ExecEulerIntegrator(const EvaluatorType& evaluator)
: Evaluator(evaluator)
{
}
template <typename Device>
class ExecObject
: public IntegratorBase::ExecObjectBaseImpl<
vtkm::cont::internal::ExecutionObjectType<FieldEvaluateType, Device>,
typename EulerIntegrator::template ExecObject<Device>>
template <typename Particle>
VTKM_EXEC IntegratorStatus CheckStep(Particle& particle,
vtkm::FloatDefault stepLength,
vtkm::Vec3f& velocity) const
{
VTKM_IS_DEVICE_ADAPTER_TAG(Device);
auto time = particle.Time;
auto inpos = particle.Pos;
vtkm::VecVariable<vtkm::Vec3f, 2> vectors;
GridEvaluatorStatus status = this->Evaluator.Evaluate(inpos, time, vectors);
if (status.CheckOk())
velocity = particle.Velocity(vectors, stepLength);
return IntegratorStatus(status);
}
using FieldEvaluateExecType =
vtkm::cont::internal::ExecutionObjectType<FieldEvaluateType, Device>;
using Superclass =
IntegratorBase::ExecObjectBaseImpl<FieldEvaluateExecType,
typename EulerIntegrator::template ExecObject<Device>>;
private:
EvaluatorType Evaluator;
};
public:
VTKM_EXEC_CONT
ExecObject(const FieldEvaluateExecType& evaluator,
vtkm::FloatDefault stepLength,
vtkm::FloatDefault tolerance)
: Superclass(evaluator, stepLength, tolerance)
{
}
template <typename EvaluatorType>
class EulerIntegrator
{
private:
EvaluatorType Evaluator;
VTKM_EXEC
IntegratorStatus CheckStep(vtkm::Particle* particle,
vtkm::FloatDefault stepLength,
vtkm::Vec3f& velocity) const
{
auto time = particle->Time;
auto inpos = particle->Pos;
vtkm::VecVariable<vtkm::Vec3f, 2> vectors;
GridEvaluatorStatus status = this->Evaluator.Evaluate(inpos, time, vectors);
if (status.CheckOk())
velocity = particle->Velocity(vectors, stepLength);
return IntegratorStatus(status);
}
};
public:
EulerIntegrator() = default;
private:
FieldEvaluateType Evaluator;
VTKM_CONT
EulerIntegrator(const EvaluatorType& evaluator)
: Evaluator(evaluator)
{
}
protected:
VTKM_CONT virtual void PrepareForExecutionImpl(
vtkm::cont::DeviceAdapterId device,
vtkm::cont::VirtualObjectHandle<IntegratorBase::ExecObject>& execObjectHandle,
vtkm::cont::Token& token) const override
VTKM_CONT auto PrepareForExecution(vtkm::cont::DeviceAdapterId device,
vtkm::cont::Token& token) const
-> ExecEulerIntegrator<decltype(this->Evaluator.PrepareForExecution(device, token))>
{
vtkm::cont::TryExecuteOnDevice(device,
detail::IntegratorPrepareForExecutionFunctor<ExecObject>(),
execObjectHandle,
this->Evaluator,
this->StepLength,
this->Tolerance,
token);
auto evaluator = this->Evaluator.PrepareForExecution(device, token);
using ExecEvaluatorType = decltype(evaluator);
return ExecEulerIntegrator<ExecEvaluatorType>(evaluator);
}
}; //EulerIntegrator
......
......@@ -26,22 +26,8 @@ namespace worklet
namespace particleadvection
{
class ExecutionField : public vtkm::VirtualObjectBase
{
public:
VTKM_EXEC_CONT
virtual ~ExecutionField() noexcept override {}
VTKM_EXEC
virtual void GetValue(const vtkm::VecVariable<vtkm::Id, 8>& indices,
const vtkm::Id vertices,
const vtkm::Vec3f& parametric,
const vtkm::UInt8 cellShape,
vtkm::VecVariable<vtkm::Vec3f, 2>& value) const = 0;
};
template <typename FieldArrayType>
class ExecutionVelocityField : public vtkm::worklet::particleadvection::ExecutionField
class ExecutionVelocityField
{
public:
using FieldPortalType = typename FieldArrayType::ReadPortalType;
......@@ -73,7 +59,7 @@ private:
};
template <typename FieldArrayType>
class ExecutionElectroMagneticField : public vtkm::worklet::particleadvection::ExecutionField
class ExecutionElectroMagneticField
{
public:
using FieldPortalType = typename FieldArrayType::ReadPortalType;
......@@ -112,22 +98,15 @@ private:
FieldPortalType MagneticValues;
};
class Field : public vtkm::cont::ExecutionObjectBase
template <typename FieldArrayType>
class VelocityField : public vtkm::cont::ExecutionObjectBase
{
public:
using HandleType = vtkm::cont::VirtualObjectHandle<ExecutionField>;
virtual ~Field() = default;
using ExecutionType = ExecutionVelocityField<FieldArrayType>;
VTKM_CONT
virtual const ExecutionField* PrepareForExecution(vtkm::cont::DeviceAdapterId deviceId,
vtkm::cont::Token& token) const = 0;
};
VelocityField() = default;
template <typename FieldArrayType>
class VelocityField : public vtkm::worklet::particleadvection::Field
{
public:
VTKM_CONT
VelocityField(const FieldArrayType& fieldValues)
: FieldValues(fieldValues)
......@@ -135,24 +114,25 @@ public:
}
VTKM_CONT
const ExecutionField* PrepareForExecution(vtkm::cont::DeviceAdapterId device,
vtkm::cont::Token& token) const override
const ExecutionType PrepareForExecution(vtkm::cont::DeviceAdapterId device,
vtkm::cont::Token& token) const
{
using ExecutionType = ExecutionVelocityField<FieldArrayType>;
ExecutionType* execObject = new ExecutionType(this->FieldValues, device, token);
this->ExecHandle.Reset(execObject);
return this->ExecHandle.PrepareForExecution(device, token);
return ExecutionType(this->FieldValues, device, token);
}
private:
FieldArrayType FieldValues;
mutable HandleType ExecHandle;
};
template <typename FieldArrayType>
class ElectroMagneticField : public vtkm::worklet::particleadvection::Field
class ElectroMagneticField : public vtkm::cont::ExecutionObjectBase
{
public:
using ExecutionType = ExecutionElectroMagneticField<FieldArrayType>;
VTKM_CONT
ElectroMagneticField() = default;
VTKM_CONT
ElectroMagneticField(const FieldArrayType& electricField, const FieldArrayType& magneticField)
: ElectricField(electricField)
......@@ -161,20 +141,15 @@ public:
}
VTKM_CONT
const ExecutionField* PrepareForExecution(vtkm::cont::DeviceAdapterId device,
vtkm::cont::Token& token) const override
const ExecutionType PrepareForExecution(vtkm::cont::DeviceAdapterId device,
vtkm::cont::Token& token) const
{
using ExecutionType = ExecutionElectroMagneticField<FieldArrayType>;
ExecutionType* execObject =
new ExecutionType(this->ElectricField, this->MagneticField, device, token);
this->ExecHandle.Reset(execObject);
return this->ExecHandle.PrepareForExecution(device, token);
return ExecutionType(this->ElectricField, this->MagneticField, device, token);
}
private:
FieldArrayType ElectricField;
FieldArrayType MagneticField;
mutable HandleType ExecHandle;
};
} // namespace particleadvection
......
......@@ -22,9 +22,6 @@
#include <vtkm/cont/DataSet.h>
#include <vtkm/cont/DeviceAdapter.h>
#include <vtkm/worklet/particleadvection/CellInterpolationHelper.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
namespace vtkm
{
namespace worklet
......
......@@ -26,7 +26,6 @@
#include <vtkm/worklet/particleadvection/CellInterpolationHelper.h>
#include <vtkm/worklet/particleadvection/Field.h>
#include <vtkm/worklet/particleadvection/GridEvaluatorStatus.h>
#include <vtkm/worklet/particleadvection/IntegratorBase.h>
namespace vtkm
{
......@@ -127,7 +126,7 @@ public:
vtkm::VecVariable<vtkm::Vec3f, 8> fieldValues;
InterpolationHelper->GetCellInfo(cellId, cellShape, nVerts, ptIndices);
this->Field->GetValue(ptIndices, nVerts, parametric, cellShape, out);
this->Field.GetValue(ptIndices, nVerts, parametric, cellShape, out);
status.SetOk();
}
......@@ -146,7 +145,7 @@ private:
using GhostCellPortal = typename vtkm::cont::ArrayHandle<vtkm::UInt8>::ReadPortalType;
vtkm::Bounds Bounds;
const vtkm::worklet::particleadvection::ExecutionField* Field;
typename FieldType::ExecutionType Field;
GhostCellPortal GhostCells;
bool HaveGhostCells;
const vtkm::exec::CellInterpolationHelper* InterpolationHelper;
......
//=============================================================================
//
// 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_worklet_particleadvection_IntegratorBase_h
#define vtk_m_worklet_particleadvection_IntegratorBase_h
#include <limits>
#include <vtkm/Bitset.h>
#include <vtkm/TypeTraits.h>
#include <vtkm/Types.h>
#include <vtkm/VectorAnalysis.h>
#include <vtkm/cont/DataSet.h>
#include <vtkm/cont/VirtualObjectHandle.h>
#include <vtkm/worklet/particleadvection/GridEvaluators.h>
#include <vtkm/worklet/particleadvection/IntegratorStatus.h>
#include <vtkm/worklet/particleadvection/Particles.h>
namespace vtkm
{
namespace worklet
{
namespace particleadvection
{
class IntegratorBase : public vtkm::cont::ExecutionObjectBase
{
protected:
VTKM_CONT
IntegratorBase() = default;
VTKM_CONT
IntegratorBase(vtkm::FloatDefault stepLength)
: StepLength(stepLength)
{
}
public:
class ExecObject : public vtkm::VirtualObjectBase
{
protected:
VTKM_EXEC_CONT
ExecObject(const vtkm::FloatDefault stepLength, vtkm::FloatDefault tolerance)
: StepLength(stepLength)
, Tolerance(tolerance)
{
}
public:
VTKM_EXEC
virtual IntegratorStatus Step(vtkm::Particle* inpos,
vtkm::FloatDefault& time,
vtkm::Vec3f& outpos) const = 0;
VTKM_EXEC
virtual IntegratorStatus SmallStep(vtkm::Particle* inpos,
vtkm::FloatDefault& time,
vtkm::Vec3f& outpos) const = 0;
protected:
vtkm::FloatDefault StepLength = 1.0f;
vtkm::FloatDefault Tolerance = 0.001f;
};
template <typename Device>
VTKM_CONT const ExecObject* PrepareForExecution(Device, vtkm::cont::Token& token) const
{
this->PrepareForExecutionImpl(
Device(),
const_cast<vtkm::cont::VirtualObjectHandle<ExecObject>&>(this->ExecObjectHandle),
token);
return this->ExecObjectHandle.PrepareForExecution(Device(), token);
}
private:
vtkm::cont::VirtualObjectHandle<ExecObject> ExecObjectHandle;
protected:
vtkm::FloatDefault StepLength;
vtkm::FloatDefault Tolerance =
std::numeric_limits<vtkm::FloatDefault>::epsilon() * static_cast<vtkm::FloatDefault>(100.0f);
VTKM_CONT virtual void PrepareForExecutionImpl(
vtkm::cont::DeviceAdapterId device,
vtkm::cont::VirtualObjectHandle<ExecObject>& execObjectHandle,
vtkm::cont::Token& token) const = 0;
template <typename FieldEvaluateType, typename DerivedType>
class ExecObjectBaseImpl : public ExecObject
{
protected:
VTKM_EXEC_CONT
ExecObjectBaseImpl(const FieldEvaluateType& evaluator,
vtkm::FloatDefault stepLength,
vtkm::FloatDefault tolerance)
: ExecObject(stepLength, tolerance)
, Evaluator(evaluator)
{
}
public:
VTKM_EXEC
IntegratorStatus Step(vtkm::Particle* particle,
vtkm::FloatDefault& time,
vtkm::Vec3f& outpos) const override
{
vtkm::Vec3f velocity(0, 0, 0);
auto status = this->CheckStep(particle, this->StepLength, velocity);
if (status.CheckOk())
{
outpos = particle->Pos + this->StepLength * velocity;
time += this->StepLength;
}
else
outpos = particle->Pos;
return status;
}
VTKM_EXEC
IntegratorStatus SmallStep(vtkm::Particle* particle,
vtkm::FloatDefault& time,
vtkm::Vec3f& outpos) const override
{
//Stepping by this->StepLength goes beyond the bounds of the dataset.
//We need to take an Euler step that goes outside of the dataset.