teaser v8: a 58 s story instead of a feature list (the game is done; the stores pile up; one missing line; hand it to your AI; a montage of builds, screenshots, products, forms, consoles; the scan turns green; one button is yours; Waiting for review; the end card), one short line per scene, cuts on the 120 BPM beat; music rewritten for the arc (calm, tension, near silence, a driving build, a stop, a resolve), mastered with one gain instead of dynamic loudnorm; the pile shows real console plan, Data safety CSV and price sheet lines, the builds beat real apple / play build dry runs; desktop.ts captures submit-ready (Send for review before the press); tests check every line, the beat-aligned cuts and the caption times; two unused teaser icons dropped
This commit is contained in:
parent
d5ffc159c0
commit
0b6c8cd7a0
11 changed files with 1117 additions and 1041 deletions
|
|
@ -1,76 +1,74 @@
|
|||
# storebound teaser (62 s, 16:9)
|
||||
# storebound teaser (v8, 58 s, 16:9)
|
||||
|
||||
A calm, scripted motion piece: from an empty folder to everything ready on both stores. Every frame is a pure function
|
||||
of time, rendered from an HTML/CSS/JS timeline in headless Chrome and encoded with ffmpeg. The music and the sound
|
||||
design are original and synthesized from scratch in the same browser (Web Audio `OfflineAudioContext`): no samples,
|
||||
no downloaded audio, nothing to license.
|
||||
A short story, not a feature list: the game is done, the stores pile up work, one missing line sends you back to the
|
||||
start, so you hand it all to your AI, it does the work, and one button stays yours. Little text (one short line per
|
||||
scene at most, big and calm), real product footage only, and the music carries the arc: calm, tension, near silence,
|
||||
a driving build, a stop, a resolve. Every frame is a pure function of time, rendered from an HTML/CSS/JS timeline in
|
||||
headless Chrome and encoded with ffmpeg. The music and the sound design are original and synthesized from scratch in
|
||||
the same browser (Web Audio `OfflineAudioContext`): no samples, no downloaded audio, nothing to license.
|
||||
|
||||
One idea per scene, 4-5 s each (whole half seconds, so every cut lands on a beat of the music), one camera move per
|
||||
scene (a quick ease-out that settles before the cut), short dissolves on the cuts, no whips or rapid montages. Long terminal output streams faster rather than being cut. Each scene
|
||||
has one plain-English caption at the top, fully on screen for at least 3 s; below it, the real product.
|
||||
120 BPM: every cut lands on a beat (whole half seconds). The story scenes dissolve and drift slowly; the montage cuts
|
||||
hard on the beat with one quick push each.
|
||||
|
||||
| s | shows | caption |
|
||||
|---|---|---|
|
||||
| 0-4.5 | the demo game's icon, "Done"; the stores' to-do list line by line; one rejection mail (Guideline 2.1) | Your app is done. The stores are not. |
|
||||
| 4.5-9 | an empty folder; `bunx storebound init` is typed; the files it creates list in | storebound takes it from an empty folder. |
|
||||
| 9-14 | the prompt "Get my app ready for both stores."; `storebound release plan 1.0.0`: 26 steps in fix order | You ask once. It plans every step. |
|
||||
| 14-19 | the demo game's store text in 4 languages; its renders in 7 store sizes x 4 languages | Store text and screenshots. Every language, every size. |
|
||||
| 19-23.5 | `play products --dry` (174 regions), then `catalog diff` (175 / 174 region prices, 0 mismatches) | In-app products on both stores, priced in 175 countries. |
|
||||
| 23.5-28.5 | the scan's declarations proposal: detected answers with file:line, one "ask owner" line highlighted; 768 Data safety answers | The forms, answered from your code. It asks what it can't know. |
|
||||
| 28.5-33.5 | `storebound console plan apple-app-privacy`: steps, answer sheet, the never-press list and "Final button (the owner's): Publish" highlighted (40 steps, 92 answers); then the desktop app's console plan panel (App info) with that real plan, at the final button the owner keeps | No API? Your AI fills the console. It stops at Publish. |
|
||||
| 33.5-38.5 | `storebound scan`: three findings, each with a plain reason; fixed, the re-scan is clean | It catches rejections before Apple does. |
|
||||
| 38.5-43 | the desktop app's Portfolio: every app of three studios, App Store and Google Play per app, rollout %, crash-rate sparklines | Stop switching between two consoles. Every app, both stores, one window. |
|
||||
| 43-47.5 | the Growth chart (visx) with the pointer sweeping across it, the crosshair and tooltip moving day by day; then the Health tab's crash rate, swept the same way | Installs, conversion and crashes, charted. |
|
||||
| 47.5-52 | the Prices tab: products x key territories, both stores' prices per country, the gaps between them marked | Products and prices on both stores, side by side. |
|
||||
| 52-57 | Releases › Send for review, back from App Review (UNRESOLVED_ISSUES): the rejected version item ("marked resolved when you resubmit"), build 52 picked, the pointer resting on Resubmit | Rejected? Fix it, resubmit in one click. |
|
||||
| 57-62 | Submit for review: the plan panel with the dry run (nothing sent yet) and the pointer resting on "Continue" (it never clicks); then the card with the new submission "Waiting for review"; then the end card: storebound.dev, Open source · CLI · Desktop app | You press Submit. That's it. |
|
||||
| s | shows | text | music |
|
||||
|---|---|---|---|
|
||||
| 0-5 | the demo game's own screens (its store captures), floating, a slow drift | The game is done. | calm: a warm D major pad, a slow pluck |
|
||||
| 5-11 | store work lands card after card, faster and faster: the App Privacy answer sheet and console steps, the Data safety CSV (768 rows), the screenshot sizes, the price sheet | Then come the stores. | tension: B minor, a growing low pulse, a ticking clock, a riser; a thud per card |
|
||||
| 11-15 | one real scan finding (BLOCKER 5.1.1(v), at Planner/LoginView.swift:11) grows until it fills the frame; the picture goes dark | One missing line, and you start over. | a low boom, a dark drone sinking to nothing |
|
||||
| 15-19 | in the dark, one request is typed to the AI agent: "Get this game ready for review on both stores." | So I handed it all to my AI. | near silence: room tone, key clicks, a swell into the drop |
|
||||
| 19-23 | `apple build --dry` and `play build --dry`: build 52, versionCode 52 | Builds. | the drop: kick, bass, arpeggio |
|
||||
| 23-27 | the demo game's renders: 7 store sizes x 4 languages | Screenshots, every size. | + hats |
|
||||
| 27-30.5 | `play products --dry` (174 regions), `catalog diff` (175 / 174 region prices, 0 mismatches) | Products, 175 countries. | + claps |
|
||||
| 30.5-34 | the scan's declarations proposal (one "ask owner" line), the Data safety rows filling, 768 answers | Forms. | + sixteenths |
|
||||
| 34-37 | `console plan apple-app-privacy`, then the desktop app's plan panel with that real plan, at the owner's Publish | Consoles. | + a brighter lead |
|
||||
| 37-42 | `storebound scan`: five findings turn green one per beat, the re-scan is clean (0 blocker, 0 high) | Nothing left for a reviewer to catch. | the drive peaks, a chime per fix |
|
||||
| 42-48 | the desktop app's Releases › Send for review (build 52 picked); the camera settles on "Submit for review", the pointer rests on it | One button is yours. | the music stops; a quiet low pulse |
|
||||
| 48-53 | the click; the same card shows the new submission "Waiting for review" (the app's own state) | (none) | the resolve: a wide D major chord, bells |
|
||||
| 53-58 | the storebound mark (brand/logo-mark-256.png) | From an empty folder to Submit. · Open source · storebound.dev | the chord holds, fades |
|
||||
|
||||
v6's "Both stores, one view. Ready for review." scene (release timeline, Store readiness) does not fit the 62 s; its
|
||||
point lives on in the submit scene's dry run. The native confirm dialog that follows "Continue" is the system's
|
||||
(macOS), outside the web view, so the video shows the app's own plan step before it and never draws a system dialog.
|
||||
The demo game has 4 languages (en, tr, ja, ar), so the screenshot beat says "every size", not a language count.
|
||||
The video shows no drawn system dialog and no mail: between the click and "Waiting for review" the real app shows its
|
||||
own dry-run plan and then the system's confirm dialog, which the story skips.
|
||||
|
||||
| file | what |
|
||||
|---|---|
|
||||
| `script.js` | the timeline: scenes in seconds, camera moves, captions, every line shown, the sound cues |
|
||||
| `desktop.ts` | the desktop frames: apps/desktop's Vite dev server in fixture mode (`VITE_FIXTURES=1`, example.com-style data), captured headlessly in dark at 1280x800 @2x with the dev markers hidden, plus `boxes.json` (callout and pointer targets, the hover sweeps) -> `out/desktop/`. The chart hovers are real: the mouse moves across the chart in small steps and a frame is taken for every day the tooltip shows; the video moves its pointer the same way and shows the day it has reached. The console plan panel gets the real `storebound console plan apple-app-privacy --json` of a fresh `storebound init` folder in place of the fixture's shortened plan; the send-for-review frames press "Read state", pick build 52 and open the plan panel as the owner would; the "Waiting for review" frame serves the fixture's apple status with the new submission waiting |
|
||||
| `desktop.ts` | the desktop frames: apps/desktop's Vite dev server in fixture mode (`VITE_FIXTURES=1`, example.com-style data), captured headlessly in dark at 1280x800 @2x with the dev markers hidden, plus `boxes.json` (ring and pointer targets) -> `out/desktop/`. The console plan panel gets the real `storebound console plan apple-app-privacy --json` of a fresh `storebound init` folder; the send-for-review frames press "Read state" and pick build 52 as the owner would (`submit-ready`), and the "Waiting for review" frame serves the fixture's apple status with the new submission waiting. It also captures the frames the site uses (`site-shots.ts`) |
|
||||
| `index.html` + `teaser.js` | the picture; `window.teaser.seek(t)` sets every element for time `t` |
|
||||
| `music.js` | music (D major, one chord per scene: pads, a soft pluck every half second, a quiet sub) and soft sound design: a bell and an airy swell on each scene change (each on a beat), key clicks, quiet ticks, chimes for the fixes and the submission |
|
||||
| `render.ts` | frames at 60 fps blended to 30 fps -> ffmpeg (H.264 high, yuv420p), sound -> loudnorm (-16 LUFS, -1.5 dBTP), mux, poster, the 1280x720 web version |
|
||||
| `music.js` | music and sound design, one section per part of the arc (see the table) |
|
||||
| `render.ts` | frames at 60 fps blended to 30 fps -> ffmpeg (H.264 high, yuv420p); sound: one gain to about -16 LUFS with the true peak at or below -1.5 dBTP (no dynamic normalization, so the quiet parts stay quiet), mux, poster, the 1280x720 web version |
|
||||
| `icons/` | the mouse cursor and the UI icons: Phosphor files copied unchanged by `bun tools/site-icons.ts` (no hand-written SVG; CI checks it) |
|
||||
|
||||
Every CLI line in the video is real output, and `tests/teaser.test.ts` runs each command and checks every line (the
|
||||
clock prefix and the "(0s)" timer left out):
|
||||
clock prefix and the "(0s)" timer left out), in a fresh `storebound init` folder with two products:
|
||||
|
||||
- `storebound init` in an empty temp folder.
|
||||
- `storebound release plan 1.0.0`, `play products --dry` and `catalog diff` in that folder, with the stores answered by
|
||||
`tests/helpers/teaser-store-mock.ts` (preloaded through a `bunfig.toml` in the folder, so the children `release plan`
|
||||
starts use it too; nothing reaches the network): a brand-new app record with nothing on it for the plan and the dry
|
||||
run, then the two products on both stores for the diff. Regions: the App Store's 175 storefronts, Google Play 174
|
||||
(the count Play answered in a recorded read-only run).
|
||||
- `storebound scan` of `tests/fixtures/scan/teaser` (findings, declarations proposal) and of `teaser-fixed` after the
|
||||
fixes, and the Data safety answer count of `storebound check`.
|
||||
- `storebound console plan apple-app-privacy` in the init folder (offline): the lines in order, the step and answer
|
||||
counts of the pill, the never-press list and the owner's final button.
|
||||
- `storebound console plan apple-app-privacy` (offline): the answer sheet and step lines of the pile, the plan lines of
|
||||
the consoles beat, the never-press list and the owner's final button.
|
||||
- `storebound play data-safety --dry` (the CSV lines), `storebound check` (768 rows), `storebound prices ppp --offline
|
||||
--dry` (the price rows).
|
||||
- `storebound apple build --dry` and `storebound play build --dry` in a minimal Capacitor project.
|
||||
- `storebound play products --dry` and `catalog diff`, with the stores answered by
|
||||
`tests/helpers/teaser-store-mock.ts` (preloaded through a `bunfig.toml` in the folder; nothing reaches the network).
|
||||
- `storebound scan` of `tests/fixtures/scan/teaser` (the 5.1.1(v) finding, all five findings, the declarations
|
||||
proposal) and of `teaser-fixed` after the fixes.
|
||||
|
||||
The plain reasons under the findings and the callouts on the desktop frames are annotations, set apart from the CLI
|
||||
text. The store text is `examples/demo-game/store/shots/copy.json`, the screenshots its real renders, the app icon its
|
||||
`store/icon/icon.png`. The mail row is fictional: no real names or addresses, no mail-app branding. The test also checks
|
||||
the timing (scenes 4-5 s in whole half seconds, captions on screen at least 3 s, 60-65 s in total, 16:9 only, a chord
|
||||
for every scene) and that every desktop frame a
|
||||
scene names is one `desktop.ts` captures, and, where they were captured, that each file is there (2560x1600 JPEG, one
|
||||
sweep frame per hovered day).
|
||||
The test also checks the timing (every cut on a half-second beat, scenes 3-6 s, the montage at 19-37 s speeding up with
|
||||
cuts rather than dissolves, captions of at most 8 words fully on screen at least 2.5 s inside their scene, 56-62 s in
|
||||
total, 16:9 only), that the game screens and screenshot tiles are the demo game's own, and that every desktop frame a
|
||||
scene names is one `desktop.ts` captures (where they were captured: each file there, 2560x1600 JPEG).
|
||||
|
||||
## Render
|
||||
|
||||
Needs Bun, ffmpeg, Playwright (repo devDependency; Playwright's Chromium or an installed Google Chrome) and the demo
|
||||
game's store renders:
|
||||
game's store captures and renders:
|
||||
|
||||
```sh
|
||||
cd examples/demo-game && bun serve.ts & bun ../../cli/index.ts shots capture && bun ../../cli/index.ts shots fonts && bun ../../cli/index.ts shots render
|
||||
# from the repo root
|
||||
bun media/teaser/render.ts > media/teaser/out/render.log 2>&1 & # master, sound, poster, web version: about 20 min
|
||||
bun media/teaser/render.ts --desktop # capture the desktop app frames again (after a UI change)
|
||||
bun media/teaser/render.ts --stills 2,30.5,57.8 # PNG stills in out/stills for a quick layout check
|
||||
bun media/teaser/render.ts --stills 2.5,13.5,46 # PNG stills in out/stills for a quick layout check
|
||||
bun media/teaser/render.ts --sound # the music only (out/music.wav)
|
||||
bun media/teaser/render.ts --serve --port 8750 # live preview: /index.html?play=1 (or ?t=12.5)
|
||||
```
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue