Back

TetrahedralCorotationalFEMForceField

sofa::component::solidmechanics::fem::elastic::TetrahedralCorotationalFEMForceField
BaseLinearElasticityFEMForceField
Doc (from source)

Corotational FEM Tetrahedral finite elements Compute Finite Element forces based on tetrahedral elements.

Abstract (AI generated)

The `TetrahedralCorotationalFEMForceField` computes finite element forces based on tetrahedral elements using corotational FEM, supporting small, large, and polar displacements. It facilitates accurate modeling of elastic behavior under deformation and provides visualization capabilities for stress analysis.

Metadata
module
Sofa.Component.SolidMechanics.FEM.Elastic
namespace
sofa::component::solidmechanics::fem::elastic
include
sofa/component/solidmechanics/fem/elastic/TetrahedralCorotationalFEMForceField.h
inherits
  • BaseLinearElasticityFEMForceField
templates
  • sofa::defaulttype::Vec3Types
description

The TetrahedralCorotationalFEMForceField is designed to simulate solid mechanics using the Finite Element Method (FEM) with tetrahedral elements. This component inherits from BaseLinearElasticityFEMForceField, which provides foundational support for linear elasticity computations. The primary goal of this component is to compute forces on each tetrahedral element based on its material properties and deformation, thereby providing a realistic model of elastic behavior under various loading conditions.

Key Components and Mathematical Formulations:

Material Stiffness Matrix (Κ)

Each tetrahedral element's stiffness matrix Κ is calculated using the material properties and geometry. The material properties include Young’s modulus (E) and Poisson’s ratio (ν), which are used to compute Lamé parameters:

egin{align}
\lambda &= \frac{E\nu}{(1 + \nu)(1 - 2\nu)}, \
\mu &= \frac{E}{2(1+\nu)}.
\end{align
}

The material stiffness matrix is given by:

egin{equation}
\mathbf{C} = \lambda \mathbf{I}\otimes\mathbf{I} + 2\mu\mathbf{J},
\end{equation}
where αβ is the identity tensor and Φ is a fourth-order tensor with components:

egin{align}
\mathbf{I}{ij} &= \delta{ij},\
\mathbf{J}{ijkl} &= \frac{1}{2}(\delta{ik}\delta_{jl} + \delta_{il}\delta_{jk}).
\end{align
}

Strain-Displacement Matrix (B)

The strain-displacement matrix B relates the nodal displacements to the strain field within the element. For a tetrahedral element, it is computed based on the shape functions and their derivatives.

The strain-displacement relation for an infinitesimal element can be written as:

egin{equation}
\mathbf{\varepsilon} = \mathbf{B}\mathbf{u},
\end{equation}
where ε is the strain vector and u is the displacement vector.

Stiffness Matrix (K)

The stiffness matrix for each tetrahedral element is derived from these relations:

egin{equation}
\mathbf{K} = \int_{V}^{ }\mathbf{B}^T\mathbf{C}\mathbf{B}\,dV,
\end{equation}
where V represents the volume of the tetrahedral element.

Corotational Framework

The corotational framework separates large rotations from deformations. The displacement is decomposed into rigid body motion and deformational part:

egin{align}
\mathbf{R} &= \text{rotation matrix}, \
\mathbf{u}_{deform} &= \mathbf{R}(\mathbf{x}_d - \mathbf{x}_r),
\end{align
}
where ρ is the deformed configuration, and ρ₀ is the rotated reference configuration.

The rotation matrix R can be computed using various methods such as polar decomposition or QR factorization, depending on the displacement method (small/large/polar).

Small Displacements Method

For small deformations, the strain-displacement matrix B and stiffness matrix K are directly calculated based on initial element geometry.

egin{equation}
\mathbf{K}{\text{small}} = \int{V}^{ }\mathbf{B}_0^T\mathbf{C}\mathbf{B}_0\,dV,
\end{equation}
where β₀ is the initial strain-displacement matrix.

Large Displacements Method

For large deformations, the method computes a local rotation to align the deformed element with its reference configuration:

egin{align}
\mathbf{R}{0 \rightarrow 1} &= \text{initial rotation}, \
\mathbf{u}
{deform} &= \mathbf{R}\left(\mathbf{x}_d - \mathbf{x}_r\right).
\end{align
}

The stiffness matrix is then updated based on the local rotations:

egin{equation}
\mathbf{K}{\text{large}} = \int{V}^{ }\mathbf{R}^T\mathbf{B}_d^T\mathbf{C}\mathbf{B}_d\mathbf{R}\,dV,
\end{equation}
where βₔ is the strain-displacement matrix in the deformed configuration.

Polar Decomposition Method

In this method, the deformation gradient F is decomposed into a rotation R and stretch U:

egin{align}
\mathbf{F} &= \mathbf{R}\mathbf{U}, \
\mathbf{K}{\text{polar}} &= \int{V}^{ }\left(\mathbf{B}_d^T\right)\mathbf{C}\mathbf{B}_d\,dV.
\end{align
}

Force Computation

The internal forces are computed as:

egin{equation}
\mathbf{f} = - \mathbf{Ku},
\end{equation}
where u is the displacement vector and κ represents the stiffness matrix.

Visualization of Stress (Von Mises)

The component computes von Mises stress, a measure used to predict yielding or failure under complex loading conditions. This computed stress is used for visualization purposes.

egin{align}
\sigma_{\text{vonMises}} &= \sqrt{\frac{3}{2}\mathbf{s}^T:\mathbf{s}}, \
\mathbf{s} &= \mathbf{D}:\varepsilon,
\end{align
}
where s is the deviatoric stress tensor and D is a fourth-order tensor related to elastic constants.

Conclusion

The TetrahedralCorotationalFEMForceField provides a comprehensive approach for modeling linear elasticity with tetrahedral elements, supporting different displacement methods. This component facilitates accurate simulation of solid mechanics by computing forces based on material properties and deformation, while also offering visualization capabilities for stress analysis.

Data Fields
NameTypeDefaultHelp
d_localStiffnessFactor VecReal Allow specification of different stiffness per element. If there are N element and M values are specified, the youngModulus factor for element i would be localStiffnessFactor[i*M/N]
d_updateStiffnessMatrix bool
d_assembling bool
d_drawing bool draw the forcefield if true
_displayWholeVolume bool
d_drawColor1 sofa::type::RGBAColor draw color for faces 1
d_drawColor2 sofa::type::RGBAColor draw color for faces 2
d_drawColor3 sofa::type::RGBAColor draw color for faces 3
d_drawColor4 sofa::type::RGBAColor draw color for faces 4
d_computeVonMisesStress bool compute and display von Mises stress: 0: no computations, 1: using corotational strain, 2: using full Green strain. Set listening=1
Methods
void setMethod (int val)
void setUpdateStiffnessMatrix (bool val)
void setComputeGlobalMatrix (bool val)
void init ()
void reinit ()
void addForce (const core::MechanicalParams * mparams, DataVecDeriv & d_f, const DataVecCoord & d_x, const DataVecDeriv & d_v)
void addDForce (const core::MechanicalParams * mparams, DataVecDeriv & d_df, const DataVecDeriv & d_dx)
SReal getPotentialEnergy (const core::MechanicalParams * , const DataVecCoord & )
void addKToMatrix (sofa::linearalgebra::BaseMatrix * m, SReal kFactor, unsigned int & offset)
void buildStiffnessMatrix (core::behavior::StiffnessMatrix * matrix)
void buildDampingMatrix (core::behavior::DampingMatrix * )
void getRotation (Transformation & R, int nodeIdx)
void getRotations ()
void getElementRotation (Transformation & R, int elementIdx)
void getElementStiffnessMatrix (Real * stiffness, int nodeIdx)
void draw (const core::visual::VisualParams * vparams)
void computeBBox (const core::ExecParams * params, bool onlyVisible)
void computeVonMisesStress ()
void createTetrahedronInformation (int tetrahedronIndex, TetrahedronInformation & tInfo, const core::topology::BaseMeshTopology::Tetrahedron & tetra, const int & ancestors, const int & coefs)
void computeStrainDisplacement (StrainDisplacementTransposed & J, Coord a, Coord b, Coord c, Coord d)
Real peudo_determinant_for_coef (const type::Mat<2, 3, Real> & M)
void computeStiffnessMatrix (StiffnessMatrix & S, StiffnessMatrix & SR, const MaterialStiffness & K, const StrainDisplacementTransposed & J, const Transformation & Rot)
void computeMaterialStiffness (int i, int & a, int & b, int & c, int & d)
void computeMaterialStiffness (int tetrahedronId, MaterialStiffness & materialMatrix, int & a, int & b, int & c, int & d, SReal localStiffnessFactor) virtual
void computeForce (Displacement & F, const Displacement & Depl, const MaterialStiffness & K, const StrainDisplacementTransposed & J)
void computeForce (Displacement & F, const Displacement & Depl, const MaterialStiffness & K, const StrainDisplacementTransposed & J, SReal fact)
void initSmall (int i, int & a, int & b, int & c, int & d)
void accumulateForceSmall (Vector & f, const Vector & p, int elementIndex)
void applyStiffnessSmall (Vector & f, const Vector & x, int i, int a, int b, int c, int d, SReal fact)
void initLarge (int i, int & a, int & b, int & c, int & d)
void computeRotationLarge (Transformation & r, const Vector & p, const int & a, const int & b, const int & c)
void accumulateForceLarge (Vector & f, const Vector & p, int elementIndex)
void applyStiffnessLarge (Vector & f, const Vector & x, int i, int a, int b, int c, int d, SReal fact)
void initPolar (int i, int & a, int & b, int & c, int & d)
void accumulateForcePolar (Vector & f, const Vector & p, int elementIndex)
void applyStiffnessPolar (Vector & f, const Vector & x, int i, int a, int b, int c, int d, SReal fact)
void printStiffnessMatrix (int idTetra)
{
  "name": "TetrahedralCorotationalFEMForceField",
  "namespace": "sofa::component::solidmechanics::fem::elastic",
  "module": "Sofa.Component.SolidMechanics.FEM.Elastic",
  "include": "sofa/component/solidmechanics/fem/elastic/TetrahedralCorotationalFEMForceField.h",
  "doc": "Corotational FEM Tetrahedral finite elements\n\nCompute Finite Element forces based on tetrahedral elements.",
  "inherits": [
    "BaseLinearElasticityFEMForceField"
  ],
  "templates": [
    "sofa::defaulttype::Vec3Types"
  ],
  "data_fields": [
    {
      "name": "d_localStiffnessFactor",
      "type": "VecReal",
      "xmlname": "localStiffnessFactor",
      "help": "Allow specification of different stiffness per element. If there are N element and M values are specified, the youngModulus factor for element i would be localStiffnessFactor[i*M/N]"
    },
    {
      "name": "d_updateStiffnessMatrix",
      "type": "bool",
      "xmlname": "updateStiffnessMatrix",
      "help": ""
    },
    {
      "name": "d_assembling",
      "type": "bool",
      "xmlname": "computeGlobalMatrix",
      "help": ""
    },
    {
      "name": "d_drawing",
      "type": "bool",
      "xmlname": "drawing",
      "help": " draw the forcefield if true"
    },
    {
      "name": "_displayWholeVolume",
      "type": "bool"
    },
    {
      "name": "d_drawColor1",
      "type": "sofa::type::RGBAColor",
      "xmlname": "drawColor1",
      "help": " draw color for faces 1"
    },
    {
      "name": "d_drawColor2",
      "type": "sofa::type::RGBAColor",
      "xmlname": "drawColor2",
      "help": " draw color for faces 2"
    },
    {
      "name": "d_drawColor3",
      "type": "sofa::type::RGBAColor",
      "xmlname": "drawColor3",
      "help": " draw color for faces 3"
    },
    {
      "name": "d_drawColor4",
      "type": "sofa::type::RGBAColor",
      "xmlname": "drawColor4",
      "help": " draw color for faces 4"
    },
    {
      "name": "d_computeVonMisesStress",
      "type": "bool",
      "xmlname": "computeVonMisesStress",
      "help": "compute and display von Mises stress: 0: no computations, 1: using corotational strain, 2: using full Green strain. Set listening=1"
    }
  ],
  "links": [],
  "methods": [
    {
      "name": "setMethod",
      "return_type": "void",
      "params": [
        {
          "name": "val",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "setUpdateStiffnessMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "val",
          "type": "bool"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "setComputeGlobalMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "val",
          "type": "bool"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "init",
      "return_type": "void",
      "params": [],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "reinit",
      "return_type": "void",
      "params": [],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "addForce",
      "return_type": "void",
      "params": [
        {
          "name": "mparams",
          "type": "const core::MechanicalParams *"
        },
        {
          "name": "d_f",
          "type": "DataVecDeriv &"
        },
        {
          "name": "d_x",
          "type": "const DataVecCoord &"
        },
        {
          "name": "d_v",
          "type": "const DataVecDeriv &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "addDForce",
      "return_type": "void",
      "params": [
        {
          "name": "mparams",
          "type": "const core::MechanicalParams *"
        },
        {
          "name": "d_df",
          "type": "DataVecDeriv &"
        },
        {
          "name": "d_dx",
          "type": "const DataVecDeriv &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "getPotentialEnergy",
      "return_type": "SReal",
      "params": [
        {
          "name": "",
          "type": "const core::MechanicalParams *"
        },
        {
          "name": "",
          "type": "const DataVecCoord &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "addKToMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "m",
          "type": "sofa::linearalgebra::BaseMatrix *"
        },
        {
          "name": "kFactor",
          "type": "SReal"
        },
        {
          "name": "offset",
          "type": "unsigned int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "buildStiffnessMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "matrix",
          "type": "core::behavior::StiffnessMatrix *"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "buildDampingMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "",
          "type": "core::behavior::DampingMatrix *"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "getRotation",
      "return_type": "void",
      "params": [
        {
          "name": "R",
          "type": "Transformation &"
        },
        {
          "name": "nodeIdx",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "getRotations",
      "return_type": "void",
      "params": [],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "getElementRotation",
      "return_type": "void",
      "params": [
        {
          "name": "R",
          "type": "Transformation &"
        },
        {
          "name": "elementIdx",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "getElementStiffnessMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "stiffness",
          "type": "Real *"
        },
        {
          "name": "nodeIdx",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "draw",
      "return_type": "void",
      "params": [
        {
          "name": "vparams",
          "type": "const core::visual::VisualParams *"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "computeBBox",
      "return_type": "void",
      "params": [
        {
          "name": "params",
          "type": "const core::ExecParams *"
        },
        {
          "name": "onlyVisible",
          "type": "bool"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "computeVonMisesStress",
      "return_type": "void",
      "params": [],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "public"
    },
    {
      "name": "createTetrahedronInformation",
      "return_type": "void",
      "params": [
        {
          "name": "tetrahedronIndex",
          "type": "int"
        },
        {
          "name": "tInfo",
          "type": "TetrahedronInformation &"
        },
        {
          "name": "tetra",
          "type": "const core::topology::BaseMeshTopology::Tetrahedron &"
        },
        {
          "name": "ancestors",
          "type": "const int &"
        },
        {
          "name": "coefs",
          "type": "const int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeStrainDisplacement",
      "return_type": "void",
      "params": [
        {
          "name": "J",
          "type": "StrainDisplacementTransposed &"
        },
        {
          "name": "a",
          "type": "Coord"
        },
        {
          "name": "b",
          "type": "Coord"
        },
        {
          "name": "c",
          "type": "Coord"
        },
        {
          "name": "d",
          "type": "Coord"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "peudo_determinant_for_coef",
      "return_type": "Real",
      "params": [
        {
          "name": "M",
          "type": "const type::Mat<2, 3, Real> &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeStiffnessMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "S",
          "type": "StiffnessMatrix &"
        },
        {
          "name": "SR",
          "type": "StiffnessMatrix &"
        },
        {
          "name": "K",
          "type": "const MaterialStiffness &"
        },
        {
          "name": "J",
          "type": "const StrainDisplacementTransposed &"
        },
        {
          "name": "Rot",
          "type": "const Transformation &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeMaterialStiffness",
      "return_type": "void",
      "params": [
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int &"
        },
        {
          "name": "b",
          "type": "int &"
        },
        {
          "name": "c",
          "type": "int &"
        },
        {
          "name": "d",
          "type": "int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeMaterialStiffness",
      "return_type": "void",
      "params": [
        {
          "name": "tetrahedronId",
          "type": "int"
        },
        {
          "name": "materialMatrix",
          "type": "MaterialStiffness &"
        },
        {
          "name": "a",
          "type": "int &"
        },
        {
          "name": "b",
          "type": "int &"
        },
        {
          "name": "c",
          "type": "int &"
        },
        {
          "name": "d",
          "type": "int &"
        },
        {
          "name": "localStiffnessFactor",
          "type": "SReal"
        }
      ],
      "is_virtual": true,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeForce",
      "return_type": "void",
      "params": [
        {
          "name": "F",
          "type": "Displacement &"
        },
        {
          "name": "Depl",
          "type": "const Displacement &"
        },
        {
          "name": "K",
          "type": "const MaterialStiffness &"
        },
        {
          "name": "J",
          "type": "const StrainDisplacementTransposed &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeForce",
      "return_type": "void",
      "params": [
        {
          "name": "F",
          "type": "Displacement &"
        },
        {
          "name": "Depl",
          "type": "const Displacement &"
        },
        {
          "name": "K",
          "type": "const MaterialStiffness &"
        },
        {
          "name": "J",
          "type": "const StrainDisplacementTransposed &"
        },
        {
          "name": "fact",
          "type": "SReal"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "initSmall",
      "return_type": "void",
      "params": [
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int &"
        },
        {
          "name": "b",
          "type": "int &"
        },
        {
          "name": "c",
          "type": "int &"
        },
        {
          "name": "d",
          "type": "int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "accumulateForceSmall",
      "return_type": "void",
      "params": [
        {
          "name": "f",
          "type": "Vector &"
        },
        {
          "name": "p",
          "type": "const Vector &"
        },
        {
          "name": "elementIndex",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "applyStiffnessSmall",
      "return_type": "void",
      "params": [
        {
          "name": "f",
          "type": "Vector &"
        },
        {
          "name": "x",
          "type": "const Vector &"
        },
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int"
        },
        {
          "name": "b",
          "type": "int"
        },
        {
          "name": "c",
          "type": "int"
        },
        {
          "name": "d",
          "type": "int"
        },
        {
          "name": "fact",
          "type": "SReal"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "initLarge",
      "return_type": "void",
      "params": [
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int &"
        },
        {
          "name": "b",
          "type": "int &"
        },
        {
          "name": "c",
          "type": "int &"
        },
        {
          "name": "d",
          "type": "int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "computeRotationLarge",
      "return_type": "void",
      "params": [
        {
          "name": "r",
          "type": "Transformation &"
        },
        {
          "name": "p",
          "type": "const Vector &"
        },
        {
          "name": "a",
          "type": "const int &"
        },
        {
          "name": "b",
          "type": "const int &"
        },
        {
          "name": "c",
          "type": "const int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "accumulateForceLarge",
      "return_type": "void",
      "params": [
        {
          "name": "f",
          "type": "Vector &"
        },
        {
          "name": "p",
          "type": "const Vector &"
        },
        {
          "name": "elementIndex",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "applyStiffnessLarge",
      "return_type": "void",
      "params": [
        {
          "name": "f",
          "type": "Vector &"
        },
        {
          "name": "x",
          "type": "const Vector &"
        },
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int"
        },
        {
          "name": "b",
          "type": "int"
        },
        {
          "name": "c",
          "type": "int"
        },
        {
          "name": "d",
          "type": "int"
        },
        {
          "name": "fact",
          "type": "SReal"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "initPolar",
      "return_type": "void",
      "params": [
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int &"
        },
        {
          "name": "b",
          "type": "int &"
        },
        {
          "name": "c",
          "type": "int &"
        },
        {
          "name": "d",
          "type": "int &"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "accumulateForcePolar",
      "return_type": "void",
      "params": [
        {
          "name": "f",
          "type": "Vector &"
        },
        {
          "name": "p",
          "type": "const Vector &"
        },
        {
          "name": "elementIndex",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "applyStiffnessPolar",
      "return_type": "void",
      "params": [
        {
          "name": "f",
          "type": "Vector &"
        },
        {
          "name": "x",
          "type": "const Vector &"
        },
        {
          "name": "i",
          "type": "int"
        },
        {
          "name": "a",
          "type": "int"
        },
        {
          "name": "b",
          "type": "int"
        },
        {
          "name": "c",
          "type": "int"
        },
        {
          "name": "d",
          "type": "int"
        },
        {
          "name": "fact",
          "type": "SReal"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    },
    {
      "name": "printStiffnessMatrix",
      "return_type": "void",
      "params": [
        {
          "name": "idTetra",
          "type": "int"
        }
      ],
      "is_virtual": false,
      "is_pure_virtual": false,
      "is_static": false,
      "access": "protected"
    }
  ],
  "description": "The `TetrahedralCorotationalFEMForceField` is a component in the SOFA framework designed for solid mechanics simulations, specifically implementing corotational Finite Element Method (FEM) forces based on tetrahedral elements. This component inherits from `BaseLinearElasticityFEMForceField`, which provides a base class for linear elasticity computations using FEM. It supports various displacement methods including small, large, and polar displacements to handle different deformation scenarios.\n\nThe primary role of this component is to compute finite element forces by discretizing the mechanical model into tetrahedral elements. Each element's stiffness matrix is computed based on its material properties and geometry. The stiffness matrices are then used in force calculations during the simulation steps, facilitating accurate modeling of elastic behavior under deformation.\n\nThis component interacts with other components such as `MechanicalState` for position data and `BaseMeshTopology` for topological information about tetrahedral elements. It also provides methods to visualize the distribution of forces and stresses through drawing functions that utilize the visual parameters provided by SOFA's rendering tools.\n\nThe component supports customization through various parameters, including the method for displacement (small/large/polar), whether to assemble system matrices, and options for computing and displaying von Mises stress. Additionally, it offers methods for extracting rotational data of tetrahedra at different stages and contributes to building global stiffness matrices for the entire mechanical model.",
  "maths": "The `TetrahedralCorotationalFEMForceField` is designed to simulate solid mechanics using the Finite Element Method (FEM) with tetrahedral elements. This component inherits from `BaseLinearElasticityFEMForceField`, which provides foundational support for linear elasticity computations. The primary goal of this component is to compute forces on each tetrahedral element based on its material properties and deformation, thereby providing a realistic model of elastic behavior under various loading conditions.\n\n### Key Components and Mathematical Formulations:\n\n#### Material Stiffness Matrix (Κ)\nEach tetrahedral element's stiffness matrix Κ is calculated using the material properties and geometry. The material properties include Young’s modulus (E) and Poisson’s ratio (ν), which are used to compute Lamé parameters:\n\n\begin{align*}\n\\lambda &= \\frac{E\\nu}{(1 + \\nu)(1 - 2\\nu)}, \\\\\n\\mu &= \\frac{E}{2(1+\\nu)}.\n\\end{align*}\n\nThe material stiffness matrix is given by:\n\n\begin{equation}\n\\mathbf{C} = \\lambda \\mathbf{I}\\otimes\\mathbf{I} + 2\\mu\\mathbf{J},\n\\end{equation}\nwhere αβ is the identity tensor and Φ is a fourth-order tensor with components:\n\n\begin{align*}\n\\mathbf{I}_{ij} &= \\delta_{ij},\\\\\n\\mathbf{J}_{ijkl} &= \\frac{1}{2}(\\delta_{ik}\\delta_{jl} + \\delta_{il}\\delta_{jk}).\n\\end{align*}\n\n#### Strain-Displacement Matrix (B)\nThe strain-displacement matrix B relates the nodal displacements to the strain field within the element. For a tetrahedral element, it is computed based on the shape functions and their derivatives.\n\nThe strain-displacement relation for an infinitesimal element can be written as:\n\n\begin{equation}\n\\mathbf{\\varepsilon} = \\mathbf{B}\\mathbf{u},\n\\end{equation}\nwhere ε is the strain vector and u is the displacement vector.\n\n#### Stiffness Matrix (K)\nThe stiffness matrix for each tetrahedral element is derived from these relations:\n\n\begin{equation}\n\\mathbf{K} = \\int_{V}^{ }\\mathbf{B}^T\\mathbf{C}\\mathbf{B}\\,dV,\n\\end{equation}\nwhere V represents the volume of the tetrahedral element.\n\n#### Corotational Framework\nThe corotational framework separates large rotations from deformations. The displacement is decomposed into rigid body motion and deformational part:\n\n\begin{align*}\n\\mathbf{R} &= \\text{rotation matrix}, \\\\\n\\mathbf{u}_{deform} &= \\mathbf{R}(\\mathbf{x}_d - \\mathbf{x}_r),\n\\end{align*}\nwhere ρ is the deformed configuration, and ρ₀ is the rotated reference configuration.\n\nThe rotation matrix R can be computed using various methods such as polar decomposition or QR factorization, depending on the displacement method (small/large/polar).\n\n#### Small Displacements Method\nFor small deformations, the strain-displacement matrix B and stiffness matrix K are directly calculated based on initial element geometry.\n\n\begin{equation}\n\\mathbf{K}_{\\text{small}} = \\int_{V}^{ }\\mathbf{B}_0^T\\mathbf{C}\\mathbf{B}_0\\,dV,\n\\end{equation}\nwhere β₀ is the initial strain-displacement matrix.\n\n#### Large Displacements Method\nFor large deformations, the method computes a local rotation to align the deformed element with its reference configuration:\n\n\begin{align*}\n\\mathbf{R}_{0 \\rightarrow 1} &= \\text{initial rotation}, \\\\\n\\mathbf{u}_{deform} &= \\mathbf{R}\\left(\\mathbf{x}_d - \\mathbf{x}_r\\right).\n\\end{align*}\n\nThe stiffness matrix is then updated based on the local rotations:\n\n\begin{equation}\n\\mathbf{K}_{\\text{large}} = \\int_{V}^{ }\\mathbf{R}^T\\mathbf{B}_d^T\\mathbf{C}\\mathbf{B}_d\\mathbf{R}\\,dV,\n\\end{equation}\nwhere βₔ is the strain-displacement matrix in the deformed configuration.\n\n#### Polar Decomposition Method\nIn this method, the deformation gradient F is decomposed into a rotation R and stretch U:\n\n\begin{align*}\n\\mathbf{F} &= \\mathbf{R}\\mathbf{U}, \\\\\n\\mathbf{K}_{\\text{polar}} &= \\int_{V}^{ }\\left(\\mathbf{B}_d^T\\right)\\mathbf{C}\\mathbf{B}_d\\,dV.\n\\end{align*}\n\n#### Force Computation\nThe internal forces are computed as:\n\n\begin{equation}\n\\mathbf{f} = - \\mathbf{Ku},\n\\end{equation}\nwhere u is the displacement vector and κ represents the stiffness matrix.\n\n### Visualization of Stress (Von Mises)\nThe component computes von Mises stress, a measure used to predict yielding or failure under complex loading conditions. This computed stress is used for visualization purposes.\n\n\begin{align*}\n\\sigma_{\\text{vonMises}} &= \\sqrt{\\frac{3}{2}\\mathbf{s}^T:\\mathbf{s}}, \\\\\n\\mathbf{s} &= \\mathbf{D}:\\varepsilon,\n\\end{align*}\nwhere s is the deviatoric stress tensor and D is a fourth-order tensor related to elastic constants.\n\n### Conclusion\nThe `TetrahedralCorotationalFEMForceField` provides a comprehensive approach for modeling linear elasticity with tetrahedral elements, supporting different displacement methods. This component facilitates accurate simulation of solid mechanics by computing forces based on material properties and deformation, while also offering visualization capabilities for stress analysis.",
  "abstract": "The `TetrahedralCorotationalFEMForceField` computes finite element forces based on tetrahedral elements using corotational FEM, supporting small, large, and polar displacements. It facilitates accurate modeling of elastic behavior under deformation and provides visualization capabilities for stress analysis.",
  "sheet": "# TetrahedralCorotationalFEMForceField\n\n## Overview\nThe `TetrahedralCorotationalFEMForceField` is a component in the SOFA framework designed to compute finite element forces based on tetrahedral elements using corotational FEM. It supports small, large, and polar displacements for handling different deformation scenarios. This component inherits from `BaseLinearElasticityFEMForceField`, providing foundational support for linear elasticity computations.\n\n## Mathematical Model\nThe stiffness matrix \\(\\mathbf{K}\\) for each tetrahedral element is computed based on material properties (Young's modulus \\(E\\) and Poisson's ratio \\(\\nu\\)) and geometry. The strain-displacement relation is given by:\n\n\begin{equation}\n  \boldsymbol{ε} = \boldsymbol{B} \boldsymbol{u},\n\tag{1}\n\text{where } \boldsymbol{ε} \\text{ is the strain vector and } \boldsymbol{u} \\text{ is the displacement vector.}\n\\end{equation}\n\nThe stiffness matrix for small displacements is:\n\n\begin{equation}\n  \boldsymbol{K}_{\\text{small}} = \\int_{V}^{ }\boldsymbol{B}_0^T \boldsymbol{C} \boldsymbol{B}_0 dV,\n\tag{2}\n\\end{equation}\n\nwhere \\(\\boldsymbol{B}_0\\) is the initial strain-displacement matrix.\n\nFor large displacements, the stiffness matrix is updated based on local rotations:\n\n\begin{equation}\n  \boldsymbol{K}_{\\text{large}} = \\int_{V}^{ }\boldsymbol{R}^T \boldsymbol{B}_d^T \boldsymbol{C} \boldsymbol{B}_d \boldsymbol{R} dV,\n\tag{3}\n\\end{equation}\n\nwhere \\(\\boldsymbol{B}_d\\) is the strain-displacement matrix in the deformed configuration.\n\nThe internal forces are computed as:\n\n\begin{equation}\n  \boldsymbol{f} = - \boldsymbol{Ku},\n\tag{4}\n\\end{equation}\n\nwhere \\(\\boldsymbol{u}\\) is the displacement vector and \\(\\boldsymbol{K}\\) represents the stiffness matrix.\n\n## Parameters and Data\n- **localStiffnessFactor**: Allow specification of different stiffness per element. If there are N elements and M values are specified, the Young's modulus factor for element i would be `localStiffnessFactor[i*M/N]`.\n- **updateStiffnessMatrix**: Boolean flag to update the stiffness matrix.\n- **computeGlobalMatrix**: Boolean flag to compute the global stiffness matrix.\n- **drawing**: Draw the forcefield if true.\n- **drawColor1, drawColor2, drawColor3, drawColor4**: Colors for drawing faces 1, 2, 3, and 4 respectively.\n- **computeVonMisesStress**: Compute and display von Mises stress: `0` (no computations), `1` (using corotational strain), or `2` (using full Green strain). Set listening=1 to enable this feature.\n\n## Dependencies and Connections\nThis component typically requires interaction with other SOFA components such as `MechanicalState` for position data and `BaseMeshTopology` for topological information about tetrahedral elements. It also interacts with rendering tools for visualization purposes."
}