hkpConstraintAtom.h
上传用户:yisoukefu
上传日期:2020-08-09
资源大小:39506k
文件大小:48k
源码类别:

其他游戏

开发平台:

Visual C++

  1. /* 
  2.  * 
  3.  * Confidential Information of Telekinesys Research Limited (t/a Havok). Not for disclosure or distribution without Havok's
  4.  * prior written consent. This software contains code, techniques and know-how which is confidential and proprietary to Havok.
  5.  * Level 2 and Level 3 source code contains trade secrets of Havok. Havok Software (C) Copyright 1999-2009 Telekinesys Research Limited t/a Havok. All Rights Reserved. Use of this software is subject to the terms of an end user license agreement.
  6.  * 
  7.  */
  8. #ifndef HK_DYNAMICS2_CONSTRAINT_ATOM_H
  9. #define HK_DYNAMICS2_CONSTRAINT_ATOM_H
  10. #include <Common/Base/hkBase.h>
  11. #include <Physics/ConstraintSolver/Constraint/Contact/hkpSimpleContactConstraintInfo.h>
  12. #include <Common/Base/Types/Physics/ContactPoint/hkContactPoint.h>
  13. #include <Physics/Dynamics/Constraint/hkpConstraintData.h>
  14. HK_REFLECTION_CLASSFILE_DESTINATION("../../../Dynamics/Constraint/Atom");
  15. class hkContactPoint;
  16. class hkpConstraintMotor;
  17. class hkpContactPointPropertiesStream;
  18. #define HK_CONSTRAINT_FILL_PADDING_WITH_ZERO(fromAfter, to) { for (hkUint8* ptr = reinterpret_cast<hkUint8*>(fromAfter.next()); ptr < reinterpret_cast<hkUint8*>(&to); *(ptr++) = 0) { } }
  19.   /// Constraint atoms are building blocks that specify hkConstraintDatas.
  20.   ///
  21.   /// hkConstraintDatas either use hkpBridgeAtoms, which allow them to implement their custom logic, or use a set of generic hkConstraintAtoms
  22.   /// to describe the geometry of the constraint.
  23.   ///
  24.   /// Each hkpConstraintAtom is used to specify a constraint's orientation in space or to create one or more solver-constraints of a given type.
  25.   /// During simulation, hkConstraintAtoms are processed in the order in which they're organized in a hkpConstraintData.
  26.   ///
  27.   /// Generally the first constraint in a list is one that specifies the local bases of the constraint in each of the constrained bodies' spaces.
  28.   /// Those bases are persistent throughout processing of a list of atoms. The following atoms apply a kind of a constraint (linear, angular,
  29.   /// limit, motor, etc.) in relation to one or more of the axes of the specified local bases. See individual descriptions of atoms for more info.
  30.   ///
  31.   ///
  32. struct hkpConstraintAtom
  33. {
  34. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpConstraintAtom );
  35. HK_DECLARE_REFLECTION();
  36. public:
  37. enum AtomType
  38. {
  39. TYPE_INVALID = 0,
  40. TYPE_BRIDGE,
  41. TYPE_SET_LOCAL_TRANSFORMS,
  42. TYPE_SET_LOCAL_TRANSLATIONS,
  43. TYPE_SET_LOCAL_ROTATIONS,
  44. TYPE_BALL_SOCKET,
  45. TYPE_STIFF_SPRING,
  46. TYPE_LIN,
  47. TYPE_LIN_SOFT,
  48. TYPE_LIN_LIMIT,
  49. TYPE_LIN_FRICTION,
  50. TYPE_LIN_MOTOR,
  51. TYPE_2D_ANG,
  52. TYPE_ANG,
  53. TYPE_ANG_LIMIT,
  54. TYPE_TWIST_LIMIT,
  55. TYPE_CONE_LIMIT,
  56. TYPE_ANG_FRICTION,
  57. TYPE_ANG_MOTOR,
  58. TYPE_RAGDOLL_MOTOR,
  59. TYPE_PULLEY,
  60. TYPE_OVERWRITE_PIVOT,
  61. TYPE_CONTACT,
  62. //
  63. // modifiers, must be the end of the list
  64. //
  65. TYPE_MODIFIER_SOFT_CONTACT, // not supported by the spu
  66. TYPE_MODIFIER_MASS_CHANGER, // spu supported
  67. TYPE_MODIFIER_VISCOUS_SURFACE, // not supported by the spu
  68. TYPE_MODIFIER_MOVING_SURFACE, // spu supported
  69. TYPE_MODIFIER_IGNORE_CONSTRAINT,  // spu supported
  70. TYPE_MODIFIER_CENTER_OF_MASS_CHANGER, // not supported by the spu
  71. TYPE_MAX
  72. };
  73. // flag indicating whether this constraint needs some special callback treatment
  74. // those flags can be combined
  75. enum CallbackRequest
  76. {
  77. CALLBACK_REQUEST_NONE = 0,
  78. CALLBACK_REQUEST_NEW_CONTACT_POINT = 1,
  79. CALLBACK_REQUEST_SETUP_PPU_ONLY = 2,
  80. CALLBACK_REQUEST_SETUP_CALLBACK = 4
  81. };
  82. public:
  83. HK_FORCE_INLINE enum AtomType getType() const { return m_type; }
  84. HK_FORCE_INLINE int isModifierType() const { return m_type >= TYPE_MODIFIER_SOFT_CONTACT; }
  85. protected:
  86. hkpConstraintAtom(enum AtomType type) : m_type(type) {}
  87. public:
  88. hkpConstraintAtom(hkFinishLoadedObjectFlag f) {}
  89. private:
  90. // Illegal constructor
  91. hkpConstraintAtom();
  92. public:
  93. hkEnum<AtomType,hkUint16> m_type;
  94. };
  95. typedef void (HK_CALL *hkConstraintAtomBuildJacobianFunc) ( class hkpConstraintData* m_constraintData, const hkpConstraintQueryIn &in, hkpConstraintQueryOut &out );
  96. /// This atom is used to allow to call the old hkpConstraintData classes
  97. struct hkpBridgeConstraintAtom: public hkpConstraintAtom
  98. {
  99. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpBridgeConstraintAtom );
  100. HK_DECLARE_REFLECTION();
  101. hkpBridgeConstraintAtom(  ): hkpConstraintAtom( TYPE_BRIDGE ){ }
  102. hkpBridgeConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f)
  103. {
  104. if( f.m_finishing )
  105. {
  106. init(m_constraintData);
  107. }
  108. }
  109. // call this to do stuff not done in the constructor yet
  110. void init (class hkpConstraintData* m_constraintData);
  111. HK_FORCE_INLINE hkpConstraintAtom* next() { return (this+1); }
  112. // bridge atoms are always the last atom, so no need to increment solver result, just make sure the
  113. // program crashes if the result of this function is used
  114. HK_FORCE_INLINE int numSolverResults() const    { return 100000; }
  115. // addToConstraintInfo not needed
  116. hkConstraintAtomBuildJacobianFunc       m_buildJacobianFunc; //+nosave +overridetype(void*)
  117. class hkpConstraintData* m_constraintData;
  118. };
  119. struct hkpBridgeAtoms
  120. {
  121. HK_DECLARE_REFLECTION();
  122. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpBridgeAtoms );
  123. struct hkpBridgeConstraintAtom m_bridgeAtom;
  124. hkpBridgeAtoms(){}
  125. hkpBridgeAtoms(hkFinishLoadedObjectFlag f) : m_bridgeAtom(f) {}
  126. // get a pointer to the first atom
  127. const hkpConstraintAtom* getAtoms() const { return &m_bridgeAtom; }
  128. // get the size of all atoms (we can't use sizeof(*this) because of align16 padding)
  129. int getSizeOfAllAtoms() const               { return hkGetByteOffsetInt(this, &m_bridgeAtom+1); }
  130. };
  131. /// hkpSimpleContactConstraintAtom holds contact information for a single hkpSimpleContactConstraintData.
  132. ///
  133. /// It is for internal use only and is unique in the following ways:
  134. ///  - it is not a member of the owning hkpConstraintData, it is allocated externally
  135. ///  - its size is dynamic and varies depending on the number of contact points in the constraint
  136. ///  - it is a stand-alone constraint, therefore it derives from hkpConstraintAtom and cannot be followed by any other atom
  137. struct hkpSimpleContactConstraintAtom : public hkpConstraintAtom
  138. {
  139. HK_DECLARE_REFLECTION();
  140. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpSimpleContactConstraintAtom );
  141. public:
  142. // Size of hkpSimpleContactConstraintAtom is dynamically changed by the engine. It holds up to 256 contact points.
  143. // We initialize the size of the atom to what it is when no contact points are present.
  144. hkpSimpleContactConstraintAtom() : hkpConstraintAtom(TYPE_CONTACT) {}
  145. hkpSimpleContactConstraintAtom(hkFinishLoadedObjectFlag f);
  146. HK_FORCE_INLINE hkContactPoint* getContactPoints() const { return const_cast<hkContactPoint*>( reinterpret_cast<const hkContactPoint*>( this+1 ) ); }
  147. HK_FORCE_INLINE int getContactPointPropertiesStriding() const;
  148. HK_FORCE_INLINE hkpContactPointPropertiesStream* getContactPointPropertiesStream() const { return const_cast<hkpContactPointPropertiesStream*>( reinterpret_cast<const hkpContactPointPropertiesStream*>( hkAddByteOffsetConst( getContactPoints(), sizeof(hkContactPoint) * m_numReservedContactPoints ) ) ); }
  149. HK_FORCE_INLINE hkpContactPointPropertiesStream* getContactPointPropertiesStream(int i) const;
  150. public:
  151. HK_FORCE_INLINE hkpConstraintAtom* next() const { HK_ASSERT2(0x5b5a6955, false, "Not implemented. Need to compute the entire size of contact points & properties."); return HK_NULL; }
  152. HK_FORCE_INLINE int numSolverResults() const    { return m_numContactPoints+3; }
  153. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const
  154. {
  155. int size = m_numContactPoints;
  156. infoOut.m_sizeOfSchemas    += HK_SIZE_OF_JACOBIAN_HEADER_SCHEMA 
  157. + (size >> 1) * HK_SIZE_OF_JACOBIAN_PAIR_CONTACT_SCHEMA 
  158.                         + (size & 1) * HK_SIZE_OF_JACOBIAN_SINGLE_CONTACT_SCHEMA 
  159. + HK_SIZE_OF_JACOBIAN_2D_FRICTION_SCHEMA;
  160. infoOut.m_maxSizeOfSchema = infoOut.m_sizeOfSchemas + (HK_SIZE_OF_JACOBIAN_3D_FRICTION_SCHEMA - HK_SIZE_OF_JACOBIAN_2D_FRICTION_SCHEMA);
  161. infoOut.m_numSolverResults   += size + 2;
  162. infoOut.m_numSolverElemTemps += size + (2 + 1); // extra one for friction
  163. if ( size >= 2 )
  164. {
  165. infoOut.m_sizeOfSchemas   += HK_SIZE_OF_JACOBIAN_3D_FRICTION_SCHEMA - HK_SIZE_OF_JACOBIAN_2D_FRICTION_SCHEMA;
  166. infoOut.m_numSolverResults   += 1; // is that needed ?? solver results are stroed in the info struct
  167. infoOut.m_numSolverElemTemps += 1 + 0; // just one elem for both 2d & 3d friction anyways.
  168. }
  169. #if defined HK_ENABLE_ROLLING_FRICITON_CODE
  170. if (m_info.m_rollingFrictionMultiplier != 0.0f)
  171. {
  172. infoOut.m_sizeOfSchemas += HK_SIZE_OF_JACOBIAN_2D_ROLLING_FRICTION_SCHEMA;
  173. infoOut.m_maxSizeOfSchema += HK_SIZE_OF_JACOBIAN_2D_ROLLING_FRICTION_SCHEMA;
  174. infoOut.m_numSolverResults += 2; 
  175. infoOut.m_numSolverElemTemps += 2 * (1 + 1);
  176. }
  177. #endif
  178. }
  179. public:
  180. hkUint16 m_sizeOfAllAtoms;
  181. hkUint16 m_numContactPoints;
  182. hkUint16 m_numReservedContactPoints;
  183. // 8 bytes left from here
  184. // Extra storage for bodyA. Holds hkpShapeKey hierarchy, by default.
  185. hkUint8 m_numUserDatasForBodyA;
  186. // Extra storage for bodyA. Holds hkpShapeKey hierarchy, by default.
  187. hkUint8 m_numUserDatasForBodyB;
  188. // store striding in here to avoid recomputing in getContactPointPropsStriding()..
  189. hkUint8 m_contactPointPropertiesStriding;
  190. // Maximum number for contact points. The limitation is driven by buffer size on SPU, and by contactPointProperties size.
  191. hkUint16 m_maxNumContactPoints; // -- this will not be cross-platform, and will use problems with contact points saved on PC, and to be loaded on PS3 <ag.todo.b>
  192. HK_ALIGN16(class hkpSimpleContactConstraintDataInfo m_info);
  193. };
  194. // Only include it after the hkpSimpleContactConstraintAtom is defined
  195. #include <Physics/ConstraintSolver/Constraint/Contact/hkpContactPointProperties.h>
  196. HK_FORCE_INLINE int hkpSimpleContactConstraintAtom::getContactPointPropertiesStriding() const { return m_contactPointPropertiesStriding; }
  197. HK_FORCE_INLINE hkpContactPointPropertiesStream* hkpSimpleContactConstraintAtom::getContactPointPropertiesStream(int i) const 
  198. {
  199. const hkContactPoint* endContactPoint = hkAddByteOffsetConst( getContactPoints(), sizeof(hkContactPoint) * m_numReservedContactPoints);
  200. const hkpContactPointPropertiesStream* beginningOfProperties = reinterpret_cast<const hkpContactPointPropertiesStream*>( endContactPoint );
  201. return const_cast<hkpContactPointPropertiesStream*>( hkAddByteOffsetConst(  beginningOfProperties, HK_HINT_SIZE16(i) * HK_HINT_SIZE16( getContactPointPropertiesStriding())  ) );
  202. }
  203. # define HK_GET_LOCAL_CONTACT_ATOM(ATOM) ATOM
  204. # define HK_CONTACT_ATOM_SET_PPU(ATOM)
  205. /// Fully eliminates relative linear movement of bodies' pivots.
  206. ///
  207. /// This is the most common atom. It is advised to place it at the end of the list of atoms to minimize results error.
  208. /// This atom eliminates 3 degrees of freedom and returns 3 solver results. It has no parameters.
  209. struct hkpBallSocketConstraintAtom : public hkpConstraintAtom
  210. {
  211. //+version(1)
  212. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpBallSocketConstraintAtom );
  213. HK_DECLARE_REFLECTION();
  214. public:
  215. hkpBallSocketConstraintAtom() : hkpConstraintAtom(TYPE_BALL_SOCKET), m_bodiesToNotify(0), m_stabilizationFactor(1.0f), m_maxImpulse(HK_REAL_MAX) {}
  216. hkpBallSocketConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  217. /// Return the next atom after this.
  218. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  219. /// This tells how many solver-constraints this atom generates and how may solver-results slots it requires.
  220. HK_FORCE_INLINE int numSolverResults() const    { return 3; }
  221. /// This tells how much memory the system will need to store solver schemas and jacobians for this atom.
  222. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( 3 * HK_SIZE_OF_JACOBIAN_1D_BILATERAL_SCHEMA, 3, 3 ); }
  223. /// Marks the body to be notified when the m_maxImpulse is breached.
  224. hkUint8 m_bodiesToNotify; //+default(0)
  225. /// This sets the multiplier that's used to add bodies' velocities to the solver's jacobians RHS.
  226. /// This defaults to 1.0f and results in the constraints positional constraint being slightly violated for the advantage of 
  227. /// extra stabilization. At low (low frame rate, few solver iterations) this setting can cause uncontrollable jitter however.
  228. /// In such cases disable it setting the factor to lower values or zero.
  229. hkUFloat8 m_stabilizationFactor; //+default(1.0f)
  230. /// Maximum impulse applied by each of the three resulting 1d bilinear constraints.
  231. /// When any of the three limits is breached and the constraint has runtime allocated, a constraint-impulse-limit breached callback is triggered.
  232. hkReal m_maxImpulse; //+default(HK_REAL_MAX)
  233. };
  234. /// Enforces a constant distance between the pivot points of linked bodies.
  235. struct hkpStiffSpringConstraintAtom : public hkpConstraintAtom
  236. {
  237. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpStiffSpringConstraintAtom );
  238. HK_DECLARE_REFLECTION();
  239. public:
  240. hkpStiffSpringConstraintAtom() : hkpConstraintAtom(TYPE_STIFF_SPRING) {}
  241. hkpStiffSpringConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  242. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  243. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  244. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_BILATERAL_SCHEMA, 1, 1 ); }
  245. /// The rest length / distance between pivot points.
  246. hkReal m_length;
  247. };
  248. /// This specifies constraint spaces and pivot points in the local spaces of each body.
  249. ///
  250. /// Pivot points are stored in the translation part of the transforms.
  251. struct hkpSetLocalTransformsConstraintAtom : public hkpConstraintAtom
  252. {
  253. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpSetLocalTransformsConstraintAtom );
  254. HK_DECLARE_REFLECTION();
  255. hkpSetLocalTransformsConstraintAtom() : hkpConstraintAtom(TYPE_SET_LOCAL_TRANSFORMS) {}
  256. hkpSetLocalTransformsConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  257. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  258. HK_FORCE_INLINE int numSolverResults() const    { return 0; }
  259. // addToConstraintInfo not needed
  260. /// Constraint orientation and origin/pivot point in bodyA's local space.
  261. hkTransform m_transformA;
  262. /// Constraint orientation and origin/pivot point in bodyB's local space.
  263. hkTransform m_transformB;
  264. };
  265. /// This specifies pivot points in the local spaces of each body.
  266. ///
  267. /// Note that this does not overwrite the constraint space's orientation.
  268. /// This is used when constraint orientation is irrelevant, e.g. in hkpBallAndSocketConstraintData.
  269. struct hkpSetLocalTranslationsConstraintAtom : public hkpConstraintAtom
  270. {
  271. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpSetLocalTranslationsConstraintAtom );
  272. HK_DECLARE_REFLECTION();
  273. hkpSetLocalTranslationsConstraintAtom() : hkpConstraintAtom(TYPE_SET_LOCAL_TRANSLATIONS) {}
  274. hkpSetLocalTranslationsConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  275. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  276. HK_FORCE_INLINE int numSolverResults() const    { return 0; }
  277. // addToConstraintInfo not needed
  278. /// Pivot point in bodyA's local space.
  279. hkVector4 m_translationA;
  280. /// Pivot point in bodyB's local space.
  281. hkVector4 m_translationB;
  282. };
  283. /// This specifies constraint spaces in the local spaces of each body.
  284. ///
  285. /// Note that this does not overwrite the pivot points.
  286. /// This is used when the constraint space must be reoriented for some atoms in more complex hkConstraintDatas, e.g. in the hkpWheelConstraintData.
  287. struct hkpSetLocalRotationsConstraintAtom : public hkpConstraintAtom
  288. {
  289. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpSetLocalRotationsConstraintAtom );
  290. HK_DECLARE_REFLECTION();
  291. hkpSetLocalRotationsConstraintAtom() : hkpConstraintAtom(TYPE_SET_LOCAL_ROTATIONS) {}
  292. hkpSetLocalRotationsConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  293. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  294. HK_FORCE_INLINE int numSolverResults() const    { return 0; }
  295. // addToConstraintInfo not needed
  296. /// Constraint orientation in bodyA's local space.
  297. hkRotation m_rotationA;
  298. /// Constraint orientation in bodyB's local space.
  299. hkRotation m_rotationB;
  300. };
  301. struct hkpOverwritePivotConstraintAtom : public hkpConstraintAtom
  302. {
  303. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpOverwritePivotConstraintAtom );
  304. HK_DECLARE_REFLECTION();
  305. hkpOverwritePivotConstraintAtom() : hkpConstraintAtom(TYPE_OVERWRITE_PIVOT), m_copyToPivotBFromPivotA(true) { }
  306. hkpOverwritePivotConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  307. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  308. HK_FORCE_INLINE int numSolverResults() const    { return 0; }
  309. hkUint8 m_copyToPivotBFromPivotA;
  310. };
  311. /// Eliminates relative linear velocity of bodies' pivot points along one specified axis.
  312. ///
  313. /// This is used when relative linear movement is only partly constrained as it is in e.g. prismatic or point-to-plane constraints.
  314. struct hkpLinConstraintAtom : public hkpConstraintAtom
  315. {
  316. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpLinConstraintAtom );
  317. HK_DECLARE_REFLECTION();
  318. hkpLinConstraintAtom() : hkpConstraintAtom(TYPE_LIN) {}
  319. hkpLinConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  320. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  321. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  322. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_BILATERAL_SCHEMA, 1, 1 ); }
  323. /// Specifies the index of the axis of the bodyB's constraint base, that will be constrained.
  324. hkUint8 m_axisIndex;
  325. };
  326. /// Softens/controls relative linear velocity of bodies' pivot points along one specified axis.
  327. ///
  328. /// This results in a spring-like reaction, it's used in the hkpWheelConstraintData.
  329. struct hkpLinSoftConstraintAtom : public hkpConstraintAtom
  330. {
  331. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpLinSoftConstraintAtom );
  332. HK_DECLARE_REFLECTION();
  333. hkpLinSoftConstraintAtom() : hkpConstraintAtom(TYPE_LIN_SOFT) {}
  334. hkpLinSoftConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  335. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  336. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  337. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_BILATERAL_USER_TAU_SCHEMA, 1, 1 ); }
  338. /// Specifies the index of the axis of the bodyB's constraint base, that will be constrained.
  339. hkUint8 m_axisIndex;
  340. /// Specifies a custom value for the tau parameter used by the solver.
  341. hkReal m_tau;
  342. /// Specifies a custom value for the damping parameter used by the solver.
  343. hkReal m_damping;
  344. };
  345. /// Limits allowed relative distance between bodies' pivot points along one specified axis.
  346. ///
  347. /// This allows unconstrained movement within the specified range, and applies hard limits at its ends.
  348. struct hkpLinLimitConstraintAtom : public hkpConstraintAtom
  349. {
  350. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpLinLimitConstraintAtom );
  351. HK_DECLARE_REFLECTION();
  352. hkpLinLimitConstraintAtom() : hkpConstraintAtom(TYPE_LIN_LIMIT) {}
  353. hkpLinLimitConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  354. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  355. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  356. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_LINEAR_LIMIT_SCHEMA, 1, 1 ); }
  357. /// The index of the axis of the bodyB's constraint base, that will be limited.
  358. hkUint8 m_axisIndex;
  359. /// Minimum distance along the axis (may be negative).
  360. hkReal m_min;
  361. /// Maximum distance along the axis (may be negative).
  362. hkReal m_max;
  363. };
  364. /// Eliminates two degrees of freedom of angular movement and allows relative rotation along a specified axis only.
  365. ///
  366. /// Angular-constraint atoms are often combined with linear-constraint atoms, e.g. this atoms combined with the ball-and-socket
  367. /// atom forms a hkpHingeConstraintData.
  368. struct hkp2dAngConstraintAtom : public hkpConstraintAtom
  369. {
  370. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkp2dAngConstraintAtom );
  371. HK_DECLARE_REFLECTION();
  372. hkp2dAngConstraintAtom() : hkpConstraintAtom(TYPE_2D_ANG) {}
  373. hkp2dAngConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  374. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  375. HK_FORCE_INLINE int numSolverResults() const    { return 2; }
  376. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( 2 * HK_SIZE_OF_JACOBIAN_1D_BILATERAL_SCHEMA, 2, 2 ); }
  377. /// Specifies the index of the unconstrained axis of relative rotation in bodyB's constraint base.
  378. hkUint8 m_freeRotationAxis;
  379. };
  380. /// Eliminates one, two, or three degrees of freedom of angular movement.
  381. ///
  382. /// Note: this is only tested for eliminating three degrees of freedom.
  383. struct hkpAngConstraintAtom : public hkpConstraintAtom
  384. {
  385. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpAngConstraintAtom );
  386. HK_DECLARE_REFLECTION();
  387. hkpAngConstraintAtom() : hkpConstraintAtom(TYPE_ANG) {}
  388. hkpAngConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  389. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  390. HK_FORCE_INLINE int numSolverResults() const    { return m_numConstrainedAxes; }
  391. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( m_numConstrainedAxes * HK_SIZE_OF_JACOBIAN_1D_BILATERAL_SCHEMA, m_numConstrainedAxes, m_numConstrainedAxes ); }
  392. /// Index of the first axis to constrain, in bodyA's constraint base.
  393. hkUint8 m_firstConstrainedAxis;
  394. /// Number of subsequent base axes to constrain.
  395. hkUint8 m_numConstrainedAxes;
  396. };
  397. /// Limits allowed relative angle between bodies' rotations along one specified rotation axis.
  398. ///
  399. /// This allows unconstrained movement within the specified range, and applies hard limits at its ends.
  400. struct hkpAngLimitConstraintAtom : public hkpConstraintAtom
  401. {
  402. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpAngLimitConstraintAtom );
  403. HK_DECLARE_REFLECTION();
  404. hkpAngLimitConstraintAtom() : hkpConstraintAtom(TYPE_ANG_LIMIT), m_isEnabled(true) {}
  405. hkpAngLimitConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  406. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  407. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  408. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_ANGULAR_LIMITS_SCHEMA, 1, 1 ); }
  409. /// Tells whether the atom should be handled by the solver.
  410. ///
  411. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  412. hkUint8 m_isEnabled;
  413. /// The index of the axis in the bodyA's constraint base, that will be limited.
  414. hkUint8 m_limitAxis;
  415. /// Mininum angle value in radians (may be negative).
  416. hkReal m_minAngle;
  417. /// Maximum angle value in radians (may be negative).
  418. hkReal m_maxAngle;
  419. /// A stiffness factor [0..1] used by the solver; defaults to 1.0.
  420. hkReal m_angularLimitsTauFactor; //+default(1.0) +absmin(0) +absmax(1)
  421. };
  422. /// Limits allowed relative angle between bodies' rotations along one specified rotation axis.
  423. ///
  424. /// This constraint allows unconstrained movement within the specified range, and applies hard limits at its ends.
  425. struct hkpTwistLimitConstraintAtom : public hkpConstraintAtom
  426. {
  427. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpTwistLimitConstraintAtom );
  428. HK_DECLARE_REFLECTION();
  429. hkpTwistLimitConstraintAtom() : hkpConstraintAtom(TYPE_TWIST_LIMIT), m_isEnabled(true) {}
  430. hkpTwistLimitConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  431. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  432. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  433. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_ANGULAR_LIMITS_SCHEMA, 1, 1 ); }
  434. /// Tells whether the atom should be handled by the solver.
  435. ///
  436. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  437. hkUint8 m_isEnabled;
  438. /// The index of the axis in the bodyA's constraint base, that will be limited.
  439. hkUint8 m_twistAxis;
  440. /// The index of a perpendicular axis used as a reference to measure the angle.
  441. hkUint8 m_refAxis;
  442. /// Mininum angle value in radians (may be negative).
  443. hkReal m_minAngle;
  444. /// Maximum angle value in radians (may be negative).
  445. hkReal m_maxAngle;
  446. /// A stiffness factor [0..1] used by the solver; defaults to 1.0.
  447. hkReal m_angularLimitsTauFactor; //+default(1.0) +absmin(0) +absmax(1)
  448. };
  449. /// Limits allowed relative angle between bodies' rotations as measured between two chosen axes.
  450. ///
  451. /// This allows unconstrained movement within the specified range, and applies hard limits at its ends.
  452. struct hkpConeLimitConstraintAtom : public hkpConstraintAtom
  453. {
  454. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpConeLimitConstraintAtom );
  455. HK_DECLARE_REFLECTION();
  456. hkpConeLimitConstraintAtom() : hkpConstraintAtom(TYPE_CONE_LIMIT), m_isEnabled(true), m_memOffsetToAngleOffset(0) {}
  457. hkpConeLimitConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  458. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  459. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  460. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_ANGULAR_LIMITS_SCHEMA, 1, 1 ); }
  461. /// Tells whether the atom should be handled by the solver.
  462. ///
  463. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  464. hkUint8 m_isEnabled;
  465. /// The index of the axis in the bodyA's constraint base, that will be used as a reference vector and constrained to lie within the limit cone.
  466. hkUint8 m_twistAxisInA;
  467. /// The index of the axis in the bodyB's constraint base, that will be used as a reference and limit-cone axis.
  468. hkUint8 m_refAxisInB;
  469. /// Specifies how the angle between the two reference vectors is measured.
  470. enum MeasurementMode
  471. {
  472. // Do not change enumeration values! They're used in calculations.
  473. /// Zero-angle corresponds to situation where the two vectors are aligned.
  474. ZERO_WHEN_VECTORS_ALIGNED = 0,
  475. /// Zero-angle corresponds to situation where the two vectors are perpendicular, and (+)90-degree corresponds to vectors being aligned.
  476. ZERO_WHEN_VECTORS_PERPENDICULAR = 1
  477. };
  478. /// Specifies how the angle between the two reference vectors is measured.
  479. hkEnum<MeasurementMode, hkUint8> m_angleMeasurementMode;
  480. /// Memory offset to location in runtime where m_coneAngleOffset is stored.
  481. /// That is used to stablize the constraint.
  482. /// Zero offset means, that no extra stabilization is done.
  483. hkUint8 m_memOffsetToAngleOffset; //+default(1)
  484. /// Mininum angle value in radians (may be negative).
  485. hkReal m_minAngle;
  486. /// Maximum angle value in radians (may be negative).
  487. hkReal m_maxAngle;
  488. /// A stiffness factor [0..1] used by the solver; defaults to 1.0.
  489. hkReal m_angularLimitsTauFactor; //+default(1.0) +absmin(0) +absmax(1)
  490. };
  491. /// Applies friction torque along one, two, or three specified rotation axes.
  492. struct hkpAngFrictionConstraintAtom : public hkpConstraintAtom
  493. {
  494. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpAngFrictionConstraintAtom );
  495. HK_DECLARE_REFLECTION();
  496. hkpAngFrictionConstraintAtom() : hkpConstraintAtom(TYPE_ANG_FRICTION), m_isEnabled(true), m_numFrictionAxes(1) {}
  497. hkpAngFrictionConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  498. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  499. HK_FORCE_INLINE int numSolverResults() const    { return m_numFrictionAxes; }
  500. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( m_numFrictionAxes * HK_SIZE_OF_JACOBIAN_1D_ANGULAR_FRICTION_SCHEMA, m_numFrictionAxes, (1+1) * m_numFrictionAxes ); }
  501. /// Tells whether the atom should be handled by the solver.
  502. ///
  503. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  504. hkUint8 m_isEnabled;
  505. /// Index of the first axis to apply friction along, in bodyA's constraint base.
  506. hkUint8 m_firstFrictionAxis;
  507. /// Number of subsequent base axes to constrain.
  508. hkUint8 m_numFrictionAxes;
  509. /// Maximum allowed torque to be applied due to friction.
  510. hkReal m_maxFrictionTorque;
  511. };
  512. /// Controls relative rotation angle between bodies around a specified rotation axes.
  513. ///
  514. /// Note that motor atoms require access to external variables stored in hkpConstraintInstance's runtime.
  515. /// The atom accesses those variables using memory offsets (stored in the atom's members).
  516. /// Also when the motor is to operate in a range exceeding the [-Pi, Pi] range it must have a reference
  517. /// onto solver results of a corresponding hkpAngLimitConstraintAtom to retrieve the proper angle value.
  518. struct hkpAngMotorConstraintAtom : public hkpConstraintAtom
  519. {
  520. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpAngMotorConstraintAtom );
  521. HK_DECLARE_REFLECTION();
  522. hkpAngMotorConstraintAtom() : hkpConstraintAtom(TYPE_ANG_MOTOR) { m_isEnabled = true; m_initializedOffset = 0; m_previousTargetAngleOffset = 0; }
  523. hkpAngMotorConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  524. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  525. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  526. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_ANGULAR_MOTOR_SCHEMA, 1, (1+2) ); }
  527. /// Tells whether the atom should be handled by the solver.
  528. ///
  529. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  530. hkBool m_isEnabled;
  531. /// The index of the axis in the bodyA's constraint base, that will be controlled.
  532. hkUint8 m_motorAxis;
  533. /// Memory offset from atom's solver results to runtime's m_initialized member.
  534. hkInt16 m_initializedOffset;
  535. /// Memory offset from atom's solver results to runtime's m_previousTargetAngle member
  536. hkInt16 m_previousTargetAngleOffset;
  537. /// This is an optional offset to solver results of an angular limit atom.
  538. /// The results store the actual angle from the last frame, and are needed if the motor
  539. /// is to allow 'screw' functionality (ie. orientation is not represented by a cyclic
  540. /// [-180deg, 180deg] range, but as an unlimited number of degrees/rotations).
  541. hkInt16 m_correspondingAngLimitSolverResultOffset;
  542. /// The target angle for the motor.
  543. hkReal m_targetAngle;
  544. /// Motor; note that it is reference counted and should be handled by the owning constraint's get/set methods.
  545. HK_CPU_PTR(class hkpConstraintMotor*) m_motor;
  546. };
  547. /// Controls relative rotation angle between bodies in three dimensiond; used by the hkpRagdollConstraintData.
  548. ///
  549. /// Note that motor atoms require access to external variables stored in hkpConstraintInstance's runtime.
  550. /// The atom accesses those variables using memory offsets (stored in the atom's members).
  551. struct hkpRagdollMotorConstraintAtom : public hkpConstraintAtom
  552. {
  553. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpRagdollMotorConstraintAtom );
  554. HK_DECLARE_REFLECTION();
  555. hkpRagdollMotorConstraintAtom() : hkpConstraintAtom(TYPE_RAGDOLL_MOTOR) { m_isEnabled = true; m_initializedOffset = 0; m_previousTargetAnglesOffset = 0; }
  556. hkpRagdollMotorConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  557. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  558. HK_FORCE_INLINE int numSolverResults() const    { return 3; }
  559. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( 3 * HK_SIZE_OF_JACOBIAN_1D_ANGULAR_MOTOR_SCHEMA, 3, (1+2) * 3 ); }
  560. /// Tells whether the atom should be handled by the solver.
  561. ///
  562. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  563. hkBool m_isEnabled;
  564. /// Memory offset from atom's solver results to runtime's m_initialized member.
  565. hkInt16 m_initializedOffset;
  566. /// Memory offset from atom's solver results to runtime's m_previousTargetAngle member.
  567. hkInt16 m_previousTargetAnglesOffset;
  568. /// The target relative rotation the motors will try to match.
  569. /// This is the target rotation from bodyA's constraint space into the bodyB's (non-constraint) space. 
  570. hkMatrix3 m_target_bRca;
  571. /// Three motors; note that they are reference counted and should be handled by the owning constraint's get/set methods.
  572. HK_CPU_PTR(class hkpConstraintMotor*) m_motors[3];
  573. };
  574. /// Applies friction force along a specified axes.
  575. struct hkpLinFrictionConstraintAtom : public hkpConstraintAtom
  576. {
  577. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpLinFrictionConstraintAtom );
  578. HK_DECLARE_REFLECTION();
  579. hkpLinFrictionConstraintAtom() : hkpConstraintAtom(TYPE_LIN_FRICTION), m_isEnabled(true) {}
  580. hkpLinFrictionConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  581. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  582. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  583. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_FRICTION_SCHEMA, 1, (1+1) ); }
  584. /// Tells whether the atom should be handled by the solver.
  585. ///
  586. /// Note that if it is not, the atom's corresponding hkpSolverResults are not updated.
  587. hkUint8 m_isEnabled;
  588. /// Index of the axis to apply friction along, in bodyB's constraint base.
  589. hkUint8 m_frictionAxis;
  590. /// Maximum allowed force to be applied due to friction.
  591. hkReal m_maxFrictionForce;
  592. };
  593. /// Controls relative velocity of bodies along a specified axis.
  594. ///
  595. /// Note that motor atoms require access to external variables stored in hkpConstraintInstance's runtime.
  596. /// The atom accesses those variables using memory offsets (stored in the atom's members).
  597. struct hkpLinMotorConstraintAtom : public hkpConstraintAtom
  598. {
  599. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpLinMotorConstraintAtom );
  600. HK_DECLARE_REFLECTION();
  601. hkpLinMotorConstraintAtom() : hkpConstraintAtom(TYPE_LIN_MOTOR) { m_isEnabled = true; m_initializedOffset = 0; m_previousTargetPositionOffset = 0; }
  602. hkpLinMotorConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  603. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  604. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  605. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_LINEAR_MOTOR_SCHEMA, 1, (1+2) ); }
  606. /// A flag saying whether the motor is active
  607. hkBool  m_isEnabled;
  608. /// The index of the axis in the bodyB's constraint base, that will be controlled.
  609. hkUint8 m_motorAxis;
  610. /// Memory offset from atom's solver results to runtime's m_initialized member.
  611. hkInt16 m_initializedOffset;
  612. /// Memory offset from atom's solver results to runtime's m_previousTargetPosition member.
  613. hkInt16 m_previousTargetPositionOffset;
  614. /// The target position for the motor.
  615. hkReal m_targetPosition;
  616. /// Motor; note that it is reference counted and should be handled by the owning constraint's get/set methods.
  617. HK_CPU_PTR(class hkpConstraintMotor*) m_motor;
  618. };
  619. /// This implements a functionality of a pulley, where bodies are attached to a rope, and the rope is lead through two pulley wheels at fixed world positions.
  620. struct hkpPulleyConstraintAtom : public hkpConstraintAtom
  621. {
  622. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR( HK_MEMORY_CLASS_CONSTRAINT, hkpPulleyConstraintAtom );
  623. HK_DECLARE_REFLECTION();
  624. hkpPulleyConstraintAtom() : hkpConstraintAtom(TYPE_PULLEY) { }
  625. hkpPulleyConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  626. HK_FORCE_INLINE hkpConstraintAtom* next() const { return const_cast<hkpConstraintAtom*>( static_cast<const hkpConstraintAtom*>(this+1) ); }
  627. HK_FORCE_INLINE int numSolverResults() const    { return 1; }
  628. HK_FORCE_INLINE void addToConstraintInfo(hkpConstraintInfo& infoOut) const { infoOut.add( HK_SIZE_OF_JACOBIAN_1D_PULLEY_SCHEMA, 1, 1 ); }
  629. /// Pulley's first fixed pivot point.
  630. hkVector4 m_fixedPivotAinWorld;
  631. /// Pulley's second fixed pivot point.
  632. hkVector4 m_fixedPivotBinWorld;
  633. /// The rest length (equal to ((BodyA's rope) + leverageOnBodyB * (BodyB's rope length)) )
  634. hkReal m_ropeLength;
  635. /// Leverage ratio: e.g. value of 2 means that bodyA's rope length changes by twice as much as bodyB's,
  636. /// and the constraint exerts twice as big forces upon bodyB.
  637. hkReal m_leverageOnBodyB;
  638. };
  639. //
  640. // Atom Modifiers
  641. //
  642. struct hkpModifierConstraintAtom : public hkpConstraintAtom
  643. {
  644. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpModifierConstraintAtom );
  645. HK_DECLARE_REFLECTION();
  646. public:
  647. // adds the constraintInfo of one modifier to cinfo and returns the hkpConstraintAtom::CallbackRequest
  648. int addModifierDataToConstraintInfo( hkpConstraintInfo& cinfo ) const;
  649. // adds its constraintInfo of all linked modifiers to cinfo and returns the hkpConstraintAtom::CallbackRequest
  650. static int HK_CALL addAllModifierDataToConstraintInfo( hkpModifierConstraintAtom* firstModifier, hkpConstraintInfo& cinfo );
  651. protected:
  652. hkpModifierConstraintAtom(enum AtomType type, int size) : hkpConstraintAtom(type), m_modifierAtomSize( hkUint16(size)) {}
  653. public:
  654. hkpModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpConstraintAtom(f) {}
  655. public:
  656. HK_ALIGN16( hkUint16   m_modifierAtomSize );
  657. hkUint16                      m_childSize;
  658. HK_CPU_PTR(hkpConstraintAtom*) m_child;
  659. hkUint32 m_pad[2];
  660. };
  661. // ************************ Soft Contact **************************
  662. // ************************ Soft Contact **************************
  663. // ************************ Soft Contact **************************
  664. struct hkpSoftContactModifierConstraintAtom : public hkpModifierConstraintAtom
  665. {
  666. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpSoftContactModifierConstraintAtom );
  667. HK_DECLARE_REFLECTION();
  668. public:
  669. hkpSoftContactModifierConstraintAtom() : hkpModifierConstraintAtom(TYPE_MODIFIER_SOFT_CONTACT, sizeof(hkpSoftContactModifierConstraintAtom)),  m_tau(0.1f), m_maxAcceleration( 20.0f) { }
  670. hkpSoftContactModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpModifierConstraintAtom(f) {}
  671. void collisionResponseBeginCallback( const hkContactPoint& cp, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  672. void collisionResponseEndCallback(   const hkContactPoint& cp, hkReal impulseApplied, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  673. HK_FORCE_INLINE int numSolverResults() const { return 0; }
  674. int getConstraintInfo( hkpConstraintInfo& info ) const { return hkpConstraintAtom::CALLBACK_REQUEST_SETUP_PPU_ONLY; }
  675. public:
  676. hkReal m_tau;
  677. /// The maximum acceleration, the solver will apply
  678. hkReal m_maxAcceleration;
  679. };
  680. // ************************ Mass Changer **************************
  681. // ************************ Mass Changer **************************
  682. // ************************ Mass Changer **************************
  683. struct hkpMassChangerModifierConstraintAtom : public hkpModifierConstraintAtom
  684. {
  685. //+version(1)
  686. HK_DECLARE_REFLECTION();
  687. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpMassChangerModifierConstraintAtom );
  688. public:
  689. hkpMassChangerModifierConstraintAtom() : hkpModifierConstraintAtom(TYPE_MODIFIER_MASS_CHANGER, sizeof(hkpMassChangerModifierConstraintAtom)) {}
  690. hkpMassChangerModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpModifierConstraintAtom(f) {}
  691. HK_FORCE_INLINE int numSolverResults() const { return 0; }
  692. void collisionResponseBeginCallback( const hkContactPoint& cp, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  693. void collisionResponseEndCallback(   const hkContactPoint& cp, hkReal impulseApplied, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  694. int getConstraintInfo( hkpConstraintInfo& info ) const
  695. {
  696. info.m_sizeOfSchemas   += 2 * HK_SIZE_OF_JACOBIAN_SET_MASS_SCHEMA  + HK_SIZE_OF_JACOBIAN_HEADER_SCHEMA;
  697. return hkpConstraintAtom::CALLBACK_REQUEST_SETUP_PPU_ONLY;
  698. }
  699. public:
  700. hkVector4 m_factorA;
  701. hkVector4 m_factorB;
  702. };
  703. // ************************ Center of Mass Modifier **************************
  704. // ************************ Center of Mass Modifier **************************
  705. // ************************ Center of Mass Modifier **************************
  706. struct hkpCenterOfMassChangerModifierConstraintAtom : public hkpModifierConstraintAtom
  707. {
  708. HK_DECLARE_REFLECTION();
  709. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpMassChangerModifierConstraintAtom );
  710. public:
  711. hkpCenterOfMassChangerModifierConstraintAtom() : hkpModifierConstraintAtom(TYPE_MODIFIER_CENTER_OF_MASS_CHANGER, sizeof(hkpCenterOfMassChangerModifierConstraintAtom)) {}
  712. hkpCenterOfMassChangerModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpModifierConstraintAtom(f) {}
  713. HK_FORCE_INLINE int numSolverResults() const { return 0; }
  714. void collisionResponseBeginCallback( const hkContactPoint& cp, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  715. void collisionResponseEndCallback(   const hkContactPoint& cp, hkReal impulseApplied, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  716. int getConstraintInfo( hkpConstraintInfo& info ) const
  717. {
  718. info.m_sizeOfSchemas   += 2 * HK_SIZE_OF_JACOBIAN_ADD_ANGULAR_VELOCITY_SCHEMA  + HK_SIZE_OF_JACOBIAN_HEADER_SCHEMA;
  719. return hkpConstraintAtom::CALLBACK_REQUEST_NONE;
  720. }
  721. public:
  722. // Two displacements in local space of each of the bodies
  723. hkVector4 m_displacementA;
  724. hkVector4 m_displacementB;
  725. };
  726. // ************************ Viscous Surface **************************
  727. // ************************ Viscous Surface **************************
  728. // ************************ Viscous Surface **************************
  729. struct hkpViscousSurfaceModifierConstraintAtom : public hkpModifierConstraintAtom
  730. {
  731. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpViscousSurfaceModifierConstraintAtom );
  732. HK_DECLARE_REFLECTION();
  733. public:
  734. hkpViscousSurfaceModifierConstraintAtom() : hkpModifierConstraintAtom(TYPE_MODIFIER_VISCOUS_SURFACE, sizeof(hkpViscousSurfaceModifierConstraintAtom)) { }
  735. hkpViscousSurfaceModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpModifierConstraintAtom(f) {}
  736. int getConstraintInfo( hkpConstraintInfo& info ) const { return hkpConstraintAtom::CALLBACK_REQUEST_SETUP_PPU_ONLY; }
  737. HK_FORCE_INLINE int numSolverResults() const { return 0; }
  738. };
  739. // ************************ Moving Surface **************************
  740. // ************************ Moving Surface **************************
  741. // ************************ Moving Surface **************************
  742. struct hkpMovingSurfaceModifierConstraintAtom : public hkpModifierConstraintAtom
  743. {
  744. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpMovingSurfaceModifierConstraintAtom );
  745. HK_DECLARE_REFLECTION();
  746. public:
  747. hkpMovingSurfaceModifierConstraintAtom() : hkpModifierConstraintAtom(TYPE_MODIFIER_MOVING_SURFACE, sizeof(hkpMovingSurfaceModifierConstraintAtom)) { }
  748. hkpMovingSurfaceModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpModifierConstraintAtom(f) {}
  749. HK_FORCE_INLINE int numSolverResults() const { return 0; }
  750. int getConstraintInfo( hkpConstraintInfo& info ) const
  751. {
  752. info.m_sizeOfSchemas   += 2 * HK_SIZE_OF_JACOBIAN_ADD_VELOCITY_SCHEMA + HK_SIZE_OF_JACOBIAN_HEADER_SCHEMA;
  753. return hkpConstraintAtom::CALLBACK_REQUEST_NONE;
  754. }
  755. void collisionResponseBeginCallback( const hkContactPoint& cp, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  756. void collisionResponseEndCallback(   const hkContactPoint& cp, hkReal impulseApplied, struct hkpSimpleConstraintInfoInitInput& inA, struct hkpBodyVelocity& velA, hkpSimpleConstraintInfoInitInput& inB, hkpBodyVelocity& velB);
  757. hkVector4& getVelocity() { return m_velocity; }
  758. const hkVector4& getVelocity() const { return m_velocity; }
  759. public:
  760.   hkVector4 m_velocity;
  761. };
  762. // ************************ Ignore Constraint **************************
  763. // ************************ Ignore Constraint **************************
  764. // ************************ Ignore Constraint **************************
  765. struct hkpIgnoreModifierConstraintAtom : public hkpModifierConstraintAtom
  766. {
  767. HK_DECLARE_NONVIRTUAL_CLASS_ALLOCATOR(HK_MEMORY_CLASS_CONSTRAINT, hkpIgnoreModifierConstraintAtom );
  768. HK_DECLARE_REFLECTION();
  769. public:
  770. hkpIgnoreModifierConstraintAtom() : hkpModifierConstraintAtom(TYPE_MODIFIER_IGNORE_CONSTRAINT, sizeof(hkpIgnoreModifierConstraintAtom)) { }
  771. hkpIgnoreModifierConstraintAtom(hkFinishLoadedObjectFlag f) : hkpModifierConstraintAtom(f) {}
  772. HK_FORCE_INLINE int numSolverResults() const { return 0; }
  773. int getConstraintInfo( hkpConstraintInfo& info ) const;
  774. };
  775. #endif // HK_DYNAMICS2_CONSTRAINT_ATOM_H
  776. /*
  777. * Havok SDK - NO SOURCE PC DOWNLOAD, BUILD(#20090216)
  778. * Confidential Information of Havok.  (C) Copyright 1999-2009
  779. * Telekinesys Research Limited t/a Havok. All Rights Reserved. The Havok
  780. * Logo, and the Havok buzzsaw logo are trademarks of Havok.  Title, ownership
  781. * rights, and intellectual property rights in the Havok software remain in
  782. * Havok and/or its suppliers.
  783. * Use of this software for evaluation purposes is subject to and indicates
  784. * acceptance of the End User licence Agreement for this product. A copy of
  785. * the license is included with this software and is also available at www.havok.com/tryhavok.
  786. */