A console for particle life
From a matrix of 64 numbers — attraction, repulsion, nothing else — comes behavior that looks like breathing.
The entire rule set is an N×N matrix of values between −1 and 1. Each cell says how one species of particle is drawn toward — or repelled from — another. That's all. There is no scripted behavior, no hardcoded flocking, no coded membrane formation.
Everything you see is emergent.
Open it. Hit R a few times. Most configurations do nothing interesting. Then — suddenly — one is alive.
- Cells that form membranes, drift, and enclose
- Chasers that hunt across the field with apparent purpose
- Oscillations that breathe in and out
- Swarms that cohere, dissolve, and reform
- Symmetry that no one designed
None of these are programmed. They arise — when they arise — from a random draw of the matrix. The hit rate is part of the point.
Could life be generated here?
The particles don't replicate. They don't consume energy or maintain homeostasis in the biological sense. By the standard textbook definition, nothing here is alive.
But watch long enough, and you'll see structures that persist — that hold their shape against perturbation, that move with apparent purpose, that respond to their environment. The question of whether that resemblance is superficial — or whether life is just a particularly stable configuration of matter following simple rules — is not a settled question.
The artificial life research community has studied particle life systems seriously for decades. Emergent replicators, primitive metabolisms, and even rudimentary evolution have been found in related cellular automata and agent-based systems. Whether this particular implementation can reach those regimes is genuinely open.
That ambiguity is the point.
The world is a toroidal (wrap-around) unit square. Each particle carries a species index. At every timestep:
- Build a spatial hash over the field — O(N) neighbor lookup rather than O(N²)
- Sum forces from all neighbors within reach, using the force curve:
- Inside the repulsive core (radius
β × rMax): always push apart, regardless of species - In the interaction band: scale by the matrix value for that species pair
- Inside the repulsive core (radius
- Integrate velocity with damping, advance position, wrap to torus
The force curve — f(r, a) where r ∈ [0,1] is normalized distance and a ∈ [−1, 1] is the matrix value — produces a hard inner repulsion and a soft outer band whose sign is controlled by the matrix. This is the canonical particle-life formulation; the hard push prevents collapse regardless of what the matrix says.
- Typed arrays (
Float32Array,Uint8Array) throughout — avoids garbage collection pressure in the inner loop - Additive blending (
globalCompositeOperation = "lighter") for particle glow — natural bloom without a shader - Pre-rendered sprites per species — avoids per-frame gradient allocation
- Spatial hash with 3×3 neighborhood search — correct because
gridN = ⌊1/rMax⌋ensures each cell is ≤ rMax wide - Vanilla canvas, not React — reconciliation overhead is measurable at 60fps over thousands of particles
Open emergence.html in any modern browser. No server required, no build step, no dependencies except two Google Fonts.
| Control | Effect |
|---|---|
| Drag a matrix cell ↑ | Increase attraction toward that species |
| Drag a matrix cell ↓ | Increase repulsion from that species |
| Double-click a cell | Neutralize (set to 0) |
| Drag on the stage | Stir the field toward your cursor |
| Shift + drag | Push outward — explosive perturbation |
Space |
Pause / Resume |
R |
Randomize the matrix |
The four presets — Drift, Cells, Swarm, Frenzy — set specific physical parameters (reach, damping, force, particle count) and randomize the matrix fresh. The names describe the regime, not the guaranteed outcome; since the matrix is random, what actually emerges varies each time.
The default of 1,200 particles targets 60fps on modern hardware. At 3,000 particles on slower devices, expect frame drops. To compensate: reduce Reach first (it shrinks the neighbor search space), then Particles.
Directions worth exploring — not implemented, but natural fits for the model.
- Swarm robotics parameter search — the matrix UI is a natural interface for tuning multi-agent interaction rules before deploying to physical robots; each cell = one behavioral policy between robot types
- Complex systems pedagogy — teaching emergence and artificial life; the hit-rate mechanic (most configs produce nothing, rarely one comes alive) is the central lesson
- Generative art pipeline — record stable configs as presets, export frames, couple the simulation with audio reactivity
- Crowd / pedestrian simulation — species = demographic groups, matrix = attraction/avoidance; segregation, flow, and jamming emerge from rules alone; used by urban planners and safety engineers
- Ecological modeling — species = organism types, matrix = predation/mutualism/competition; boom-and-bust cycles arise without scripting, asymmetry maps directly onto predator-prey dynamics
- Molecular interaction intuition — particle types = molecule classes, matrix = binding affinity; not predictive, but useful for coarse-grained intuition in drug discovery and materials science
- Evolutionary matrix search — apply a genetic algorithm selecting for persistent structures or specific behavioral signatures; the current randomize-and-observe loop is manual evolution — automating the fitness function turns this into a research instrument
- 3D particle life — same physics in a three-dimensional toroidal volume via WebGL/WebGPU; membrane formation in 3D produces closed shells resembling biological vesicles
The particle life / clusters model is well-established in the artificial life field, with roots reaching back to the 1990s. The force curve used here is the common formulation found across implementations. I cannot cite a single authoritative paper with confidence; searching "particle life Jeffery Ventrella" or "primordial particle system" will surface the research lineage.
This is not an invention. It is a window.
The code's syntax has been verified; the live rendering has not been observed in a controlled browser environment by the author. What I can tell you is: the physics is correct, the spatial hash is correctly bounded, the toroidal wrapping is applied consistently, and the force curve is the standard formulation with continuous endpoints.
The rest — what actually emerges — you'll have to see for yourself.
Melanie Baratto Contact: melaniesigrid@protonmail.com GitHub: github.com/melaniesigrid
Made with a matrix of numbers and the question of what that might mean.