26 #ifndef COUPLEDELEMENT_H
27 #define COUPLEDELEMENT_H
38 #ifndef VCOUPLEDELEMENT_H
39 #define VCOUPLEDELEMENT_H
48 template<
class ELEMENT>
103 const unsigned DIM = this->dim();
107 lin_mo.initialise(0);
108 ang_mo.initialise(0);
114 unsigned n_intpt = this->integral_pt()->nweight();
117 Vector<double> s(DIM);
120 const unsigned n_node = this->nnode();
123 const unsigned n_position_type = this->nnodal_position_type();
126 Shape psi(n_node, n_position_type);
127 DShape dpsidxi(n_node, n_position_type, DIM);
130 double lambda_sq = this->lambda_sq();
133 for (
unsigned ipt = 0; ipt < n_intpt; ipt++)
136 for (
unsigned i = 0;
i < DIM;
i++)
137 { s[
i] = this->integral_pt()->knot(ipt,
i); }
140 double w = this->integral_pt()->weight(ipt);
143 double J = this->dshape_lagrangian_at_knot(ipt, psi, dpsidxi);
146 double coupling_w = 0;
147 for (
unsigned l = 0; l < n_node; l++)
149 double nodal_coupling_w =
dynamic_cast<CoupledSolidNode*
>(this->node_pt(l))->get_coupling_weight();
150 double psi_ = psi(l);
151 coupling_w += psi_ * nodal_coupling_w;
155 Vector<double> interpolated_xi(DIM, 0.0);
156 Vector<double> veloc(DIM, 0.0);
159 for (
unsigned l = 0; l < n_node; l++)
162 for (
unsigned k = 0; k < n_position_type; k++)
165 for (
unsigned i = 0;
i < DIM;
i++)
168 interpolated_xi[
i] += this->lagrangian_position_gen(l, k,
i) * psi(l, k);
173 veloc[
i] += this->dnodal_position_gen_dt(l, k,
i) * psi(l, k);
181 this->get_isotropic_growth(ipt, s, interpolated_xi,
gamma);
185 double W =
gamma * w * ( 1.0 - coupling_w ) * J;
187 DenseMatrix<double> sigma(DIM, DIM);
188 DenseMatrix<double> strain(DIM, DIM);
191 this->get_stress(s, sigma);
194 for (
unsigned i = 0;
i < DIM;
i++)
196 for (
unsigned j = 0; j < DIM; j++)
198 sigma(
i, j) += this->prestress(
i, j, interpolated_xi);
203 this->get_strain(s, strain);
206 double local_pot_en = 0;
210 for (
unsigned i = 0;
i < DIM;
i++)
212 for (
unsigned j = 0; j < DIM; j++)
214 local_pot_en += sigma(
i, j) * strain(
i, j);
216 veloc_sq += veloc[
i] * veloc[
i];
220 mass += lambda_sq * W;
222 Vector<double> cross_product(DIM, 0);
223 VectorHelpers::cross(interpolated_xi, veloc, cross_product);
224 for (
unsigned i = 0;
i < DIM;
i++)
226 lin_mo[
i] += lambda_sq * veloc[
i] * W;
227 ang_mo[
i] += lambda_sq * cross_product[
i] * W;
230 pot_en += 0.5 * local_pot_en * W;
232 kin_en += lambda_sq * 0.5 * veloc_sq * W;
239 DenseMatrix<double>& jacobian,
240 const unsigned& flag)
override
244 const unsigned DIM = this->dim();
247 if (this->Solid_ic_pt != 0)
249 this->fill_in_residuals_for_solid_ic(residuals);
254 const unsigned n_node = this->nnode();
257 const unsigned n_position_type = this->nnodal_position_type();
260 Shape psi(n_node, n_position_type);
261 DShape dpsidxi(n_node, n_position_type, DIM);
264 const unsigned n_intpt = this->integral_pt()->nweight();
267 Vector<double> s(DIM);
270 double lambda_sq = this->lambda_sq();
273 double time_factor = 0.0;
276 time_factor = this->node_pt(0)->position_time_stepper_pt()->weight(2, 0);
283 for (
unsigned ipt = 0; ipt < n_intpt; ipt++)
286 for (
unsigned i = 0;
i < DIM; ++
i)
287 { s[
i] = this->integral_pt()->knot(ipt,
i); }
290 double w = this->integral_pt()->weight(ipt);
293 double J = this->dshape_lagrangian_at_knot(ipt, psi, dpsidxi);
296 double coupling_w = 0;
297 for (
unsigned l = 0; l < n_node; l++)
299 double nodal_coupling_w =
dynamic_cast<CoupledSolidNode*
>(this->node_pt(l))->get_coupling_weight();
300 double psi_ = psi(l);
301 coupling_w += psi_ * nodal_coupling_w;
306 DenseMatrix<double> interpolated_G(DIM);
309 Vector<double> accel(DIM);
312 for (
unsigned i = 0;
i < DIM;
i++)
316 for (
unsigned j = 0; j < DIM; j++)
318 interpolated_G(
i, j) = 0.0;
323 Vector<double> interpolated_xi(DIM, 0.0);
326 for (
unsigned l = 0; l < n_node; l++)
329 for (
unsigned k = 0; k < n_position_type; k++)
331 double psi_ = psi(l, k);
333 for (
unsigned i = 0;
i < DIM;
i++)
336 interpolated_xi[
i] += this->lagrangian_position_gen(l, k,
i) * psi_;
339 if (( lambda_sq > 0.0 ) && ( this->Unsteady ))
341 accel[
i] += this->dnodal_position_gen_dt(2, l, k,
i) * psi_;
345 for (
unsigned j = 0; j < DIM; j++)
347 interpolated_G(j,
i) +=
348 this->nodal_position_gen(l, k,
i) * dpsidxi(l, k, j);
356 this->get_isotropic_growth(ipt, s, interpolated_xi,
gamma);
360 Vector<double> b(DIM);
361 this->body_force(interpolated_xi, b);
366 double diag_entry = pow(
gamma, 2.0 /
double(DIM));
367 DenseMatrix<double> g(DIM);
368 for (
unsigned i = 0;
i < DIM;
i++)
370 for (
unsigned j = 0; j < DIM; j++)
373 { g(
i, j) = diag_entry; }
381 double W =
gamma * w * ( 1.0 - coupling_w ) * J;
384 DenseMatrix<double> G(DIM);
387 for (
unsigned i = 0;
i < DIM;
i++)
390 for (
unsigned j =
i; j < DIM; j++)
395 for (
unsigned k = 0; k < DIM; k++)
397 G(
i, j) += interpolated_G(
i, k) * interpolated_G(j, k);
401 for (
unsigned j = 0; j <
i; j++)
408 DenseMatrix<double> sigma(DIM);
409 ELEMENT::get_stress(g, G, sigma);
412 for (
unsigned i = 0;
i < DIM;
i++)
414 for (
unsigned j = 0; j < DIM; j++)
416 sigma(
i, j) += this->prestress(
i, j, interpolated_xi);
424 RankFourTensor<double> d_stress_dG(DIM, DIM, DIM, DIM, 0.0);
426 RankFiveTensor<double> d_G_dX(n_node, n_position_type, DIM, DIM, DIM, 0.0);
436 for (
unsigned ll = 0; ll < n_node; ll++)
438 for (
unsigned kk = 0; kk < n_position_type; kk++)
440 for (
unsigned ii = 0; ii < DIM; ii++)
442 for (
unsigned aa = 0; aa < DIM; aa++)
444 for (
unsigned bb = aa; bb < DIM; bb++)
446 d_G_dX(ll, kk, ii, aa, bb) =
447 interpolated_G(aa, ii) * dpsidxi(ll, kk, bb) +
448 interpolated_G(bb, ii) * dpsidxi(ll, kk, aa);
457 this->get_d_stress_dG_upper(g, G, sigma, d_stress_dG);
463 for (
unsigned l = 0; l < n_node; l++)
466 for (
unsigned k = 0; k < n_position_type; k++)
469 const unsigned offset5 = dpsidxi.offset(l, k);
472 for (
unsigned i = 0;
i < DIM;
i++)
475 local_eqn = this->position_local_eqn(l, k,
i);
484 sum += ( lambda_sq * accel[
i] - b[
i] ) * psi(l, k);
487 for (
unsigned a = 0; a < DIM; a++)
489 unsigned count = offset5;
490 for (
unsigned b = 0; b < DIM; b++)
493 sum += sigma(a, b) * interpolated_G(a,
i) *
494 dpsidxi.raw_direct_access(count);
498 residuals[local_eqn] += W * sum;
504 const unsigned offset1 = d_G_dX.offset(l, k,
i);
507 for (
unsigned ll = 0; ll < n_node; ll++)
510 for (
unsigned kk = 0; kk < n_position_type; kk++)
513 for (
unsigned ii = 0; ii < DIM; ii++)
516 int local_unknown = this->position_local_eqn(ll, kk, ii);
519 if (local_unknown >= 0)
522 const unsigned offset2 = d_G_dX.offset(ll, kk, ii);
523 const unsigned offset4 = dpsidxi.offset(ll, kk);
528 unsigned count1 = offset1;
529 for (
unsigned a = 0; a < DIM; a++)
534 for (
unsigned b = a; b < DIM; b++)
536 double factor = d_G_dX.raw_direct_access(count1);
537 if (a == b) factor *= 0.5;
540 unsigned offset3 = d_stress_dG.offset(a, b);
541 unsigned count2 = offset2;
542 unsigned count3 = offset3;
544 for (
unsigned aa = 0; aa < DIM; aa++)
552 for (
unsigned bb = aa; bb < DIM; bb++)
555 d_stress_dG.raw_direct_access(count3) *
556 d_G_dX.raw_direct_access(count2);
568 jacobian(local_eqn, local_unknown) += sum * W;
572 if ((
i == ii ) && ( local_unknown >= local_eqn ))
578 sum += lambda_sq * time_factor * psi(ll, kk) * psi(l, k);
581 unsigned count4 = offset4;
582 for (
unsigned a = 0; a < DIM; a++)
585 const double factor =
586 dpsidxi.raw_direct_access(count4);
589 unsigned count5 = offset5;
590 for (
unsigned b = 0; b < DIM; b++)
592 sum += sigma(a, b) * factor *
593 dpsidxi.raw_direct_access(count5);
598 jacobian(local_eqn, local_unknown) += sum * W;
600 if (local_eqn != local_unknown)
602 jacobian(local_unknown, local_eqn) += sum * W;
622 DenseMatrix<double>& jacobian,
623 const unsigned& flag)
629 const unsigned n_node = this->nnode();
630 const unsigned DIM = this->dim();
633 unsigned n_position_type = this->nnodal_position_type();
641 for (
unsigned l = 0; l < n_node; l++)
644 for (
unsigned k = 0; k < n_position_type; k++)
647 for (
unsigned i = 0;
i < DIM;
i++)
650 local_eqn = this->position_local_eqn(l, k,
i);
664 for (
unsigned ll = 0; ll < n_node; ll++)
667 for (
unsigned kk = 0; kk < n_position_type; kk++)
670 for (
unsigned ii = 0; ii < DIM; ii++)
673 int local_unknown = this->position_local_eqn(ll, kk, ii);
675 if (( local_unknown >= 0 ) && (
i == ii ) && ( local_unknown >= local_eqn ))
679 if (local_eqn != local_unknown)
693 void output(std::ostream& outfile,
const unsigned& n_plot)
override
695 const unsigned DIM = this->dim();
696 Vector<double> x(DIM);
697 Vector<double> dxdt(DIM);
698 Vector<double> s(DIM);
701 outfile << this->tecplot_zone_string(n_plot);
704 unsigned num_plot_points = this->nplot_points(n_plot);
705 for (
unsigned iplot = 0; iplot < num_plot_points; iplot++)
708 this->get_s_plot(iplot, n_plot, s);
711 this->interpolated_x(s, x);
712 SolidFiniteElement* el_pt =
dynamic_cast<SolidFiniteElement*
>(
this);
713 el_pt->interpolated_dxdt(s, 1, dxdt);
719 for (
unsigned i = 0;
i < DIM;
i++)
723 for (
unsigned i = 0;
i < DIM;
i++)
730 const unsigned n_node = this->nnode();
732 const unsigned n_position_type = this->nnodal_position_type();
734 Shape psi(n_node, n_position_type);
740 for (
unsigned l = 0; l < n_node; l++)
742 double nodal_coupling_w =
dynamic_cast<CoupledSolidNode*
>(this->node_pt(l))->get_coupling_weight();
743 w += nodal_coupling_w * psi(l);
748 outfile << std::endl;
752 this->write_tecplot_zone_footer(outfile, n_plot);
753 outfile << std::endl;
771 template<
class ELEMENT>
Definition: CoupledSolidNodes.h:16
FaceGeometry()
Constructor [this was only required explicitly from gcc 4.5.2 onwards...].
Definition: VCoupledElement.h:779
Definition: VCoupledElement.h:50
void add_internal_coupling_forces_to_residuals(Vector< double > &residuals, DenseMatrix< double > &jacobian, const unsigned &flag)
Add the point source contribution to the residual vector.
Definition: VCoupledElement.h:621
Vector< Vector< double > > nodal_coupling_residual
Nodal coupling forces.
Definition: VCoupledElement.h:757
Vector< Vector< double > > nodal_coupling_jacobian
Nodal coupling jacobian.
Definition: VCoupledElement.h:760
void fill_in_contribution_to_residuals(Vector< double > &residuals) override
Add the element's contribution to its residual vector (wrapper)
Definition: VCoupledElement.h:63
VolumeCoupledElement()
Constructor: Call constructor of underlying element.
Definition: VCoupledElement.h:55
double & getCouplingStiffness(const unsigned &m, const unsigned &l)
Definition: VCoupledElement.h:97
void setCouplingStiffness(Vector< Vector< double > > &cStiffness)
Definition: VCoupledElement.h:94
void fill_in_generic_contribution_to_residuals_pvd(Vector< double > &residuals, DenseMatrix< double > &jacobian, const unsigned &flag) override
Definition: VCoupledElement.h:238
double & get_nodal_coupling_jacobian(const unsigned &l, const unsigned &ll)
Definition: VCoupledElement.h:91
void set_nodal_coupling_jacobian(Vector< Vector< double > > &cJacobian)
Definition: VCoupledElement.h:88
void set_nodal_coupling_residual(Vector< Vector< double > > &cResidual)
Definition: VCoupledElement.h:82
double & get_nodal_coupling_residual(const unsigned &l, const unsigned &i)
Definition: VCoupledElement.h:85
Vector< Vector< double > > couplingStiffness
Coupling stiffness to discrete particles (FIXME: should be moved into DPMVCoupledElement)
Definition: VCoupledElement.h:763
void output(std::ostream &outfile, const unsigned &n_plot) override
Definition: VCoupledElement.h:693
~VolumeCoupledElement()
Destructor (empty)
Definition: VCoupledElement.h:59
void fill_in_contribution_to_jacobian(Vector< double > &residuals, DenseMatrix< double > &jacobian) override
Add the element's contribution to its residual vector and Jacobian matrix (wrapper)
Definition: VCoupledElement.h:73
void get_momentum_and_energy(double &mass, Vector< double > &lin_mo, Vector< double > &ang_mo, double &pot_en, double &kin_en)
Definition: VCoupledElement.h:100
Global variables.
Definition: TwenteMeshGluing.cpp:56
double lenScale
Length scale.
Definition: VCoupledElement.h:31
double timeScale
Time scale.
Definition: VCoupledElement.h:34
const std::complex< Mdouble > i
Definition: ExtendedMath.h:51
Mdouble gamma(Mdouble gamma_in)
This is the gamma function returns the true value for the half integer value.
Definition: ExtendedMath.cc:137
Definition: AnisotropicHookean.h:31