Kuudu: Breathe a Vesak Lantern Home with Your Breath - DEV Community

DEV Community

Cover image for Kuudu: Breathe a Vesak Lantern Home with Your Breath
chamod  dhananjaya
chamod dhananjaya

Posted on AI-assisted

Kuudu: Breathe a Vesak Lantern Home with Your Breath

Presage SmartSpectra SDK Challenge Submission

This is a submission for the Presage SmartSpectra SDK Challenge

What I Built

Kuudu: Breathe the Lantern Home is a relaxing rhythm game where your breathing is the
controller. You guide a glowing paper lantern down a night river: breathe in and it rises, breathe
out and it drifts down. A slow, even rhythm carries it through floating festival gates, and every
gate in a row leaves another light on the water behind you.

The game is inspired by the kuudu, the paper lanterns hung across Sri Lanka for Vesak under the
full Poya moon. All the art and sound are original and generated in code: the eight-sided lantern
with its paper tails, the bamboo gates strung with lights, the river, the moon, and a soft drone
that brightens as you breathe in.

  • Drift: a calm two-minute run with wide gates.
  • Festival: three one-minute levels. Each asks for a slower breath (7.5 → 6.5 → 6 breaths per minute) and has narrower gates.

At the end, the lantern floats away and your whole run is drawn across the sky as a glowing
ribbon over the target wave, with your score, rhythm match and breathing pace.

Gameplay in Drift mode: a glowing pink and gold paper lantern floats low over a night river, between bamboo gates strung with festival lights. A dotted path shows the breathing wave ahead, a full moon shines above the hills, and a trail of 14 small lights glows on the water behind the lantern. Top right: score 2,612, 58 seconds left, streak 14.

Demo

Code

Kuudu: Breathe the Lantern Home

A relaxing rhythm game where you guide a glowing paper lantern down a night river with your breath.

Breathe in and the lantern rises. Breathe out and it drifts down. Follow the slow wave of the river to float through the festival gates, and the water lights up behind you.

The game is inspired by the kuudu, the paper lanterns of Vesak in Sri Lanka, under a full Poya moon. All artwork and sound are original and generated in code.

Built for the Presage SmartSpectra SDK Challenge with Electron and the SmartSpectra Node SDK.

▶ Watch the demo video (3 min)

Kuudu demo video: a glowing paper lantern over a night river, with the title Kuudu, Breathe the lantern home

Mid-run: the lantern floats between bamboo gates strung with festival lights, with a trail of lights on the river behind it

Get started

You need Node.js 24+, a webcam, and a free SmartSpectra API key.

  1. Get a free API key at physiology.presagetech.com.

  2. Install and add the key to a .env file in the project folder:

    git clone https://github.com/dhananjaya-hbc/Kuudu-Breathe-the-Lantern-Home.git
    cd Kuudu-Breathe-the-Lantern-Home
    npm install
    …
    Enter fullscreen mode Exit fullscreen mode

Setup takes a few minutes: npm install, add your free SmartSpectra API key to .env, then
npm run dev. Full instructions and troubleshooting are in the README.

How It Responds to Human Signals

Most vitals apps show a number. Kuudu turns the live breathing waveform into a game
controller, so the experience reacts to every breath, not to a 30-second average.

SmartSpectra signal How Kuudu responds in real time
Chest breathing waveform (breathing.upperTrace, ~30 samples a second) Moves the lantern on every frame
Breathing rate (with confidence) Your pace on the end screen, from readings the SDK marks reliable (confidence ≥ 45)
Validation status (no face, too dark, chest not visible…) Friendly hints such as "Find a little more light" that pause the game until the view is clear
Errors (network, usage limit…) The camera turns off, with a clear message and Try again

How the integration works:

  1. Electron + the SmartSpectra Node SDK. The main process hosts the SDK through bindSmartSpectraIpc. The sandboxed renderer runs SmartSpectraSDK from @smartspectra/node-sdk/renderer and decodes each metrics packet with decodeMetrics. The API key stays in .env, is read by the main process, and is handed over at runtime. It is never bundled.
  2. Settling in. Presage's docs note that the breathing waveform needs up to 30 seconds to become reliable, so each run waits until the SDK marks a sample stable (or 30 s) before calibrating.
  3. Guided calibration. Two slow breaths following a light. Lining the waveform up with the guide measures the signal's direction, your breath size, and the end-to-end delay. If the lantern ever moves the wrong way, pressing F flips it instantly.
  4. A signal pipeline built for steering:
    • drift removal over 20 s, so leaning back doesn't sink the lantern
    • scaling to your typical breath range (3rd–97th percentile, so a cough can't shrink every breath after it)
    • smoothing, then easing to 60 fps
  5. Fair scoring. Glow is a rolling correlation between the lantern and the target wave, shifted by your calibrated delay, so signal lag never counts against you. Jerky breathing or holding your breath while the wave moves makes the lantern flicker.

One lesson from building it: breathing.rate is a ~30-second average, so it can't steer anything.
The waveform's stable flag also follows the rate's confidence, which drops whenever you change
pace. So the lantern follows the raw chest waveform, and only the end-of-run pace waits for
confident readings.

The signal, calibration, gates, scoring and storage are covered by 58 unit tests.

Prize Categories

Most Creative or Delightful Use. Kuudu uses SmartSpectra as a game controller rather than a
dashboard. Your breath becomes a lantern drifting home through a Vesak festival, and every
reaction to the signal is something to see or hear:

  • the glow of the lantern
  • the flicker for a held breath
  • chimes and gate lamps that flare
  • river lights that grow with your streak
  • the final ribbon of your breathing across the night sky

Consent and Data Handling

  • The camera is off until you turn it on. Before the camera starts, a consent screen explains what is measured (the rise and fall of your chest, and your breathing rate), why (to move the lantern), where it happens, and what is saved. The camera turns on only when you press Start camera.
  • You can always see and stop it. A "Camera on" badge and a small mirrored preview of what the camera sees stay on screen the whole time the camera is on. Its Stop button or Esc turns the camera off immediately, from any screen. The camera also turns off at the end of every run and when the app closes.
  • Only two metrics are requested: the chest waveform and the breathing rate.
  • Where processing happens: the SmartSpectra SDK measures breathing on the computer. Presage's documentation describes vitals as computed on-device. The SDK connects to Presage to authenticate the API key and track usage.
  • SDK telemetry is turned off. The SDK sends diagnostic telemetry by default. Kuudu sets enableTelemetry: false, which per Presage's SDK Telemetry & Privacy documentation means the SDK starts no telemetry session and transmits nothing.
  • Storage and retention: video and images are never recorded or saved. Breathing data stays in memory during a run and is discarded afterwards. The only thing saved is your best score and its date for each mode, in local storage on your computer.
  • Deletion: Settings → Reset data deletes the saved scores. Uninstalling removes everything.
  • Sharing: none. There are no accounts, analytics, ads or tracking, and Kuudu's code contacts no server of its own.
  • AI services: none at runtime. Kuudu never requests the SDK's optional LLM insights.
  • Not a medical device. Kuudu is a relaxing rhythm game. It does not diagnose, treat or monitor any condition, and its readings are used for gameplay only.
  • No covert use. Kuudu measures only the person who started it, in front of the screen, with the camera badge visible.

Each promise is linked to the code that keeps it in
docs/consent-and-data.md.

Top comments (0)