306 {
308
309 const size_t nb_gauss_pts = getGaussPts().size2();
310 const size_t row_nb_dofs = row_data.
getIndices().size();
311 const size_t col_nb_dofs = col_data.
getIndices().size();
312
313 if (row_nb_dofs && col_nb_dofs) {
314
315
316 auto t_normal = getFTensor1Normal();
317 const double ls = sqrt(t_normal(
i) * t_normal(
i));
319
320 auto t_disp = getFTensor1FromMat<3>(*(
commonDataPtr->mDispPtr));
321 auto t_traction =
323 auto t_coords = getFTensor1CoordsAtGaussPts();
324
325 auto t_w = getFTensor0IntegrationWeight();
327 size_t nb_face_functions = row_data.
getN().size2() / 3;
328
329 auto t_contact_normal =
331 auto t_gap = getFTensor0FromVec(*(
commonDataPtr->contactGapPtr));
332 auto t_gap_diff =
334 auto t_diff_normal =
335 getFTensor2FromMat<3, 3>(*(
commonDataPtr->contactNormalDiffPtr));
337 auto &
cn = (*cache).cn_cont;
338
339 for (size_t gg = 0; gg != nb_gauss_pts; ++gg) {
340
341 const double alpha = t_w * getMeasure();
342
343 if (getNormalsAtGaussPts().size1() == nb_gauss_pts) {
345 auto t_n = getFTensor1FromPtr<3>(&*
n.data().begin());
346 t_normal(
i) = t_n(
i) / sqrt(t_n(
j) * t_n(
j));
347 }
348
349 Tensor3<double, 3, 3, 3> t_diff_contact_tangent_tensor;
350 t_diff_contact_tangent_tensor(
i,
j,
k) =
351 -t_diff_normal(
i,
k) * t_contact_normal(
j) -
352 t_contact_normal(
i) * t_diff_normal(
j,
k);
353
354 Tensor2<double, 3, 3> t_P;
355 t_P(
i,
j) = t_contact_normal(
i) * t_contact_normal(
j);
356
357 Tensor2<double, 3, 3> t_Q;
359 const double gap_0 =
gap0(t_gap, t_disp, t_contact_normal);
360
361 t1(
i) = t_contact_normal(
i) - 0.5 * t_gap_diff(
i) +
362 0.5 *
cn * t_traction(
j) * t_diff_normal(
i,
j) +
363 t_disp(
j) * t_diff_normal(
i,
j) +
364 0.5 *
sign(t_gap +
cn * t_traction(
k) * t_contact_normal(
k)) *
365 (t_gap_diff(
i) +
cn * t_traction(
j) * t_diff_normal(
i,
j));
366
369 size_t rr = 0;
370 for (; rr != row_nb_dofs / 3; ++rr) {
371
372 auto t_mat = getFTensor2FromArray<3, 3, 3>(locMat, 3 * rr);
373 const double row_base = t_row_base(
i) * t_normal(
i);
374
376
377 for (size_t cc = 0; cc != col_nb_dofs / 3; ++cc) {
378 const double beta =
alpha * row_base * t_col_base;
379
380
381 t_mat(
i,
j) -= beta * t_contact_normal(
i) * t1(
j);
383
384
385 t_mat(
i,
j) -= beta * t_Q(
i,
j);
387 beta * t_diff_contact_tangent_tensor(
i,
j,
k) * t_disp(
j);
388
389
390 t_mat(
i,
k) += beta * t_diff_contact_tangent_tensor(
i,
j,
k) *
391 (*cache).cn_cont * t_traction(
j);
392
393 ++t_col_base;
394 ++t_mat;
395 }
396 ++t_row_base;
397 }
398 for (; rr < nb_face_functions; ++rr)
399 ++t_row_base;
400
401 ++t_contact_normal;
402 ++t_gap;
403 ++t_gap_diff;
404 ++t_diff_normal;
405 ++t_disp;
406 ++t_traction;
407 ++t_coords;
408 ++t_w;
409 }
410
411 }
412
414}
#define MoFEMFunctionBegin
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
#define MoFEMFunctionReturn(a)
Last executable line of each PETSc function used for error handling. Replaces return()
FTensor::Index< 'n', SPACE_DIM > n
FTensor::Index< 'i', SPACE_DIM > i
FTensor::Index< 'j', 3 > j
FTensor::Index< 'k', 3 > k
Tensor2_Expr< Kronecker_Delta< T >, T, Dim0, Dim1, i, j > kronecker_delta(const Index< i, Dim0 > &, const Index< j, Dim1 > &)
Rank 2.
UBlasVector< double > VectorDouble
FTensor::Tensor0< FTensor::PackPtr< double *, 1 > > getFTensor0N(const FieldApproximationBase base)
Get base function as Tensor0.
MatrixDouble & getN(const FieldApproximationBase base)
get base functions this return matrix (nb. of rows is equal to nb. of Gauss pts, nb....
FTensor::Tensor1< FTensor::PackPtr< double *, Tensor_Dim >, Tensor_Dim > getFTensor1N(FieldApproximationBase base)
Get base functions for Hdiv/Hcurl spaces.
const VectorInt & getIndices() const
Get global indices of dofs on entity.