Simbody 3.7
Contact.h
Go to the documentation of this file.
1#ifndef SimTK_SIMMATH_CONTACT_H_
2#define SimTK_SIMMATH_CONTACT_H_
3
4/* -------------------------------------------------------------------------- *
5 * Simbody(tm): SimTKmath *
6 * -------------------------------------------------------------------------- *
7 * This is part of the SimTK biosimulation toolkit originating from *
8 * Simbios, the NIH National Center for Physics-Based Simulation of *
9 * Biological Structures at Stanford, funded under the NIH Roadmap for *
10 * Medical Research, grant U54 GM072970. See https://simtk.org/home/simbody. *
11 * *
12 * Portions copyright (c) 2008-12 Stanford University and the Authors. *
13 * Authors: Peter Eastman, Michael Sherman *
14 * Contributors: *
15 * *
16 * Licensed under the Apache License, Version 2.0 (the "License"); you may *
17 * not use this file except in compliance with the License. You may obtain a *
18 * copy of the License at http://www.apache.org/licenses/LICENSE-2.0. *
19 * *
20 * Unless required by applicable law or agreed to in writing, software *
21 * distributed under the License is distributed on an "AS IS" BASIS, *
22 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. *
23 * See the License for the specific language governing permissions and *
24 * limitations under the License. *
25 * -------------------------------------------------------------------------- */
26
27#include "SimTKcommon.h"
29
30#include <set>
31
32namespace SimTK {
33
34
40
51
59
60
61class ContactImpl;
62class UntrackedContactImpl;
63class BrokenContactImpl;
64class CircularPointContactImpl;
65class EllipticalPointContactImpl;
66class BrickHalfSpaceContactImpl;
67class TriangleMeshContactImpl;
68
69class PointContactImpl; // deprecated
70
71
72//==============================================================================
73// CONTACT
74//==============================================================================
86public:
89 enum Condition {
95 Broken
96 };
100 static const char* nameOfCondition(Condition);
101
103 Contact() : impl(0) {}
106 Contact(const Contact& source);
109 ~Contact() {clear();}
112 Contact& operator=(const Contact& source);
115 void clear();
117 bool isEmpty() const {return impl==0;}
118
134 const Transform& getTransform() const;
135
145
149
154
155 const ContactImpl& getImpl() const {assert(impl); return *impl;}
156 ContactImpl& updImpl() {assert(impl); return *impl;}
157protected:
158 explicit Contact(ContactImpl* impl);
159private:
160 ContactImpl* impl;
161};
162
163inline std::ostream& operator<<(std::ostream& o, const Contact& c) {
164 o << "Contact id=" << c.getContactId()
165 << " (typeId=" << c.getTypeId() << "):\n";
166 o << " surf1,surf2=" << c.getSurface1() << ","
167 << c.getSurface2() << "\n";
168 o << " condition=" << Contact::nameOfCondition(c.getCondition()) << "\n";
169 return o;
170}
171
172
173
174//==============================================================================
175// UNTRACKED CONTACT
176//==============================================================================
183public:
192
194 static bool isInstance(const Contact& contact);
197
198private:
199 const UntrackedContactImpl& getImpl() const
200 { assert(isInstance(*this));
201 return reinterpret_cast<const UntrackedContactImpl&>
202 (Contact::getImpl()); }
203};
204
205
206
207//==============================================================================
208// BROKEN CONTACT
209//==============================================================================
217public:
225 const Transform& X_S1S2, Real separation);
226
231
233 static bool isInstance(const Contact& contact);
236
237private:
238 const BrokenContactImpl& getImpl() const
239 { assert(isInstance(*this));
240 return reinterpret_cast<const BrokenContactImpl&>(Contact::getImpl()); }
241};
242
243
244
245//==============================================================================
246// CIRCULAR POINT CONTACT
247//==============================================================================
261public:
277 (ContactSurfaceIndex surf1, Real radius1,
278 ContactSurfaceIndex surf2, Real radius2,
279 const Transform& X_S1S2, Real radius, Real depth,
280 const Vec3& origin_S1, const UnitVec3& normal_S1);
281
293 Real getDepth() const;
295 const Vec3& getOrigin() const;
299 const UnitVec3& getNormal() const;
300
302 static bool isInstance(const Contact& contact);
303 static const CircularPointContact& getAs(const Contact& contact)
304 { assert(isInstance(contact));
305 return static_cast<const CircularPointContact&>(contact); }
307 { assert(isInstance(contact));
308 return static_cast<CircularPointContact&>(contact); }
309
312
313private:
314 const CircularPointContactImpl& getImpl() const
315 { assert(isInstance(*this));
316 return reinterpret_cast<const CircularPointContactImpl&>
317 (Contact::getImpl()); }
318};
319
320
321
322//==============================================================================
323// ELLIPTICAL POINT CONTACT
324//==============================================================================
356public:
372 const Transform& X_S1S2,
373 const Transform& X_S1C, const Vec2& k, Real depth);
374
377 const Vec2& getCurvatures() const;
389 Real getDepth() const;
390
392 static bool isInstance(const Contact& contact);
393 static const EllipticalPointContact& getAs(const Contact& contact)
394 { assert(isInstance(contact));
395 return static_cast<const EllipticalPointContact&>(contact); }
397 { assert(isInstance(contact));
398 return static_cast<EllipticalPointContact&>(contact); }
399
402
403private:
404 const EllipticalPointContactImpl& getImpl() const
405 { assert(isInstance(*this));
406 return reinterpret_cast<const EllipticalPointContactImpl&>
407 (Contact::getImpl()); }
408};
409
410
411
412//==============================================================================
413// BRICK HALFSPACE CONTACT
414//==============================================================================
419public:
432 const Transform& X_HB,
433 int lowestVertex,
434 Real depth);
435
438 int getLowestVertex() const;
439
442 Real getDepth() const;
443
445 static bool isInstance(const Contact& contact);
446
449 static const BrickHalfSpaceContact& getAs(const Contact& contact)
450 { assert(isInstance(contact));
451 return static_cast<const BrickHalfSpaceContact&>(contact); }
452
456 { assert(isInstance(contact));
457 return static_cast<BrickHalfSpaceContact&>(contact); }
458
462
463private:
464 const BrickHalfSpaceContactImpl& getImpl() const
465 { assert(isInstance(*this));
466 return reinterpret_cast<const BrickHalfSpaceContactImpl&>
467 (Contact::getImpl()); }
468};
469
470
471
472//==============================================================================
473// TRIANGLE MESH CONTACT
474//==============================================================================
479public:
493 const Transform& X_S1S2,
494 const std::set<int>& faces1,
495 const std::set<int>& faces2);
496
500 const std::set<int>& getSurface1Faces() const;
504 const std::set<int>& getSurface2Faces() const;
505
507 static bool isInstance(const Contact& contact);
510 static const TriangleMeshContact& getAs(const Contact& contact)
511 { assert(isInstance(contact));
512 return static_cast<const TriangleMeshContact&>(contact); }
516 { assert(isInstance(contact));
517 return static_cast<TriangleMeshContact&>(contact); }
518
522
523private:
524 const TriangleMeshContactImpl& getImpl() const
525 { assert(isInstance(*this));
526 return reinterpret_cast<const TriangleMeshContactImpl&>
527 (Contact::getImpl()); }
528};
529
530
531
532
533//==============================================================================
534// POINT CONTACT
535//==============================================================================
543public:
561 Vec3& location, Vec3& normal, Real radius1, Real radius2, Real depth);
578 Vec3& location, Vec3& normal, Real radius, Real depth);
608 Real getDepth() const;
612 static bool isInstance(const Contact& contact);
617
618private:
619 const PointContactImpl& getImpl() const
620 { assert(isInstance(*this));
621 return reinterpret_cast<const PointContactImpl&>(Contact::getImpl()); }
622};
623
624} // namespace SimTK
625
626#endif // SimTK_SIMMATH_CONTACT_H_
Includes internal headers providing declarations for the basic SimTK Core classes,...
This is the header file that every Simmath compilation unit should include first.
#define SimTK_SIMMATH_EXPORT
Definition: SimTKmath/include/simmath/internal/common.h:64
This subclass of Contact is used when one ContactGeometry object is a half plane and the other is a B...
Definition: Contact.h:418
static ContactTypeId classTypeId()
Obtain the unique small-integer id for the BrickHalfSpaceContact class.
Real getDepth() const
Get the penetration depth (>0) or separation distance (<0) from the brick's lowest vertex to the half...
static const BrickHalfSpaceContact & getAs(const Contact &contact)
Recast a brick-halfspace contact given as a generic Contact object to a const reference to a concrete...
Definition: Contact.h:449
static BrickHalfSpaceContact & updAs(Contact &contact)
Recast a brick-halfspace contact given as a generic Contact object to a writable reference to a concr...
Definition: Contact.h:455
static bool isInstance(const Contact &contact)
Determine whether a Contact object is a BrickHalfSpaceContact.
int getLowestVertex() const
Get the vertex index (0-7) of the brick's vertex that is closest to or most penetrated into the halfs...
BrickHalfSpaceContact(ContactSurfaceIndex halfSpace, ContactSurfaceIndex brick, const Transform &X_HB, int lowestVertex, Real depth)
Create a BrickHalfSpaceContact object.
This subclass of Contact represents a pair of contact surfaces that were in contact (meaning within c...
Definition: Contact.h:216
Real getSeparation() const
Get the separation (> cutoff >= 0) between the two surfaces at the time we decided the contact had be...
BrokenContact(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2, const Transform &X_S1S2, Real separation)
Create a BrokenContact object.
static bool isInstance(const Contact &contact)
Determine whether a Contact object is a BrokenContact.
static ContactTypeId classTypeId()
Obtain the unique small-integer id for the BrokenContact class.
This subclass of Contact represents a contact between two non-conforming surfaces 1 and 2 that initia...
Definition: Contact.h:260
const UnitVec3 & getNormal() const
Get the z axis of the contact patch frame, which is the common surface normal at the initial contact ...
static bool isInstance(const Contact &contact)
Determine whether a Contact object is a CircularPointContact.
Real getEffectiveRadius() const
Get the precalculated effective radius R at the contact point, where R=1/(1/R1+1/R2).
static const CircularPointContact & getAs(const Contact &contact)
Definition: Contact.h:303
Real getRadius2() const
Get the radius of surface2 at the contact point.
static ContactTypeId classTypeId()
Get the unique small-integer id for the CircularPointContact class.
CircularPointContact(ContactSurfaceIndex surf1, Real radius1, ContactSurfaceIndex surf2, Real radius2, const Transform &X_S1S2, Real radius, Real depth, const Vec3 &origin_S1, const UnitVec3 &normal_S1)
Create a CircularPointContact object.
Real getRadius1() const
Get the radius of surface1 at the contact point.
const Vec3 & getOrigin() const
Get the origin OP of the contact patch frame P, in S1.
Real getDepth() const
Get the penetration depth (>0) or separation distance (<0), also known as the "approach".
static CircularPointContact & updAs(Contact &contact)
Definition: Contact.h:306
This is a unique integer Id assigned to each contact pair when we first begin to track it.
This defines a unique index for all the contact surfaces being handled either by a ContactTrackerSubs...
This is a small integer that serves as the unique typeid for each type of concrete Contact class.
A Contact contains information about the spatial relationship between two surfaces that are near,...
Definition: Contact.h:85
Contact & setSurfaces(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2)
Set the surfaces tracked by this Contact object.
Contact(const Contact &source)
Copy constructor is shallow and reference-counted; this handle will point to the same object as does ...
bool isEmpty() const
See if this handle is empty.
Definition: Contact.h:117
static ContactId createNewContactId()
This creates a new ContactId starting from 1 and increasing for a very long time (to a billion or so)...
const ContactImpl & getImpl() const
Definition: Contact.h:155
~Contact()
Destructor clears the handle, deleting the referenced object if this was the last reference.
Definition: Contact.h:109
ContactSurfaceIndex getSurface1() const
Get the first surface involved in the contact, specified by its index within its contact set or Conta...
void clear()
Clear this handle, deleting the referenced object if this was the last reference.
const Transform & getTransform() const
Return the transform X_S1S2 giving the pose of surface 2's frame measured and expressed in surface 1'...
Contact & operator=(const Contact &source)
Copy assignment is shallow and reference-counted; this handle will point to the same object as does t...
Contact()
The default constructor creates an empty handle.
Definition: Contact.h:103
Contact & setCondition(Condition condition)
Set the current Condition.
static const char * nameOfCondition(Condition)
Returns a human-readable name corresponding to the given Condition; useful for debugging.
Contact(ContactImpl *impl)
ContactTypeId getTypeId() const
Return a unique small integer corresponding to the concrete type of Contact object being referenced b...
Contact & setTransform(const Transform &X_S1S2)
Set the surface-to-surface relative transform X_S1S2.
Condition
The Contact::Condition tracks the status of a Contact through its lifetime.
Definition: Contact.h:89
@ Unknown
this is an illegal value
Definition: Contact.h:90
@ Ongoing
was new or ongoing before; still in contact now
Definition: Contact.h:94
@ Anticipated
we expect these to contact soon
Definition: Contact.h:92
@ Untracked
this pair not yet being tracked; might not contact
Definition: Contact.h:91
@ NewContact
first time seen; needs a ContactId assigned
Definition: Contact.h:93
ContactSurfaceIndex getSurface2() const
Get the second surface involved in the contact, specified by its index within its contact set or Cont...
ContactId getContactId() const
Get the persistent ContactId that has been assigned to this Contact object if there is one (otherwise...
Contact & setContactId(ContactId id)
Set the ContactId for this Contact object.
ContactImpl & updImpl()
Definition: Contact.h:156
Condition getCondition() const
Find out the current condition of this Contact object.
This subclass of Contact represents a contact between two non-conforming surfaces 1 and 2 that initia...
Definition: Contact.h:355
static ContactTypeId classTypeId()
Get the unique small-integer id for the CircularPointContact class.
const Transform & getContactFrame() const
Get the frame C in which the contact paraboloid is expressed, as the transform X_S1C.
EllipticalPointContact(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2, const Transform &X_S1S2, const Transform &X_S1C, const Vec2 &k, Real depth)
Create a EllipticalPointContact object.
static EllipticalPointContact & updAs(Contact &contact)
Definition: Contact.h:396
static const EllipticalPointContact & getAs(const Contact &contact)
Definition: Contact.h:393
static bool isInstance(const Contact &contact)
Determine whether a Contact object is an EllipticalPointContact.
const Vec2 & getCurvatures() const
Get the relative curvatures at the contact point, ordered kmax,kmin with kmax >= kmin.
Real getDepth() const
Get the penetration depth (>0) or separation distance (<0), also known as the "approach".
OBSOLETE – use CircularPointContact or EllipticalPointContact.
Definition: Contact.h:542
PointContact(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2, Vec3 &location, Vec3 &normal, Real radius1, Real radius2, Real depth)
Create a PointContact object representing a general (elliptical) contact.
Vec3 getLocation() const
The location where the two surfaces touch, specified in the ground frame.
Real getEffectiveRadiusOfCurvature() const
Get the effective relative radius of curvature of the contact surface.
PointContact(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2, Vec3 &location, Vec3 &normal, Real radius, Real depth)
Create a PointContact object representing a circularly symmetric contact.
static ContactTypeId classTypeId()
Obtain the unique small-integer id for the PointContact class.
Real getRadiusOfCurvature2() const
Get the second principal relative radius of curvature of the contact surface.
Real getDepth() const
Get the penetration depth.
Vec3 getNormal() const
Get the surface normal at the contact location.
Real getRadiusOfCurvature1() const
Get the first principal relative radius of curvature of the contact surface.
static bool isInstance(const Contact &contact)
Determine whether a Contact object is a PointContact.
This subclass of Contact is used when one or both of the ContactGeometry objects is a TriangleMesh.
Definition: Contact.h:478
const std::set< int > & getSurface1Faces() const
Get the indices of all faces of surface1 that are partly or completely inside surface2.
static bool isInstance(const Contact &contact)
Determine whether a Contact object is a TriangleMeshContact.
const std::set< int > & getSurface2Faces() const
Get the indices of all faces of surface2 that are partly or completely inside surface1.
static const TriangleMeshContact & getAs(const Contact &contact)
Recast a triangle mesh given as a generic Contact object to a const reference to a concrete TriangleM...
Definition: Contact.h:510
static TriangleMeshContact & updAs(Contact &contact)
Recast a triangle mesh given as a generic Contact object to a writable reference to a concrete Triang...
Definition: Contact.h:515
static ContactTypeId classTypeId()
Obtain the unique small-integer id for the TriangleMeshContact class.
TriangleMeshContact(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2, const Transform &X_S1S2, const std::set< int > &faces1, const std::set< int > &faces2)
Create a TriangleMeshContact object.
This subclass of Contact represents a pair of contact surfaces that are not yet being tracked; there ...
Definition: Contact.h:182
UntrackedContact()
Default constructor creates an empty handle.
Definition: Contact.h:185
UntrackedContact(ContactSurfaceIndex surf1, ContactSurfaceIndex surf2)
Create an UntrackedContact object.
static bool isInstance(const Contact &contact)
Determine whether a Contact object is an UntrackedContact.
static ContactTypeId classTypeId()
Obtain the unique small-integer id for the UntrackedContact class.
This is the top-level SimTK namespace into which all SimTK names are placed to avoid collision with o...
Definition: Assembler.h:37
std::ostream & operator<<(std::ostream &o, const ContactForce &f)
Definition: CompliantContactSubsystem.h:387
SimTK_Real Real
This is the default compiled-in floating point type for SimTK, either float or double.
Definition: SimTKcommon/include/SimTKcommon/internal/common.h:606
SimTK_DEFINE_UNIQUE_INDEX_TYPE(AssemblyConditionIndex)