[Bepu1Int] Issues with determinsim
Posted: Thu Sep 12, 2019 5:45 pm
I understand this is the forum for normal Bepu but the fixed point port points to this forum so my hope is that maybe some assistance could be given here as well
I'm working on a 2D lockstep networked game so I'm looking at using BEPU1Int to be my collision separation solution. However the simulations of two players keeps diverging. I've created a simple in process test that fails due to divergence.
The test is pretty simple. Two boxes are created on top of each in a space and allowed to simulation for 100 frames. Then a secondary space is created and the two boxes have their state copied over. A new box in both spaces is created to further interact with the two original boxes. This is allowed to run for 1000 more frames.
At the end of this their positions do not match. I'm not sure if I missing state or otherwise haven't set something up correctly. Or if I just messed up the test but I've looked over it numerous times and don't see anything.
If able to help it would be much appreciated! Thanks!
I'm working on a 2D lockstep networked game so I'm looking at using BEPU1Int to be my collision separation solution. However the simulations of two players keeps diverging. I've created a simple in process test that fails due to divergence.
Code: Select all
[Test]
public void TestDeterminismLateJoin()
{
// Can't use mutlithreading so don't pass in an IParallelLooper
Space space1 = new Space();
space1.TimeStepSettings.TimeStepDuration = ((Fix64) 1 / 60);
Box box11 = CreatePhysicsObject(space1);
box11.ActivityInformation.IsAlwaysActive = true;
box11.LinearDamping = ((Fix64) 1 / 2);
Box box12 = CreatePhysicsObject(space1);
box11.ActivityInformation.IsAlwaysActive = true;
box11.LinearDamping = ((Fix64) 1 / 2);
int preIterations = 100;
for (int i = 0; i < preIterations; i++)
{
space1.Update(space1.TimeStepSettings.TimeStepDuration);
}
Box box13 = CreatePhysicsObject(space1);
box13.ActivityInformation.IsAlwaysActive = true;
box13.LinearDamping = ((Fix64) 1 / 2);
box13.Position = box11.Position;
Space space2 = new Space();
// As far as I can tell this will impact the random(?) solver
space2.Solver.PermutationMapper.PermutationIndex = space1.Solver.PermutationMapper.PermutationIndex;
space2.TimeStepSettings.TimeStepDuration = ((Fix64) 1 / 60);
Box box21 = CreatePhysicsObject(space2);
box21.ActivityInformation.IsAlwaysActive = true;
box21.LinearDamping = ((Fix64) 1 / 2);
// Saw in a forum post that this is what is needed to get full state across
box21.Position = box11.Position;
box21.LinearVelocity = box11.LinearVelocity;
box21.Orientation = box11.Orientation;
box21.AngularVelocity = box11.AngularVelocity;
Box box22 = CreatePhysicsObject(space2);
box22.ActivityInformation.IsAlwaysActive = true;
box22.LinearDamping = ((Fix64) 1 / 2);
box22.Position = box12.Position;
box22.LinearVelocity = box12.LinearVelocity;
box22.Orientation = box12.Orientation;
box22.AngularVelocity = box12.AngularVelocity;
Box box23 = CreatePhysicsObject(space2);
box23.ActivityInformation.IsAlwaysActive = true;
box23.LinearDamping = ((Fix64) 1 / 2);
box23.Position = box21.Position;
Assert.IsTrue(box11.Position != Vector3.Zero);
Assert.IsTrue(box12.Position != Vector3.Zero);
Assert.IsTrue(box21.Position != Vector3.Zero);
Assert.IsTrue(box22.Position != Vector3.Zero);
int iterations = 1000;
for (int i = 0; i < iterations; i++)
{
space1.Update(space1.TimeStepSettings.TimeStepDuration);
space2.Update(space2.TimeStepSettings.TimeStepDuration);
}
// THESE ASSERTS FAIL
Assert.IsTrue(box11.Position == box21.Position);
Assert.IsTrue(box12.Position == box22.Position);
Assert.IsTrue(box13.Position == box23.Position);
}
private static Box CreatePhysicsObject(Space space)
{
Box box = new Box(Vector3.Zero, 1, 1, 1, 1);
box.PositionUpdateMode = PositionUpdateMode.Continuous;
PointOnPlaneJoint pointOnPlaneJoint = new PointOnPlaneJoint(
null,
box,
new Vector3(),
new Vector3(0, 0, -1),
box.Position);
space.Add(pointOnPlaneJoint);
RevoluteAngularJoint angularJoint = new RevoluteAngularJoint(
null,
box,
new Vector3(0, 0, -1));
space.Add(angularJoint);
space.Add(box);
return box;
}
At the end of this their positions do not match. I'm not sure if I missing state or otherwise haven't set something up correctly. Or if I just messed up the test but I've looked over it numerous times and don't see anything.
If able to help it would be much appreciated! Thanks!