38 #ifndef FCL_CONTINUOUS_COLLISION_INL_H 39 #define FCL_CONTINUOUS_COLLISION_INL_H 41 #include "fcl/narrowphase/continuous_collision.h" 43 #include "fcl/math/motion/translation_motion.h" 44 #include "fcl/math/motion/interp_motion.h" 45 #include "fcl/math/motion/screw_motion.h" 46 #include "fcl/math/motion/spline_motion.h" 47 #include "fcl/narrowphase/collision.h" 48 #include "fcl/narrowphase/collision_result.h" 49 #include "fcl/narrowphase/detail/traversal/collision_node.h" 56 double continuousCollide(
57 const CollisionGeometry<double>* o1,
58 const MotionBase<double>* motion1,
59 const CollisionGeometry<double>* o2,
60 const MotionBase<double>* motion2,
61 const ContinuousCollisionRequest<double>& request,
62 ContinuousCollisionResult<double>& result);
66 double continuousCollide(
67 const CollisionGeometry<double>* o1,
68 const Transform3<double>& tf1_beg,
69 const Transform3<double>& tf1_end,
70 const CollisionGeometry<double>* o2,
71 const Transform3<double>& tf2_beg,
72 const Transform3<double>& tf2_end,
73 const ContinuousCollisionRequest<double>& request,
74 ContinuousCollisionResult<double>& result);
78 double continuousCollide(
79 const CollisionObject<double>* o1,
80 const Transform3<double>& tf1_end,
81 const CollisionObject<double>* o2,
82 const Transform3<double>& tf2_end,
83 const ContinuousCollisionRequest<double>& request,
84 ContinuousCollisionResult<double>& result);
89 const ContinuousCollisionObject<double>* o1,
90 const ContinuousCollisionObject<double>* o2,
91 const ContinuousCollisionRequest<double>& request,
92 ContinuousCollisionResult<double>& result);
95 template<
typename GJKSolver>
96 detail::ConservativeAdvancementFunctionMatrix<GJKSolver>&
97 getConservativeAdvancementFunctionLookTable()
99 static detail::ConservativeAdvancementFunctionMatrix<GJKSolver> table;
104 template <
typename S>
105 MotionBasePtr<S> getMotionBase(
106 const Transform3<S>& tf_beg,
107 const Transform3<S>& tf_end,
108 CCDMotionType motion_type)
113 return MotionBasePtr<S>(
new TranslationMotion<S>(tf_beg, tf_end));
116 return MotionBasePtr<S>(
new InterpMotion<S>(tf_beg, tf_end));
119 return MotionBasePtr<S>(
new ScrewMotion<S>(tf_beg, tf_end));
122 return MotionBasePtr<S>(
new SplineMotion<S>(tf_beg, tf_end));
125 return MotionBasePtr<S>();
130 template <
typename S>
131 S continuousCollideNaive(
132 const CollisionGeometry<S>* o1,
133 const MotionBase<S>* motion1,
134 const CollisionGeometry<S>* o2,
135 const MotionBase<S>* motion2,
136 const ContinuousCollisionRequest<S>& request,
137 ContinuousCollisionResult<S>& result)
139 std::size_t n_iter = std::min(request.num_max_iterations, (std::size_t)ceil(1 / request.toc_err));
140 Transform3<S> cur_tf1, cur_tf2;
141 for(std::size_t i = 0; i < n_iter; ++i)
143 S t = i / (S) (n_iter - 1);
144 motion1->integrate(t);
145 motion2->integrate(t);
147 motion1->getCurrentTransform(cur_tf1);
148 motion2->getCurrentTransform(cur_tf2);
150 CollisionRequest<S> c_request;
151 CollisionResult<S> c_result;
153 if(collide(o1, cur_tf1, o2, cur_tf2, c_request, c_result))
155 result.is_collide =
true;
156 result.time_of_contact = t;
157 result.contact_tf1 = cur_tf1;
158 result.contact_tf2 = cur_tf2;
163 result.is_collide =
false;
164 result.time_of_contact = S(1);
165 return result.time_of_contact;
172 template<
typename BV>
173 typename BV::S continuousCollideBVHPolynomial(
174 const CollisionGeometry<typename BV::S>* o1_,
175 const TranslationMotion<typename BV::S>* motion1,
176 const CollisionGeometry<typename BV::S>* o2_,
177 const TranslationMotion<typename BV::S>* motion2,
178 const ContinuousCollisionRequest<typename BV::S>& request,
179 ContinuousCollisionResult<typename BV::S>& result)
181 using S =
typename BV::S;
183 const BVHModel<BV>* o1__ =
static_cast<const BVHModel<BV>*
>(o1_);
184 const BVHModel<BV>* o2__ =
static_cast<const BVHModel<BV>*
>(o2_);
187 BVHModel<BV>* o1 =
const_cast<BVHModel<BV>*
>(o1__);
188 BVHModel<BV>* o2 =
const_cast<BVHModel<BV>*
>(o2__);
189 std::vector<Vector3<S>> new_v1(o1->num_vertices);
190 std::vector<Vector3<S>> new_v2(o2->num_vertices);
192 for(std::size_t i = 0; i < new_v1.size(); ++i)
193 new_v1[i] = o1->vertices[i] + motion1->getVelocity();
194 for(std::size_t i = 0; i < new_v2.size(); ++i)
195 new_v2[i] = o2->vertices[i] + motion2->getVelocity();
197 o1->beginUpdateModel();
198 o1->updateSubModel(new_v1);
199 o1->endUpdateModel(
true,
true);
201 o2->beginUpdateModel();
202 o2->updateSubModel(new_v2);
203 o2->endUpdateModel(
true,
true);
205 MeshContinuousCollisionTraversalNode<BV> node;
206 CollisionRequest<S> c_request;
208 motion1->integrate(0);
209 motion2->integrate(0);
212 motion1->getCurrentTransform(tf1);
213 motion2->getCurrentTransform(tf2);
214 if(!initialize<BV>(node, *o1, tf1, *o2, tf2, c_request))
219 result.is_collide = (node.pairs.size() > 0);
220 result.time_of_contact = node.time_of_contact;
222 if(result.is_collide)
224 motion1->integrate(node.time_of_contact);
225 motion2->integrate(node.time_of_contact);
226 motion1->getCurrentTransform(tf1);
227 motion2->getCurrentTransform(tf2);
228 result.contact_tf1 = tf1;
229 result.contact_tf2 = tf2;
232 return result.time_of_contact;
238 template <
typename S>
239 S continuousCollideBVHPolynomial(
240 const CollisionGeometry<S>* o1,
241 const TranslationMotion<S>* motion1,
242 const CollisionGeometry<S>* o2,
243 const TranslationMotion<S>* motion2,
244 const ContinuousCollisionRequest<S>& request,
245 ContinuousCollisionResult<S>& result)
247 switch(o1->getNodeType())
250 if(o2->getNodeType() == BV_AABB)
251 return detail::continuousCollideBVHPolynomial<AABB<S>>(o1, motion1, o2, motion2, request, result);
254 if(o2->getNodeType() == BV_OBB)
255 return detail::continuousCollideBVHPolynomial<OBB<S>>(o1, motion1, o2, motion2, request, result);
258 if(o2->getNodeType() == BV_RSS)
259 return detail::continuousCollideBVHPolynomial<RSS<S>>(o1, motion1, o2, motion2, request, result);
262 if(o2->getNodeType() == BV_kIOS)
263 return detail::continuousCollideBVHPolynomial<kIOS<S>>(o1, motion1, o2, motion2, request, result);
266 if(o2->getNodeType() == BV_OBBRSS)
267 return detail::continuousCollideBVHPolynomial<OBBRSS<S>>(o1, motion1, o2, motion2, request, result);
270 if(o2->getNodeType() == BV_KDOP16)
271 return detail::continuousCollideBVHPolynomial<KDOP<S, 16> >(o1, motion1, o2, motion2, request, result);
274 if(o2->getNodeType() == BV_KDOP18)
275 return detail::continuousCollideBVHPolynomial<KDOP<S, 18> >(o1, motion1, o2, motion2, request, result);
278 if(o2->getNodeType() == BV_KDOP24)
279 return detail::continuousCollideBVHPolynomial<KDOP<S, 24> >(o1, motion1, o2, motion2, request, result);
285 std::cerr <<
"Warning: BV type not supported by polynomial solver CCD" << std::endl;
294 template<
typename NarrowPhaseSolver>
295 typename NarrowPhaseSolver::S continuousCollideConservativeAdvancement(
296 const CollisionGeometry<typename NarrowPhaseSolver::S>* o1,
297 const MotionBase<typename NarrowPhaseSolver::S>* motion1,
298 const CollisionGeometry<typename NarrowPhaseSolver::S>* o2,
299 const MotionBase<typename NarrowPhaseSolver::S>* motion2,
300 const NarrowPhaseSolver* nsolver_,
301 const ContinuousCollisionRequest<typename NarrowPhaseSolver::S>& request,
302 ContinuousCollisionResult<typename NarrowPhaseSolver::S>& result)
304 using S =
typename NarrowPhaseSolver::S;
306 const NarrowPhaseSolver* nsolver = nsolver_;
308 nsolver =
new NarrowPhaseSolver();
310 const auto& looktable = getConservativeAdvancementFunctionLookTable<NarrowPhaseSolver>();
312 NODE_TYPE node_type1 = o1->getNodeType();
313 NODE_TYPE node_type2 = o2->getNodeType();
317 if(!looktable.conservative_advancement_matrix[node_type1][node_type2])
319 std::cerr <<
"Warning: collision function between node type " << node_type1 <<
" and node type " << node_type2 <<
" is not supported"<< std::endl;
323 res = looktable.conservative_advancement_matrix[node_type1][node_type2](o1, motion1, o2, motion2, nsolver, request, result);
329 if(result.is_collide)
331 motion1->integrate(result.time_of_contact);
332 motion2->integrate(result.time_of_contact);
336 motion1->getCurrentTransform(tf1);
337 motion2->getCurrentTransform(tf2);
338 result.contact_tf1 = tf1;
339 result.contact_tf2 = tf2;
347 template <
typename S>
348 S continuousCollideConservativeAdvancement(
349 const CollisionGeometry<S>* o1,
350 const MotionBase<S>* motion1,
351 const CollisionGeometry<S>* o2,
352 const MotionBase<S>* motion2,
353 const ContinuousCollisionRequest<S>& request,
354 ContinuousCollisionResult<S>& result)
356 switch(request.gjk_solver_type)
360 detail::GJKSolver_libccd<S> solver;
361 return detail::continuousCollideConservativeAdvancement(o1, motion1, o2, motion2, &solver, request, result);
365 detail::GJKSolver_indep<S> solver;
366 return detail::continuousCollideConservativeAdvancement(o1, motion1, o2, motion2, &solver, request, result);
374 template <
typename S>
386 return continuousCollideNaive(o1, motion1,
391 case CCDC_CONSERVATIVE_ADVANCEMENT:
392 return continuousCollideConservativeAdvancement(o1, motion1,
397 case CCDC_RAY_SHOOTING:
403 std::cerr <<
"Warning! Invalid continuous collision setting" << std::endl;
405 case CCDC_POLYNOMIAL_SOLVER:
413 std::cerr <<
"Warning! Invalid continuous collision checking" << std::endl;
416 std::cerr <<
"Warning! Invalid continuous collision setting" << std::endl;
423 template <
typename S>
426 const Transform3<S>& tf1_beg,
427 const Transform3<S>& tf1_end,
429 const Transform3<S>& tf2_beg,
430 const Transform3<S>& tf2_end,
434 MotionBasePtr<S> motion1 = getMotionBase(tf1_beg, tf1_end, request.
ccd_motion_type);
435 MotionBasePtr<S> motion2 = getMotionBase(tf2_beg, tf2_end, request.
ccd_motion_type);
437 return continuousCollide(o1, motion1.get(), o2, motion2.get(), request, result);
441 template <
typename S>
444 const Transform3<S>& tf1_end,
446 const Transform3<S>& tf2_end,
456 template <
typename S>
virtual OBJECT_TYPE getObjectType() const
get the type of the object
Definition: collision_geometry-inl.h:72
NODE_TYPE
traversal node type: bounding volume (AABB, OBB, RSS, kIOS, OBBRSS, KDOP16, KDOP18, kDOP24), basic shape (box, sphere, ellipsoid, capsule, cone, cylinder, convex, plane, halfspace, triangle), and octree
Definition: collision_geometry.h:54
Main namespace.
Definition: broadphase_bruteforce-inl.h:45
Definition: bv_motion_bound_visitor.h:57
const std::shared_ptr< const CollisionGeometry< S > > & collisionGeometry() const
get geometry from the object instance
Definition: continuous_collision_object-inl.h:170
the object for continuous collision or distance computation, contains the geometry and the motion inf...
Definition: continuous_collision_object.h:51
The geometry for the object for collision or distance computation.
Definition: collision_geometry.h:59
Definition: continuous_collision_request.h:51
CCDMotionType ccd_motion_type
ccd motion type
Definition: continuous_collision_request.h:60
Definition: bv_motion_bound_visitor.h:45
const Transform3< S > & getTransform() const
get object's transform
Definition: collision_object-inl.h:170
continuous collision result
Definition: continuous_collision_result.h:48
const std::shared_ptr< const CollisionGeometry< S > > & collisionGeometry() const
get geometry from the object instance
Definition: collision_object-inl.h:243
the object for collision or distance computation, contains the geometry and the transform information...
Definition: collision_object.h:51
MotionBase< S > * getMotion() const
get motion from the object instance
Definition: continuous_collision_object-inl.h:154
CCDSolverType ccd_solver_type
ccd solver type
Definition: continuous_collision_request.h:66