OGS
MFrontGeneric.h
Go to the documentation of this file.
1
10#pragma once
11
12#include <MGIS/Behaviour/Behaviour.hxx>
13#include <MGIS/Behaviour/BehaviourData.hxx>
14#include <MGIS/Behaviour/Integrate.hxx>
15#include <boost/mp11.hpp>
16
20#include "NumLib/Exceptions.h"
24#include "Variable.h"
25
27{
28namespace MPL = MaterialPropertyLib;
29
35template <typename Derived>
36constexpr auto eigenSwap45View(Eigen::MatrixBase<Derived> const& matrix)
37{
38 using Matrix =
39 Eigen::Matrix<typename Derived::Scalar, Derived::RowsAtCompileTime,
40 Derived::ColsAtCompileTime>;
41
42 return Matrix::NullaryExpr(
43 matrix.rows(), matrix.cols(),
44 [&m = matrix.derived()](Eigen::Index const row, Eigen::Index const col)
45 {
46 constexpr std::ptrdiff_t result[6] = {0, 1, 2, 3, 5, 4};
47 return m(result[row], result[col]);
48 });
49}
50
58template <int DisplacementDim, typename Derived>
59constexpr auto ogsTensorToMFrontTensor(Eigen::MatrixBase<Derived> const& matrix)
60{
61 using Matrix =
62 Eigen::Matrix<typename Derived::Scalar, Derived::RowsAtCompileTime,
63 Derived::ColsAtCompileTime>;
64
65 if constexpr (DisplacementDim == 2)
66 {
67 return Matrix::NullaryExpr(
68 matrix.rows(), matrix.cols(),
69 [&m = matrix.derived()](Eigen::Index const row,
70 Eigen::Index const col)
71 {
72 constexpr std::ptrdiff_t result[5] = {0, 3, 4, 1, 2};
73 return m(result[row], result[col]);
74 });
75 }
76 if constexpr (DisplacementDim == 3)
77 {
78 return Matrix::NullaryExpr(
79 matrix.rows(), matrix.cols(),
80 [&m = matrix.derived()](Eigen::Index const row,
81 Eigen::Index const col)
82 {
83 constexpr std::ptrdiff_t result[9] = {0, 4, 8, 1, 3,
84 2, 6, 5, 7};
85 return m(result[row], result[col]);
86 });
87 }
88}
89
90const char* varTypeToString(int v);
91
92int getEquivalentPlasticStrainOffset(mgis::behaviour::Behaviour const& b);
93
99template <int DisplacementDim>
100OGSMFrontTangentOperatorData tangentOperatorDataMFrontToOGS(
101 std::vector<double> const& mfront_data,
102 std::optional<
104 mgis::behaviour::Behaviour const& behaviour);
105
106extern template OGSMFrontTangentOperatorData tangentOperatorDataMFrontToOGS<2>(
107 std::vector<double> const& mfront_data,
108 std::optional<MathLib::KelvinVector::KelvinMatrixType<2>> const& Q,
109 mgis::behaviour::Behaviour const& behaviour);
110extern template OGSMFrontTangentOperatorData tangentOperatorDataMFrontToOGS<3>(
111 std::vector<double> const& mfront_data,
112 std::optional<MathLib::KelvinVector::KelvinMatrixType<3>> const& Q,
113 mgis::behaviour::Behaviour const& behaviour);
114
115// TODO template parameter only because of base class.
116template <int DisplacementDim>
119{
121 int const equivalent_plastic_strain_offset,
122 mgis::behaviour::Behaviour const& b)
123 : equivalent_plastic_strain_offset_(equivalent_plastic_strain_offset),
124 _behaviour_data{b}
125 {
126 }
127
132
133 void pushBackState() override { mgis::behaviour::update(_behaviour_data); }
134
136 mgis::behaviour::BehaviourData _behaviour_data;
137
138 double getEquivalentPlasticStrain() const override
139 {
140 if (equivalent_plastic_strain_offset_ >= 0)
141 {
142 return _behaviour_data.s1
143 .internal_state_variables[static_cast<mgis::size_type>(
144 equivalent_plastic_strain_offset_)];
145 }
146
147 return 0.0;
148 }
149};
150
151namespace detail
152{
154template <int DisplacementDim, mgis::behaviour::Variable::Type MFrontType>
156
157template <int DisplacementDim>
162
163template <int DisplacementDim>
168
169template <int DisplacementDim>
174
175template <int DisplacementDim, mgis::behaviour::Variable::Type MFrontType>
177
180template <int DisplacementDim>
182{
184 std::optional<
186 double* target;
187
188 template <typename Grad>
189 void operator()(Grad)
190 {
191 auto constexpr num_comp = Grad::template size<DisplacementDim>();
192
193 if constexpr (Grad::type == mgis::behaviour::Variable::Type::SCALAR)
194 {
195 *target = variable_array.*Grad::mpl_var;
196 }
197 else if constexpr (Grad::type ==
198 mgis::behaviour::Variable::Type::STENSOR)
199 {
201 auto const& grad_ogs =
202 std::get<MPLType>(variable_array.*Grad::mpl_var);
203
204 auto const grad_mfront =
205 Q ? eigenSwap45View(Q->transpose() * grad_ogs).eval()
206 : eigenSwap45View(grad_ogs).eval();
207 std::copy_n(grad_mfront.data(), num_comp, target);
208 }
209 else if constexpr (Grad::type ==
210 mgis::behaviour::Variable::Type::TENSOR)
211 {
213 auto const& grad_ogs =
214 std::get<MPLType>(variable_array.*Grad::mpl_var);
215
216 if (Q.has_value())
217 {
218 OGS_FATAL("Rotations of tensors are not implemented.");
219 }
220
221 Eigen::Map<Eigen::Vector<double, num_comp>>{target} =
222 ogsTensorToMFrontTensor<DisplacementDim>(grad_ogs);
223 }
224 else
225 {
226 OGS_FATAL("Unsupported gradient type {}.",
227 varTypeToString(Grad::type));
228 }
229
230 target += num_comp;
231 }
232};
233} // namespace detail
234
237template <int DisplacementDim,
238 typename Gradients,
239 typename TDynForces,
240 typename ExtStateVars>
242{
243 static_assert(boost::mp11::mp_is_set<Gradients>::value);
244 static_assert(boost::mp11::mp_is_set<TDynForces>::value);
245 static_assert(boost::mp11::mp_is_set<ExtStateVars>::value);
246
248 boost::mp11::mp_append<Gradients, ExtStateVars>;
249
250 static_assert(boost::mp11::mp_is_set<GradientsAndExtStateVars>::value);
251
252public:
259
261 mgis::behaviour::Behaviour&& behaviour,
262 std::vector<ParameterLib::Parameter<double> const*>&&
263 material_properties,
264 std::map<std::string, ParameterLib::Parameter<double> const*>&&
265 state_variables_initial_properties,
266 std::optional<ParameterLib::CoordinateSystem> const&
267 local_coordinate_system)
268 : _behaviour(std::move(behaviour)),
269 equivalent_plastic_strain_offset_(
271 _material_properties(std::move(material_properties)),
272 _state_variables_initial_properties(
273 std::move(state_variables_initial_properties)),
274 _local_coordinate_system(local_coordinate_system
275 ? &local_coordinate_system.value()
276 : nullptr)
277 {
278 {
279 auto check_gradient = [&grads = _behaviour.gradients,
280 hyp = _behaviour.hypothesis,
281 i = 0]<typename Grad>(Grad) mutable
282 {
283 // TODO allow reordering of gradients and thermodynamic forces?
284 if (grads[i].name != Grad::name)
285 {
286 OGS_FATAL(
287 "OGS expects the {}th gradient to be {} but MFront "
288 "provides {}.",
289 i, Grad::name, grads[i].name);
290 }
291
292 if (grads[i].type != Grad::type)
293 {
294 OGS_FATAL(
295 "The behaviour's {}th driver ({}) must be of type {}.",
296 i, grads[i].name, varTypeToString(Grad::type));
297 }
298
299 if (mgis::behaviour::getVariableSize(grads[i], hyp) !=
300 Grad::template size<DisplacementDim>())
301 {
302 OGS_FATAL(
303 "The behaviour's {}th driver's ({}) size in OGS is {} "
304 "but {} in MFront.",
305 i, grads[i].name,
306 Grad::template size<DisplacementDim>(),
307 mgis::behaviour::getVariableSize(grads[i], hyp));
308 }
309
310 i++;
311 };
312
313 if (_behaviour.gradients.size() !=
314 boost::mp11::mp_size<Gradients>::value)
315 OGS_FATAL(
316 "The behaviour must have exactly {} gradients as input.",
317 boost::mp11::mp_size<Gradients>::value);
318
319 boost::mp11::mp_for_each<Gradients>(check_gradient);
320 }
321
322 {
323 auto check_tdyn_force = [&tdfs = _behaviour.thermodynamic_forces,
324 hyp = _behaviour.hypothesis,
325 i = 0]<typename TDF>(TDF) mutable
326 {
327 if (tdfs[i].name != TDF::name)
328 {
329 OGS_FATAL(
330 "OGS expects the {}th thermodynamic force to be {} but "
331 "MFront provides {}.",
332 i, TDF::name, tdfs[i].name);
333 }
334
335 if (tdfs[i].type != TDF::type)
336 {
337 OGS_FATAL(
338 "The behaviour's {}th thermodynamic force ({}) must be "
339 "of type {}.",
340 i, tdfs[i].name, varTypeToString(TDF::type));
341 }
342
343 if (mgis::behaviour::getVariableSize(tdfs[i], hyp) !=
344 TDF::template size<DisplacementDim>())
345 {
346 OGS_FATAL(
347 "The behaviour's {}th thermodynamic force ({}) must "
348 "have size {} instead of {}.",
349 i, tdfs[i].name, TDF::template size<DisplacementDim>(),
350 mgis::behaviour::getVariableSize(tdfs[i], hyp));
351 }
352
353 i++;
354 };
355
356 if (_behaviour.thermodynamic_forces.size() !=
357 boost::mp11::mp_size<TDynForces>::value)
358 OGS_FATAL(
359 "The behaviour must compute exactly {} thermodynamic "
360 "forces.",
361 boost::mp11::mp_size<TDynForces>::value);
362
363 boost::mp11::mp_for_each<TDynForces>(check_tdyn_force);
364 }
365
366 auto const hypothesis = _behaviour.hypothesis;
367
368 static_assert(
369 std::is_same_v<ExtStateVars, boost::mp11::mp_list<Temperature>>,
370 "Temperature is the only allowed external state variable.");
371
372 if (!_behaviour.esvs.empty())
373 {
374 if (_behaviour.esvs[0].name != "Temperature")
375 {
376 OGS_FATAL(
377 "Only temperature is supported as external state "
378 "variable.");
379 }
380
381 if (mgis::behaviour::getVariableSize(_behaviour.esvs[0],
382 hypothesis) != 1)
383 OGS_FATAL(
384 "Temperature must be a scalar instead of having {:d} "
385 "components.",
386 mgis::behaviour::getVariableSize(
387 _behaviour.thermodynamic_forces[0], hypothesis));
388 }
389
390 if (_behaviour.mps.size() != _material_properties.size())
391 {
392 ERR("There are {:d} material properties in the loaded behaviour:",
393 _behaviour.mps.size());
394 for (auto const& mp : _behaviour.mps)
395 {
396 ERR("\t{:s}", mp.name);
397 }
398 OGS_FATAL("But the number of passed material properties is {:d}.",
399 _material_properties.size());
400 }
401 }
402
403 std::unique_ptr<
404 typename MechanicsBase<DisplacementDim>::MaterialStateVariables>
406 {
407 return std::make_unique<MaterialStateVariablesMFront<DisplacementDim>>(
408 equivalent_plastic_strain_offset_, _behaviour);
409 }
410
412 double const t,
415 material_state_variables) const
416 {
418 &material_state_variables));
419
420 auto& state =
422 material_state_variables);
423
424 auto const& ivs = getInternalVariables();
425
426 for (auto& [name, parameter] : _state_variables_initial_properties)
427 {
428 // find corresponding internal variable
429 auto const& iv = BaseLib::findElementOrError(
430 ivs,
431 [name = name](InternalVariable const& iv)
432 { return iv.name == name; },
433 [name = name]()
434 { OGS_FATAL("Internal variable `{:s}' not found.", name); });
435
436 // evaluate parameter
437 std::vector<double> values = (*parameter)(t, x);
438
439 // copy parameter data into iv
440 auto const values_span = iv.reference(state);
441 assert(values.size() == values_span.size());
442 std::copy_n(begin(values), values_span.size(), values_span.begin());
443 }
444
445 auto const& s1 = state._behaviour_data.s1.internal_state_variables;
446 auto& s0 = state._behaviour_data.s0.internal_state_variables;
447 std::copy(begin(s1), end(s1), begin(s0));
448 }
449
450 std::optional<std::tuple<OGSMFrontThermodynamicForcesData,
451 std::unique_ptr<typename MechanicsBase<
452 DisplacementDim>::MaterialStateVariables>,
455 MaterialPropertyLib::VariableArray const& variable_array_prev,
456 MaterialPropertyLib::VariableArray const& variable_array,
457 double const t,
459 double const dt,
461 material_state_variables) const
462 {
463 using namespace MathLib::KelvinVector;
464
465 assert(
467 &material_state_variables));
468 // New state, copy of current one, packed in unique_ptr for return.
469 auto state = std::make_unique<
472 material_state_variables));
473 auto& behaviour_data = state->_behaviour_data;
474
475 behaviour_data.dt = dt;
476 behaviour_data.rdt = 1.0;
477 behaviour_data.K[0] =
478 4.0; // if K[0] is greater than 3.5, the consistent
479 // tangent operator must be computed.
480 if (behaviour_data.s0.b.btype ==
481 mgis::behaviour::Behaviour::STANDARDFINITESTRAINBEHAVIOUR)
482 {
483 behaviour_data.K[1] = 1.0; // The second Piola-Kirchoff stress is
484 // used for the stress measure
485 behaviour_data.K[2] =
486 1.0; // The derivative of the second
487 // Piola-Kirchoff stress with respect to
488 // the Green-Lagrange strain is returned.
489 }
490
491 // evaluate parameters at (t, x)
492 {
493 {
494 auto out = behaviour_data.s0.material_properties.begin();
495 for (auto* param : _material_properties)
496 {
497 auto const& vals = (*param)(t - dt, x);
498 out = std::copy(vals.begin(), vals.end(), out);
499 }
500 assert(out == behaviour_data.s0.material_properties.end());
501 }
502
503 {
504 auto out = behaviour_data.s1.material_properties.begin();
505 for (auto* param : _material_properties)
506 {
507 auto const& vals = (*param)(t, x);
508 out = std::copy(vals.begin(), vals.end(), out);
509 }
510 assert(out == behaviour_data.s1.material_properties.end());
511 }
512 }
513
514 // TODO unify with gradient handling? Make gradient and external state
515 // var input both optional?
516 if (!behaviour_data.s0.external_state_variables.empty())
517 {
518 // assuming that there is only temperature
519 // NOTE the temperature can be NaN, e.g., if OGS's process does not
520 // have a temperature defined
521 behaviour_data.s0.external_state_variables[0] =
522 variable_array_prev.temperature;
523 }
524
525 if (!behaviour_data.s1.external_state_variables.empty())
526 {
527 // assuming that there is only temperature
528 // NOTE the temperature can be NaN, e.g., if OGS's process does not
529 // have a temperature defined
530 behaviour_data.s1.external_state_variables[0] =
531 variable_array.temperature;
532 }
533
534 // rotation tensor
535 std::optional<KelvinMatrixType<DisplacementDim>> Q;
536 if (_local_coordinate_system)
537 {
538 Q = fourthOrderRotationMatrix(
539 _local_coordinate_system->transformation<DisplacementDim>(x));
540 }
541
542 boost::mp11::mp_for_each<Gradients>(
544 variable_array_prev, Q, behaviour_data.s0.gradients.data()});
545 boost::mp11::mp_for_each<Gradients>(
547 variable_array, Q, behaviour_data.s1.gradients.data()});
548
549 // previous and current state of thermodynamic forces are both set from
550 // variable_array_prev. TODO optimization potential compute Q * grad_ogs
551 // only once for both cases.
552 boost::mp11::mp_for_each<TDynForces>(
554 variable_array_prev, Q,
555 behaviour_data.s0.thermodynamic_forces.data()});
556 boost::mp11::mp_for_each<TDynForces>(
558 variable_array_prev, Q,
559 behaviour_data.s1.thermodynamic_forces.data()});
560
561 auto v = mgis::behaviour::make_view(behaviour_data);
562 auto const status = mgis::behaviour::integrate(v, _behaviour);
563 if (status != 1)
564 {
566 "MFront: integration failed with status " +
567 std::to_string(status) + ".");
568 }
569
570 OGSMFrontThermodynamicForcesData tdyn_forces_data;
571 tdyn_forces_data.data.resize( // TODO data stored on heap but size is
572 // compile-time constant
573 behaviour_data.s1.thermodynamic_forces.size());
574
575 boost::mp11::mp_for_each<TDynForces>(
576 [&out_data = tdyn_forces_data,
577 &in_data = behaviour_data.s1.thermodynamic_forces,
578 &Q]<typename TDF>(TDF tdf)
579 {
580 OGSMFrontThermodynamicForcesView<DisplacementDim, TDynForces>
581 view;
582
583 if constexpr (TDF::type ==
584 mgis::behaviour::Variable::Type::STENSOR)
585 {
586 if (Q)
587 {
588 view.block(tdf, out_data) =
589 *Q * eigenSwap45View(view.block(tdf, in_data));
590 }
591 else
592 {
593 view.block(tdf, out_data) =
594 eigenSwap45View(view.block(tdf, in_data));
595 }
596 }
597 else if constexpr (TDF::type ==
598 mgis::behaviour::Variable::Type::SCALAR)
599 {
600 view.block(tdf, out_data) = view.block(tdf, in_data);
601 }
602 else
603 {
604 OGS_FATAL("Not yet implemented.");
605 }
606 });
607
608 return std::make_optional(
609 std::make_tuple<OGSMFrontThermodynamicForcesData,
610 std::unique_ptr<typename MechanicsBase<
611 DisplacementDim>::MaterialStateVariables>,
613 std::move(tdyn_forces_data),
614 std::move(state),
615 tangentOperatorDataMFrontToOGS<DisplacementDim>(
616 behaviour_data.K, Q, _behaviour)));
617 }
618
619 std::vector<InternalVariable> getInternalVariables() const
620 {
621 std::vector<InternalVariable> internal_variables;
622
623 for (auto const& iv : _behaviour.isvs)
624 {
625 auto const name = iv.name;
626 auto const offset = mgis::behaviour::getVariableOffset(
627 _behaviour.isvs, name, _behaviour.hypothesis);
628 auto const size =
629 mgis::behaviour::getVariableSize(iv, _behaviour.hypothesis);
630
631 // TODO (naumov): For orthotropic materials the internal variables
632 // should be rotated to the global coordinate system before output.
633 // MFront stores the variables in local coordinate system.
634 // The `size` variable could be used to find out the type of
635 // variable.
636 InternalVariable new_variable{
637 name, static_cast<int>(size),
638 [offset, size](
639 typename MechanicsBase<
640 DisplacementDim>::MaterialStateVariables const& state,
641 std::vector<double>& cache) -> std::vector<double> const&
642 {
643 assert(dynamic_cast<MaterialStateVariablesMFront<
644 DisplacementDim> const*>(&state) != nullptr);
645 auto const& internal_state_variables =
647 DisplacementDim> const&>(state)
648 ._behaviour_data.s1.internal_state_variables;
649
650 cache.resize(size);
651 std::copy_n(internal_state_variables.data() + offset,
652 size,
653 begin(cache));
654 return cache;
655 },
656 [offset, size](typename MechanicsBase<
657 DisplacementDim>::MaterialStateVariables& state)
658 -> std::span<double>
659 {
660 assert(dynamic_cast<MaterialStateVariablesMFront<
661 DisplacementDim> const*>(&state) != nullptr);
662 auto& internal_state_variables =
663 static_cast<
665 state)
666 ._behaviour_data.s1.internal_state_variables;
667
668 return {internal_state_variables.data() + offset, size};
669 }};
670 internal_variables.push_back(new_variable);
671 }
672
673 return internal_variables;
674 }
675
676 template <typename ForcesGradsCombinations =
677 typename ForcesGradsCombinations<Gradients, TDynForces,
678 ExtStateVars>::type>
681 {
682 return OGSMFrontTangentOperatorBlocksView<DisplacementDim,
684 _behaviour.to_blocks};
685 }
686
692
693 double getBulkModulus(double const /*t*/,
695 KelvinMatrix const* const C) const
696 {
697 if (C == nullptr)
698 {
699 OGS_FATAL(
700 "MFront::getBulkModulus() requires the tangent stiffness C "
701 "input "
702 "argument to be valid.");
703 }
704 auto const& identity2 = MathLib::KelvinVector::Invariants<
706 DisplacementDim)>::identity2;
707 return 1. / 9. * identity2.transpose() * *C * identity2;
708 }
709
711 double const /*t*/,
713 double const /*dt*/,
714 KelvinVector const& /*eps*/,
715 KelvinVector const& /*sigma*/,
717 /*material_state_variables*/) const
718 {
719 // TODO implement
720 return std::numeric_limits<double>::quiet_NaN();
721 }
722
723private:
724 mgis::behaviour::Behaviour _behaviour;
726 std::vector<ParameterLib::Parameter<double> const*> _material_properties;
727 std::map<std::string, ParameterLib::Parameter<double> const*>
730};
731} // namespace MaterialLib::Solids::MFront
#define OGS_FATAL(...)
Definition Error.h:26
std::optional< std::tuple< OGSMFrontThermodynamicForcesData, std::unique_ptr< typename MechanicsBase< DisplacementDim >::MaterialStateVariables >, OGSMFrontTangentOperatorData > > integrateStress(MaterialPropertyLib::VariableArray const &variable_array_prev, MaterialPropertyLib::VariableArray const &variable_array, double const t, ParameterLib::SpatialPosition const &x, double const dt, typename MechanicsBase< DisplacementDim >::MaterialStateVariables const &material_state_variables) const
OGSMFrontTangentOperatorBlocksView< DisplacementDim, ForcesGradsCombinations > createTangentOperatorBlocksView() const
std::vector< InternalVariable > getInternalVariables() const
std::unique_ptr< typename MechanicsBase< DisplacementDim >::MaterialStateVariables > createMaterialStateVariables() const
MathLib::KelvinVector::KelvinVectorType< DisplacementDim > KelvinVector
double computeFreeEnergyDensity(double const, ParameterLib::SpatialPosition const &, double const, KelvinVector const &, KelvinVector const &, typename MechanicsBase< DisplacementDim >::MaterialStateVariables const &) const
OGSMFrontThermodynamicForcesView< DisplacementDim, TDynForces > createThermodynamicForcesView() const
std::vector< ParameterLib::Parameter< double > const * > _material_properties
void initializeInternalStateVariables(double const t, ParameterLib::SpatialPosition const &x, typename MechanicsBase< DisplacementDim >::MaterialStateVariables &material_state_variables) const
typename MechanicsBase< DisplacementDim >::InternalVariable InternalVariable
std::map< std::string, ParameterLib::Parameter< double > const * > _state_variables_initial_properties
boost::mp11::mp_append< Gradients, ExtStateVars > GradientsAndExtStateVars
MFrontGeneric(mgis::behaviour::Behaviour &&behaviour, std::vector< ParameterLib::Parameter< double > const * > &&material_properties, std::map< std::string, ParameterLib::Parameter< double > const * > &&state_variables_initial_properties, std::optional< ParameterLib::CoordinateSystem > const &local_coordinate_system)
double getBulkModulus(double const, ParameterLib::SpatialPosition const &, KelvinMatrix const *const C) const
ParameterLib::CoordinateSystem const *const _local_coordinate_system
MathLib::KelvinVector::KelvinMatrixType< DisplacementDim > KelvinMatrix
ranges::range_reference_t< Range > findElementOrError(Range &range, std::predicate< ranges::range_reference_t< Range > > auto &&predicate, std::invocable auto error_callback)
Definition Algorithm.h:77
typename MapToMPLType< DisplacementDim, MFrontType >::type MapToMPLType_t
OGSMFrontTangentOperatorData tangentOperatorDataMFrontToOGS(std::vector< double > const &mfront_data, std::optional< MathLib::KelvinVector::KelvinMatrixType< DisplacementDim > > const &Q, mgis::behaviour::Behaviour const &behaviour)
constexpr auto ogsTensorToMFrontTensor(Eigen::MatrixBase< Derived > const &matrix)
constexpr auto eigenSwap45View(Eigen::MatrixBase< Derived > const &matrix)
const char * varTypeToString(int v)
int getEquivalentPlasticStrainOffset(mgis::behaviour::Behaviour const &b)
Eigen::Matrix< double, tensorSize(Dim), 1 > Tensor
Definition Tensor.h:52
Eigen::Matrix< double, symmetric_tensor_size< GlobalDim >, 1 > SymmetricTensor
constexpr int kelvin_vector_dimensions(int const displacement_dim)
Kelvin vector dimensions for given displacement dimension.
Eigen::Matrix< double, kelvin_vector_dimensions(DisplacementDim), 1, Eigen::ColMajor > KelvinVectorType
Eigen::Matrix< double, kelvin_vector_dimensions(DisplacementDim), kelvin_vector_dimensions(DisplacementDim), Eigen::RowMajor > KelvinMatrixType
MaterialStateVariablesMFront(int const equivalent_plastic_strain_offset, mgis::behaviour::Behaviour const &b)
MaterialStateVariablesMFront(MaterialStateVariablesMFront< DisplacementDim > &&)=delete
MaterialStateVariablesMFront(MaterialStateVariablesMFront< DisplacementDim > const &)=default
Used for disambiguation with MFront's thermodynamic forces data.
Used for disambiguation with MFront's tangent operator blocks data.
A struct mapping a MGIS variable type to its corresponding OGS type.
std::optional< MathLib::KelvinVector::KelvinMatrixType< DisplacementDim > > const & Q
MaterialPropertyLib::VariableArray const & variable_array
Helper type for providing access to internal variables.
A local coordinate system used for tensor transformations.