42 #include <gtest/gtest.h> 
   43 #include <Eigen/Dense> 
   59   S min_distance = (p_F1 - p_F2).norm() - radius1 - radius2;
 
   67                                          S solver_tolerance, S test_tol,
 
   68                                          S min_distance_expected) {
 
   91   tf1.translation() = p_F1;
 
   92   tf2.translation() = p_F2;
 
  107   EXPECT_EQ(res, min_distance_expected >= 0);
 
  109   EXPECT_NEAR(dist, min_distance_expected, test_tol);
 
  112   EXPECT_NEAR((p_FN1 - p_FN2).norm(), std::abs(dist),
 
  116   EXPECT_NEAR((p_FN1 - p_F1).norm(), radius1, test_tol);
 
  117   EXPECT_NEAR((p_FN2 - p_F2).norm(), radius2, test_tol);
 
  122   EXPECT_NEAR((p_F1 + p_FN2 - p_FN1 - p_F2).norm(), radius1 + radius2,
 
  143 template <
typename S>
 
  151 template <
typename S>
 
  153   std::vector<SphereSpecification<S>> spheres;
 
  154   spheres.emplace_back(0.5, 
Vector3<S>(0, 0, -1.2));
 
  155   spheres.emplace_back(0.5, 
Vector3<S>(1.25, 0, 0));
 
  156   spheres.emplace_back(0.3, 
Vector3<S>(-0.2, 0, 0));
 
  157   spheres.emplace_back(0.4, 
Vector3<S>(-0.2, 0, 1.1));
 
  158   for (
int i = 0; i < static_cast<int>(spheres.size()); ++i) {
 
  159     for (
int j = i + 1; j < static_cast<int>(spheres.size()); ++j) {
 
  160       if ((spheres[i].center - spheres[j].center).norm() >
 
  161           spheres[i].radius + spheres[j].radius) {
 
  163         for (
const S solver_tolerance : {S(1e-4), S(1e-5), S(1e-6)}) {
 
  164           const S min_distance_expected =
 
  166                                           spheres[i].center, spheres[j].center);
 
  171           TestSphereToSphereGJKSignedDistance<S>(
 
  172               spheres[i].radius, spheres[j].radius, spheres[i].center,
 
  173               spheres[j].center, solver_tolerance, 10 * solver_tolerance,
 
  174               min_distance_expected);
 
  177         GTEST_FAIL() << 
"The two spheres collide." 
  178                      << 
"\nSpheres[" << i << 
"] with radius " 
  179                      << spheres[i].radius << 
", centered at " 
  180                      << spheres[i].center.transpose() << 
"\nSpheres[" << j
 
  181                      << 
"] with radius " << spheres[j].radius
 
  182                      << 
", centered at " << spheres[j].center.transpose()
 
  189 template <
typename S>
 
  191   std::vector<SphereSpecification<S>> spheres;
 
  192   spheres.emplace_back(0.5, 
Vector3<S>(0, 0, 0));
 
  193   spheres.emplace_back(0.5, 
Vector3<S>(0.75, 0, 0));
 
  194   spheres.emplace_back(0.3, 
Vector3<S>(0.2, 0, 0));
 
  195   spheres.emplace_back(0.4, 
Vector3<S>(0.2, 0, 0.4));
 
  196   for (
int i = 0; i < static_cast<int>(spheres.size()); ++i) {
 
  197     for (
int j = i + 1; j < static_cast<int>(spheres.size()); ++j) {
 
  198       if ((spheres[i].center - spheres[j].center).norm() <
 
  199           spheres[i].radius + spheres[j].radius) {
 
  201         const S min_distance_expected =
 
  203                                         spheres[i].center, spheres[j].center);
 
  204         for (
const S solver_tolerance : {S(1E-4), S(1E-5), S(1E-6)}) {
 
  207           TestSphereToSphereGJKSignedDistance<S>(
 
  208               spheres[i].radius, spheres[j].radius, spheres[i].center,
 
  209               spheres[j].center, solver_tolerance, solver_tolerance,
 
  210               min_distance_expected);
 
  213         GTEST_FAIL() << 
"The two spheres failed to collide." 
  214                      << 
"\nSpheres[" << i << 
"] with radius " 
  215                      << spheres[i].radius << 
", centered at " 
  216                      << spheres[i].center.transpose() << 
"\nSpheres[" << j
 
  217                      << 
"] with radius " << spheres[j].radius
 
  218                      << 
", centered at " << spheres[j].center.transpose()
 
  226   TestNonCollidingSphereGJKSignedDistance<double>();
 
  227   TestNonCollidingSphereGJKSignedDistance<float>();
 
  228   TestCollidingSphereGJKSignedDistance<double>();
 
  229   TestCollidingSphereGJKSignedDistance<float>();
 
  236 template <
typename S>
 
  238   EIGEN_MAKE_ALIGNED_OPERATOR_NEW
 
  246 template <
typename S>
 
  258   X_FB1.translation() << 0, 0, 0.5;
 
  265   X_FB2.linear() << 0.6, -0.8, 0, 0.8, 0.6, 0, 0, 0, 1;
 
  271   auto CheckDistance = [&box1_size, &box2_size, &X_FB1, &X_WF](
 
  274       S solver_distance_tolerance, S test_distance_tolerance,
 
  275       S test_witness_tolerance) {
 
  295     if (distance_expected < 0) {
 
  297     } 
else if (distance_expected > 0) {
 
  301     EXPECT_NEAR(dist, distance_expected, test_distance_tolerance);
 
  303         X_WF.linear().transpose() * (p_WN1 - X_WF.translation());
 
  305         X_WF.linear().transpose() * (p_WN2 - X_WF.translation());
 
  307     EXPECT_TRUE(p_FN1.template head<2>().isApprox(p_xy_FN1_expected,
 
  308                                                   test_witness_tolerance));
 
  309     EXPECT_TRUE(p_FN2.template head<2>().isApprox(p_xy_FN2_expected,
 
  310                                                   test_witness_tolerance));
 
  312     EXPECT_NEAR(p_FN1(2), p_FN2(2), test_witness_tolerance);
 
  315     EXPECT_GE(p_FN1(2), 0);
 
  316     EXPECT_GE(p_FN2(2), 0);
 
  317     EXPECT_LE(p_FN1(2), 1);
 
  318     EXPECT_LE(p_FN2(2), 1);
 
  324   auto CheckBoxEdgeBoxFaceDistance = [&CheckDistance](
 
  326       S test_distance_tolerance, S test_witness_tolerance) {
 
  330         Vector2<S>(X_FB2.translation()(0) + 0.5, X_FB2.translation()(1)),
 
  331         solver_distance_tolerance, test_distance_tolerance,
 
  332         test_witness_tolerance);
 
  341   for (
int i = 0; i < static_cast<int>(solver_tolerances.size()); ++i) {
 
  342     const S solver_distance_tolerance = solver_tolerances[i];
 
  347     const S test_distance_tolerance = 10 * solver_distance_tolerance;
 
  348     const S test_witness_tolerance = test_distance_tolerance;
 
  350     X_FB2.translation() << -1, 0, 0.5;
 
  351     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  352                                 test_distance_tolerance,
 
  353                                 test_witness_tolerance);
 
  357     X_FB2.translation() << -1, 0.1, 0.5;
 
  358     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  359                                 test_distance_tolerance,
 
  360                                 test_witness_tolerance);
 
  363     X_FB2.translation() << -1, -0.1, 0.5;
 
  364     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  365                                 test_distance_tolerance,
 
  366                                 test_witness_tolerance);
 
  374   for (
int i = 0; i < static_cast<int>(solver_tolerances.size()); ++i) {
 
  375     const S solver_distance_tolerance = solver_tolerances[i];
 
  379     const S test_distance_tolerance = solver_distance_tolerance;
 
  380     const S test_witness_tolerance = test_distance_tolerance;
 
  382     X_FB2.translation() << -0.9, 0, 0.5;
 
  383     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  384                                 test_distance_tolerance,
 
  385                                 test_witness_tolerance);
 
  388     X_FB2.translation() << -0.9, 0.1, 0.5;
 
  389     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  390                                 test_distance_tolerance,
 
  391                                 test_witness_tolerance);
 
  394     X_FB2.translation() << -0.9, -0.05, 0.5;
 
  395     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  396                                 test_distance_tolerance,
 
  397                                 test_witness_tolerance);
 
  400     X_FB2.translation() << -0.9, -0.1, 0.5;
 
  401     CheckBoxEdgeBoxFaceDistance(X_FB2, solver_distance_tolerance,
 
  402                                 test_distance_tolerance,
 
  403                                 test_witness_tolerance);
 
  407 template <
typename S>
 
  415   X_WF.translation() << 0, 0, 1;
 
  418   X_WF.translation() << 0, 1, 0;
 
  421   X_WF.translation() << 1, 0, 0;
 
  441   X_WF.translation() << 0.1, 0.2, 0.3;
 
  453 int main(
int argc, 
char* argv[]) {
 
  454   ::testing::InitGoogleTest(&argc, argv);
 
  455   return RUN_ALL_TESTS();