https://mooseframework.inl.gov
Loading...
Searching...
No Matches
AddVariableAction.C
Go to the documentation of this file.
1//* This file is part of the MOOSE framework
2//* https://mooseframework.inl.gov
3//*
4//* All rights reserved, see COPYRIGHT for full restrictions
5//* https://github.com/idaholab/moose/blob/master/COPYRIGHT
6//*
7//* Licensed under LGPL 2.1, please see LICENSE for details
8//* https://www.gnu.org/licenses/lgpl-2.1.html
9
10// MOOSE includes
11#include "AddVariableAction.h"
12#include "FEProblem.h"
13#include "Factory.h"
14#include "MooseEnum.h"
15#include "MooseEigenSystem.h"
16#include "MooseObjectAction.h"
17#include "MooseMesh.h"
18#include "CopyNodalVarsAction.h"
19
20#include "libmesh/string_to_enum.h"
21#include "libmesh/fe_interface.h"
22
23registerMooseAction("MooseApp", AddVariableAction, "add_variable");
24
27{
28 auto params = MooseObjectAction::validParams();
29 params.addClassDescription("Add a non-linear variable to the simulation.");
30
31 // The user may specify a type in the Variables block, but if they don't we'll just use all the
32 // parameters available from MooseVariableBase
33 params.set<std::string>("type") = "MooseVariableBase";
34
35 // The below is for backwards compatibility
36 params.addParam<MooseEnum>("family",
38 "Specifies the family of FE shape functions to use for this variable");
39 params.addParam<MooseEnum>("order",
41 "Specifies the order of the FE shape function to use for this "
42 "variable (additional orders not listed are allowed)");
43 params.addParam<std::vector<Real>>("scaling",
44 "Specifies a scaling factor to apply to this variable");
45 params.addParam<std::vector<Real>>("initial_condition",
46 "Specifies a constant initial condition for this variable");
47 params.transferParam<std::string>(CopyNodalVarsAction::validParams(), "initial_from_file_var");
48 return params;
49}
50
52 : MooseObjectAction(params),
53 _fe_type(feType(params)),
54 _scalar_var(_fe_type.family == SCALAR),
55 _fv_var(false),
56 _components(1)
57{
58}
59
62{
63 return MooseEnum("LAGRANGE MONOMIAL HERMITE SCALAR HIERARCHIC CLOUGH XYZ SZABAB BERNSTEIN "
64 "L2_LAGRANGE L2_HIERARCHIC NEDELEC_ONE LAGRANGE_VEC MONOMIAL_VEC "
65 "RAVIART_THOMAS RATIONAL_BERNSTEIN SIDE_HIERARCHIC L2_HIERARCHIC_VEC "
66 "L2_LAGRANGE_VEC L2_RAVIART_THOMAS",
67 "LAGRANGE");
68}
69
72{
73 return MooseEnum(
74 "CONSTANT FIRST SECOND THIRD FOURTH FIFTH SIXTH SEVENTH EIGHTH NINTH TENTH ELEVENTH TWELFTH "
75 "THIRTEENTH FOURTEENTH FIFTEENTH SIXTEENTH SEVENTEENTH EIGHTTEENTH NINETEENTH TWENTIETH "
76 "TWENTYFIRST TWENTYSECOND TWENTYTHIRD TWENTYFOURTH TWENTYFIFTH TWENTYSIXTH TWENTYSEVENTH "
77 "TWENTYEIGHTH TWENTYNINTH THIRTIETH THIRTYFIRST THIRTYSECOND THIRTYTHIRD THIRTYFOURTH "
78 "THIRTYFIFTH THIRTYSIXTH THIRTYSEVENTH THIRTYEIGHTH THIRTYNINTH FORTIETH FORTYFIRST "
79 "FORTYSECOND FORTYTHIRD",
80 "FIRST",
81 true);
82}
83
84FEType
86{
87 return {Utility::string_to_enum<Order>(params.get<MooseEnum>("order")),
88 Utility::string_to_enum<FEFamily>(params.get<MooseEnum>("family"))};
89}
90
91void
93{
94 _components = _moose_object_pars.get<unsigned int>("components");
95 if (_components == 0)
96 mooseError("There must be at least one variable component, but somehow 0 has been specified");
97
98 // We have to do some sanity checks because of our work to maintain backwards compatibility.
99 // `family`, `order`, and `scaling` are all parameters duplicated between this action and the
100 // `MooseVariable*` object itself. Consequently during input file parsing, the params objects for
101 // both the action and MooseVariable object can be populated with the exact same parameters.
102 // However, some applications actually create their variables solely through creation and setting
103 // of `AddVariableAction` parameters which means that the `MooseVariableBase*` params will never
104 // be populated. So we should apply the parameters directly from the action. There should be no
105 // case in which both params objects get set by the user and they have different values
106
107 if (isParamSetByUser("family") && _moose_object_pars.isParamSetByUser("family") &&
108 !getParam<MooseEnum>("family").compareCurrent(_moose_object_pars.get<MooseEnum>("family")))
109 mooseError("Both the MooseVariable* and Add*VariableAction parameters objects have had the "
110 "`family` parameter set, and they are different values: ",
112 " and ",
113 getParam<MooseEnum>("family"),
114 " respectively. I don't know how you achieved this, but you need to rectify it.");
115
116 if (isParamSetByUser("order") && _moose_object_pars.isParamSetByUser("order") &&
117 !getParam<MooseEnum>("order").compareCurrent(_moose_object_pars.get<MooseEnum>("order")))
118 mooseError("Both the MooseVariable* and Add*VariableAction parameters objects have had the "
119 "`order` parameter set, and they are different values: ",
121 " and ",
122 getParam<MooseEnum>("order"),
123 " respectively. I don't know how you achieved this, but you need to rectify it.");
124
125 if (isParamSetByUser("scaling") && _moose_object_pars.isParamSetByUser("scaling") &&
126 getParam<std::vector<Real>>("scaling") !=
127 _moose_object_pars.get<std::vector<Real>>("scaling"))
128 mooseError("Both the MooseVariable* and Add*VariableAction parameters objects have had the "
129 "`scaling` parameter set, and they are different values. I don't know how you "
130 "achieved this, but you need to rectify it.");
131
132 if (isParamSetByUser("initial_condition") && isParamSetByUser("initial_from_file_var"))
133 paramError("initial_condition",
134 "Two initial conditions have been provided for the variable ",
135 name(),
136 " using the 'initial_condition' and 'initial_from_file_var' parameters. Please "
137 "remove one of them.");
138
139 _moose_object_pars.applySpecificParameters(_pars, {"order", "family", "scaling"});
140
141 // Determine the MooseVariable type
142 _fv_var = _moose_object_pars.get<bool>("fv");
143 const auto is_array = _components > 1 || _moose_object_pars.get<bool>("array");
144 if (_type == "MooseVariableBase")
145 _type = variableType(_fe_type, _fv_var, is_array);
146 if (_fv_var)
147 _problem->needFV();
148
149 // Need static_cast to resolve overloads
150 _problem_add_var_method = static_cast<void (FEProblemBase::*)(
151 const std::string &, const std::string &, InputParameters &)>(&FEProblemBase::addVariable);
152}
153
154void
156{
157 // If we've been called that means that current_task == "add_variable"
158 init();
159
160 // Get necessary data for creating a variable
161 const auto var_name = varName();
162 addVariable(var_name);
163
164 // Set the initial condition
165 if (isParamValid("initial_condition"))
166 {
167 const auto & value = getParam<std::vector<Real>>("initial_condition");
169 }
170}
171
172void
174{
175 // Variable name
176 const auto var_name = varName();
177
178 // Create the object name
179 std::string long_name("");
180 long_name += var_name;
181 long_name += "_moose";
182
183 // Set the parameters for the action
184 InputParameters action_params = _action_factory.getValidParams("AddOutputAction");
185 action_params.set<ActionWarehouse *>("awh") = &_awh;
186
187 // Associate all action and initial condition errors with "initial_condition"
188 associateWithParameter("initial_condition", action_params);
189
190 const auto fe_field_type = FEInterface::field_type(_fe_type);
191 const bool is_vector = fe_field_type == libMesh::TYPE_VECTOR;
192 const auto is_array = _components > 1 || _moose_object_pars.get<bool>("array");
193
194 if (_scalar_var)
195 action_params.set<std::string>("type") = "ScalarConstantIC";
196 else if (!is_array)
197 {
198 if (is_vector)
199 action_params.set<std::string>("type") = "VectorConstantIC";
200 else
201 {
202 if (_fv_var)
203 action_params.set<std::string>("type") = "FVConstantIC";
204 else
205 action_params.set<std::string>("type") = "ConstantIC";
206 }
207 }
208 else
209 {
210 action_params.set<std::string>("type") = "ArrayConstantIC";
211 if (value.size() != _components)
212 mooseError("Size of 'initial_condition' is not consistent");
213 }
214
215 // Create the action
216 std::shared_ptr<MooseObjectAction> action;
217 if (_fv_var)
218 action = std::static_pointer_cast<MooseObjectAction>(
219 _action_factory.create("AddFVInitialConditionAction", long_name, action_params));
220 else
221 action = std::static_pointer_cast<MooseObjectAction>(
222 _action_factory.create("AddInitialConditionAction", long_name, action_params));
223
224 // Set the required parameters for the object to be created
225 action->getObjectParams().set<VariableName>("variable") = var_name;
226 if (is_array)
227 {
228 RealEigenVector v(_components);
229 for (unsigned int i = 0; i < _components; ++i)
230 v(i) = value[i];
231 action->getObjectParams().set<RealEigenVector>("value") = v;
232 }
233 else if (is_vector)
234 {
235 action->getObjectParams().set<Real>("x_value") = value[0];
236 if (value.size() > 0)
237 action->getObjectParams().set<Real>("y_value") = value[1];
238 if (value.size() > 1)
239 action->getObjectParams().set<Real>("z_value") = value[2];
240 }
241 else
242 action->getObjectParams().set<Real>("value") = value[0];
243
244 // Store the action in the ActionWarehouse
245 _awh.addActionBlock(action);
246}
247
248std::string
249AddVariableAction::determineType(const FEType & fe_type, unsigned int components, bool is_fv)
250{
251 ::mooseDeprecated("AddVariableAction::determineType() is deprecated. Use "
252 "AddVariableAction::variableType() instead.");
253 return variableType(fe_type, is_fv, components > 1);
254}
255
256std::string
257AddVariableAction::variableType(const FEType & fe_type, const bool is_fv, const bool is_array)
258{
259 if (is_fv)
260 return "MooseVariableFVReal";
261
262 const auto fe_field_type = FEInterface::field_type(fe_type);
263
264 if (is_array)
265 {
266 if (fe_field_type == libMesh::TYPE_VECTOR)
267 ::mooseError("Vector finite element families do not currently have ArrayVariable support");
268 else
269 return "ArrayMooseVariable";
270 }
271 else if (fe_type == FEType(0, MONOMIAL))
272 return "MooseVariableConstMonomial";
273 else if (fe_type.family == SCALAR)
274 return "MooseVariableScalar";
275 else if (fe_field_type == libMesh::TYPE_VECTOR)
276 return "VectorMooseVariable";
277 else
278 return "MooseVariable";
279}
280
281void
282AddVariableAction::addVariable(const std::string & var_name)
283{
284 // Compare sizes of scaling_factor and components for Array Variables
285 const auto & scale_factor = _moose_object_pars.isParamValid("scaling")
286 ? _moose_object_pars.get<std::vector<Real>>("scaling")
287 : std::vector<Real>(_components, 1);
288 if (scale_factor.size() != _components)
289 mooseError("Size of 'scaling' is not consistent");
290
292
293 if (_moose_object_pars.get<bool>("eigen"))
294 {
295 // MooseEigenSystem will be eventually removed. NonlinearEigenSystem will be used intead.
296 // It is legal for NonlinearEigenSystem to specify a variable as eigen in input file,
297 // but we do not need to do anything here.
298 MooseEigenSystem * esys =
299 dynamic_cast<MooseEigenSystem *>(&_problem->getNonlinearSystemBase(/*nl_sys=*/0));
300 if (esys)
301 esys->markEigenVariable(var_name);
302 }
303}
304
305std::set<SubdomainID>
307{
308 // Extract and return the block ids supplied in the input
309 std::set<SubdomainID> blocks;
310 std::vector<SubdomainName> block_param =
311 _moose_object_pars.get<std::vector<SubdomainName>>("block");
312 for (const auto & subdomain_name : block_param)
313 {
314 SubdomainID blk_id = _problem->mesh().getSubdomainID(subdomain_name);
315 blocks.insert(blk_id);
316 }
317 return blocks;
318}
registerMooseAction("MooseApp", AddVariableAction, "add_variable")
subdomain_id_type SubdomainID
char ** blocks
std::shared_ptr< Action > create(const std::string &action, const std::string &action_name, InputParameters &parameters)
InputParameters getValidParams(const std::string &name)
Storage for action instances.
void addActionBlock(std::shared_ptr< Action > blk)
This method add an Action instance to the warehouse.
void associateWithParameter(const std::string &param_name, InputParameters &params) const
Associates the object's parameters params with the input location from this Action's parameter with t...
Definition Action.C:170
std::shared_ptr< FEProblemBase > & _problem
Convenience reference to a problem this action works on.
Definition Action.h:178
ActionWarehouse & _awh
Reference to ActionWarehouse where we store object build by actions.
Definition Action.h:169
Adds nonlinear variable.
virtual void act() override
Method to add objects to the simulation or perform other setup tasks.
void createInitialConditionAction(const std::vector< Real > &value)
Create the action to generate the InitialCondition object.
static MooseEnum getNonlinearVariableFamilies()
Get the possible variable families.
std::function< void(FEProblemBase &, const std::string &, const std::string &, InputParameters &)> _problem_add_var_method
libMesh::FEType _fe_type
FEType for the variable being created.
static libMesh::FEType feType(const InputParameters &params)
determine the FEType by examining family and order in the provided parameters
static MooseEnum getNonlinearVariableOrders()
Get the possible variable orders.
AddVariableAction(const InputParameters &params)
static std::string determineType(const libMesh::FEType &fe_type, unsigned int components, bool is_fv=false)
DEPRECATED: Use variableType instead.
static std::string variableType(const libMesh::FEType &fe_type, const bool is_fv=false, const bool is_array=false)
Determines a variable type.
unsigned int _components
Number of components for an array variable.
virtual std::string varName() const
Return the name of the nonlinear variable to be created.
std::set< SubdomainID > getSubdomainIDs()
Get the block ids from the input parameters.
bool _fv_var
True if the variable being created is finite volume.
static InputParameters validParams()
bool _scalar_var
True if the variable being created is a scalar.
virtual void init()
Initialize the action's member variables.
void addVariable(const std::string &var_name)
Adds a nonlinear variable to the system.
static InputParameters validParams()
Specialization of SubProblem for solving nonlinear equations plus auxiliary equations.
virtual void addVariable(const std::string &var_type, const std::string &var_name, InputParameters &params)
Canonical method for adding a non-linear variable.
The main MOOSE class responsible for handling user-defined parameters in almost every MOOSE system.
void applySpecificParameters(const InputParameters &common, const std::vector< std::string > &include, bool allow_private=false)
Method for applying common parameters.
bool isParamSetByUser(const std::string &name) const
Method returns true if the parameter was set by the user.
std::vector< std::pair< R1, R2 > > get(const std::string &param1, const std::string &param2) const
Combine two vector parameters into a single vector of pairs.
T & set(const std::string &name, bool quiet_mode=false)
Returns a writable reference to the named parameters.
bool isParamValid(const std::string &name) const
This method returns parameters that have been initialized in one fashion or another,...
const std::string & name() const
Get the name of the class.
Definition MooseBase.h:103
void paramError(const std::string &param, Args... args) const
Emits an error prefixed with the file and line number of the given param (from the input file) along ...
Definition MooseBase.h:457
bool isParamSetByUser(const std::string &name) const
Test if the supplied parameter is set by a user, as opposed to not set or set to default.
Definition MooseBase.h:205
void mooseError(Args &&... args) const
Emits an error prefixed with object name and type and optionally a file path to the top-level block p...
Definition MooseBase.h:271
const InputParameters & _pars
The object's parameters.
Definition MooseBase.h:384
const T & getParam(const std::string &name) const
Retrieve a parameter for the object.
Definition MooseBase.h:406
bool isParamValid(const std::string &name) const
Test if the supplied parameter is valid.
Definition MooseBase.h:199
virtual void markEigenVariable(const VariableName &var_name)
Mark a variable as a variable of the eigen system.
This is a "smart" enum class intended to replace many of the shortcomings in the C++ enum type It sho...
Definition MooseEnum.h:55
InputParameters _moose_object_pars
The parameters for the object to be created.
static InputParameters validParams()
std::string _type
The Object type that is being created.
ActionFactory & _action_factory
Builds Actions.
void mooseDeprecated(Args &&... args) const