Skip to content

Commit

Permalink
Add converter to go from functors to regular material properties
Browse files Browse the repository at this point in the history
  • Loading branch information
GiudGiud authored and tanoret committed Jul 10, 2023
1 parent 200aac8 commit 87daeed
Show file tree
Hide file tree
Showing 3 changed files with 142 additions and 0 deletions.
10 changes: 10 additions & 0 deletions framework/doc/content/source/materials/MaterialFunctorConverter.md
@@ -0,0 +1,10 @@
# MaterialFunctorConverter

The `MaterialFunctorConverter` is used to explicitly convert functors, such as [functor material properties](syntax/FunctorMaterials/index.md)
into regular nonAD or AD material properties.

!syntax parameters /Materials/MaterialFunctorConverter

!syntax inputs /Materials/MaterialFunctorConverter

!syntax children /Materials/MaterialFunctorConverter
41 changes: 41 additions & 0 deletions framework/include/materials/MaterialFunctorConverter.h
@@ -0,0 +1,41 @@
//* This file is part of the MOOSE framework
//* https://www.mooseframework.org
//*
//* All rights reserved, see COPYRIGHT for full restrictions
//* https://github.com/idaholab/moose/blob/master/COPYRIGHT
//*
//* Licensed under LGPL 2.1, please see LICENSE for details
//* https://www.gnu.org/licenses/lgpl-2.1.html

#pragma once

#include "Material.h"

/**
* This material converts functor to regular (AD or not) material properties
*/
template <typename T>
class MaterialFunctorConverterTempl : public Material
{
public:
static InputParameters validParams();

MaterialFunctorConverterTempl(const InputParameters & parameters);

protected:
virtual void computeQpProperties() override;
void initQpStatefulProperties() override;

/// Number of material properties to create
const std::size_t _num_functors_to_convert;

/// Incoming functors to convert
std::vector<const Moose::Functor<Moose::GenericType<T, true>> *> _functors_in;
/// Regular material properties to create
std::vector<MaterialProperty<T> *> _reg_props_out;
/// AD material properties to create
std::vector<ADMaterialProperty<T> *> _ad_props_out;
};

typedef MaterialFunctorConverterTempl<Real> MaterialFunctorConverter;
typedef MaterialFunctorConverterTempl<RealVectorValue> VectorMaterialFunctorConverter;
91 changes: 91 additions & 0 deletions framework/src/materials/MaterialFunctorConverter.C
@@ -0,0 +1,91 @@
//* This file is part of the MOOSE framework
//* https://www.mooseframework.org
//*
//* All rights reserved, see COPYRIGHT for full restrictions
//* https://github.com/idaholab/moose/blob/master/COPYRIGHT
//*
//* Licensed under LGPL 2.1, please see LICENSE for details
//* https://www.gnu.org/licenses/lgpl-2.1.html

#include "MaterialFunctorConverter.h"

#include "metaphysicl/raw_type.h"

registerMooseObject("MooseApp", MaterialFunctorConverter);
registerMooseObject("MooseApp", VectorMaterialFunctorConverter);

template <typename T>
InputParameters
MaterialFunctorConverterTempl<T>::validParams()
{
InputParameters params = Material::validParams();
params.addClassDescription("Converts functor to nonAD and AD regular material properties");
params.addParam<std::vector<MooseFunctorName>>(
"functors_in", "The names of the functors to convert to AD properties");
params.addParam<std::vector<MaterialPropertyName>>("ad_props_out",
"The names of the output AD properties");
params.addParam<std::vector<MaterialPropertyName>>("reg_props_out",
"The names of the output regular properties");
return params;
}

template <typename T>
MaterialFunctorConverterTempl<T>::MaterialFunctorConverterTempl(const InputParameters & parameters)
: Material(parameters),
_num_functors_to_convert(getParam<std::vector<MooseFunctorName>>("functors_in").size())
{
auto functors_in = getParam<std::vector<MooseFunctorName>>("functors_in");
auto reg_props_out = getParam<std::vector<MaterialPropertyName>>("reg_props_out");
auto ad_props_out = getParam<std::vector<MaterialPropertyName>>("ad_props_out");

if (isParamValid("reg_props_out") && isParamValid("ad_props_out"))
paramError("reg_props_out",
"We dont support converting functors to both AD and regular material properties. "
"Please use another " +
type() + " to convert to both types.");

if (functors_in.size() != reg_props_out.size() && functors_in.size() != ad_props_out.size())
paramError(
"functors_in",
"The number of output properties must match the number of input functors, which is " +
std::to_string(functors_in.size()));

_functors_in.resize(_num_functors_to_convert);
_ad_props_out.resize(ad_props_out.size());
_reg_props_out.resize(reg_props_out.size());

for (const auto i : make_range(_num_functors_to_convert))
_functors_in[i] = &getFunctor<Moose::GenericType<T, true>>(functors_in[i]);

for (const auto i : index_range(ad_props_out))
_ad_props_out[i] = &declareADProperty<T>(ad_props_out[i]);

for (const auto i : index_range(reg_props_out))
_reg_props_out[i] = &declareProperty<T>(reg_props_out[i]);
}

template <typename T>
void
MaterialFunctorConverterTempl<T>::initQpStatefulProperties()
{
computeQpProperties();
}

template <typename T>
void
MaterialFunctorConverterTempl<T>::computeQpProperties()
{
// TODO: do we know when we are on a face or an element?
const Moose::ElemQpArg arg = {_current_elem, _qp, _qrule};
mooseAssert(_current_elem, "We must know where we are");
mooseAssert(_qrule, "We must know the quadrature");
const auto state = Moose::currentState();
for (const auto i : index_range(_ad_props_out))
(*_ad_props_out[i])[_qp] = (*_functors_in[i])(arg, state);

for (const auto i : index_range(_reg_props_out))
(*_reg_props_out[i])[_qp] = MetaPhysicL::raw_value((*_functors_in[i])(arg, state));
}

template class MaterialFunctorConverterTempl<Real>;
template class MaterialFunctorConverterTempl<RealVectorValue>;

0 comments on commit 87daeed

Please sign in to comment.