64 _fluid_component(this->template getParam<unsigned
int>(
"fluid_component")),
66 _var_is_porflow_var(_dictator.isPorousFlowVariable(_var.number())),
67 _num_phases(_dictator.numPhases()),
68 _strain_at_nearest_qp(this->template getParam<bool>(
"strain_at_nearest_qp")),
69 _multiply_by_density(this->template getParam<bool>(
"multiply_by_density")),
70 _base_name(this->isParamValid(
"base_name")
71 ? this->template getParam<
std::string>(
"base_name") +
"_"
74 this->template hasMaterialProperty<
RankTwoTensor>(_base_name +
"total_strain")),
75 _total_strain_old(_has_total_strain ? &this->template getMaterialPropertyOld<
RankTwoTensor>(
76 _base_name +
"total_strain")
78 _porosity(this->template getGenericMaterialProperty<Real, is_ad>(
"PorousFlow_porosity_nodal")),
79 _porosity_old(this->template getMaterialPropertyOld<Real>(
"PorousFlow_porosity_nodal")),
80 _dporosity_dvar(is_ad ? nullptr
81 : &this->template getMaterialProperty<
std::vector<Real>>(
82 "dPorousFlow_porosity_nodal_dvar")),
83 _dporosity_dgradvar(is_ad ? nullptr
84 : &this->template getMaterialProperty<
std::vector<RealGradient>>(
85 "dPorousFlow_porosity_nodal_dgradvar")),
86 _nearest_qp(_strain_at_nearest_qp ? &this->template getMaterialProperty<unsigned
int>(
87 "PorousFlow_nearestqp_nodal")
89 _fluid_density(_multiply_by_density
90 ? &this->template getGenericMaterialProperty<
std::vector<Real>, is_ad>(
91 "PorousFlow_fluid_phase_density_nodal")
93 _fluid_density_old(_multiply_by_density
94 ? &this->template getMaterialPropertyOld<
std::vector<Real>>(
95 "PorousFlow_fluid_phase_density_nodal")
97 _dfluid_density_dvar(_multiply_by_density && !is_ad
98 ? &this->template getMaterialProperty<
std::vector<
std::vector<Real>>>(
99 "dPorousFlow_fluid_phase_density_nodal_dvar")
101 _fluid_saturation_nodal(this->template getGenericMaterialProperty<
std::vector<Real>, is_ad>(
102 "PorousFlow_saturation_nodal")),
103 _fluid_saturation_nodal_old(
104 this->template getMaterialPropertyOld<
std::vector<Real>>(
"PorousFlow_saturation_nodal")),
105 _dfluid_saturation_nodal_dvar(
107 : &this->template getMaterialProperty<
std::vector<
std::vector<Real>>>(
108 "dPorousFlow_saturation_nodal_dvar")),
109 _mass_frac(this->template getGenericMaterialProperty<
std::vector<
std::vector<Real>>, is_ad>(
110 "PorousFlow_mass_frac_nodal")),
111 _mass_frac_old(this->template getMaterialPropertyOld<
std::vector<
std::vector<Real>>>(
112 "PorousFlow_mass_frac_nodal")),
115 : &this->template getMaterialProperty<
std::vector<
std::vector<
std::vector<Real>>>>(
116 "dPorousFlow_mass_frac_nodal_dvar"))
121 "The Dictator proclaims that the maximum fluid component index in this simulation is ",
123 " whereas you have used ",
125 ". Remember that indexing starts at 0. The Dictator does not take such mistakes lightly.");
134 for (
unsigned ph = 0; ph < _num_phases; ++ph)
138 mass += dens * _fluid_saturation_nodal[_i][ph] * _mass_frac[_i][ph][_fluid_component];
139 const Real dens_old = (_multiply_by_density ? (*_fluid_density_old)[_i][ph] : 1.0);
141 dens_old * _fluid_saturation_nodal_old[_i][ph] * _mass_frac_old[_i][ph][_fluid_component];
143 const Real strain = (_has_total_strain ? (*_total_strain_old)[_qp].trace() : 0.0);
145 return _test[_i][_qp] * (1.0 + strain) * (_porosity[_i] * mass - _porosity_old[_i] * mass_old) /
181 if constexpr (!is_ad)
183 const unsigned nearest_qp = (_strain_at_nearest_qp ? (*_nearest_qp)[_i] : _i);
185 const Real strain = (_has_total_strain ? (*_total_strain_old)[_qp].trace() : 0.0);
188 for (
unsigned ph = 0; ph < _num_phases; ++ph)
190 const Real dens = (_multiply_by_density ? (*_fluid_density)[_i][ph] : 1.0);
191 dmass += dens * _fluid_saturation_nodal[_i][ph] * _mass_frac[_i][ph][_fluid_component] *
192 (*_dporosity_dgradvar)[_i][pvar] * _grad_phi[_j][nearest_qp];
196 return _test[_i][_qp] * (1.0 + strain) * dmass / _dt;
198 for (
unsigned ph = 0; ph < _num_phases; ++ph)
200 if (_multiply_by_density)
201 dmass += (*_dfluid_density_dvar)[_i][ph][pvar] * _fluid_saturation_nodal[_i][ph] *
202 _mass_frac[_i][ph][_fluid_component] * _porosity[_i];
203 const Real dens = (_multiply_by_density ? (*_fluid_density)[_i][ph] : 1.0);
204 dmass += dens * (*_dfluid_saturation_nodal_dvar)[_i][ph][pvar] *
205 _mass_frac[_i][ph][_fluid_component] * _porosity[_i];
206 dmass += dens * _fluid_saturation_nodal[_i][ph] *
207 (*_dmass_frac_dvar)[_i][ph][_fluid_component][pvar] * _porosity[_i];
208 dmass += dens * _fluid_saturation_nodal[_i][ph] * _mass_frac[_i][ph][_fluid_component] *
209 (*_dporosity_dvar)[_i][pvar];
211 return _test[_i][_qp] * (1.0 + strain) * dmass / _dt;
214 libmesh_ignore(pvar);