test_bullet_simulation.py 2.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364
  1. import pytest
  2. from .conftest import simulate_until
  3. # Skip these tests if we can't import bullet.
  4. bullet = pytest.importorskip("panda3d.bullet")
  5. from panda3d import core
  6. def test_basics(world, scene):
  7. # N.B. see `scene` fixture's docstring in conftest.py to understand what's
  8. # being simulated here
  9. # Step forward until the ball crosses the threshold
  10. ball = scene.find('**/ball')
  11. assert simulate_until(world, lambda: ball.get_x() >= 0)
  12. # Continue simulating until upper box falls
  13. upper_box = scene.find('**/upper_box')
  14. assert upper_box.get_z() > 5.0
  15. assert simulate_until(world, lambda: upper_box.get_z() < 5.0)
  16. def test_restitution(world, scene):
  17. ball = scene.find('**/ball')
  18. scene.find('**/ramp').node().restitution = 1.0
  19. for with_bounce in (False, True):
  20. # Reset ball
  21. ball.node().set_angular_velocity(core.Vec3(0))
  22. ball.node().set_linear_velocity(core.Vec3(0))
  23. ball.set_pos(-2, 0, 100)
  24. ball.node().restitution = 1.0 * with_bounce
  25. # Simulate until ball rolls/bounces across Y axis
  26. assert simulate_until(world, lambda: ball.get_x() >= 0)
  27. if with_bounce:
  28. # The ball bounced across, so it should be off the ground a bit
  29. assert ball.get_z() > 1.2
  30. else:
  31. # The ball rolled, so it should be on the ground
  32. assert ball.get_z() < 1.2
  33. def test_friction(world, scene):
  34. ball = scene.find('**/ball')
  35. for with_friction in (False, True):
  36. # Reset ball, give it a huge negative (CCW) spin about the X axis so
  37. # it'll roll in +Y direction if there's any friction
  38. ball.node().set_angular_velocity(core.Vec3(-1000,0,0))
  39. ball.node().set_linear_velocity(core.Vec3(0))
  40. ball.set_pos(-2, 0, 5)
  41. ball.node().friction = 1.0 * with_friction
  42. # Simulate until ball crosses Y axis
  43. assert simulate_until(world, lambda: ball.get_x() >= 0)
  44. if with_friction:
  45. # The ball had friction, so should've gone off in the +Y direction
  46. assert ball.get_y() > 1
  47. else:
  48. # No friction means the Y axis should be unaffected
  49. assert abs(ball.get_y()) < 0.1