aboutsummaryrefslogtreecommitdiff
path: root/PhysX_3.4/Include/PxContact.h
diff options
context:
space:
mode:
authorgit perforce import user <a@b>2016-10-25 12:29:14 -0600
committerSheikh Dawood Abdul Ajees <Sheikh Dawood Abdul Ajees>2016-10-25 18:56:37 -0500
commit3dfe2108cfab31ba3ee5527e217d0d8e99a51162 (patch)
treefa6485c169e50d7415a651bf838f5bcd0fd3bfbd /PhysX_3.4/Include/PxContact.h
downloadphysx-3.4-3dfe2108cfab31ba3ee5527e217d0d8e99a51162.tar.xz
physx-3.4-3dfe2108cfab31ba3ee5527e217d0d8e99a51162.zip
Initial commit:
PhysX 3.4.0 Update @ 21294896 APEX 1.4.0 Update @ 21275617 [CL 21300167]
Diffstat (limited to 'PhysX_3.4/Include/PxContact.h')
-rw-r--r--PhysX_3.4/Include/PxContact.h583
1 files changed, 583 insertions, 0 deletions
diff --git a/PhysX_3.4/Include/PxContact.h b/PhysX_3.4/Include/PxContact.h
new file mode 100644
index 00000000..c98e84a3
--- /dev/null
+++ b/PhysX_3.4/Include/PxContact.h
@@ -0,0 +1,583 @@
+// This code contains NVIDIA Confidential Information and is disclosed to you
+// under a form of NVIDIA software license agreement provided separately to you.
+//
+// Notice
+// NVIDIA Corporation and its licensors retain all intellectual property and
+// proprietary rights in and to this software and related documentation and
+// any modifications thereto. Any use, reproduction, disclosure, or
+// distribution of this software and related documentation without an express
+// license agreement from NVIDIA Corporation is strictly prohibited.
+//
+// ALL NVIDIA DESIGN SPECIFICATIONS, CODE ARE PROVIDED "AS IS.". NVIDIA MAKES
+// NO WARRANTIES, EXPRESSED, IMPLIED, STATUTORY, OR OTHERWISE WITH RESPECT TO
+// THE MATERIALS, AND EXPRESSLY DISCLAIMS ALL IMPLIED WARRANTIES OF NONINFRINGEMENT,
+// MERCHANTABILITY, AND FITNESS FOR A PARTICULAR PURPOSE.
+//
+// Information and code furnished is believed to be accurate and reliable.
+// However, NVIDIA Corporation assumes no responsibility for the consequences of use of such
+// information or for any infringement of patents or other rights of third parties that may
+// result from its use. No license is granted by implication or otherwise under any patent
+// or patent rights of NVIDIA Corporation. Details are subject to change without notice.
+// This code supersedes and replaces all information previously supplied.
+// NVIDIA Corporation products are not authorized for use as critical
+// components in life support devices or systems without express written approval of
+// NVIDIA Corporation.
+//
+// Copyright (c) 2008-2016 NVIDIA Corporation. All rights reserved.
+// Copyright (c) 2004-2008 AGEIA Technologies, Inc. All rights reserved.
+// Copyright (c) 2001-2004 NovodeX AG. All rights reserved.
+
+
+#ifndef PX_CONTACT_H
+#define PX_CONTACT_H
+
+#include "foundation/PxVec3.h"
+#include "foundation/PxAssert.h"
+
+#if !PX_DOXYGEN
+namespace physx
+{
+#endif
+
+#if PX_VC
+#pragma warning(push)
+#pragma warning(disable: 4324) // Padding was added at the end of a structure because of a __declspec(align) value.
+#endif
+
+#define PXC_CONTACT_NO_FACE_INDEX 0xffffffff
+
+PX_ALIGN_PREFIX(16)
+struct PxMassModificationProps
+{
+ PxReal mInvMassScale0;
+ PxReal mInvInertiaScale0;
+ PxReal mInvMassScale1;
+ PxReal mInvInertiaScale1;
+}
+PX_ALIGN_SUFFIX(16);
+
+/**
+\brief Header for contact patch where all points share same material and normal
+*/
+
+PX_ALIGN_PREFIX(16)
+struct PxContactPatch
+{
+ enum PxContactPatchFlags
+ {
+ eHAS_FACE_INDICES = 1, //!< Indicates this contact stream has face indices.
+ eMODIFIABLE = 2, //!< Indicates this contact stream is modifiable.
+ eFORCE_NO_RESPONSE = 4, //!< Indicates this contact stream is notify-only (no contact response).
+ eHAS_MODIFIED_MASS_RATIOS = 8, //!< Indicates this contact stream has modified mass ratios
+ eHAS_TARGET_VELOCITY = 16, //!< Indicates this contact stream has target velocities set
+ eHAS_MAX_IMPULSE = 32, //!< Indicates this contact stream has max impulses set
+ eREGENERATE_PATCHES = 64, //!< Indicates this contact stream needs patches re-generated.
+ //!< This is required if the application modified either the contact normal or the material properties
+ eCOMPRESSED_MODIFIED_CONTACT = 128
+ };
+
+ PX_ALIGN(16, PxMassModificationProps mMassModification); //16
+ /**
+ \brief Contact normal
+ */
+ PX_ALIGN(16, PxVec3 normal); //28
+ /**
+ \brief Restitution coefficient
+ */
+ PxReal restitution; //32
+
+ PxReal dynamicFriction; //36
+ PxReal staticFriction; //40
+ PxU8 startContactIndex; //41
+ PxU8 nbContacts; //42 //Can be a U8
+
+ PxU8 materialFlags; //43 //Can be a U16
+ PxU8 internalFlags; //44 //Can be a U16
+ PxU16 materialIndex0; //46 //Can be a U16
+ PxU16 materialIndex1; //48 //Can be a U16
+
+
+}
+PX_ALIGN_SUFFIX(16);
+
+/**
+\brief Contact point data including face (feature) indices
+*/
+
+PX_ALIGN_PREFIX(16)
+struct PxContact
+{
+ /**
+ \brief Contact point in world space
+ */
+ PxVec3 contact; //12
+ /**
+ \brief Separation value (negative implies penetration).
+ */
+ PxReal separation; //16
+}
+PX_ALIGN_SUFFIX(16);
+
+PX_ALIGN_PREFIX(16)
+struct PxExtendedContact : public PxContact
+{
+ /**
+ \brief Target velocity
+ */
+ PX_ALIGN(16, PxVec3 targetVelocity); //28
+ /**
+ \brief Maximum impulse
+ */
+ PxReal maxImpulse; //32
+}
+PX_ALIGN_SUFFIX(16);
+
+/**
+\brief A modifiable contact point. This has additional fields per-contact to permit modification by user.
+\note Not all fields are currently exposed to the user.
+*/
+PX_ALIGN_PREFIX(16)
+struct PxModifiableContact : public PxExtendedContact
+{
+ /**
+ \brief Contact normal
+ */
+ PX_ALIGN(16, PxVec3 normal); //44
+ /**
+ \brief Restitution coefficient
+ */
+ PxReal restitution; //48
+
+ /**
+ \brief Material Flags
+ */
+ PxU32 materialFlags; //52
+
+ /**
+ \brief Shape A's material index
+ */
+ PxU16 materialIndex0; //54
+ /**
+ \brief Shape B's material index
+ */
+ PxU16 materialIndex1; //56
+ /**
+ \brief static friction coefficient
+ */
+ PxReal staticFriction; //60
+ /**
+ \brief dynamic friction coefficient
+ */
+ PxReal dynamicFriction; //64
+}
+PX_ALIGN_SUFFIX(16);
+
+/**
+\brief A class to iterate over a compressed contact stream. This supports read-only access to the various contact formats.
+*/
+struct PxContactStreamIterator
+{
+ enum StreamFormat
+ {
+ eSIMPLE_STREAM,
+ eMODIFIABLE_STREAM,
+ eCOMPRESSED_MODIFIABLE_STREAM
+ };
+ /**
+ \brief Utility zero vector to optimize functions returning zero vectors when a certain flag isn't set.
+ \note This allows us to return by reference instead of having to return by value. Returning by value will go via memory (registers -> stack -> registers), which can
+ cause performance issues on certain platforms.
+ */
+ PxVec3 zero;
+ /**
+ \brief The patch headers.
+ */
+ const PxContactPatch* patch;
+
+ /**
+ \brief The contacts
+ */
+ const PxContact* contact;
+
+ /**
+ \brief The contact triangle face index
+ */
+ const PxU32* faceIndice;
+
+
+ /**
+ \brief The total number of patches in this contact stream
+ */
+ PxU32 totalPatches;
+
+ /**
+ \brief The total number of contact points in this stream
+ */
+ PxU32 totalContacts;
+
+ /**
+ \brief The current contact index
+ */
+ PxU32 nextContactIndex;
+
+ /**
+ \brief The current patch Index
+ */
+ PxU32 nextPatchIndex;
+
+ /*
+ \brief Size of contact patch header
+ \note This varies whether the patch is modifiable or not.
+ */
+ PxU32 contactPatchHeaderSize;
+ /**
+ \brief Contact point size
+ \note This varies whether the patch has feature indices or is modifiable.
+ */
+ PxU32 contactPointSize;
+ /**
+ \brief The stream format
+ */
+ StreamFormat mStreamFormat;
+ /**
+ \brief Indicates whether this stream is notify-only or not.
+ */
+ PxU32 forceNoResponse;
+
+ bool pointStepped;
+
+ PxU32 hasFaceIndices;
+
+ /**
+ \brief Constructor
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxContactStreamIterator(const PxU8* contactPatches, const PxU8* contactPoints, const PxU32* contactFaceIndices, PxU32 nbPatches, PxU32 nbContacts)
+ : zero(0.f)
+ {
+ bool modify = false;
+ bool compressedModify = false;
+ bool response = false;
+ bool indices = false;
+
+ PxU32 pointSize = 0;
+ PxU32 patchHeaderSize = sizeof(PxContactPatch);
+
+ const PxContactPatch* patches = reinterpret_cast<const PxContactPatch*>(contactPatches);
+
+ if(patches)
+ {
+ modify = (patches->internalFlags & PxContactPatch::eMODIFIABLE) != 0;
+ compressedModify = (patches->internalFlags & PxContactPatch::eCOMPRESSED_MODIFIED_CONTACT) != 0;
+ indices = (patches->internalFlags & PxContactPatch::eHAS_FACE_INDICES) != 0;
+
+ patch = patches;
+
+ contact = reinterpret_cast<const PxContact*>(contactPoints);
+
+ faceIndice = contactFaceIndices;
+
+ pointSize = compressedModify ? sizeof(PxExtendedContact) : modify ? sizeof(PxModifiableContact) : sizeof(PxContact);
+
+ response = (patch->internalFlags & PxContactPatch::eFORCE_NO_RESPONSE) == 0;
+ }
+
+
+ mStreamFormat = compressedModify ? eCOMPRESSED_MODIFIABLE_STREAM : modify ? eMODIFIABLE_STREAM : eSIMPLE_STREAM;
+ hasFaceIndices = PxU32(indices);
+ forceNoResponse = PxU32(!response);
+
+ contactPatchHeaderSize = patchHeaderSize;
+ contactPointSize = pointSize;
+ nextPatchIndex = 0;
+ nextContactIndex = 0;
+ totalContacts = nbContacts;
+ totalPatches = nbPatches;
+
+ pointStepped = false;
+ }
+
+ /**
+ \brief Returns whether there are more patches in this stream.
+ \return Whether there are more patches in this stream.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE bool hasNextPatch() const
+ {
+ return nextPatchIndex < totalPatches;
+ }
+
+ /**
+ \brief Returns the total contact count.
+ \return Total contact count.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU32 getTotalContactCount() const
+ {
+ return totalContacts;
+ }
+
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU32 getTotalPatchCount() const
+ {
+ return totalPatches;
+ }
+
+ /**
+ \brief Advances iterator to next contact patch.
+ */
+ PX_CUDA_CALLABLE PX_INLINE void nextPatch()
+ {
+ PX_ASSERT(nextPatchIndex < totalPatches);
+ if(nextPatchIndex)
+ {
+ if(nextContactIndex < patch->nbContacts)
+ {
+ PxU32 nbToStep = patch->nbContacts - this->nextContactIndex;
+ contact = reinterpret_cast<const PxContact*>(reinterpret_cast<const PxU8*>(contact) + contactPointSize * nbToStep);
+ }
+ patch = reinterpret_cast<const PxContactPatch*>(reinterpret_cast<const PxU8*>(patch) + contactPatchHeaderSize);
+ }
+ nextPatchIndex++;
+ nextContactIndex = 0;
+ }
+
+ /**
+ \brief Returns if the current patch has more contacts.
+ \return If there are more contacts in the current patch.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE bool hasNextContact() const
+ {
+ return nextContactIndex < (patch->nbContacts);
+ }
+
+ /**
+ \brief Advances to the next contact in the patch.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE void nextContact()
+ {
+ PX_ASSERT(nextContactIndex < patch->nbContacts);
+ if(pointStepped)
+ {
+ contact = reinterpret_cast<const PxContact*>(reinterpret_cast<const PxU8*>(contact) + contactPointSize);
+ faceIndice++;
+ }
+ nextContactIndex++;
+ pointStepped = true;
+ }
+
+
+ /**
+ \brief Gets the current contact's normal
+ \return The current contact's normal.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE const PxVec3& getContactNormal() const
+ {
+ return getContactPatch().normal;
+ }
+
+ /**
+ \brief Gets the inverse mass scale for body 0.
+ \return The inverse mass scale for body 0.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getInvMassScale0() const
+ {
+ return patch->mMassModification.mInvMassScale0;
+ }
+
+ /**
+ \brief Gets the inverse mass scale for body 1.
+ \return The inverse mass scale for body 1.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getInvMassScale1() const
+ {
+ return patch->mMassModification.mInvMassScale1;
+ }
+
+ /**
+ \brief Gets the inverse inertia scale for body 0.
+ \return The inverse inertia scale for body 0.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getInvInertiaScale0() const
+ {
+ return patch->mMassModification.mInvInertiaScale0;
+ }
+
+ /**
+ \brief Gets the inverse inertia scale for body 1.
+ \return The inverse inertia scale for body 1.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getInvInertiaScale1() const
+ {
+ return patch->mMassModification.mInvInertiaScale1;
+ }
+
+ /**
+ \brief Gets the contact's max impulse.
+ \return The contact's max impulse.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getMaxImpulse() const
+ {
+ return mStreamFormat != eSIMPLE_STREAM ? getExtendedContact().maxImpulse : PX_MAX_REAL;
+ }
+
+ /**
+ \brief Gets the contact's target velocity.
+ \return The contact's target velocity.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE const PxVec3& getTargetVel() const
+ {
+ return mStreamFormat != eSIMPLE_STREAM ? getExtendedContact().targetVelocity : zero;
+ }
+
+ /**
+ \brief Gets the contact's contact point.
+ \return The contact's contact point.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE const PxVec3& getContactPoint() const
+ {
+ return contact->contact;
+ }
+
+ /**
+ \brief Gets the contact's separation.
+ \return The contact's separation.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getSeparation() const
+ {
+ return contact->separation;
+ }
+
+ /**
+ \brief Gets the contact's face index for shape 0.
+ \return The contact's face index for shape 0.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU32 getFaceIndex0() const
+ {
+ return PXC_CONTACT_NO_FACE_INDEX;
+ }
+
+ /**
+ \brief Gets the contact's face index for shape 1.
+ \return The contact's face index for shape 1.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU32 getFaceIndex1() const
+ {
+ return hasFaceIndices ? *faceIndice : PXC_CONTACT_NO_FACE_INDEX;
+ }
+
+ /**
+ \brief Gets the contact's static friction coefficient.
+ \return The contact's static friction coefficient.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getStaticFriction() const
+ {
+ return getContactPatch().staticFriction;
+ }
+
+ /**
+ \brief Gets the contact's static dynamic coefficient.
+ \return The contact's static dynamic coefficient.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getDynamicFriction() const
+ {
+ return getContactPatch().dynamicFriction;
+ }
+
+ /**
+ \brief Gets the contact's restitution coefficient.
+ \return The contact's restitution coefficient.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxReal getRestitution() const
+ {
+ return getContactPatch().restitution;
+ }
+
+ /**
+ \brief Gets the contact's material flags.
+ \return The contact's material flags.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU32 getMaterialFlags() const
+ {
+ return getContactPatch().materialFlags;
+ }
+
+ /**
+ \brief Gets the contact's material index for shape 0.
+ \return The contact's material index for shape 0.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU16 getMaterialIndex0() const
+ {
+ return PxU16(getContactPatch().materialIndex0);
+ }
+
+ /**
+ \brief Gets the contact's material index for shape 1.
+ \return The contact's material index for shape 1.
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE PxU16 getMaterialIndex1() const
+ {
+ return PxU16(getContactPatch().materialIndex1);
+ }
+
+ /**
+ \brief Advances the contact stream iterator to a specific contact index.
+ */
+ bool advanceToIndex(const PxU32 initialIndex)
+ {
+ PX_ASSERT(this->nextPatchIndex == 0 && this->nextContactIndex == 0);
+
+ PxU32 numToAdvance = initialIndex;
+
+ if(numToAdvance == 0)
+ {
+ PX_ASSERT(hasNextPatch());
+ nextPatch();
+ return true;
+ }
+
+ while(numToAdvance)
+ {
+ while(hasNextPatch())
+ {
+ nextPatch();
+ PxU32 patchSize = patch->nbContacts;
+ if(numToAdvance <= patchSize)
+ {
+ contact = reinterpret_cast<const PxContact*>(reinterpret_cast<const PxU8*>(contact) + contactPointSize * numToAdvance);
+ nextContactIndex += numToAdvance;
+ return true;
+ }
+ else
+ {
+ numToAdvance -= patchSize;
+ }
+ }
+ }
+ return false;
+ }
+
+private:
+
+ /**
+ \brief Internal helper
+ */
+ PX_CUDA_CALLABLE PX_FORCE_INLINE const PxContactPatch& getContactPatch() const
+ {
+ return *static_cast<const PxContactPatch*>(patch);
+ }
+
+ PX_CUDA_CALLABLE PX_FORCE_INLINE const PxExtendedContact& getExtendedContact() const
+ {
+ PX_ASSERT(mStreamFormat == eMODIFIABLE_STREAM || mStreamFormat == eCOMPRESSED_MODIFIABLE_STREAM);
+ return *static_cast<const PxExtendedContact*>(contact);
+ }
+
+};
+
+
+#if PX_VC
+#pragma warning(pop)
+#endif
+
+#if !PX_DOXYGEN
+} // namespace physx
+#endif
+
+#endif