Apps · Screener

The cut never leaves the edit bay

A conferencing app re-encodes your picture twice and crushes the grade your colorist spent a day on. Screener does not touch it: the file is read in slices where it sits, the slices cross a direct connection, and the client’s browser plays the exact bytes on your disk. No upload, no copy in a bucket, no screen share.

0 bytes uploaded the channel introduces the browsers; the film goes straight between them
6–10 honest seats one copy leaves per viewer, so a 3 Mbps cut to six people is 18 Mbps up — the figure is shown before you press play
flat memory at the far end played video is dropped behind the playhead, so a two-hour film never needs two hours of buffer
sha-256 on the approval sign-off records the hash of the exact file that played, and how many notes were still open
How it works

A byte stream, not a file transfer

The player is handed chunks as they arrive and drops what it has played. Sending waits on the channel’s own buffer rather than on a timer, so a slow seat slows its own stream and nobody else’s.

  • Preflight before anyone is invited. The container is sniffed and the whole file is hashed. A plain MP4 with its index at the end is refused now — with the ffmpeg command that fixes it — rather than stalling five minutes into the screening.
  • The door is host-locked. A browser that reaches the room gets no bytes until you admit it.
  • Everybody sees the same frame. You pace the room; drift is absorbed by playing imperceptibly faster or slower, never by a visible seek.
  • Approval is a certificate. It hashes the file that actually streamed into an append-only chain, with the number of notes still open at that moment. “Looks great!” in a chat thread is worth nothing on a disputed invoice.
meridian · cut 4preflight passed
  webm · plays from a byte stream
  2.1 Mbps per seat
  6.3 Mbps up at 3 seats
  sha-256 9c8f736e…1715

  SEATS            3 of 10
   priya    100% sent  12s buffered
   marcus   100% sent  9s  buffered
   ana       74% sent  3s  buffered

  NOTES              2 open
   00:41:22  the door cut is late
   01:02:08  grade drifts warm

What “the client never holds the file” actually means

There is no download button and no file on disk: chunks are appended to the player and the played ones are dropped. That is cooperative eviction — the page drops them because the page is written to. A determined viewer running a modified client can keep what it is sent, and anything that reaches a screen can be filmed off it. This is a review tool that stops a cut drifting into somebody’s downloads folder; it is not DRM, and a page that claimed otherwise would be lying to the person who most needs the truth.

The container, honestly

A browser plays a byte stream, not a file. WebM works as it is, and so does fragmented MP4. A plain MP4 keeps its index at the end, so a player would need the last bytes first — and that is the file most people actually have. Today Screener refuses it with the one-line ffmpeg command that converts it. In-browser remux is not built yet, and until it is, that first step is real friction rather than a footnote.

Not a broadcast platform

The host sends one copy per viewer. A 3 Mbps cut to six people is 18 Mbps of upload, which is a screening, a review or a film club — not an audience. The number is on screen before you press play, because the alternative is a room that degrades and blames the wifi.

Pricing

What it costs

Commercial — per screening room, per month

A licence per bay, checked when the console opens. Without one the screening still runs and every certificate it writes is stamped licensed:false.

How it's built

The part that matters, in the open

Sending waits on the channel's own buffer and resumes on bufferedamountlow — never on a fixed sleep, which is a guess about somebody else's network.

js/reel.js
send: (buf) => dc.send(buf),
bufferedAmount: () => dc.bufferedAmount,
readyState: () => dc.readyState,
onLowWater: (threshold, fn) => {
    dc.bufferedAmountLowThreshold = threshold;
    dc.onbufferedamountlow = () => { dc.onbufferedamountlow = null; fn(); };
},

Taken from this app's source, not written for the page. Built on the Messaging Platform SDK.