A whole pile answers.
Wrench Transport makes the connected response of a pile the center of a standalone rigid-body engine. In 64-body packing tests, it reaches stable rest with 0.0136 mm maximum overlap, at compute costs in the same range as Rapier and about 20–50 times lower than the tested MuJoCo configurations.
Loading the native recording…
Drag to orbit; scroll to zoom. The time slider inspects poses exported by the C++ engine. All bodies remain awake throughout this eight-second run. Download the recording.
Tighter contact. Competitive compute.
Eight seconds of motion take 0.336 seconds of compute. All three scenes settle at 60 Hz, with 0.0136 mm maximum final overlap. None of the other tested configurations reaches that overlap, including those spending substantially more compute.
| Engine / configuration | Median compute time | Relative compute | Largest final overlap | Scenes settled |
|---|---|---|---|---|
| Wrench Transport · 60 Hz | 0.336 s | 1.00× | 0.0136 mm | 3 / 3 |
| Wrench Transport · 120 Hz | 0.481 s | 1.43× | 0.0244 mm | 3 / 3 |
| Rapier · 60 Hz | 0.227 s | 0.67× | 6.9746 mm | 3 / 3 |
| Rapier · 60 Hz, scaled | 0.181 s | 0.54× | 9.7940 mm | 0 / 3 |
| Rapier · 240 Hz, scaled | 0.653 s | 1.94× | 6.3298 mm | 2 / 3 |
| MuJoCo · 60 Hz | 6.291 s | 18.72× | 30.6366 mm | 0 / 3 |
| MuJoCo · 120 Hz | 10.075 s | 29.98× | 6.0643 mm | 0 / 3 |
| MuJoCo · 480 Hz, stiff | 16.400 s | 48.80× | 0.2410 mm | 0 / 3 |
Relative compute uses Wrench Transport at 60 Hz as 1×. Eight simulated seconds per run; three seeds, three measured repeats per configuration after warm-up. A scene settles when every body stays below 4 mm/s through the end of the run.
Rapier costs about the same order of compute, with much larger overlap. Its default 60 Hz configuration is cheaper—0.675 times Wrench Transport’s cost—and settles every scene, with about 500 times the maximum overlap. At 240 Hz with more iterations, Rapier costs 1.94 times as much, retains about 466 times the overlap, and settles two of the three scenes.
The tested MuJoCo configurations require 19–49 times as much compute. The stiff 480 Hz configuration gives MuJoCo its smallest maximum overlap, but that is still about 18 times Wrench Transport’s, and the scenes remain above the settling threshold.
These are measured operating points. The cost for another engine to match Wrench Transport’s overlap and settling result remains unmeasured: none of the tested configurations reaches it.
All engines receive the same 64 hulls, initial poses, density, friction, and gravity. Sleeping is off. Final overlap comes from a common exhaustive separating-axis calculation. Ratios compare the aggregate runtime and maximum overlap across the tested scenes. Wrench Transport is native C++; MuJoCo 3.2.3 uses its native solver through Python; Rapier 0.21.0 uses WebAssembly through Node. Timings include the respective step-call boundary. The paper specifies the solver settings and protocol.
“Contact forces are just light.”
Set one rock on another: the new load belongs to everything underneath. Joshuah Rainstar’s opening intuition was to treat an influence as something transported through a connected system. Then came the sharper question. What if the rock below could receive the combined load and rotational consequence of the structure above it?
For a rigid body, the useful message has six components: three for force, three for torque. That is a wrench. The engine keeps the impulses that contacts already carry, then solves the bodies’ connected response within the frame.
A game needed rocks. The answer became a physics engine, a set of experiments, and a paper. It’s just Tuesday.
Keep the support. Solve the consequence.
A still pile is carrying a load even when nothing moves. Each contact remembers the impulse it supplied last frame. The next solve begins with that retained field, with its numerical scale set by the mass the contact supports.
Inside the solve, a friction-cone projection determines admissible contact impulses. A sparse system couples each body’s linear and angular motion. Eliminating one body folds its load and response into the bodies still connected to it; back-substitution brings their response back.
This is the useful meaning of the “macro-frame”: the structure contributes its combined mechanical response. Branches and loops remain part of the mathematics, including the extra matrix entries they create.
An engine you can take out of the game.
Convex and compound bodies. Static geometry. Friction and restitution. Rolling resistance, sleeping islands, and a bounded crane hold. The library has no rendering or window-system dependency.
Its checks cover rest, tall stacks, large mass ratios, overhangs, incline friction, drops, support removal, waking, compound shapes, and deterministic replay. The block solve also faces an independent dense solver; collision detection faces 6,000 exhaustive SAT comparisons.
Discrete speculative collision, a finite solve budget, and graph fill define the present operating envelope. Continuous collision detection and general joints are future work.
Build a small world.
cmake -S wrench-physics -B build
cmake --build build -j4
ctest --test-dir build
build/wrench_minimalEmbed with CMake’s Wrench::Physics target. The public C++ namespace is zc::phys.
Wrench Transport
Retained contact impulses and coupled body response for rigid-body simulation. The paper develops the contact solve and measures the compute required for tight, settled contact against Rapier and MuJoCo.
By Joshuah Rainstar. Related work includes Castro, Permenter, and Han’s convex contact formulation and Baraff’s structured constrained dynamics.