conspire/domain/fem/block/element/solid/hyperelastic_viscoplastic/
mod.rs1use crate::{
2 constitutive::{ConstitutiveError, solid::hyperelastic_viscoplastic::HyperelasticViscoplastic},
3 domain::block::element::solid::hyperelastic_viscoplastic::HyperelasticViscoplasticElement,
4 fem::block::element::{
5 Element, ElementNodalCoordinates, FiniteElement, FiniteElementError,
6 solid::{
7 SolidElement, SolidFiniteElement,
8 elastic_viscoplastic::ElasticViscoplasticFiniteElement,
9 viscoplastic::ViscoplasticStateVariables,
10 },
11 },
12 math::{Differentiable, Quantity, Tensor},
13 units::Energy,
14};
15
16pub trait HyperelasticViscoplasticFiniteElement<
17 C,
18 const G: usize,
19 const M: usize,
20 const N: usize,
21 const P: usize,
22 Y,
23> where
24 C: HyperelasticViscoplastic<Y>,
25 Self: ElasticViscoplasticFiniteElement<C, G, M, N, P, Y>
26 + HyperelasticViscoplasticElement<C, G, Y>,
27 Y: Differentiable + Tensor,
28{
29}
30
31impl<T, C, const G: usize, const M: usize, const N: usize, const P: usize, Y>
32 HyperelasticViscoplasticFiniteElement<C, G, M, N, P, Y> for T
33where
34 C: HyperelasticViscoplastic<Y>,
35 T: ElasticViscoplasticFiniteElement<C, G, M, N, P, Y>
36 + HyperelasticViscoplasticElement<C, G, Y>,
37 Y: Differentiable + Tensor,
38{
39}
40
41impl<C, const G: usize, const N: usize, const O: usize, Y> HyperelasticViscoplasticElement<C, G, Y>
42 for Element<3, G, N, O>
43where
44 C: HyperelasticViscoplastic<Y>,
45 Self: SolidFiniteElement<G, 3, N, N>,
46 Y: Differentiable + Tensor,
47{
48 fn helmholtz_free_energy(
49 &self,
50 constitutive_model: &C,
51 nodal_coordinates: &ElementNodalCoordinates<N>,
52 state_variables: &ViscoplasticStateVariables<G, Y>,
53 ) -> Result<Quantity<Energy>, FiniteElementError> {
54 self.deformation_gradients(nodal_coordinates)
55 .iter()
56 .zip(state_variables)
57 .zip(self.integration_weights())
58 .map(
59 |((deformation_gradient, state_variable), integration_weight)| {
60 let (deformation_gradient_p, _) = state_variable.into();
61 Ok::<_, ConstitutiveError>(
62 constitutive_model.helmholtz_free_energy_density(
63 deformation_gradient,
64 deformation_gradient_p,
65 )? * integration_weight,
66 )
67 },
68 )
69 .sum::<Result<_, ConstitutiveError>>()
70 .map_err(|error| FiniteElementError::upstream(error, self))
71 }
72}