Skip to content

Commit 40ef9d6

Browse files
authored
add primitives rendering benchmark (#1346)
1 parent d56967e commit 40ef9d6

6 files changed

Lines changed: 113 additions & 10 deletions

File tree

benchmarks/render/README.md

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Render
2+
3+
## Description
4+
5+
GPU ray-traced rendering of the [primitives](../../mujoco_warp/test_data/primitives.xml) scene. This benchmark measures rendering performance using a 5×5 grid of spheres, capsules, ellipsoids, cylinders, and boxes above a plane.
6+
7+
### primitives
8+
9+
| Property | Value |
10+
|----------|-------|
11+
| Bodies | 126 |
12+
| DoFs | 750 |
13+
| Geoms | 127 |
14+
| Cameras | 1 |
15+
| Resolution | 64×64 |
16+
| Worlds | 8192 |
17+
18+
![primitives](primitives.webp)

benchmarks/render/__init__.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
BENCHMARKS = [
2+
{
3+
"name": "primitives",
4+
"mjcf": "primitives.xml",
5+
"function": "render",
6+
"nworld": 8192,
7+
"nconmax": 100,
8+
"njmax": 256,
9+
"nstep": 100,
10+
},
11+
]

benchmarks/render/primitives.webp

21.7 KB
Loading

benchmarks/render/primitives.xml

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
<mujoco model="primitives">
2+
3+
<visual>
4+
<map znear="0.01" zfar="200" />
5+
<quality shadowsize="8192" />
6+
<headlight diffuse=".8 .8 .8" ambient=".2 .2 .2" specular="1 1 1" />
7+
<global azimuth="140" elevation="-20" />
8+
</visual>
9+
10+
<asset>
11+
<texture type="skybox" builtin="gradient" rgb1="1 1 1" rgb2="1 1 1" width="800" height="800" />
12+
<texture name="grid" type="2d" builtin="checker" width="512" height="512" rgb1=".1 .2 .3" rgb2=".2 .3 .4"/>
13+
<material name="grid" texture="grid" texrepeat="1 1" texuniform="true" reflectance=".2"/>
14+
</asset>
15+
16+
<worldbody>
17+
<geom name="floor" size="0 0 .05" type="plane" material="grid" contype="1" conaffinity="1"/>
18+
<camera pos="3 0 2" xyaxes="0 1 0 -0.6 0 1"/>
19+
<light pos="0 0 3" dir="0 0 -1" directional="true" />
20+
21+
<geom name="table" pos="0.8 0.0 0.5" type="box" size="0.5 1.0 0.01" quat="1.0 0.0 0.0 0.0" contype="1" conaffinity="1"/>
22+
23+
<replicate count="5" offset="0.1 0 0">
24+
<replicate count="5" offset="0 0.2 0">
25+
<body name="sphere" pos="0.6 -0.4 0.8">
26+
<freejoint name="sphere"/>
27+
<geom name="geom_sphere" type="sphere" size="0.05" contype="1" conaffinity="1" rgba="1 0 0 1"/>
28+
</body>
29+
</replicate>
30+
</replicate>
31+
32+
<replicate count="5" offset="0.1 0 0">
33+
<replicate count="5" offset="0 0.2 0">
34+
<body name="capsule" pos="0.6 -0.4 0.95">
35+
<freejoint name="capsule"/>
36+
<geom name="geom_capsule" type="capsule" size="0.04 0.05" contype="1" conaffinity="1" rgba="0 1 0 1"/>
37+
</body>
38+
</replicate>
39+
</replicate>
40+
41+
<replicate count="5" offset="0.1 0 0">
42+
<replicate count="5" offset="0 0.2 0">
43+
<body name="ellipsoid" pos="0.6 -0.4 1.1">
44+
<freejoint name="ellipsoid"/>
45+
<geom name="geom_ellipsoid" type="ellipsoid" size="0.05 0.04 0.03" contype="1" conaffinity="1" rgba="0 0 1 1"/>
46+
</body>
47+
</replicate>
48+
</replicate>
49+
50+
<replicate count="5" offset="0.1 0 0">
51+
<replicate count="5" offset="0 0.2 0">
52+
<body name="cylinder" pos="0.6 -0.4 1.2">
53+
<freejoint name="cylinder"/>
54+
<geom name="geom_cylinder" type="cylinder" size="0.04 0.04" contype="1" conaffinity="1" rgba="1 1 0 1"/>
55+
</body>
56+
</replicate>
57+
</replicate>
58+
59+
<replicate count="5" offset="0.1 0 0">
60+
<replicate count="5" offset="0 0.2 0">
61+
<body name="box1" pos="0.6 -0.4 1.4">
62+
<freejoint name="joint1"/>
63+
<geom name="geom1" type="box" size="0.03 0.03 0.03" contype="1" conaffinity="1" rgba="0 1 1 1"/>
64+
</body>
65+
</replicate>
66+
</replicate>
67+
</worldbody>
68+
</mujoco>

benchmarks/run.py

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,11 @@
3838

3939
_ARGS = None # module level variable that gets populated with argparse results
4040

41+
# Ensure the active virtual environment's bin directory is in PATH so 'uv' can be found
42+
_venv_bin = Path(sys.executable).parent.as_posix()
43+
if _venv_bin not in os.environ.get("PATH", ""):
44+
os.environ["PATH"] = f"{_venv_bin}{os.path.pathsep}{os.environ.get('PATH', '')}"
45+
4146
logging.basicConfig(format="[%(asctime)s] %(message)s", datefmt="%Y-%m-%d %H:%M:%S", level=logging.INFO)
4247
log = logging.getLogger(__name__)
4348

@@ -133,15 +138,12 @@ def _run_benchmark(bm: dict, input_dir: Path) -> dict:
133138
"--measure_solver=true",
134139
"--measure_alloc=true",
135140
]
136-
if "nconmax" in bm:
137-
cmd.append(f"--nconmax={bm['nconmax']}")
138-
if "njmax" in bm:
139-
cmd.append(f"--njmax={bm['njmax']}")
141+
for field in ("nconmax", "njmax", "function", "nstep", "render_width", "render_height"):
142+
if field in bm:
143+
cmd.append(f"--{field}={bm[field]}")
140144
if "replay" in bm:
141145
replay_path = Path(_ARGS.assets_root) / bm["name"] / bm["replay"]
142146
cmd.append(f"--replay={replay_path.as_posix()}")
143-
if "nstep" in bm:
144-
cmd.append(f"--nstep={bm['nstep']}")
145147

146148
result = _uv_run(*cmd, cwd=input_dir)
147149

benchmarks/sweep.py

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,11 @@
5858

5959
_ARGS = None # module level variable that gets populated with argparse results
6060

61+
# Ensure the active virtual environment's bin directory is in PATH so 'uv' can be found
62+
_venv_bin = Path(sys.executable).parent.as_posix()
63+
if _venv_bin not in os.environ.get("PATH", ""):
64+
os.environ["PATH"] = f"{_venv_bin}{os.path.pathsep}{os.environ.get('PATH', '')}"
65+
6166
logging.basicConfig(format="[%(asctime)s] %(message)s", datefmt="%Y-%m-%d %H:%M:%S", level=logging.INFO)
6267
log = logging.getLogger(__name__)
6368

@@ -154,10 +159,9 @@ def _run_benchmark(bm: dict, input_dir: Path, *, mock: bool) -> dict:
154159
"--measure_solver=true",
155160
"--measure_alloc=true",
156161
]
157-
if "nconmax" in bm:
158-
cmd.append(f"--nconmax={bm['nconmax']}")
159-
if "njmax" in bm:
160-
cmd.append(f"--njmax={bm['njmax']}")
162+
for field in ("nconmax", "njmax", "function", "render_width", "render_height"):
163+
if field in bm:
164+
cmd.append(f"--{field}={bm[field]}")
161165
if "replay" in bm:
162166
replay_path = Path(_ARGS.assets_root) / bm["name"] / bm["replay"]
163167
cmd.append(f"--replay={replay_path.as_posix()}")

0 commit comments

Comments
 (0)