Blender V2.61 - r43446
|
00001 /* 00002 Bullet Continuous Collision Detection and Physics Library 00003 Copyright (c) 2003-2010 Erwin Coumans http://continuousphysics.com/Bullet/ 00004 00005 This software is provided 'as-is', without any express or implied warranty. 00006 In no event will the authors be held liable for any damages arising from the use of this software. 00007 Permission is granted to anyone to use this software for any purpose, 00008 including commercial applications, and to alter it and redistribute it freely, 00009 subject to the following restrictions: 00010 00011 1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required. 00012 2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software. 00013 3. This notice may not be removed or altered from any source distribution. 00014 */ 00015 00016 #ifndef TYPED_CONSTRAINT_H 00017 #define TYPED_CONSTRAINT_H 00018 00019 class btRigidBody; 00020 #include "LinearMath/btScalar.h" 00021 #include "btSolverConstraint.h" 00022 00023 class btSerializer; 00024 00025 //Don't change any of the existing enum values, so add enum types at the end for serialization compatibility 00026 enum btTypedConstraintType 00027 { 00028 POINT2POINT_CONSTRAINT_TYPE=3, 00029 HINGE_CONSTRAINT_TYPE, 00030 CONETWIST_CONSTRAINT_TYPE, 00031 D6_CONSTRAINT_TYPE, 00032 SLIDER_CONSTRAINT_TYPE, 00033 CONTACT_CONSTRAINT_TYPE, 00034 D6_SPRING_CONSTRAINT_TYPE, 00035 MAX_CONSTRAINT_TYPE 00036 }; 00037 00038 00039 enum btConstraintParams 00040 { 00041 BT_CONSTRAINT_ERP=1, 00042 BT_CONSTRAINT_STOP_ERP, 00043 BT_CONSTRAINT_CFM, 00044 BT_CONSTRAINT_STOP_CFM 00045 }; 00046 00047 #if 1 00048 #define btAssertConstrParams(_par) btAssert(_par) 00049 #else 00050 #define btAssertConstrParams(_par) 00051 #endif 00052 00053 00055 class btTypedConstraint : public btTypedObject 00056 { 00057 int m_userConstraintType; 00058 00059 union 00060 { 00061 int m_userConstraintId; 00062 void* m_userConstraintPtr; 00063 }; 00064 00065 bool m_needsFeedback; 00066 00067 btTypedConstraint& operator=(btTypedConstraint& other) 00068 { 00069 btAssert(0); 00070 (void) other; 00071 return *this; 00072 } 00073 00074 protected: 00075 btRigidBody& m_rbA; 00076 btRigidBody& m_rbB; 00077 btScalar m_appliedImpulse; 00078 btScalar m_dbgDrawSize; 00079 00081 btScalar getMotorFactor(btScalar pos, btScalar lowLim, btScalar uppLim, btScalar vel, btScalar timeFact); 00082 00083 static btRigidBody& getFixedBody(); 00084 00085 public: 00086 00087 virtual ~btTypedConstraint() {}; 00088 btTypedConstraint(btTypedConstraintType type, btRigidBody& rbA); 00089 btTypedConstraint(btTypedConstraintType type, btRigidBody& rbA,btRigidBody& rbB); 00090 00091 struct btConstraintInfo1 { 00092 int m_numConstraintRows,nub; 00093 }; 00094 00095 struct btConstraintInfo2 { 00096 // integrator parameters: frames per second (1/stepsize), default error 00097 // reduction parameter (0..1). 00098 btScalar fps,erp; 00099 00100 // for the first and second body, pointers to two (linear and angular) 00101 // n*3 jacobian sub matrices, stored by rows. these matrices will have 00102 // been initialized to 0 on entry. if the second body is zero then the 00103 // J2xx pointers may be 0. 00104 btScalar *m_J1linearAxis,*m_J1angularAxis,*m_J2linearAxis,*m_J2angularAxis; 00105 00106 // elements to jump from one row to the next in J's 00107 int rowskip; 00108 00109 // right hand sides of the equation J*v = c + cfm * lambda. cfm is the 00110 // "constraint force mixing" vector. c is set to zero on entry, cfm is 00111 // set to a constant value (typically very small or zero) value on entry. 00112 btScalar *m_constraintError,*cfm; 00113 00114 // lo and hi limits for variables (set to -/+ infinity on entry). 00115 btScalar *m_lowerLimit,*m_upperLimit; 00116 00117 // findex vector for variables. see the LCP solver interface for a 00118 // description of what this does. this is set to -1 on entry. 00119 // note that the returned indexes are relative to the first index of 00120 // the constraint. 00121 int *findex; 00122 // number of solver iterations 00123 int m_numIterations; 00124 00125 //damping of the velocity 00126 btScalar m_damping; 00127 }; 00128 00130 virtual void buildJacobian() {}; 00131 00133 virtual void setupSolverConstraint(btConstraintArray& ca, int solverBodyA,int solverBodyB, btScalar timeStep) 00134 { 00135 (void)ca; 00136 (void)solverBodyA; 00137 (void)solverBodyB; 00138 (void)timeStep; 00139 } 00140 00142 virtual void getInfo1 (btConstraintInfo1* info)=0; 00143 00145 virtual void getInfo2 (btConstraintInfo2* info)=0; 00146 00148 void internalSetAppliedImpulse(btScalar appliedImpulse) 00149 { 00150 m_appliedImpulse = appliedImpulse; 00151 } 00153 btScalar internalGetAppliedImpulse() 00154 { 00155 return m_appliedImpulse; 00156 } 00157 00159 virtual void solveConstraintObsolete(btRigidBody& /*bodyA*/,btRigidBody& /*bodyB*/,btScalar /*timeStep*/) {}; 00160 00161 00162 const btRigidBody& getRigidBodyA() const 00163 { 00164 return m_rbA; 00165 } 00166 const btRigidBody& getRigidBodyB() const 00167 { 00168 return m_rbB; 00169 } 00170 00171 btRigidBody& getRigidBodyA() 00172 { 00173 return m_rbA; 00174 } 00175 btRigidBody& getRigidBodyB() 00176 { 00177 return m_rbB; 00178 } 00179 00180 int getUserConstraintType() const 00181 { 00182 return m_userConstraintType ; 00183 } 00184 00185 void setUserConstraintType(int userConstraintType) 00186 { 00187 m_userConstraintType = userConstraintType; 00188 }; 00189 00190 void setUserConstraintId(int uid) 00191 { 00192 m_userConstraintId = uid; 00193 } 00194 00195 int getUserConstraintId() const 00196 { 00197 return m_userConstraintId; 00198 } 00199 00200 void setUserConstraintPtr(void* ptr) 00201 { 00202 m_userConstraintPtr = ptr; 00203 } 00204 00205 void* getUserConstraintPtr() 00206 { 00207 return m_userConstraintPtr; 00208 } 00209 00210 int getUid() const 00211 { 00212 return m_userConstraintId; 00213 } 00214 00215 bool needsFeedback() const 00216 { 00217 return m_needsFeedback; 00218 } 00219 00222 void enableFeedback(bool needsFeedback) 00223 { 00224 m_needsFeedback = needsFeedback; 00225 } 00226 00229 btScalar getAppliedImpulse() const 00230 { 00231 btAssert(m_needsFeedback); 00232 return m_appliedImpulse; 00233 } 00234 00235 btTypedConstraintType getConstraintType () const 00236 { 00237 return btTypedConstraintType(m_objectType); 00238 } 00239 00240 void setDbgDrawSize(btScalar dbgDrawSize) 00241 { 00242 m_dbgDrawSize = dbgDrawSize; 00243 } 00244 btScalar getDbgDrawSize() 00245 { 00246 return m_dbgDrawSize; 00247 } 00248 00251 virtual void setParam(int num, btScalar value, int axis = -1) = 0; 00252 00254 virtual btScalar getParam(int num, int axis = -1) const = 0; 00255 00256 virtual int calculateSerializeBufferSize() const; 00257 00259 virtual const char* serialize(void* dataBuffer, btSerializer* serializer) const; 00260 00261 }; 00262 00263 // returns angle in range [-SIMD_2_PI, SIMD_2_PI], closest to one of the limits 00264 // all arguments should be normalized angles (i.e. in range [-SIMD_PI, SIMD_PI]) 00265 SIMD_FORCE_INLINE btScalar btAdjustAngleToLimits(btScalar angleInRadians, btScalar angleLowerLimitInRadians, btScalar angleUpperLimitInRadians) 00266 { 00267 if(angleLowerLimitInRadians >= angleUpperLimitInRadians) 00268 { 00269 return angleInRadians; 00270 } 00271 else if(angleInRadians < angleLowerLimitInRadians) 00272 { 00273 btScalar diffLo = btFabs(btNormalizeAngle(angleLowerLimitInRadians - angleInRadians)); 00274 btScalar diffHi = btFabs(btNormalizeAngle(angleUpperLimitInRadians - angleInRadians)); 00275 return (diffLo < diffHi) ? angleInRadians : (angleInRadians + SIMD_2_PI); 00276 } 00277 else if(angleInRadians > angleUpperLimitInRadians) 00278 { 00279 btScalar diffHi = btFabs(btNormalizeAngle(angleInRadians - angleUpperLimitInRadians)); 00280 btScalar diffLo = btFabs(btNormalizeAngle(angleInRadians - angleLowerLimitInRadians)); 00281 return (diffLo < diffHi) ? (angleInRadians - SIMD_2_PI) : angleInRadians; 00282 } 00283 else 00284 { 00285 return angleInRadians; 00286 } 00287 } 00288 00290 struct btTypedConstraintData 00291 { 00292 btRigidBodyData *m_rbA; 00293 btRigidBodyData *m_rbB; 00294 char *m_name; 00295 00296 int m_objectType; 00297 int m_userConstraintType; 00298 int m_userConstraintId; 00299 int m_needsFeedback; 00300 00301 float m_appliedImpulse; 00302 float m_dbgDrawSize; 00303 00304 int m_disableCollisionsBetweenLinkedBodies; 00305 char m_pad4[4]; 00306 00307 }; 00308 00309 SIMD_FORCE_INLINE int btTypedConstraint::calculateSerializeBufferSize() const 00310 { 00311 return sizeof(btTypedConstraintData); 00312 } 00313 00314 00315 00316 class btAngularLimit 00317 { 00318 private: 00319 btScalar 00320 m_center, 00321 m_halfRange, 00322 m_softness, 00323 m_biasFactor, 00324 m_relaxationFactor, 00325 m_correction, 00326 m_sign; 00327 00328 bool 00329 m_solveLimit; 00330 00331 public: 00333 btAngularLimit() 00334 :m_center(0.0f), 00335 m_halfRange(-1.0f), 00336 m_softness(0.9f), 00337 m_biasFactor(0.3f), 00338 m_relaxationFactor(1.0f), 00339 m_correction(0.0f), 00340 m_sign(0.0f), 00341 m_solveLimit(false) 00342 {} 00343 00347 void set(btScalar low, btScalar high, btScalar _softness = 0.9f, btScalar _biasFactor = 0.3f, btScalar _relaxationFactor = 1.0f); 00348 00351 void test(const btScalar angle); 00352 00354 inline btScalar getSoftness() const 00355 { 00356 return m_softness; 00357 } 00358 00360 inline btScalar getBiasFactor() const 00361 { 00362 return m_biasFactor; 00363 } 00364 00366 inline btScalar getRelaxationFactor() const 00367 { 00368 return m_relaxationFactor; 00369 } 00370 00372 inline btScalar getCorrection() const 00373 { 00374 return m_correction; 00375 } 00376 00378 inline btScalar getSign() const 00379 { 00380 return m_sign; 00381 } 00382 00384 inline btScalar getHalfRange() const 00385 { 00386 return m_halfRange; 00387 } 00388 00390 inline bool isLimit() const 00391 { 00392 return m_solveLimit; 00393 } 00394 00397 void fit(btScalar& angle) const; 00398 00400 btScalar getError() const; 00401 00402 btScalar getLow() const; 00403 00404 btScalar getHigh() const; 00405 00406 }; 00407 00408 00409 00410 #endif //TYPED_CONSTRAINT_H