Skip to content

PyBullet Simulator

Simulation

PyBullet is a physics simulator. the user describe bodies, joints, gravity, motors, contacts, etc., and PyBullet numerically advances the world step by step. The simulator use in robotics and reinforcement learning.

Simulation step / motion

  • Apply gravity
  • Apply external force / torque
  • Solve joint constrains
  • Detect collisions
  • Solve contact constrains
  • Integrated velocity and position
simulation loop
1
2
3
for _ in range(1000):
    p.stepSimulation()
    time.sleep(1 / 240)
empty.py
import pybullet as p
import pybullet_data
import time

p.connect(p.GUI)

p.setAdditionalSearchPath(pybullet_data.getDataPath())

p.setGravity(0, 0, -9.81)

plane_id = p.loadURDF("plane.urdf")

while True:
    p.stepSimulation()
    time.sleep(1 / 240)

alt text

Coordinate frame

  • X = red
  • Y = green
  • Z = blue

PyBullet status bar

alt text

  • dist: Change the Visual Camera distance from world origin (coordinate frame) change distance using mouse scroll
  • Pitch, Yaw: Change Visual Camera orientation hold mouse left and move

Control view

Control

enable/disable camera views
1
2
3
4
5
# Enabled / Disabled camera's viewer

p.configureDebugVisualizer(p.COV_ENABLE_RGB_BUFFER_PREVIEW, 0)
p.configureDebugVisualizer(p.COV_ENABLE_DEPTH_BUFFER_PREVIEW, 0)
p.configureDebugVisualizer(p.COV_ENABLE_SEGMENTATION_MARK_PREVIEW, 0)
# close all gui
p.configureDebugVisualizer(p.COV_ENABLE_GUI, 0)
Without GUI (debug) ![Without GUI debug view](images/pybullet_clear.png)

alt text


Nvidia

force opengl run on nvidia
__NV_PRIME_RENDER_OFFLOAD=1 __GLX_VENDOR_LIBRARY_NAME=nvidia python3 hello.py
pybullet log
GL_VENDOR=Intel
GL_RENDERER=Mesa Intel(R) Graphics (ARL)
with nvidia log
1
2
3
4
GL_VENDOR=NVIDIA Corporation
GL_RENDERER=NVIDIA GeForce RTX 5070 Laptop GPU/PCIe/SSE2
GL_VERSION=3.3.0 NVIDIA 580.142
GL_SHADING_LANGUAGE_VERSION=3.30 NVIDIA via Cg compiler

Rigid body

A rigid body is a object that does not deform likes: - box - sphere - any shape that use as a link

A rigid body can move in 6 degree of freedom - translation: x, y, z - rotation: Roll, Pitch, Yaw

Info

A rigid body is a mathematical physical object

rigid body definition

Property Meaning
position where object is
orientation rotation
linear velocity movement speed
angular velocity rotation speed
mass inertia to motion
inertia tensor resistance to rotation
collision shape physics geometry
visual shape rendering geometry

Visual Collision and Inertia

In rigid_body.py, the box is built from two separate shapes:

  • createCollisionShape(...) defines the physical geometry used by the simulator for contact, friction, bouncing, and collision tests.
  • createVisualShape(...) defines only how the object is drawn in the GUI, including color and visible size. It does not affect physics.

Both shapes are attached to the body with createMultiBody(...). PyBullet uses baseMass together with the collision shape dimensions to compute the body's default local inertia. Inertia is the body's resistance to rotation: a larger mass or a larger shape is harder to spin.

Briefly:

  • baseMass > 0 creates a dynamic body affected by gravity, forces, collisions, and inertia.
  • baseMass = 0 creates a static body. It can collide with dynamic bodies, but it does not move and PyBullet treats its inertia as fixed/infinite for simulation purposes.
rigid body example
import pybullet as p
import pybullet_data
import time

p.connect(p.GUI)

p.setAdditionalSearchPath(pybullet_data.getDataPath())

p.setGravity(0, 0, -9.81)

p.loadURDF("plane.urdf")

collision = p.createCollisionShape(
    p.GEOM_BOX,
    halfExtents=[0.2, 0.2, 0.2],
)

visual = p.createVisualShape(
    p.GEOM_BOX,
    halfExtents=[0.2, 0.2, 0.2],
    rgbaColor=[1, 0, 0, 1],
)

body = p.createMultiBody(
    baseMass=1.0,
    baseCollisionShapeIndex=collision,
    baseVisualShapeIndex=visual,
    basePosition=[0, 0, 1],
)

while True:
    p.stepSimulation()
    time.sleep(1 / 240)

Tip

install pyi for intellisense pybulley.pyi download


Demo

hello.py
import pybullet as p
import pybullet_data
import time

# Connect to PyBullet with GUI
p.connect(p.GUI, options="--opengl2 --egl")

# Set search path to PyBullet’s default data
p.setAdditionalSearchPath(pybullet_data.getDataPath())

# Load a simple plane and a cube
plane_id = p.loadURDF("plane.urdf")
cube_id = p.loadURDF("r2d2.urdf", [0, 0, 1])

# Add gravity
p.setGravity(0, 0, -9.8)

# Run simulation loop
while True:
    p.stepSimulation()
    time.sleep(1./240.)
  • pybullet_data provide many URDF examples.
  • loadURDF return integer that use to refer the robot in other pybullet commands/

Demo: Get Position and Orientation

Position orientation and apply external force
import pybullet as p
import pybullet_data
import time

# Connect to PyBullet with GUI
p.connect(p.GUI, options="--opengl2 --egl")

# Set search path to PyBullet’s default data
p.setAdditionalSearchPath(pybullet_data.getDataPath())

# Load a simple plane and a cube
plane_id = p.loadURDF("plane.urdf")
carId = p.loadURDF(racecar/racecar.urdf, basePosition=[0,0,0.2])
position, orientation = p.getBasePositionAndOrientation(carId)
for _ in range(100): 
    p.stepSimulation()

Demos and ...

PyBullet Quickstart Guide



Projects