Manifold2D
Deterministic 2D rigid-body physics, modeled on Box2D v3.
- C++23
- 2D
- Deterministic
One step, four sub-steps.
Every world.Step(dt) runs these six stages four times over. Contacts persist between steps, so each solve starts warm.
- 1Integratevelocities
- 2Warm-startpersisted contacts
- 3Biased solveTGS-Soft
- 4Integratepositions
- 5Relaxunbiased pass
- 6Restitutionfinal pass
What it does.
From the broadphase to the last restitution pass, every stage is ours, and every stage is deterministic.
Rotation-aware narrowphase
GJK distance, EPA penetration, MPR, and polygon clipping produce stable contact manifolds.
TGS-Soft solver
A sub-stepped soft-constraint solver with warm-starting, friction, and restitution.
SIMD contact solve
Lane-wide passes over graph-colored Structure-of-Arrays batches, with a scalar overflow path.
Selectable broadphase
Dynamic tree, spatial hash, or sweep-and-prune, plus tile grids for statics.
Bodies, fixtures & shapes
Static/kinematic/dynamic bodies, multi-fixture layers, sensors, collision filtering; circles, capsules, polygons, and boxes.
Seven joint types
Distance, revolute, weld, prismatic, mouse, wheel, and motor joints.
Continuous collision
Anti-tunneling bullet sweeps for fast movers, with island-based sleeping.
Deterministic by design
Index-ordered iteration replays to identical results — and matches across broadphase backends.
Seven joint types.
The ropes, ragdolls, suspensions and presses in the world above are all built from these.
A body and a joint.
Create a dynamic body from a shape
BodyDef def;
def.type = BodyType::Dynamic;
def.position = pos;
def.shape = MakeCircle(Real(1));
def.density = Real(1);
BodyHandle body = world.AddBody(def);Add a revolute joint and step the world
JointDef jd;
jd.kind = JointKind::Revolute;
jd.a = anchor;
jd.b = bob;
jd.anchor = Vec2(Real(100), Real(50));
world.AddJoint(jd);
world.Step(dt);Part of Starworks.
Read the solver.
Deterministic, sub-stepped, and modeled on Box2D v3. The source is on GitHub.
- C++23
- 2D
- Deterministic