Reference

One engine, many surfaces

Fundamental’s core (@fundamental-engine/core) computes the field against plain data and imports zero DOM — it’s renderer-agnostic. A thin host binds it to a surface. Three are real today: the Web, Native (Swift on Apple platforms, Kotlin on Android), and your own renderer.

The core is the contract; surfaces are bindings. The same physics, force catalog, and conserved particle count run on every surface — only the host and the draw change. A bug fixed in the engine is fixed on all planes (the project ships engine fixes across them deliberately).

Web — the primary surface

@fundamental-engine/dom binds the engine to the page through browserHost() and the six registries (measurement, state, feedback, relationships, visual bindings, overlays): every [data-body] element becomes a body, and the field returns as --field-* CSS variables you style with. The authoring surfaces — the <field-root> web component, React, vanilla / TypeScript — all wrap it. This is the surface the whole site runs on.

Get it: npm i @fundamental-engine/vanilla (the recommended door). Status: stable, 0.x frozen.

Native — Swift & Kotlin, and the Field Lab

A Swift port runs the same field on Apple platforms (macOS / iOS / visionOS) with native rendering (Metal / SwiftUI), free of the browser’s full-viewport compositing ceiling — so a dense field reads smoother than the web Lab. Its showcase is the Field Lab: a native app where every engine pillar is a live, interactive scene.

A Kotlin port mirrors the JS (and Swift) packages 1:1 on Android — the full 37-force core plus the integrator, held to the same cross-plane conformance gate (one shared golden, JS / Swift / Kotlin), and the FieldHandle public API (relationship edges included). It ships a :fundamental-platform module (the six-phase discover→read→compute→state→write→render scheduler + the six registries), a Jetpack Compose host (FieldView + Modifier.fieldBody()), and a non-Compose View/Canvas host for imperative apps. It has its own desktop Field Lab. Source: the repo’s android/ directory.

Parity — broad, not complete, and still preview. Both are ports, and the web plane moved first historically. The big catch-up landed in June 2026 (#822 / #823 / #824) and the shared physics-conformance golden is green across planes — the field channels (addField / sampleField), the core force set and the interactive scenes are all there. But the handle is not at full parity, and the divergence runs both ways: of the 61 callable members any plane declares, JS has 52, Swift 53 and Kotlin 59 — the ports carry loop-control methods the web does not expose, and the web carries the focus/attention substrate the ports have not taken. (These numbers are generated from the port sources, not typed here.) API parity is not production-readiness either — treat the native plane as a fast-moving preview (see Status below). For the member-by-member breakdown see the parity matrix and the imperative API reference.

Get it: the notarized .dmg download is coming; until then, build it from source — swift run FieldLab in swift/ (a packaging script, swift/Scripts/release-fieldlab.sh, produces the app bundle). Status: preview.

Your renderer — bring your own draw

@fundamental-engine/three runs the engine headless and renders its swarm as a THREE.Points layer in your WebGL scene (the Three.js guide). More generally, the engine exposes renderer-agnostic read primitives — sample, sampleScalar, readParticles, and the field channels (addField) — so you can bind the field to anything that draws, on your own loop. Habitat (a simulation garden) is this surface in production.

Get it: npm i @fundamental-engine/three three. Status: stable, 0.x frozen.

At a glance

SurfaceHost / bindingGet itStatus
Web@fundamental-engine/dom → --field-*npm i @fundamental-engine/vanillastable
Native — AppleSwift port (Metal / SwiftUI) → the Field Labbuild from source (.dmg soon)preview · behind on newest primitives
Native — AndroidKotlin port (Compose + View/Canvas) → the Field Labbuild from source (android/)preview · running on-device
Headless — Rustfundamental-core crate (f64, seeded; a body is a data record) — 36 of the 37 forces, solve(), snapshot + causal replay, a reading layerbuild from source (rust/); not yet on crates.ioexperimental
Your renderer@fundamental-engine/three / the read primitivesnpm i @fundamental-engine/threestable