algovivo is an energy-based simulation system for soft-bodied virtual creatures that runs in web browsers and Python environments. Instead of implementing physics using explicit force functions and position update rules, algovivo defines differentiable energy functions and finds the next simulation state by minimizing total energy using gradient descent. Automatic differentiation via Enzyme generates all gradient code at the LLVM IR level during compilation, enabling efficient physics simulation without manual derivative implementation. README.md12-22
The system compiles C++ energy functions to both WebAssembly (for browsers) and native shared libraries (for Python), providing a unified physics engine across platforms. A JavaScript API wraps the compiled code, and an optional neural network layer enables autonomous creature control via learned policies. README.md22-23 README.md106-108
The primary goal of algovivo is to provide a framework where complex physical behaviors emerge from energy minimization. By reformulating simulation as an optimization problem, the system can handle constraints, collisions, and muscle-driven locomotion within a single unified mathematical framework. README.md20-22
Sources: README.md1-22
Traditional physics engines compute forces and integrate accelerations to update positions. algovivo reformulates this as an optimization problem where the next position $\text{pos}_{t+1}$ is found by minimizing a total energy function: README.md20-22
$$ \text{pos}{t+1} = \arg\min{\text{pos}} E_{\text{total}}(\text{pos}, \text{pos}_t, \text{vel}_t, \text{actions}) $$
Where $E_{\text{total}}$ is the sum of six energy functions implemented in the system: README.md22
| Energy Function | Purpose | Key Property |
|---|---|---|
| Gravity | Pulls vertices downward | Position-dependent |
| Collision | Prevents ground penetration | Position-dependent |
| Neo-Hookean Triangles | Maintains mesh elasticity | Position-dependent |
| Muscles | Enables controllable contraction | Action-dependent |
| Friction | Dissipates energy at contacts | State-dependent |
| Inertia | Encodes backward Euler integration | State-dependent |
The muscle energy function is particularly noteworthy, as it depends on action signals a: README.md98-102
$$ E(x, a) = \frac{k}{2} \left(\frac{l(x)}{a\ l_0} - 1\right)^2 $$
This formulation allows direct control of desired contraction via the action parameter system.a.set([...]) without manually computing forces. README.md90-98
Sources: README.md20-104
The following diagram bridges the high-level concepts to the specific code entities that implement them.
Sources: README.md22-23 algovivo/System.js1-46
The build process transforms high-level Python descriptions into executable artifacts through multiple stages, primarily involving code generation and LLVM-based differentiation with Enzyme. README.md22-23 README.md174-181
| Stage | Input | Output | Key Tool |
|---|---|---|---|
| Code Generation | Python templates | C++ headers | codegen/codegen_csrc.py README.md174 |
| Differentiation | LLVM IR | Gradient code | Enzyme README.md22 |
| WASM Output | LLVM IR | algovivo.wasm | LLVM toolchain README.md174-181 |
| JS Bundling | ES6 Modules | algovivo.min.js | rollup rollup.config.js24-55 |
Sources: README.md164-181 rollup.config.js22-57
The JavaScript API provides a high-level object-oriented interface to the underlying WebAssembly physics engine. The System class is the central hub. algovivo/System.js9-10
System: Orchestrates the simulation loop and manages sub-components like Vertices, Muscles, and Triangles. algovivo/System.js31-45Vertices: Manages vertex positions (pos), velocities (vel), and mass. algovivo/System.js31-35Muscles: Handles muscle activations (a), rest lengths (l0), and stiffness (k). algovivo/System.js37 algovivo/System.js120-134Triangles: Manages the mesh structure and material properties like Lamé parameters (mu, lambda). algovivo/Triangles.js97-103The compiled WebAssembly module exposes several key functions defined in the C++ source that are called by the JavaScript layer:
| Function Name | Purpose | Call Site |
|---|---|---|
backward_euler_update | Main optimization loop for one simulation step. | algovivo/System.js194 |
rsi_of_pos | Computes reference shape information for triangles. | algovivo/Triangles.js84 |
Sources: algovivo/System.js192-194 algovivo/Triangles.js84-90 README.md22-23
A simple simulation can be initialized by loading the WASM module and passing it to the System constructor. README.md40-49
Sources: README.md30-86 algovivo/System.js160-173