SIMULATED — SYNTHETIC DATA No radio hardware is involved. The room, the person and the channel are produced by the built-in simulator; the right-hand panel is the real signal processing reading that simulated channel. Nothing in this view is a measurement of a real person.

demo

see it run.

This page drives the gateway's own simulator from your browser. On the left is the room we told it to build and the person we put in it; on the right is what the signal processing recovered from that synthetic channel, through the same ingest path a sensor's frames take. Move the person half a metre and the right-hand column loses them completely.

the two columns

Drag the person. Watch the pipeline lose them.

Ground truth — what we told the simulator

Everything in this panel is an input we chose, not an inference. The person is where we put them.

This column draws the simulated room from the gateway's own /api/sim, which needs JavaScript. With JavaScript off nothing is drawn: the page will not paint a room it could not fetch. The rest of this page reads normally.

Loading the simulated room…

Person — an input we set
—
Simulator predicts here
—
Breathing we told it to generate
—

Those three points are asserted by a Rust test, the_gap_the_explorer_exists_to_show, so they cannot rot into coordinates that no longer demonstrate anything.

Drag the handle, or click anywhere in the room. With the handle focused, ← ↑ ↓ → move it by one map cell and Shift and an arrow by 1 m.

The map is fetched at 0.03 m per cell and that is not a cosmetic choice. Measured against this gateway's own pipeline, with the person parked in the blind spot at 3.00, 3.61 where the pipeline reports an empty room: a 0.25 m map reads 0.79 there, a 0.10 m map reads 1.26 — brighter than this room's median — and only a 0.03 m map reads 0.21, effectively blind, which is the true answer. The pattern goes from peak to null in about 3 cm. A map that disagrees with the pipeline it is drawn to explain is the one thing this page must never ship.

What the pipeline recovered

The real DSP, fed the simulated CSI through the same ingest path as a sensor. No position appears here: a one-antenna link cannot measure one.

This column reads the gateway's published state from /api/spaces, which needs JavaScript. With JavaScript off, nothing is shown here — no placeholder numbers are substituted for the ones it could not fetch.

Occupancy, motion, stillness and breathing are the whole published vocabulary for a space. There is no position field anywhere in the gateway, and nothing in it could produce one.

the small print

What this simulator does not model

  • Two dimensions, no AGC, no carrier offset

    The simplifications the Python reference already made, which this simulator inherits.

  • The torso faces every link at once

    Its scatterers are spread across each link's own bisector, as in the reference. A real torso has one orientation.

  • The body never shadows the line of sight

    And there is no near-field: ranges below 10 cm are clamped in the scatterer amplitude.

  • A fall is a horizontal move

    Falls and sitting down happen in the 2-D slice. A real one is mostly vertical, and lying down does not change the radar cross-section here.

  • Walking is a constant speed between waypoints

    No gait sway, and a still person has no postural sway at all.

  • The phases are too clean

    They are the clean channel phase, with no CFO or SFO, so they are far better than what an ESP32 reports. The pipeline uses amplitudes.

And one thing about the room itself: this scenario runs one link, between two nodes on opposite walls. That is the honest minimum deployment, and it is the configuration whose failure mode this page exists to show. It is not the recommended one.

Measured on this same geometry, adding a second link at a wide angle fills in the first one's nulls almost perfectly: cells below the measured blindness threshold fall from 2.9% of the room to 0.12%, and the largest connected dead patch from about 20 cm across to a single cell. Nothing a person can sit down in. The blind spot you are about to drag someone into is a property of a one-link deployment, not of the technology.

how link diversity works

run this yourself

The simulator is part of the gateway. One command starts the same synthetic room, the same pipeline and the same API this page is reading.

the whole demo, on your own machine
saans-gateway --config saans.toml --simulate --speed 10

The room starts empty on purpose: the presence detector calibrates on an empty room and the breathing filters need about fifty seconds to settle, so the person appears two minutes in. --speed 10 skips that lead-in.

keep reading