1 #include <gtest/gtest.h> 47 joint_rotzyx =
Joint(
SpatialVector(0., 0., 1., 0., 0., 0.),
SpatialVector(0., 1., 0., 0., 0., 0.),
SpatialVector(1., 0., 0., 0., 0., 0.));
48 base_id = model->addBody(0,
Xtrans(
Vector3d(0., 0., 0.)), joint_rotzyx, base);
52 child_id = model->addBody(base_id,
Xtrans(
Vector3d(0., 0., 0.)), joint_rotzyx, child);
56 child_2_id = model->addBody(child_id,
Xtrans(
Vector3d(0., 0., 0.)), joint_rotzyx, child_2);
58 Q = VectorNd::Constant(model->mBodies.size() - 1, 0.);
59 QDot = VectorNd::Constant(model->mBodies.size() - 1, 0.);
60 QDDot = VectorNd::Constant(model->mBodies.size() - 1, 0.);
61 Tau = VectorNd::Constant(model->mBodies.size() - 1, 0.);
63 contact_body_id = child_id;
64 contact_point =
Vector3d(0.5, 0.5, 0.);
65 contact_normal =
Vector3d(0., 1., 0.);
102 Joint(
SpatialVector(0., 0., 0., 1., 0., 0.),
SpatialVector(0., 0., 0., 0., 1., 0.),
SpatialVector(0., 0., 0., 0., 0., 1.),
103 SpatialVector(0., 0., 1., 0., 0., 0.),
SpatialVector(0., 1., 0., 0., 0., 0.),
SpatialVector(1., 0., 0., 0., 0., 0.)),
115 unsigned int contact_body_id = base_body_id;
116 Vector3d contact_point(0., -1., 0.);
124 constraint_set.
bind(model);
133 constraint_set.
clear();
154 for (i = 0; i < constraint_set.
f_t.size(); i++)
169 for (i = 0; i < constraint_set.
d_pA.size(); i++)
174 for (i = 0; i < constraint_set.
d_a.size(); i++)
186 Joint(
SpatialVector(0., 0., 0., 1., 0., 0.),
SpatialVector(0., 0., 0., 0., 1., 0.),
SpatialVector(0., 0., 0., 0., 0., 1.),
187 SpatialVector(0., 0., 1., 0., 0., 0.),
SpatialVector(0., 1., 0., 0., 0., 0.),
SpatialVector(1., 0., 0., 0., 0., 0.)),
208 unsigned int contact_body_id = base_body_id;
209 Vector3d contact_point(0., -1., 0.);
217 constraint_set.
bind(model);
232 contact_normal.set(0., 1., 0.);
233 constraint_set.addConstraint(contact_body_id, contact_point, contact_normal);
236 constraint_set_lagrangian.
bind(*model);
237 constraint_set.bind(*model);
239 Vector3d point_accel_lagrangian, point_accel_contacts;
241 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
242 VectorNd QDDot_contacts = VectorNd::Constant(model->mBodies.size() - 1, 0.);
251 EXPECT_NEAR(constraint_set_lagrangian.
force[0], constraint_set.force[0],
TEST_PREC);
252 EXPECT_NEAR(contact_normal.dot(point_accel_lagrangian), contact_normal.dot(point_accel_contacts),
TEST_PREC);
263 contact_normal.set(0., 1., 0.);
265 constraint_set.addConstraint(contact_body_id, contact_point, contact_normal);
268 constraint_set_lagrangian.
bind(*model);
269 constraint_set.bind(*model);
271 Vector3d point_accel_lagrangian, point_accel_contacts, point_accel_contacts_opt;
273 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
274 VectorNd QDDot_contacts = VectorNd::Constant(model->mBodies.size() - 1, 0.);
275 VectorNd QDDot_contacts_opt = VectorNd::Constant(model->mBodies.size() - 1, 0.);
283 EXPECT_NEAR(constraint_set_lagrangian.
force[0], constraint_set.force[0],
TEST_PREC);
284 EXPECT_NEAR(contact_normal.dot(point_accel_lagrangian), contact_normal.dot(point_accel_contacts_opt),
TEST_PREC);
306 contact_normal.set(0., 1., 0.);
307 constraint_set.addConstraint(contact_body_id, contact_point, contact_normal);
310 constraint_set_lagrangian.
bind(*model);
311 constraint_set.bind(*model);
313 Vector3d point_accel_lagrangian, point_accel_contacts;
315 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
316 VectorNd QDDot_contacts = VectorNd::Constant(model->mBodies.size() - 1, 0.);
326 EXPECT_NEAR(constraint_set_lagrangian.
force[0], constraint_set.force[0],
TEST_PREC);
328 EXPECT_NEAR(contact_normal.dot(point_accel_lagrangian), contact_normal.dot(point_accel_contacts),
TEST_PREC);
338 constraint_set.addConstraint(contact_body_id,
Vector3d(0., 1., 0.), contact_normal);
340 constraint_set_lagrangian = constraint_set.
Copy();
341 constraint_set_lagrangian.
bind(*model);
342 constraint_set.bind(*model);
344 Vector3d point_accel_lagrangian, point_accel_contacts;
346 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
347 VectorNd QDDot_contacts = VectorNd::Constant(model->mBodies.size() - 1, 0.);
370 constraint_set.addConstraint(contact_body_id,
Vector3d(0., 1., 0.), contact_normal);
372 constraint_set_lagrangian = constraint_set.
Copy();
373 constraint_set_lagrangian.
bind(*model);
374 constraint_set.bind(*model);
376 Vector3d point_accel_lagrangian, point_accel_contacts;
378 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
379 VectorNd QDDot_contacts = VectorNd::Constant(model->mBodies.size() - 1, 0.);
404 constraint_set.addConstraint(contact_body_id, contact_point,
Vector3d(0., 1., 0.));
406 constraint_set_lagrangian = constraint_set.
Copy();
407 constraint_set_lagrangian.
bind(*model);
408 constraint_set.bind(*model);
424 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
425 VectorNd QDDot_contacts = VectorNd::Constant(model->mBodies.size() - 1, 0.);
435 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
436 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
444 constraint_set.addConstraint(contact_body_id, contact_point,
Vector3d(0., 1., 0.));
445 constraint_set.addConstraint(child_2_id, contact_point,
Vector3d(0., 1., 0.));
447 constraint_set_lagrangian = constraint_set.
Copy();
448 constraint_set_lagrangian.
bind(*model);
449 constraint_set.bind(*model);
465 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
469 Vector3d point_accel_c, point_accel_2_c;
478 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
479 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
480 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
485 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
486 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
487 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
497 constraint_set.addConstraint(contact_body_id, contact_point,
Vector3d(0., 1., 0.));
498 constraint_set.addConstraint(child_2_id, contact_point,
Vector3d(0., 1., 0.));
500 constraint_set_lagrangian = constraint_set.
Copy();
502 constraint_set_lagrangian.
bind(*model);
504 constraint_set.bind(*model);
520 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
524 Vector3d point_accel_c, point_accel_2_c;
533 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
534 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
535 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
540 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
541 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
542 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
552 constraint_set.addConstraint(contact_body_id, contact_point,
Vector3d(0., 1., 0.));
553 constraint_set.addConstraint(child_2_id, contact_point,
Vector3d(0., 1., 0.));
555 constraint_set_lagrangian = constraint_set.
Copy();
557 constraint_set_lagrangian.
bind(*model);
559 constraint_set.bind(*model);
575 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
579 Vector3d point_accel_c, point_accel_2_c;
588 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
589 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
590 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
595 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
596 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
597 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
607 constraint_set.addConstraint(contact_body_id, contact_point,
Vector3d(0., 1., 0.));
608 constraint_set.addConstraint(child_2_id, contact_point,
Vector3d(0., 1., 0.));
610 constraint_set_lagrangian = constraint_set.
Copy();
611 constraint_set_lagrangian.
bind(*model);
612 constraint_set.bind(*model);
634 VectorNd QDDot_lagrangian = VectorNd::Constant(model->mBodies.size() - 1, 0.);
638 Vector3d point_accel_c, point_accel_2_c;
647 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
648 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
649 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
654 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
655 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
656 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
666 constraint_set.addConstraint(contact_body_id, contact_point,
Vector3d(0., 1., 0.));
667 constraint_set.addConstraint(child_2_id, contact_point,
Vector3d(0., 1., 0.));
669 constraint_set_lagrangian = constraint_set.
Copy();
670 constraint_set_lagrangian.
bind(*model);
671 constraint_set.bind(*model);
673 VectorNd QDDot_lagrangian = VectorNd::Constant(model->dof_count, 0.);
697 Vector3d point_accel_c, point_accel_2_c;
706 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
707 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
708 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
713 EXPECT_NEAR(0., point_accel_c[0],
TEST_PREC);
714 EXPECT_NEAR(0., point_accel_c[1],
TEST_PREC);
715 EXPECT_NEAR(0., point_accel_2_c[1],
TEST_PREC);
722 VectorNd qddot_lagrangian(VectorNd::Zero(qddot.size()));
723 VectorNd qddot_sparse(VectorNd::Zero(qddot.size()));
729 constraint_upper_trunk.
bind(*model_3dof);
741 VectorNd qddot_lagrangian(VectorNd::Zero(qddot.size()));
754 constraint_feet.
bind(*model_3dof);
756 VectorNd qdotplus(VectorNd::Zero(qdot.size()));
767 int main(
int argc,
char** argv)
769 ::testing::InitGoogleTest(&argc, argv);
770 return RUN_ALL_TESTS();
Math::VectorNd C
Workspace for the coriolis forces.
static bool checkVectorNdEpsilonClose(const RobotDynamics::Math::VectorNd &v1, const RobotDynamics::Math::VectorNd &v2, const double epsilon)
Math::SpatialForceV f_t
Workspace for the test forces.
Math::SpatialForceV f_ext_constraints
Workspace for the actual spatial forces.
Math::VectorNd b
Workspace for the Lagrangian right-hand-side.
unsigned int contact_body_id
Describes all properties of a single body.
void clear()
Clears all variables in the constraint set.
Math::VectorNd a
Workspace for the accelerations of due to the test forces.
ConstraintSet Copy()
Copies the constraints and resets its ConstraintSet::bound flag.
SpatialTransform Xtrans(const Vector3d &r)
Get pure translation transform.
Math::SpatialForceV d_pA
Workspace for the bias force due to the test force.
unsigned int addConstraint(unsigned int body_id, const Math::Vector3d &body_point, const Math::Vector3d &world_normal, const char *constraint_name=NULL, double normal_acceleration=0.)
Adds a constraint to the constraint set.
bool checkModelZeroVectorsAndMatrices(RobotDynamics::Model &model)
Math::MatrixNd A
Workspace for the Lagrangian left-hand-side matrix.
Math::FrameVector calcPointAcceleration(Model &model, const Math::VectorNd &Q, const Math::VectorNd &QDot, const Math::VectorNd &QDDot, unsigned int body_id, const Math::Vector3d &point_position, bool update_kinematics=true)
Computes the linear acceleration of a point on a body.
Math::MotionVector gravity
the cartesian vector of the gravity
Math::VectorNd acceleration
Vector3d heel_point(0., 0., 0.)
unsigned int addBody(const unsigned int parent_id, const Math::SpatialTransform &joint_frame, const Joint &joint, const Body &body, std::string body_name="")
Connects a given body to the model.
Math::VectorNd QDDot_t
Workspace for the test accelerations.
Math::FrameVector calcPointVelocity(Model &model, const Math::VectorNd &Q, const Math::VectorNd &QDot, unsigned int body_id, const Math::Vector3d &point_position, bool update_kinematics=true)
Computes the velocity of a point on a body.
FixedBase6DoF9DoFFixture()
Structure that contains both constraint information and workspace memory.
Math::VectorNd gamma
Workspace of the lower part of b.
Describes a joint relative to the predecessor body.
std::vector< Math::Vector3d > point_accel_0
Workspace for the default point accelerations.
Math::VectorNd QDDot_0
Workspace for the default accelerations.
ConstraintSet constraint_set
Contains all information about the rigid body model.
bool bind(const Model &model)
Initializes and allocates memory for the constraint set.
Math types such as vectors and matrices and utility functions.
Math::MatrixNd K
Workspace for the Inverse Articulated-Body Inertia.
std::vector< Math::SpatialVector > d_a
Workspace for the acceleration due to the test force.
static bool checkVector3dEpsilonClose(const RobotDynamics::Math::Vector3d &v1, const RobotDynamics::Math::Vector3d &v2, const double epsilon)
static bool checkMatrixNdEq(const RobotDynamics::Math::MatrixNd &t1, const RobotDynamics::Math::MatrixNd &t2)
Math::LinearSolver linear_solver
Method that should be used to solve internal linear systems.
static bool checkVectorNdEq(const RobotDynamics::Math::VectorNd &v1, const RobotDynamics::Math::VectorNd &v2)
unsigned int dof_count
number of degrees of freedoms of the model
Namespace for all structures of the RobotDynamics library.
Math::VectorNd x
Workspace for the Lagrangian solution.
Math::MatrixNd H
Workspace for the joint space inertia matrix.