Deaktivieren der Bewegung der Y-Achse in der Bullet-Physik-Engine

11

Ich möchte ein Objekt erstellen, das sich nicht nur entlang der X- und Z-Achse bewegt, während die Y-Achse deaktiviert bleibt (es ist wie eine Bewegung in 2D, und das Objekt fällt nicht herunter).

Ich verwende derzeit eine 6-dof-Einschränkung, um die Bewegung in der Y-Achse einzuschränken, aber es funktioniert nicht:

btRigidBody* zeroBody = new btRigidBody(0, NULL, NULL); // Create the body that we attach things to
btRigidBody* robot = mCarChassis->getBulletRigidBody();

btGeneric6DofConstraint* constrict = new btGeneric6DofConstraint(*robot, *zeroBody, btTransform::getIdentity(), btTransform::getIdentity(), false);

constrict->setLinearLowerLimit( btVector3( 1, 1, 1));
constrict->setLinearUpperLimit( btVector3(-1, 1,-1));

constrict->setAngularLowerLimit( btVector3( 1,  1,  1) );
constrict->setAngularUpperLimit( btVector3(-1, -1, -1) );

mBulletWorld->getBulletDynamicsWorld()->addConstraint(constrict);

Vielen Dank!

Azer
quelle
Vielleicht hilft dies: bullphysics.org/Bullet/phpBB3/… , vielleicht setzen Sie auch die unteren / oberen Grenzen für die Y-Achse auf 0 anstatt auf 1.
verzögert am

Antworten:

20

Der bevorzugte Weg, dies in Bullet zu erreichen, besteht darin, den linearen Faktor und möglicherweise den Winkelfaktor für den betreffenden Körper festzulegen. Diese Methode wird auf der Bullet-Wiki-Seite als Code-Snippet dargestellt .

Um eine Bewegung nur entlang der Y-Achse zuzulassen, würden Sie Folgendes verwenden:

body->setLinearFactor(btVector3(0,1,0));

Wenn Sie zusätzlich die Drehung um eine bestimmte Achse deaktivieren möchten, verwenden Sie dasselbe Verfahren, verwenden jedoch stattdessen die setAngularFactorFunktion.

In diesem einfachen Beispielvideo habe ich die folgenden zwei Aufrufe verwendet, um die Bewegung entlang der Y-Achse zu deaktivieren und eine Drehung nur um die Y-Achse zuzulassen. Dies zwingt den Körper effektiv dazu, in der XZ-Ebene zu bleiben, in der er ursprünglich erzeugt wurde.

body->setLinearFactor(btVector3(1,0,1));
body->setAngularFactor(btVector3(0,1,0));
Jiddo
quelle
2

Eine Möglichkeit, dies zu tun, besteht darin, einen Physik-Tick-Rückruf zu erstellen. Dies wird jedes Mal aufgerufen, wenn die Kugel intern tickt. In diesem Rückruf können Sie die Y-Geschwindigkeit auf 0 setzen, wodurch die Y-Bewegung effektiv deaktiviert wird. Es würde ungefähr so ​​aussehen:

void myTickCallback(const btDynamicsWorld *world, btScalar timeStep) {
    //robotBody is the btRigidBody you want to constrain the movement of
    btVector3 velocity = robotBody->getLinearVelocity();
    robotBody->setLinearVelocity(velocity.x, 0, velocity.z);
} 

Weitere Informationen zu Rückrufen von Simulations-Ticks finden Sie hier .

MichaelHouse
quelle
Vielen Dank! Dies ist eine großartige Antwort, da sie auch für den Java-Port von JBullet gilt (im Gegensatz zur anderen Antwort).
Joehot200