+ Added joint feedback for constraints, needs testing/demo before 2.75 release.

See also http://www.bulletphysics.com/Bullet/phpBB3/viewtopic.php?f=9&t=2677
and http://code.google.com/p/bullet/issues/detail?id=227

To enable, use constraint->enableFeedback(true);
And then either use
constraint->getAppliedImpulse() for an estimated applied impulse,
or constraint-> getAppliedLinearImpulse(), or constraint->getAppliedAngularImpulseA() or constraint->getAppliedAngularImpulseB().

+removed a few warnings.
This commit is contained in:
erwin.coumans
2009-05-27 01:34:46 +00:00
parent 056659d2af
commit 258ef6e25a
5 changed files with 122 additions and 15 deletions

View File

@@ -660,26 +660,25 @@ btScalar btSequentialImpulseConstraintSolver::solveGroupCacheFriendlySetup(btCol
int totalNumRows = 0;
int i;
m_tmpConstraintSizesPool.resize(numConstraints);
//calculate the total number of contraint rows
for (i=0;i<numConstraints;i++)
{
btTypedConstraint::btConstraintInfo1 info1;
btTypedConstraint::btConstraintInfo1& info1 = m_tmpConstraintSizesPool[i];
constraints[i]->getInfo1(&info1);
totalNumRows += info1.m_numConstraintRows;
}
m_tmpSolverNonContactConstraintPool.resize(totalNumRows);
btTypedConstraint::btConstraintInfo1 info1;
info1.m_numConstraintRows = 0;
///setup the btSolverConstraints
int currentRow = 0;
for (i=0;i<numConstraints;i++,currentRow+=info1.m_numConstraintRows)
for (i=0;i<numConstraints;i++)
{
constraints[i]->getInfo1(&info1);
const btTypedConstraint::btConstraintInfo1& info1 = m_tmpConstraintSizesPool[i];
if (info1.m_numConstraintRows)
{
btAssert(currentRow<totalNumRows);
@@ -782,6 +781,7 @@ btScalar btSequentialImpulseConstraintSolver::solveGroupCacheFriendlySetup(btCol
}
}
}
currentRow+=m_tmpConstraintSizesPool[i].m_numConstraintRows;
}
}
@@ -972,6 +972,7 @@ btScalar btSequentialImpulseConstraintSolver::solveGroup(btCollisionObject** bod
int numPoolConstraints = m_tmpSolverContactConstraintPool.size();
int j;
//copy back the applied impulses for contacts
for (j=0;j<numPoolConstraints;j++)
{
@@ -988,6 +989,39 @@ btScalar btSequentialImpulseConstraintSolver::solveGroup(btCollisionObject** bod
//do a callback here?
}
int currentRow = 0;
int totalNumRows = m_tmpSolverNonContactConstraintPool.size();
#if 1
//copy back the applied impulses for joints
for (i=0;i<numConstraints;i++)
{
btTypedConstraint* constraint = constraints[i];
if (constraint->needsFeedback())
{
const btTypedConstraint::btConstraintInfo1& info1 = m_tmpConstraintSizesPool[i];
if (info1.m_numConstraintRows)
{
btAssert(currentRow<totalNumRows);
btSolverConstraint* currentConstraintRow = &m_tmpSolverNonContactConstraintPool[currentRow];
constraint->getAppliedLinearImpulse().setValue(0,0,0);
constraint->getAppliedAngularImpulseA().setValue(0,0,0);
constraint->getAppliedAngularImpulseB().setValue(0,0,0);
int j;
btScalar maxAppliedImpulse(0.);
for ( j=0;j<info1.m_numConstraintRows;j++)
{
btSetMax(maxAppliedImpulse,(btScalar)currentConstraintRow[i].m_appliedImpulse);
constraint->getAppliedLinearImpulse() += currentConstraintRow[i].m_contactNormal*currentConstraintRow[i].m_appliedImpulse;
constraint->getAppliedAngularImpulseA() += currentConstraintRow[i].m_relpos1CrossNormal*currentConstraintRow[i].m_appliedImpulse;
constraint->getAppliedAngularImpulseB() += currentConstraintRow[i].m_relpos2CrossNormal*currentConstraintRow[i].m_appliedImpulse;
}
constraint->internalSetAppliedImpulse(maxAppliedImpulse);
}
}
currentRow+=m_tmpConstraintSizesPool[i].m_numConstraintRows;
}
#endif
if (infoGlobal.m_splitImpulse)
{
for ( i=0;i<m_tmpSolverBodyPool.size();i++)

View File

@@ -21,7 +21,7 @@ class btIDebugDraw;
#include "btContactConstraint.h"
#include "btSolverBody.h"
#include "btSolverConstraint.h"
#include "btTypedConstraint.h"
///The btSequentialImpulseConstraintSolver is a fast SIMD implementation of the Projected Gauss Seidel (iterative LCP) method.
@@ -35,6 +35,7 @@ protected:
btConstraintArray m_tmpSolverContactFrictionConstraintPool;
btAlignedObjectArray<int> m_orderTmpConstraintPool;
btAlignedObjectArray<int> m_orderFrictionConstraintPool;
btAlignedObjectArray<btTypedConstraint::btConstraintInfo1> m_tmpConstraintSizesPool;
btSolverConstraint& addFrictionConstraint(const btVector3& normalAxis,int solverBodyIdA,int solverBodyIdB,int frictionIndex,btManifoldPoint& cp,const btVector3& rel_pos1,const btVector3& rel_pos2,btCollisionObject* colObj0,btCollisionObject* colObj1, btScalar relaxation);

View File

@@ -24,6 +24,7 @@ static btRigidBody s_fixed(0, 0,0);
btTypedConstraint::btTypedConstraint(btTypedConstraintType type)
:m_userConstraintType(-1),
m_userConstraintId(-1),
m_needsFeedback(false),
m_constraintType (type),
m_rbA(s_fixed),
m_rbB(s_fixed),
@@ -35,6 +36,7 @@ m_dbgDrawSize(DEFAULT_DEBUGDRAW_SIZE)
btTypedConstraint::btTypedConstraint(btTypedConstraintType type, btRigidBody& rbA)
:m_userConstraintType(-1),
m_userConstraintId(-1),
m_needsFeedback(false),
m_constraintType (type),
m_rbA(rbA),
m_rbB(s_fixed),
@@ -49,6 +51,7 @@ m_dbgDrawSize(DEFAULT_DEBUGDRAW_SIZE)
btTypedConstraint::btTypedConstraint(btTypedConstraintType type, btRigidBody& rbA,btRigidBody& rbB)
:m_userConstraintType(-1),
m_userConstraintId(-1),
m_needsFeedback(false),
m_constraintType (type),
m_rbA(rbA),
m_rbB(rbB),

View File

@@ -38,6 +38,7 @@ class btTypedConstraint
{
int m_userConstraintType;
int m_userConstraintId;
bool m_needsFeedback;
btTypedConstraintType m_constraintType;
@@ -54,6 +55,9 @@ protected:
btScalar m_appliedImpulse;
btScalar m_dbgDrawSize;
btVector3 m_appliedLinearImpulse;
btVector3 m_appliedAngularImpulseA;
btVector3 m_appliedAngularImpulseB;
public:
@@ -95,18 +99,30 @@ public:
int *findex;
};
///internal method used by the constraint solver, don't use them directly
virtual void buildJacobian() = 0;
///internal method used by the constraint solver, don't use them directly
virtual void setupSolverConstraint(btConstraintArray& ca, int solverBodyA,int solverBodyB, btScalar timeStep)
{
}
///internal method used by the constraint solver, don't use them directly
virtual void getInfo1 (btConstraintInfo1* info)=0;
///internal method used by the constraint solver, don't use them directly
virtual void getInfo2 (btConstraintInfo2* info)=0;
///internal method used by the constraint solver, don't use them directly
void internalSetAppliedImpulse(btScalar appliedImpulse)
{
m_appliedImpulse = appliedImpulse;
}
///internal method used by the constraint solver, don't use them directly
virtual void solveConstraintObsolete(btSolverBody& bodyA,btSolverBody& bodyB,btScalar timeStep) = 0;
///internal method used by the constraint solver, don't use them directly
btScalar getMotorFactor(btScalar pos, btScalar lowLim, btScalar uppLim, btScalar vel, btScalar timeFact);
const btRigidBody& getRigidBodyA() const
@@ -152,11 +168,64 @@ public:
return m_userConstraintId;
}
bool needsFeedback() const
{
return m_needsFeedback;
}
///enableFeedback will allow to read the applied linear and angular impulse
///use getAppliedImpulse, getAppliedLinearImpulse and getAppliedAngularImpulse to read feedback information
void enableFeedback(bool needsFeedback)
{
m_needsFeedback = needsFeedback;
}
///getAppliedImpulse is an estimated total applied impulse.
///This feedback could be used to determine breaking constraints or playing sounds.
btScalar getAppliedImpulse() const
{
btAssert(m_needsFeedback);
return m_appliedImpulse;
}
const btVector3& getAppliedLinearImpulse() const
{
btAssert(m_needsFeedback);
return m_appliedLinearImpulse;
}
btVector3& getAppliedLinearImpulse()
{
btAssert(m_needsFeedback);
return m_appliedLinearImpulse;
}
const btVector3& getAppliedAngularImpulseA() const
{
btAssert(m_needsFeedback);
return m_appliedAngularImpulseA;
}
btVector3& getAppliedAngularImpulseA()
{
btAssert(m_needsFeedback);
return m_appliedAngularImpulseA;
}
const btVector3& getAppliedAngularImpulseB() const
{
btAssert(m_needsFeedback);
return m_appliedAngularImpulseB;
}
btVector3& getAppliedAngularImpulseB()
{
btAssert(m_needsFeedback);
return m_appliedAngularImpulseB;
}
btTypedConstraintType getConstraintType () const
{
return m_constraintType;