1/*
2 * Copyright (c) 2008-2015, NVIDIA CORPORATION. All rights reserved.
3 *
4 * NVIDIA CORPORATION and its licensors retain all intellectual property
5 * and proprietary rights in and to this software, related documentation
6 * and any modifications thereto. Any use, reproduction, disclosure or
7 * distribution of this software and related documentation without an express
8 * license agreement from NVIDIA CORPORATION is strictly prohibited.
9 */
10// Copyright (c) 2004-2008 AGEIA Technologies, Inc. All rights reserved.
11// Copyright (c) 2001-2004 NovodeX AG. All rights reserved.
12
13
14#ifndef PX_PHYSICS_NX_CONSTRAINTDESC
15#define PX_PHYSICS_NX_CONSTRAINTDESC
16
17/** \addtogroup physics
18@{
19*/
20
21#include "PxPhysXConfig.h"
22#include "foundation/PxFlags.h"
23#include "foundation/PxMath.h"
24#include "foundation/PxVec3.h"
25#include "common/PxBase.h"
26
27#ifndef PX_DOXYGEN
28namespace physx { namespace debugger { namespace comm {
29#endif
30 class PvdDataStream;
31#ifndef PX_DOXYGEN
32}}}
33#endif
34
35#ifndef PX_DOXYGEN
36namespace physx
37{
38#endif
39
40class PxConstraintConnector;
41class PxRigidActor;
42class PxScene;
43class PxConstraintConnector;
44class PxRenderBuffer;
45class PxDeletionListener;
46
47
48/**
49 \brief constraint row flags
50
51 These flags configure the post-processing of constraint rows and the behavior of the solver while solving constraints
52*/
53
54struct Px1DConstraintFlag
55{
56 enum Type
57 {
58 eSPRING = 1<<0, //!< whether the constraint is a spring. Mutually exclusive with eRESTITUTION. If set, eKEEPBIAS is ignored.
59 eACCELERATION_SPRING = 1<<1, //!< whether the constraint is a force or acceleration spring. Only valid if eSPRING is set.
60 eRESTITUTION = 1<<2, //!< whether the restitution model should be applied to generate the target velocity. Mutually exclusive with eSPRING. If restitution causes a bounces, eKEEPBIAS is ignored
61 eKEEPBIAS = 1<<3, //!< whether to keep the error term when solving for velocity. Ignored if restitution generates bounce, or eSPRING is set.
62 eOUTPUT_FORCE = 1<<4, //!< whether to accumulate the force value from this constraint in the force total that is reported for the constraint and tested for breakage
63 eHAS_DRIVE_LIMIT = 1<<5 //!< whether the constraint has a drive force limit (which will be scaled by dt unless PxConstraintFlag::eLIMITS_ARE_FORCES is set)
64 };
65};
66
67typedef PxFlags<Px1DConstraintFlag::Type, PxU16> Px1DConstraintFlags;
68PX_FLAGS_OPERATORS(Px1DConstraintFlag::Type, PxU16)
69
70/**
71\brief constraint type hints which the solver uses to optimize constraint handling
72*/
73
74struct PxConstraintSolveHint
75{
76 enum Enum
77 {
78 eNONE = 0, //!< no special properties
79 eACCELERATION1 = 256, //!< a group of acceleration drive constraints with the same stiffness and drive parameters
80 eSLERP_SPRING = 258, //!< temporary special value to identify SLERP drive rows
81 eACCELERATION2 = 512, //!< a group of acceleration drive constraints with the same stiffness and drive parameters
82 eACCELERATION3 = 768, //!< a group of acceleration drive constraints with the same stiffness and drive parameters
83 eEQUALITY = 1024, //!< equality constraints with no force limit and no velocity target
84 eINEQUALITY = 1025 //!< inequality constraints with (0, PX_MAX_FLT force limits)
85 };
86};
87
88/**
89\brief A constraint
90
91A constraint is expressed as a set of 1-dimensional constraint rows which define the required constraint
92on the objects' velocities.
93
94Each constraint is either a hard constraint or a spring. We define the velocity at the constraint to be
95the quantity
96
97 v = body0vel.dot(lin0,ang0) - body1vel.dot(lin1, ang1)
98
99For a hard constraint, the solver attempts to generate
100
1011. a set of velocities for the objects which, when integrated, respect the constraint errors:
102
103 v + (geometricError / timestep) = velocityTarget
104
1052. a set of velocities for the objects which respect the constraints:
106
107 v = velocityTarget
108
109Hard constraints support restitution: if the impact velocity exceeds the bounce threshold, then the target velocity
110of the constraint will be set to restitution * -v
111
112Alternatively, the solver can attempt to resolve the velocity constraint as an implicit spring:
113
114 F = stiffness * -geometricError + damping * (velocityTarget - v)
115
116where F is the constraint force or acceleration. Springs are fully implicit: that is, the force or acceleration
117is a function of the position and velocity after the solve.
118
119All constraints support limits on the minimum or maximum impulse applied.
120
121
122*/
123
124PX_ALIGN_PREFIX(16)
125struct Px1DConstraint
126{
127 PxVec3 linear0; //!< linear component of velocity jacobian in world space
128 PxReal geometricError; //!< geometric error of the constraint along this axis
129 PxVec3 angular0; //!< angular component of velocity jacobian in world space
130 PxReal velocityTarget; //!< velocity target for the constraint along this axis
131
132 PxVec3 linear1; //!< linear component of velocity jacobian in world space
133 PxReal minImpulse; //!< minimum impulse the solver may apply to enforce this constraint
134 PxVec3 angular1; //!< angular component of velocity jacobian in world space
135 PxReal maxImpulse; //!< maximum impulse the solver may apply to enforce this constraint
136
137 union
138 {
139 struct SpringModifiers
140 {
141 PxReal stiffness; //!< spring parameter, for spring constraints
142 PxReal damping; //!< damping parameter, for spring constraints
143 } spring;
144 struct RestitutionModifiers
145 {
146 PxReal restitution; //!< restitution parameter for determining additional "bounce"
147 PxReal velocityThreshold; //!< minimum impact velocity for bounce
148 } bounce;
149 } mods;
150
151 PxReal forInternalUse; //< for internal use only
152 PxU16 flags; //!< a set of Px1DConstraintFlags
153 PxU16 solveHint; //!< constraint optimization hint, should be an element of PxConstraintSolveHint
154}
155PX_ALIGN_SUFFIX(16);
156
157
158/**
159\brief Flags for determining which components of the constraint should be visualized.
160
161@see PxConstraintVisualize
162*/
163struct PxConstraintVisualizationFlag
164{
165 enum Enum
166 {
167 eLOCAL_FRAMES = 1, //!< visualize constraint frames
168 eLIMITS = 2 //!< visualize constraint limits
169 };
170};
171
172struct PxConstraintInvMassScale
173{
174//= ATTENTION! =====================================================================================
175// Changing the data layout of this class breaks the binary serialization format. See comments for
176// PX_BINARY_SERIAL_VERSION. If a modification is required, please adjust the getBinaryMetaData
177// function. If the modification is made on a custom branch, please change PX_BINARY_SERIAL_VERSION
178// accordingly.
179//==================================================================================================
180
181 PxReal linear0; //!< multiplier for inverse mass of body0
182 PxReal angular0; //!< multiplier for inverse MoI of body0
183 PxReal linear1; //!< multiplier for inverse mass of body1
184 PxReal angular1; //!< multiplier for inverse MoI of body1
185};
186
187/** solver constraint generation shader
188
189This function is called by the constraint solver framework. The function must be reentrant, since it may be called simultaneously
190from multiple threads, and should access only the arguments passed into it, since on PS3 this function may execute on SPU.
191
192Developers writing custom constraints are encouraged to read the documentation in the user guide and the implementation code in PhysXExtensions.
193
194\param[out] constraints an array of solver constraint rows to be filled in
195\param[out] bodyAWorldOffset the origin point (offset from the position vector of bodyA's center of mass) at which the constraint is resolved. This value does not affect how constraints are solved, only the constraint force reported.
196\param[in] maxConstraints the size of the constraint buffer. At most this many constraints rows may be written
197\param[out] invMassScale the inverse mass and inertia scales for the constraint
198\param[in] constantBlock the constant data block
199\param[in] bodyAToWorld The center of mass frame of the first constrained body (the identity transform if the first actor is static, or if a NULL actor pointer was provided for it)
200\param[in] bodyBToWorld The center of mass frame of the second constrained body (the identity transform if the second actor is static, or if a NULL actor pointer was provided for it)
201
202\return the number of constraint rows written.
203*/
204
205typedef PxU32 (*PxConstraintSolverPrep)(Px1DConstraint* constraints,
206 PxVec3& bodyAWorldOffset,
207 PxU32 maxConstraints,
208 PxConstraintInvMassScale& invMassScale,
209 const void* constantBlock,
210 const PxTransform& bodyAToWorld,
211 const PxTransform& bodyBToWorld);
212
213/** solver constraint projection shader
214
215This function is called by the constraint post-solver framework. The function must be reentrant, since it may be called simultaneously
216from multiple threads and should access only the arguments passed into it, since on PS3 this function may execute on SPU.
217
218\param[in] constantBlock the constant data block
219\param[out] bodyAToWorld The center of mass frame of the first constrained body (the identity if the actor is static or a NULL pointer was provided for it)
220\param[out] bodyBToWorld The center of mass frame of the second constrained body (the identity if the actor is static or a NULL pointer was provided for it)
221\param[in] true if the constraint should be projected by moving the second body towards the first, false if the converse
222*/
223
224typedef void (*PxConstraintProject)(const void* constantBlock,
225 PxTransform& bodyAToWorld,
226 PxTransform& bodyBToWorld,
227 bool projectToA);
228
229/**
230 API used to visualize details about a constraint.
231*/
232class PxConstraintVisualizer
233{
234protected:
235 virtual ~PxConstraintVisualizer(){}
236public:
237 virtual void visualizeJointFrames( const PxTransform& parent, const PxTransform& child ) = 0;
238
239 virtual void visualizeLinearLimit( const PxTransform& t0, const PxTransform& t1, PxReal value, bool active ) = 0;
240
241 virtual void visualizeAngularLimit( const PxTransform& t0, PxReal lower, PxReal upper, bool active) = 0;
242
243 virtual void visualizeLimitCone( const PxTransform& t, PxReal ySwing, PxReal zSwing, bool active) = 0;
244
245 virtual void visualizeDoubleCone( const PxTransform& t, PxReal angle, bool active) = 0;
246};
247
248/** solver constraint visualization function
249
250This function is called by the constraint post-solver framework to visualize the constraint
251
252\param[out] out the render buffer to render to
253\param[in] constantBlock the constant data block
254\param[in] body0Transform The center of mass frame of the first constrained body (the identity if the actor is static, or a NULL pointer was provided for it)
255\param[in] body1Transform The center of mass frame of the second constrained body (the identity if the actor is static, or a NULL pointer was provided for it)
256\param[in] frameScale the visualization scale for the constraint frames
257\param[in] limitScale the visualization scale for the constraint limits
258\param[in] flags the visualization flags
259
260@see PxRenderBuffer
261*/
262typedef void (*PxConstraintVisualize)( PxConstraintVisualizer& visualizer,
263 const void* constantBlock,
264 const PxTransform& body0Transform,
265 const PxTransform& body1Transform,
266 PxU32 flags );
267
268
269struct PxPvdUpdateType
270{
271 enum Enum
272 {
273 CREATE_INSTANCE,
274 RELEASE_INSTANCE,
275 UPDATE_ALL_PROPERTIES,
276 UPDATE_SIM_PROPERTIES
277 };
278};
279
280/**
281
282\brief This class connects a custom constraint to the SDK
283
284This class connects a custom constraint to the SDK, and functions are called by the SDK
285to query the custom implementation for specific information to pass on to the application
286or inform the constraint when the application makes calls into the SDK which will update
287the custom constraint's internal implementation
288*/
289
290class PxConstraintConnector
291{
292public:
293 /**
294 when the constraint is marked dirty, this function is called at the start of the simulation
295 step for the SDK to copy the constraint data block.
296 */
297
298 virtual void* prepareData() = 0;
299
300 /**
301 this function is called by the SDK to update PVD's view of it
302 */
303
304 virtual bool updatePvdProperties(physx::debugger::comm::PvdDataStream& pvdConnection,
305 const PxConstraint* c,
306 PxPvdUpdateType::Enum updateType) const = 0;
307
308 /**
309 When the SDK deletes a PxConstraint object this function is called by the SDK. In general
310 custom constraints should not be deleted directly by applications: rather, the constraint
311 should respond to a release() request by calling PxConstraint::release(), then wait for
312 this call to release its own resources, so that even if the release() call occurs during
313 a simulation step, the deletion of the constraint is buffered until that step completes.
314
315 This function is also called when a PxConstraint object is deleted on cleanup due to
316 destruction of the PxPhysics object.
317
318 */
319
320 virtual void onConstraintRelease() = 0;
321
322 /**
323 This function is called by the SDK when the CoM of one of the actors is moved. Since the
324 API specifies constraint positions relative to actors, and the constraint shader functions
325 are supplied with coordinates relative to bodies, some synchronization is usually required
326 when the application moves an object's center of mass.
327 */
328
329 virtual void onComShift(PxU32 actor) = 0;
330
331 /**
332 This function is called by the SDK when the scene origin gets shifted and allows to adjust
333 custom data which contains world space transforms.
334
335 \note If the adjustments affect constraint shader data, it is necessary to call PxConstraint::markDirty()
336 to make sure that the data gets synced at the beginning of the next simulation step.
337
338 \param[in] shift Translation vector the origin is shifted by.
339
340 @see PxScene.shiftOrigin()
341 */
342
343 virtual void onOriginShift(const PxVec3& shift) = 0;
344
345 /**
346 \brief Fetches external data for a constraint.
347
348 This function is used by the SDK to acquire a reference to the owner of a constraint and a unique
349 owner type ID. This information will be passed on when a breakable constraint breaks or when
350 #PxConstraint::getExternalReference() is called.
351
352 \param[out] typeID Unique type identifier of the external object. The value 0xffffffff is reserved and should not be used. Furthermore, if the PhysX extensions library is used, some other IDs are reserved already (see PxConstraintExtIDs)
353 \return Reference to the external object which owns the constraint.
354
355 @see PxConstraintInfo PxSimulationEventCallback.onConstraintBreak()
356 */
357 virtual void* getExternalReference(PxU32& typeID) = 0;
358
359
360 /**
361 \brief Obtain a reference to a PxBase interface if the constraint has one.
362
363 If the constraint does not implement the PxBase interface, it should return NULL.
364 */
365
366 virtual PxBase* getSerializable() = 0;
367
368
369 /**
370 \brief virtual destructor
371 */
372 virtual ~PxConstraintConnector() {}
373};
374
375#ifndef PX_DOXYGEN
376} // namespace physx
377#endif
378
379/** @} */
380#endif
381