I am implementing an MMO game that uses Bullet Physics and I am having issues keeping the networked physics states in-sync.
The server simulates things server-side, and the client simulates things client-side. When the server-side state changes (such as a character moving a rock represented as a rigid body) the changes are sent to all the clients which incorporate them into their states and then continue the simulation on their own from there. The clients basically run the simulation and wait for updates from the server to verify that their simulation is correct, and if they differ they update to what the server has provided.
The problem that I am having is that everything stays in sync until a collision happens (such as two boxes colliding). I've verified that up until that point the physics states are identical, but after the contact is made the collision object array (acquired from btDiscreteDynamicsWorld::getCollisionObjectArray) is different, and after that cycle the linear and angular velocities can differ, as well as world transformations etc.
I've been looking everywhere for some answers to this question (forums, wiki etc). I'm quite desperate at this point. I was hoping that maybe someone has dealt with a similar issue before and/or there is some documentation somewhere that specifies the proper way to synchronize bullet physics states across the network.
I update my game-state at fixed time-steps and all the changes that happen on the server are incorporated on the same cycles and in the same order on the client(s) as they were applied on the server. I apply changes to rigid bodies like so:
Code: Select all
rigidBody->setWorldTransform(t);
motionState->setWorldTransform(t);
rigidBody->setInterpolationWorldTransform(t);
rigidBody->activate();
rigidBody->clearForces();
rigidBody->setLinearVelocity(btVector3(info.linearVelocity[0], info.linearVelocity[1], info.linearVelocity[2]));
rigidBody->setAngularVelocity(btVector3(info.angularVelocity[0], info.angularVelocity[1], info.angularVelocity[2]));
rigidBody->setInterpolationLinearVelocity(btVector3(info.linearVelocity[0], info.linearVelocity[1], info.linearVelocity[2]));
rigidBody->setInterpolationAngularVelocity(btVector3(info.angularVelocity[0], info.angularVelocity[1], info.angularVelocity[2]));
Is there anything that I can do to make the Bullet Physics states identical?