42 #define CREATE_PROFILE 1
69 extern "C" int __FC_DECL__(def_joint_ad_ass_res)(
const doublereal X1[3],
90 extern "C" int __FC_DECL__(def_joint_ad_ass_res_dv)(
const doublereal X1[3],
124 using namespace grad;
129 DeformableJointAD(
unsigned uLabel,
const DofOwner *pDO,
131 virtual ~DeformableJointAD(
void);
133 virtual void WorkSpaceDim(
integer* piNumRows,
integer* piNumCols)
const;
164 template <
typename T>
171 unsigned int iGetNumPrivData(
void)
const;
172 int iGetNumConnectedNodes(
void)
const;
173 void GetConnectedNodes(std::vector<const Node *>& connectedNodes)
const;
176 std::ostream& Restart(std::ostream& out)
const;
177 virtual unsigned int iGetInitialNumDof(
void)
const;
179 InitialWorkSpaceDim(
integer* piNumRows,
integer* piNumCols)
const;
202 TEMPLATE_META_PROG = 1,
206 #if CREATE_PROFILE == 1
220 static const char* AssemblyFuncName(
enum AssemblyFlag
flag);
224 DeformableJointAD::DeformableJointAD(
225 unsigned uLabel,
const DofOwner *pDO,
234 #if CREATE_PROFILE == 1
235 memset(&profile, 0,
sizeof(profile));
243 "Module: DeformableJointAD\n"
245 " deformable joint ad,\n"
246 " node1, (label) <node1>,\n"
247 " [offset, (Vec3) <o1>,]\n"
248 " node2, (label) <node2>,\n"
249 " [offset, (Vec3) <o2>,]\n"
250 " stiffness, (Mat3x3) S1,\n"
251 " damping, (Mat3x3) D1,\n"
265 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): keyword \"node1\" expected at line " << HP.
GetLineData() << std::endl);
272 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): structural node expected at line " << HP.
GetLineData() << std::endl);
282 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): keyword \"node2\" expected at line " << HP.
GetLineData() << std::endl);
289 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): structural node expected at line " << HP.
GetLineData() << std::endl);
298 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): keyword \"stiffness\" expected at line " << HP.
GetLineData() << std::endl);
305 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): keyword \"damping\" expected at line " << HP.
GetLineData() << std::endl);
314 }
else if (HP.
IsKeyWord(
"template" "meta" "program")) {
315 fRes = TEMPLATE_META_PROG;
319 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): keyword \"traditional\" or \"template meta program\" expected at line " << HP.
GetLineData() << std::endl);
327 }
else if (HP.
IsKeyWord(
"template" "meta" "program")) {
328 fJac = TEMPLATE_META_PROG;
332 silent_cerr(
"deformable joint ad" << GetLabel() <<
"): keyword \"traditional\" or \"template meta program\" expected at line " << HP.
GetLineData() << std::endl);
340 DeformableJointAD::~DeformableJointAD(
void)
342 #if CREATE_PROFILE == 1
343 std::cerr <<
"deformable joint ad(" << GetLabel() <<
")" << std::endl;
345 std::cerr <<
"dtRes["
346 << AssemblyFuncName(fRes)
347 <<
"]=" << profile.dtRes << std::endl;
349 std::cerr <<
"dtJac["
350 << AssemblyFuncName(fJac)
351 <<
"]=" << profile.dtJac << std::endl;
354 std::cerr <<
"dtInit[RESIDUAL]=" << profile.dtInit[RESIDUAL] << std::endl;
355 std::cerr <<
"dtGet[RESIDUAL]=" << profile.dtGet[RESIDUAL] << std::endl;
356 std::cerr <<
"dtCalc[RESIDUAL]=" << profile.dtCalc[RESIDUAL] << std::endl;
357 std::cerr <<
"dtAss[RESIDUAL]=" << profile.dtAss[RESIDUAL] << std::endl;
359 std::cerr <<
"dtInit[JACOBIAN]=" << profile.dtInit[JACOBIAN] << std::endl;
360 std::cerr <<
"dtGet[JACOBIAN]=" << profile.dtGet[JACOBIAN] << std::endl;
361 std::cerr <<
"dtCalc[JACOBIAN]=" << profile.dtCalc[JACOBIAN] << std::endl;
362 std::cerr <<
"dtAss[JACOBIAN]=" << profile.dtAss[JACOBIAN] << std::endl;
364 std::cerr << std::endl;
375 DeformableJointAD::WorkSpaceDim(
integer* piNumRows,
integer* piNumCols)
const
387 #if CREATE_PROFILE == 1
393 AssJacTrad(WorkMat, dCoef, XCurr, XPrimeCurr);
396 case TEMPLATE_META_PROG:
407 AssJacF77(WorkMat, dCoef, XCurr, XPrimeCurr);
414 #if CREATE_PROFILE == 1
427 #if CREATE_PROFILE == 1
433 AssResTrad(WorkVec, dCoef, XCurr, XPrimeCurr);
436 case TEMPLATE_META_PROG:
446 AssResF77(WorkVec, dCoef, XCurr, XPrimeCurr);
453 #if CREATE_PROFILE == 1
466 #if CREATE_PROFILE == 1
470 const Vec3& X1 = pNode1->GetXCurr();
471 const Vec3&
V1 = pNode1->GetVCurr();
472 const Mat3x3& R1 = pNode1->GetRCurr();
473 const Mat3x3& R1_0 = pNode1->GetRRef();
474 const Vec3& W1 = pNode1->GetWCurr();
475 const Vec3& W1_0 = pNode1->GetWRef();
477 const Vec3& X2 = pNode2->GetXCurr();
478 const Vec3&
V2 = pNode2->GetVCurr();
479 const Mat3x3& R2 = pNode2->GetRCurr();
480 const Mat3x3& R2_0 = pNode2->GetRRef();
481 const Vec3& W2 = pNode2->GetWCurr();
482 const Vec3& W2_0 = pNode2->GetWRef();
484 #if CREATE_PROFILE == 1
489 const Vec3 R1o1 = R1 * o1;
491 const Vec3 R1_0o1 = R1_0 * o1;
493 const Vec3 R2o2 = R2 * o2;
495 const Vec3 R2_0o2 = R2_0 * o2;
497 const Vec3 dX = R1.
MulTV(X1 + R1o1 - X2 - R2o2);
499 const Vec3 F1_R1 = -(S1 * dX + D1 * dV);
500 const Vec3 F1 = R1 * F1_R1;
514 const Mat3x3 dF1_dg2 = -R1 * (S1 * ddX_dg2 + D1 * ddV_dg2);
516 const Mat3x3 dF2_dX1 = -dF1_dX1;
517 const Mat3x3 dF2_dg1 = -dF1_dg1;
518 const Mat3x3 dF2_dX2 = -dF1_dX2;
519 const Mat3x3 dF2_dg2 = -dF1_dg2;
521 const Mat3x3 dM1_dX1 = skew_R1o1 * dF1_dX1;
523 const Mat3x3 dM1_dX2 = skew_R1o1 * dF1_dX2;
524 const Mat3x3 dM1_dg2 = skew_R1o1 * dF1_dg2;
526 const Mat3x3 dM2_dX1 = skew_R2o2 * dF2_dX1;
527 const Mat3x3 dM2_dg1 = skew_R2o2 * dF2_dg1;
528 const Mat3x3 dM2_dX2 = skew_R2o2 * dF2_dX2;
533 const Mat3x3 dF1_dgP1 = -R1 * D1 * ddV_dgP1;
537 const Mat3x3 dF1_dgP2 = -R1 * D1 * ddV_dgP2;
539 const Mat3x3 dM1_dV1 = skew_R1o1 * dF1_dV1;
540 const Mat3x3 dM1_dgP1 = skew_R1o1 * dF1_dgP1;
541 const Mat3x3 dM1_dV2 = skew_R1o1 * dF1_dV2;
542 const Mat3x3 dM1_dgP2 = skew_R1o1 * dF1_dgP2;
544 const Mat3x3 dF2_dV1 = -dF1_dV1;
545 const Mat3x3 dF2_dgP1 = -dF1_dgP1;
546 const Mat3x3 dF2_dV2 = -dF1_dV2;
547 const Mat3x3 dF2_dgP2 = -dF1_dgP2;
549 const Mat3x3 dM2_dV1 = skew_R2o2 * dF2_dV1;
550 const Mat3x3 dM2_dgP1 = skew_R2o2 * dF2_dgP1;
551 const Mat3x3 dM2_dV2 = skew_R2o2 * dF2_dV2;
552 const Mat3x3 dM2_dgP2 = skew_R2o2 * dF2_dgP2;
554 #if CREATE_PROFILE == 1
563 WorkSpaceDim(&iNumRows, &iNumCols);
567 const integer iFirstMomIndexNode1 = pNode1->iGetFirstMomentumIndex();
568 const integer iFirstMomIndexNode2 = pNode2->iGetFirstMomentumIndex();
569 const integer iFirstPosIndexNode1 = pNode1->iGetFirstPositionIndex();
570 const integer iFirstPosIndexNode2 = pNode2->iGetFirstPositionIndex();
572 for (
integer i = 1; i <= 6; ++i) {
574 WorkMat.
PutRowIndex(i + 6, iFirstMomIndexNode2 + i);
576 WorkMat.
PutColIndex(i + 6, iFirstPosIndexNode2 + i);
579 WorkMat.
Put(1, 1, -dF1_dV1 - dF1_dX1 * dCoef);
580 WorkMat.
Put(1, 4, -dF1_dgP1 - dF1_dg1 * dCoef);
581 WorkMat.
Put(1, 7, -dF1_dV2 - dF1_dX2 * dCoef);
582 WorkMat.
Put(1, 10, -dF1_dgP2 - dF1_dg2 * dCoef);
584 WorkMat.
Put(4, 1, -dM1_dV1 - dM1_dX1 * dCoef);
585 WorkMat.
Put(4, 4, -dM1_dgP1 - dM1_dg1 * dCoef);
586 WorkMat.
Put(4, 7, -dM1_dV2 - dM1_dX2 * dCoef);
587 WorkMat.
Put(4, 10, -dM1_dgP2 - dM1_dg2 * dCoef);
589 WorkMat.
Put(7, 1, -dF2_dV1 - dF2_dX1 * dCoef);
590 WorkMat.
Put(7, 4, -dF2_dgP1 - dF2_dg1 * dCoef);
591 WorkMat.
Put(7, 7, -dF2_dV2 - dF2_dX2 * dCoef);
592 WorkMat.
Put(7, 10, -dF2_dgP2 - dF2_dg2 * dCoef);
594 WorkMat.
Put(10, 1, -dM2_dV1 - dM2_dX1 * dCoef);
595 WorkMat.
Put(10, 4, -dM2_dgP1 - dM2_dg1 * dCoef);
596 WorkMat.
Put(10, 7, -dM2_dV2 - dM2_dX2 * dCoef);
597 WorkMat.
Put(10, 10, -dM2_dgP2 - dM2_dg2 * dCoef);
599 #if CREATE_PROFILE == 1
612 #if CREATE_PROFILE == 1
616 const Vec3& X1 = pNode1->GetXCurr();
617 const Vec3& XP1 = pNode1->GetVCurr();
618 const Mat3x3& R1 = pNode1->GetRCurr();
619 const Vec3& W1 = pNode1->GetWCurr();
621 const Vec3& X2 = pNode2->GetXCurr();
622 const Vec3& XP2 = pNode2->GetVCurr();
623 const Mat3x3& R2 = pNode2->GetRCurr();
624 const Vec3& W2 = pNode2->GetWCurr();
626 #if CREATE_PROFILE == 1
631 const Vec3 R1o1 = R1 * o1;
632 const Vec3 R2o2 = R2 * o2;
633 const Vec3 dX = R1.
MulTV(X1 + R1o1 - X2 - R2o2);
635 const Vec3 F1 = -(R1 * (S1 * dX + D1 * dXP));
640 #if CREATE_PROFILE == 1
645 const integer iFirstMomIndexNode1 = pNode1->iGetFirstMomentumIndex();
646 const integer iFirstMomIndexNode2 = pNode2->iGetFirstMomentumIndex();
650 WorkSpaceDim(&iNumRows, &iNumCols);
654 for (
integer i = 1; i <= 6; ++i) {
656 WorkVec.
PutRowIndex(i + 6, iFirstMomIndexNode2 + i);
664 #if CREATE_PROFILE == 1
677 #if CREATE_PROFILE == 1
682 const doublereal* g1 = pNode1->GetgCurr().pGetVec();
684 const doublereal* gP1 = pNode1->GetgPCurr().pGetVec();
688 const doublereal* g2 = pNode2->GetgCurr().pGetVec();
690 const doublereal* gP2 = pNode2->GetgPCurr().pGetVec();
694 doublereal X1d[3][12] = {{0.}}, g1d[3][12] = {{0.}};
695 doublereal XP1d[3][12] = {{0.}}, gP1d[3][12] = {{0.}};
696 doublereal X2d[3][12] = {{0.}}, g2d[3][12] = {{0.}};
697 doublereal XP2d[3][12] = {{0.}}, gP2d[3][12] = {{0.}};
699 for (
integer i = 0; i < 3; ++i) {
702 g1d[i][i + 3] = -dCoef;
703 gP1d[i][i + 3] = -1.;
704 X2d[i][i + 6] = -dCoef;
705 XP2d[i][i + 6] = -1.;
706 g2d[i][i + 9] = -dCoef;
707 gP2d[i][i + 9] = -1.;
710 #if CREATE_PROFILE == 1
716 doublereal F1d[3][12], M1d[3][12], F2d[3][12], M2d[3][12];
718 __FC_DECL__(def_joint_ad_ass_res_dv)(X1,
752 #if CREATE_PROFILE == 1
761 WorkSpaceDim(&iNumRows, &iNumCols);
765 const integer iFirstMomIndexNode1 = pNode1->iGetFirstMomentumIndex();
766 const integer iFirstMomIndexNode2 = pNode2->iGetFirstMomentumIndex();
767 const integer iFirstPosIndexNode1 = pNode1->iGetFirstPositionIndex();
768 const integer iFirstPosIndexNode2 = pNode2->iGetFirstPositionIndex();
770 for (
integer i = 1; i <= 6; ++i) {
772 WorkMat.
PutRowIndex(i + 6, iFirstMomIndexNode2 + i);
774 WorkMat.
PutColIndex(i + 6, iFirstPosIndexNode2 + i);
777 for (
integer i = 0; i < 3; ++i) {
778 for (
integer j = 0; j < 12; ++j) {
779 WorkMat.
PutCoef(i + 1, j + 1, F1d[i][j]);
780 WorkMat.
PutCoef(i + 4, j + 1, M1d[i][j]);
781 WorkMat.
PutCoef(i + 7, j + 1, F2d[i][j]);
782 WorkMat.
PutCoef(i + 10, j + 1, M2d[i][j]);
786 #if CREATE_PROFILE == 1
799 #if CREATE_PROFILE == 1
803 const doublereal* X1 = pNode1->GetXCurr().pGetVec();
804 const doublereal* g1 = pNode1->GetgCurr().pGetVec();
805 const doublereal* XP1 = pNode1->GetVCurr().pGetVec();
806 const doublereal* gP1 = pNode1->GetgPCurr().pGetVec();
807 const doublereal* R1_0 = pNode1->GetRRef().pGetMat();
808 const doublereal* W1_0 = pNode1->GetWRef().pGetVec();
809 const doublereal* X2 = pNode2->GetXCurr().pGetVec();
810 const doublereal* g2 = pNode2->GetgCurr().pGetVec();
811 const doublereal* XP2 = pNode2->GetVCurr().pGetVec();
812 const doublereal* gP2 = pNode2->GetgPCurr().pGetVec();
813 const doublereal* R2_0 = pNode2->GetRRef().pGetMat();
814 const doublereal* W2_0 = pNode2->GetWRef().pGetVec();
816 #if CREATE_PROFILE == 1
823 __FC_DECL__(def_joint_ad_ass_res)(X1,
844 #if CREATE_PROFILE == 1
849 const integer iFirstMomIndexNode1 = pNode1->iGetFirstMomentumIndex();
850 const integer iFirstMomIndexNode2 = pNode2->iGetFirstMomentumIndex();
854 WorkSpaceDim(&iNumRows, &iNumCols);
858 for (
integer i = 1; i <= 6; ++i) {
860 WorkVec.
PutRowIndex(i + 6, iFirstMomIndexNode2 + i);
863 for (
integer i = 0; i < 3; ++i) {
867 WorkVec.
PutCoef(10 + i, M2[i]);
870 #if CREATE_PROFILE == 1
877 template <
typename T>
887 #if CREATE_PROFILE == 1
892 Vec3 X1, X2, XP1, XP2, W1, W2;
894 #if CREATE_PROFILE == 1
900 pNode1->GetXCurr(X1, dCoef, func, &
dof);
901 pNode1->GetVCurr(XP1, dCoef, func, &
dof);
902 pNode1->GetRCurr(R1, dCoef, func, &
dof);
903 pNode1->GetWCurr(W1, dCoef, func, &
dof);
905 pNode2->GetXCurr(X2, dCoef, func, &
dof);
906 pNode2->GetVCurr(XP2, dCoef, func, &
dof);
907 pNode2->GetRCurr(R2, dCoef, func, &
dof);
908 pNode2->GetWCurr(W2, dCoef, func, &
dof);
910 #if CREATE_PROFILE == 1
915 const Vec3 R1o1 = R1 * o1;
916 const Vec3 R2o2 = R2 * o2;
917 const Vec3 dX =
Transpose(R1) * Vec3(X1 + R1o1 - X2 - R2o2);
920 const Vec3 F1 = -(R1 * Vec3(S1 * dX + D1 * dXP));
923 const Vec3 M1 =
Cross(R1o1, F1);
924 const Vec3 M2 =
Cross(R2o2, F2);
926 #if CREATE_PROFILE == 1
931 const integer iFirstMomIndexNode1 = pNode1->iGetFirstMomentumIndex();
932 const integer iFirstMomIndexNode2 = pNode2->iGetFirstMomentumIndex();
934 WorkVec.AddItem(iFirstMomIndexNode1 + 1, F1);
935 WorkVec.AddItem(iFirstMomIndexNode1 + 4, M1);
936 WorkVec.AddItem(iFirstMomIndexNode2 + 1, F2);
937 WorkVec.AddItem(iFirstMomIndexNode2 + 4, M2);
939 #if CREATE_PROFILE == 1
945 DeformableJointAD::iGetNumPrivData(
void)
const
951 DeformableJointAD::iGetNumConnectedNodes(
void)
const
957 DeformableJointAD::GetConnectedNodes(std::vector<const Node *>& connectedNodes)
const
959 connectedNodes.resize(iGetNumConnectedNodes());
960 connectedNodes[0] = pNode1;
961 connectedNodes[1] = pNode2;
973 DeformableJointAD::Restart(std::ostream& out)
const
979 DeformableJointAD::iGetInitialNumDof(
void)
const
985 DeformableJointAD::InitialWorkSpaceDim(
994 DeformableJointAD::InitialAssJac(
1004 DeformableJointAD::InitialAssRes(
1013 #if CREATE_PROFILE == 1
1014 const char* DeformableJointAD::AssemblyFuncName(
enum AssemblyFlag
flag)
1018 return "traditional";
1020 case TEMPLATE_META_PROG:
1021 return "template meta program";
1024 return "Fortran 77";
1035 InlineJointAD(
unsigned uLabel,
const DofOwner *pDO,
1037 virtual ~InlineJointAD(
void);
1041 virtual std::ostream&
DescribeDof(std::ostream& out,
const char *prefix,
bool bInitial)
const;
1042 virtual std::ostream&
DescribeEq(std::ostream& out,
const char *prefix,
bool bInitial)
const;
1058 template <
typename T>
1065 int iGetNumConnectedNodes(
void)
const;
1071 std::ostream&
Restart(std::ostream& out)
const;
1080 template <
typename T>
1093 enum LagrangeMultiplierIndex
1103 static const index_type iInitialWorkSpace = 28;
1106 InlineJointAD::InlineJointAD(
1107 unsigned uLabel,
const DofOwner *pDO,
1109 :
Elem(uLabel, flag(0)),
1117 memset(lambda, 0,
sizeof(lambda));
1123 "Module: InlineAD\n"
1125 " This element implements a inline joint with friction\n"
1127 " inline friction,\n"
1128 " node1, (label) <node1>,\n"
1129 " [ offset, (Vec3) <offset>, ]\n"
1130 " [ hinge, (Mat3x3) <orientation>, ]\n"
1131 " node2, (label) <node2>,\n"
1132 " [ offset, (Vec3) <offset>, ]\n"
1145 silent_cerr(
"inline friction(" << GetLabel() <<
"): keyword \"node1\" expected at line " << HP.
GetLineData() << std::endl);
1152 silent_cerr(
"inline friction ad(" << GetLabel() <<
"): structural node expected at line " << HP.
GetLineData() << std::endl);
1167 silent_cerr(
"inline friction ad(" << GetLabel() <<
"): keyword \"node2\" expected at line " << HP.
GetLineData() << std::endl);
1174 silent_cerr(
"inline friction ad(" << GetLabel() <<
"): structural node expected at line " << HP.
GetLineData() << std::endl);
1188 out <<
"inline joint ad: " << GetLabel() <<
" "
1189 << pNode1->GetLabel() <<
" "
1192 << pNode2->GetLabel() <<
" " << o2 <<
" "
1196 InlineJointAD::~InlineJointAD(
void)
1201 unsigned int InlineJointAD::iGetNumDof(
void)
const
1232 std::ostream& InlineJointAD::DescribeDof(std::ostream& out,
const char *prefix,
bool bInitial)
const
1234 const integer iFirstIndex = iGetFirstIndex();
1236 out << prefix << iFirstIndex + 1 <<
"->" << iFirstIndex + 2 <<
": reaction forces [lambda1, lambda2]" << std::endl;
1239 out << prefix << iFirstIndex + 3 <<
"->" << iFirstIndex + 4 <<
": reaction force derivatives [lambdaP1, lambdaP2]" << std::endl;
1245 std::ostream& InlineJointAD::DescribeEq(std::ostream& out,
const char *prefix,
bool bInitial)
const
1247 const integer iFirstIndex = iGetFirstIndex();
1249 out << prefix << iFirstIndex + 1 <<
"->" << iFirstIndex + 2 <<
": position constraints [c1, c2]" << std::endl;
1252 out << prefix << iFirstIndex + 3 <<
"->" << iFirstIndex + 4 <<
": velocity constraints [cP1, cP2]" << std::endl;
1258 unsigned int InlineJointAD::iGetNumPrivData(
void)
const
1263 unsigned int InlineJointAD::iGetPrivDataIdx(
const char *s)
const
1265 static const struct {
1273 const int N =
sizeof(data) /
sizeof(data[0]);
1275 for (
int i = 0; i < N; ++i) {
1276 if (0 == strcmp(data[i].name, s)) {
1277 return data[i].index;
1284 doublereal InlineJointAD::dGetPrivData(
unsigned int i)
const
1289 return lambda[i - 1];
1292 silent_cerr(
"inline ad(" << GetLabel() <<
"): invalid private data index " << i << std::endl);
1300 if ( bToBeOutput() )
1306 os << std::setw(8) << GetLabel() <<
" " << lambda[L1] <<
" " << lambda[L2] << std::endl;
1312 InlineJointAD::WorkSpaceDim(
integer* piNumRows,
integer* piNumCols)
const
1314 *piNumRows = *piNumCols = iWorkSpace;
1351 template <
typename T>
1362 const integer iFirstIndex = iGetFirstIndex();
1363 const integer iFirstMomentumIndexNode1 = pNode1->iGetFirstMomentumIndex();
1364 const integer iFirstMomentumIndexNode2 = pNode2->iGetFirstMomentumIndex();
1369 pNode1->GetXCurr(X1, dCoef, func, &
dof);
1370 pNode1->GetRCurr(R1, dCoef, func, &
dof);
1371 pNode2->GetXCurr(X2, dCoef, func, &
dof);
1372 pNode2->GetRCurr(R2, dCoef, func, &
dof);
1376 XCurr.GetVec(iFirstIndex + 1, lambda, 1., &
dof);
1378 const Vec3 R2o2 = R2 * o2;
1379 const Vec3 l1 = X2 + R2o2 - X1;
1381 const Vec3 F1 = R1 * Vec3(e.GetCol(2) * lambda(1) + e.GetCol(3) * lambda(2));
1382 const Vec3 M1 =
Cross(l1, F1);
1383 const Vec3 F2 = -F1;
1384 const Vec3 M2 =
Cross(R2o2, F2);
1388 WorkVec.AddItem(iFirstMomentumIndexNode1 + 1, F1);
1389 WorkVec.AddItem(iFirstMomentumIndexNode1 + 4, M1);
1390 WorkVec.AddItem(iFirstMomentumIndexNode2 + 1, F2);
1391 WorkVec.AddItem(iFirstMomentumIndexNode2 + 4, M2);
1393 for (
integer i = 1; i <= 2; ++i) {
1394 WorkVec.AddItem(iFirstIndex + i,
Dot(e.GetCol(i + 1),
a) / dCoef);
1399 InlineJointAD::iGetNumConnectedNodes(
void)
const
1405 InlineJointAD::GetConnectedNodes(std::vector<const Node *>& connectedNodes)
const
1407 connectedNodes.resize(iGetNumConnectedNodes());
1408 connectedNodes[0] = pNode1;
1409 connectedNodes[1] = pNode2;
1417 const integer iFirstIndex = iGetFirstIndex();
1419 for (
int i = 1; i <= 2; ++i) {
1420 X.
PutCoef(iFirstIndex + i, lambda[i - 1]);
1431 const integer iFirstIndex = iGetFirstIndex();
1433 for (
int i = 1; i <= 2; ++i) {
1434 lambda[i - 1] = XCurr(iFirstIndex + i);
1439 InlineJointAD::Restart(std::ostream& out)
const
1445 InlineJointAD::iGetInitialNumDof(
void)
const
1451 InlineJointAD::InitialWorkSpaceDim(
1455 *piNumRows = *piNumCols = iInitialWorkSpace;
1459 InlineJointAD::InitialAssJac(
1474 InlineJointAD::InitialAssRes(
1486 template <
typename T>
1495 Vec3 X1, XP1, X2, XP2, omega1, omega2;
1498 pNode1->GetXCurr(X1, 1., func, &
dof);
1499 pNode1->GetRCurr(R1, 1., func, &
dof);
1500 pNode1->GetVCurr(XP1, 1., func, &
dof);
1501 pNode1->GetWCurr(omega1, 1., func, &
dof);
1503 pNode2->GetXCurr(X2, 1., func, &
dof);
1504 pNode2->GetRCurr(R2, 1., func, &
dof);
1505 pNode2->GetVCurr(XP2, 1., func, &
dof);
1506 pNode2->GetWCurr(omega2, 1., func, &
dof);
1508 const integer iFirstIndexNode1 = pNode1->iGetFirstIndex();
1509 const integer iFirstIndexNode2 = pNode2->iGetFirstIndex();
1510 const integer iFirstIndex = iGetFirstIndex();
1512 T lambda[2], lambdaP[2];
1514 for (
integer i = 1; i <= 2; ++i) {
1515 XCurr.dGetCoef(iFirstIndex + i, lambda[i - 1], 1., &
dof);
1516 XCurr.dGetCoef(iFirstIndex + i + 2, lambdaP[i - 1], 1., &
dof);
1519 const Vec3 R2o2 = R2 * o2;
1520 const Vec3 l1 = X2 + R2o2 - X1;
1522 const Vec3 F1 = R1 * Vec3(e.GetCol(2) * lambda[L1] + e.GetCol(3) * lambda[L2]);
1523 const Vec3 M1 =
Cross(l1, F1);
1524 const Vec3 FP1 =
Cross(omega1, R1 * Vec3(e.GetCol(2) * lambda[L1] + e.GetCol(3) * lambda[L2]))
1525 + R1 * Vec3(e.GetCol(2) * lambdaP[L1] + e.GetCol(3) * lambdaP[L2]);
1526 const Vec3 MP1 = -
Cross(F1, XP2 +
Cross(omega2, R2o2) - XP1) +
Cross(l1, FP1);
1527 const Vec3 F2 = -F1;
1528 const Vec3 M2 =
Cross(R2o2, F2);
1529 const Vec3 FP2 = -FP1;
1533 const Vec3 aP =
Transpose(R1) * Vec3(
Cross(l1, omega1) + XP2 +
Cross(omega2, R2o2) - XP1);
1535 WorkVec.AddItem(iFirstIndexNode1 + 1, F1);
1536 WorkVec.AddItem(iFirstIndexNode1 + 4, M1);
1537 WorkVec.AddItem(iFirstIndexNode1 + 7, FP1);
1538 WorkVec.AddItem(iFirstIndexNode1 + 10, MP1);
1540 WorkVec.AddItem(iFirstIndexNode2 + 1, F2);
1541 WorkVec.AddItem(iFirstIndexNode2 + 4, M2);
1542 WorkVec.AddItem(iFirstIndexNode2 + 7, FP2);
1543 WorkVec.AddItem(iFirstIndexNode2 + 10, MP2);
1545 for (
int i = 1; i <= 2; ++i) {
1546 WorkVec.AddItem(iFirstIndex + i,
Dot(e.GetCol(i + 1),
a));
1547 WorkVec.AddItem(iFirstIndex + i + 2,
Dot(e.GetCol(i + 1), aP));
1557 if (!
SetUDE(
"deformable" "joint" "ad", rf))
1565 if (!
SetUDE(
"inline" "joint" "ad", rf))
1586 silent_cerr(
"autodiff_test: "
1587 "module_init(" << module_name <<
") "
1588 "failed" << std::endl);
virtual DofOrder::Order GetEqType(unsigned int i) const
flag fReadOutput(MBDynParser &HP, const T &t) const
Mat3x3 GetRotRel(const ReferenceFrame &rf)
void PutColIndex(integer iSubCol, integer iCol)
const Vec3 Zero3(0., 0., 0.)
Vec3 Cross(const Vec3 &v) const
MatrixExpression< TransposedMatrix< MatrixDirectExpr< Matrix< T, N_rows, N_cols > > >, N_cols, N_rows > Transpose(const Matrix< T, N_rows, N_cols > &A)
virtual unsigned int iGetInitialNumDof(void) const =0
#define MBDYN_EXCEPT_ARGS
virtual void ResizeReset(integer)
const MatCross_Manip MatCross
FullSubMatrixHandler & SetFull(void)
double mbdyn_clock_time()
virtual unsigned int iGetPrivDataIdx(const char *s) const
void Put(integer iRow, integer iCol, const Vec3 &v)
const Mat3x3 Eye3(1., 0., 0., 0., 1., 0., 0., 0., 1.)
void PutCoef(integer iRow, integer iCol, const doublereal &dCoef)
virtual void InitialWorkSpaceDim(integer *piNumRows, integer *piNumCols) const =0
std::vector< Hint * > Hints
virtual std::ostream & Restart(std::ostream &out) const =0
Vec3 MulTV(const Vec3 &v) const
void func(const T &u, const T &v, const T &w, doublereal e, T &f)
virtual void PutRowIndex(integer iSubRow, integer iRow)=0
Vec3 GetPosRel(const ReferenceFrame &rf)
virtual VariableSubMatrixHandler & InitialAssJac(VariableSubMatrixHandler &WorkMat, const VectorHandler &XCurr)=0
static const char * dof[]
virtual bool IsKeyWord(const char *sKeyWord)
std::ostream & Loadable(void) const
virtual Mat3x3 GetMat3x3(void)
virtual SubVectorHandler & InitialAssRes(SubVectorHandler &WorkVec, const VectorHandler &XCurr)=0
bool autodiff_test_set(void)
virtual std::ostream & DescribeEq(std::ostream &out, const char *prefix="", bool bInitial=false) const
DotTraits< VectorExprLhs, VectorExprRhs, N_rows, N_rows >::ExpressionType Dot(const VectorExpression< VectorExprLhs, N_rows > &u, const VectorExpression< VectorExprRhs, N_rows > &v)
#define ASSERT(expression)
Mat3x3 MulTM(const Mat3x3 &m) const
virtual void PutCoef(integer iRow, const doublereal &dCoef)=0
VectorExpression< VectorCrossExpr< VectorLhsExpr, VectorRhsExpr >, 3 > Cross(const VectorExpression< VectorLhsExpr, 3 > &u, const VectorExpression< VectorRhsExpr, 3 > &v)
virtual unsigned int iGetNumDof(void) const
virtual void ResizeReset(integer, integer)
virtual doublereal dGetPrivData(unsigned int i) const
virtual unsigned int iGetNumPrivData(void) const
virtual void GetConnectedNodes(std::vector< const Node * > &connectedNodes) const
const MatCrossCross_Manip MatCrossCross
const doublereal * pGetMat(void) const
virtual void Put(integer iRow, const Vec3 &v)
virtual void Output(OutputHandler &OH) const
void PutRowIndex(integer iSubRow, integer iRow)
const doublereal * pGetVec(void) const
std::ostream & GetLogFile(void) const
bool SetUDE(const std::string &s, UserDefinedElemRead *rude)
virtual DofOrder::Order GetDofType(unsigned int) const
virtual void WorkSpaceDim(integer *piNumRows, integer *piNumCols) const =0
virtual SubVectorHandler & AssRes(SubVectorHandler &WorkVec, doublereal dCoef, const VectorHandler &XCurr, const VectorHandler &XPrimeCurr)=0
static const doublereal a
Mat3x3 MulMT(const Mat3x3 &m) const
virtual void AfterPredict(VectorHandler &X, VectorHandler &XP)
SparseSubMatrixHandler & SetSparse(void)
virtual void SetValue(DataManager *pDM, VectorHandler &X, VectorHandler &XP, SimulationEntity::Hints *h=0)
virtual HighParser::ErrOut GetLineData(void) const
int module_init(const char *module_name, void *pdm, void *php)
This function registers our user defined element for the math parser.
Node * ReadNode(MBDynParser &HP, Node::Type type) const
virtual std::ostream & DescribeDof(std::ostream &out, const char *prefix="", bool bInitial=false) const
virtual VariableSubMatrixHandler & AssJac(VariableSubMatrixHandler &WorkMat, doublereal dCoef, const VectorHandler &XCurr, const VectorHandler &XPrimeCurr)=0
bool UseText(int out) const
virtual void Update(const VectorHandler &XCurr, const VectorHandler &XPrimeCurr)