Status: pre-release. October 2026.

How Margo Engine is built, and how we know it works

A WebGPU engine with a 22 KB core, built by one person directing AI, with the checks that keep it honest.

Summary

Margo Engine is a 3D engine for the web. Its core is small: the entry point that every project loads is 22,781 bytes gzipped (measured 2026-10-26). Everything else is an optional package you load only if you use it: physics, glTF loading, shadows, post-processing, voxel worlds with multiplayer, a path tracer, CAD import, exporters to Unity, Unreal, Godot and Roblox, React and Next.js support, Gaussian splats, mesh editing, scientific plotting and more than seventy others. It is open source under Apache-2.0.

I built it by directing an AI (Claude) and other AI coding tools. I think that is worth saying first, plainly, because the real question is not "did a person type every line". The question is "can you trust what it does". This paper explains the design, the process that produced it, what the checks have caught, what still fails and what we do not know yet.

1. The idea: pay only for what you import

Most engines ship one large library and let a bundler remove what you do not use. Margo works the other way round. The core draws a scene and nothing else. Every other feature is a separate package with its own entry points. A package that you do not import costs your users nothing, and a package that you do import does not change how the core behaves unless you ask it to. That last point is tested: for the optional features that touch rendering, a "proof" checks that with the feature switched off, the engine produces byte-for-byte the same output as before. There are 51 such proofs.

Two limits on the size claim, because they matter:

2. What it can do today

Rendering: physically based materials (clearcoat, sheen, transmission, subsurface, parallax and triplanar mapping), cascaded soft shadows, clustered lighting, temporal anti-aliasing, post-processing, glTF 2.0 loading, skeletal animation with retargeting, IK and a rigging package, physics through Rapier, picking and selection, text and an in-engine game UI.

Worlds and data: voxel worlds with multiplayer, lighting and a path tracer; terrain; water; sky with weather; Gaussian splats (PLY, SPZ and SOG files); scientific plotting; GPU compute (FFT, sorting, linear algebra).

Tools: mesh editing (bevels, bridges, booleans, subdivision, UV unwrap, simplification and levels of detail), a scene inspector with undo and redo, a shader node editor, a command-line asset pipeline.

Interop: CAD import (STEP and IGES) through OpenCascade; export to glTF, USDZ and engine bundles for Unity, Unreal, Godot and Roblox; React and Next.js.

We compare the engine against three.js in a 161-row feature matrix. It covers 153 rows, with 4 partial and 4 missing. The partial and missing rows are listed publicly, along with the reason for each. That table is a planning tool, not a claim of equivalence.

3. How it was built: directing AI with engineering discipline

One person set the goals and made the decisions. AI did the writing. The process was designed so that nobody has to take anyone's word for the result.

Clean room. The engine uses no code from other engines. Features are written from public specifications and published papers, and every formula in the source cites where it comes from. A separate check fails the build if the code mentions or depends on something outside an explicit, attributed list (Rapier for physics, web-ifc for BIM files, React for the React bindings).

Many helpers, one gate. Work is split into small jobs that run in parallel, each in its own copy of the repository. Only one job can land at a time, and every landing must pass the same full check first: type and API reports, about 5,700 tests, quality gates for size, duplicates, documentation and error messages, the 51 proofs, a visual regression run, every package's real-GPU test, WGSL shader validation, a no-WebGPU fallback test, and a build matrix that installs every package into clean Vite, webpack, esbuild, Rollup and Next.js projects and type-checks every README example.

Rules that grew out of mistakes. Early on, two changes were merged while one known test was failing, on the reasoning that the failure was unrelated. It was not acceptable, and the rule became: nothing lands with a failing check, and a failing check is always the author's to root-cause, related or not. Another rule: every bug gets a regression test that fails without the fix. A third: when speed work makes the engine faster than a rival because it does less, we keep the work and publish the difference instead of matching the number.

4. What the checks caught (and what they did not)

A sample of real findings from the last week, because a list of passes proves little:

5. Honest limits

6. What comes next

An honest benchmark page with rerunnable scripts, a 5-minute quickstart, a website with guides, a gallery of working demos, a device compatibility table, and the first public release of the code. Until then, this paper and the waitlist are the place to follow progress.

Margo Engine, Apache-2.0. margoengine.com