Skip to the content
Jess. All projects

Stack · Free menu bar app for macOS

Sit like you meant to. Stack remembers what that looked like.

Physios have a phrase for it: stack your spine. Ears over shoulders over hips. It is easy to do for about four minutes, and then there is a deadline and the screen gets closer.

Stack lives in your menu bar. You record a baseline once, by sitting the way you actually want to sit. After that it takes a webcam frame every thirty seconds, measures where your head sits relative to your shoulders, and compares it against that baseline. When you have been out of position for a sustained stretch, a small popup appears. It never takes keyboard focus, so it cannot interrupt a sentence you are in the middle of typing.

Download Stack

Free macOS about 276 KB

  • Runs entirely on your Mac The pose model, the comparison and the history all stay on the machine.
  • No account, no server, no telemetry There is nothing to sign up for and nothing keeping score somewhere else.
  • One network request, ever A single 9.4 MB model download at install. After that it is offline.

There is one exception, and it is switched off when the app ships: an optional setting that sends a cropped image to Google’s Gemini for a second opinion on a small random sample of checks. Leave it off and the one-request figure above is literal.

Ears over shoulders over hips. Stack measures how far the first has drifted from the other two, and compares that against how you sat on the day you calibrated it.

What it does

Three things, on a loop.

  1. It looks, every thirty seconds.

    One webcam frame goes into Google’s MediaPipe pose model, which runs on your machine. Nothing is uploaded, and nothing waits on a server to come back with an answer.

  2. It compares you against you.

    You calibrate once, sitting the way you want to sit. That becomes the reference. The score is drift from your own baseline, not a verdict handed down from a table of ideal humans.

  3. It waits before it says anything.

    One bad frame is a stretch or a reach for the coffee. The popup only arrives after you have been out of position for a sustained stretch, and it is deliberately non-activating: it will not steal your cursor or your keystrokes.

Every check is written to a local SQLite file. When you want to look at it, Stack builds an HTML dashboard that opens straight from disk, with no connection involved.

What it refuses to do

The interesting part is what it will not tell you.

Posture apps are generous with themselves. A score, a streak, a percentage improvement, and no mention anywhere that the number is resting on nothing. Stack was built the other way around. When it cannot back a claim, it does not make the claim, and it tells you why the space is empty.

It blanks your trend when you recalibrate.
Record a new baseline and the week-over-week comparison goes blank and explains itself. Scores from before and after a recalibration are measured against different references, so setting them side by side would produce a number that looks meaningful and is not. It would rather show you nothing.
It will not call its measurement a craniovertebral angle.
There is a clinical measure of forward head posture by that name. What Stack computes from a webcam is not it. The dashboard says so, in its own words, on its own page, rather than borrowing medical authority it has not earned.
It will not send a picture it cannot narrow down.
If you switch the optional second opinion on, it sends a cropped image for a small random sample of checks. When it cannot isolate a person in the frame, it sends nothing at all. Falling back to the whole picture would have been the easy behaviour and the wrong one.
It will not invent a reading.
If the camera is connected and the frame comes back unusable, the record says exactly that. A gap in the history is a fact worth keeping. A number filled in to keep a chart smooth is not.

None of this makes the app better at seeing you. It makes the numbers it does show you worth reading.

Requirements and setup

Getting it running.

  • macOS
  • A webcam, built-in is fine
  • Homebrew and uv
  • Python 3.12, which uv installs for you

Download the zip, unpack it, then run these from the project folder:

uv sync
./scripts/fetch_model.sh
uv run python scripts/identify_cameras.py
uv run python scripts/calibrate.py
./run.sh

If identify_cameras.py says No cameras found the first time, run it again. That first camera access is what triggers the macOS permission prompt, and OpenCV does not wait around for your answer.

calibrate.py is the step that matters. Sit the way you want to be sitting for the rest of the day, and let it take the frame. Everything the app says afterwards is measured against it. The download is small, 276 KB, because the 9.4 MB pose model is fetched by fetch_model.sh rather than shipped inside the zip.

Limitations

What it cannot do.

  • It sees what a desk webcam sees, which is roughly your head and shoulders. Your lower back is not in the frame, and Stack has no opinion about it.
  • Move your chair, your desk or your camera and the baseline stops describing you. Recalibrate, and expect the trend to blank itself when you do.
  • Lighting is part of the measurement. A dark room or a bright window behind you gives the pose model less to work with, and the history will show the gaps rather than paper over them.
  • It is not a medical device and it diagnoses nothing. It measures one angle and tells you when that angle has drifted from where you put it.