1
0

feat(brand): re-shoot everything at the new engine, and make it one command

**Seven new shots**, because the world grew the most photogenic things in it
after the last pass: `sfo`, `lax`, `golden-gate`, `bay-bridge`, `freeway`,
`california-relief` and `pacific-sea`. All nine existing ids are unchanged — the
manifest emits a `ShotId` union that lumbridge-v4 imports, so ids are added and
never renamed.

**A shot can now aim itself.** The chapter list has no camera for SFO, LAX, the
bridges, the freeway or the open sea, and the engine has no `?pose=` back door,
so a shot points itself by driving the app's own inputs: a click on the plan view
slides the orbit target to a lat/lng while keeping the chapter's stance, wheel
notches set the standoff, and a drag sets azimuth and elevation. The plan view's
pixel-to-coordinate map is solved at runtime from three hovers of
`#minimap-readout` rather than hard-coded, so it survives a board resize or a
restyle of the widget.

**The tera share card was a picture of the wrong thing, and had been.** Its art
came from `keyboard.press("2")`, which had landed on the California board's drive
mode once the default board changed — so the card under the headline "Cities from
above." was a chase camera on US-101, showing metre-scale cars driving between
kilometre-wide buildings, with the DRIVE readout and the mode pill baked into the
art. It renders, it looks deliberate, and it is why an unguarded key press has no
place in a capture script. `capture.mjs` now clicks an indexed chapter and
asserts its `shortLabel` the way `shots.mjs` does, waits on `#boot` and
`#chapters` instead of sleeping twenty seconds, and gives each card its own hour.

**`npm run refresh` is the durable half.** One command: build, stills, cards,
films, both manifests, and a hashed before/after diff of every deliverable. It
fails loudly and specifically on the two conditions that otherwise produce
confident wrong output — the renderer coming up as SwiftShader, and a chapter
`expect` guard firing. `--stills-only` / `--cards-only` / `--films-only` compose,
`--dry-run` lists the plan without opening a browser, and
`shots.mjs --list` prints the whole shot plan — board, chapter, expect, aim, both
hours — which is what to run first when a guard does fire.

It also re-stamps `PROVENANCE.json`, narrowly: only entries whose origin is
`repository-generated` and whose `generator` names a script the run actually
executed, by literal hash substitution rather than re-serialising the file.
Without that, every legitimate card re-shoot leaves `npm run provenance` red.

**Every film re-shot.** They were at `9c9e78f`, captured 2026-08-07, and predated
the tone mapping, the reflective sea, the sky dome, terrain shadows, the rebuilt
California board, SFO, LAX, both bridges and the moving aircraft.

Tests 1137, typecheck, build, eight budget cells and every provenance and licence
check pass.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-08-22 12:49:06 -07:00
parent f81d5218d4
commit 2aa4049258
12 changed files with 1419 additions and 115 deletions
+10 -2
View File
@@ -37,7 +37,7 @@ function twoDoors(): Plugin {
<title>Spaces — a studio you can walk around</title>
<meta
name="description"
content="Three buildings you can walk around: a live/work studio above San Francisco, a courtyard block in the LA Arts District, and a hangar at Alameda Point. Real sun, real hours, the lights on at night, the microphone on the desk. Rendered in the browser from a data file anybody can copy. Apache-2.0, self-hostable."
content="Three buildings you can walk around: a live/work studio above San Francisco, a courtyard block in the LA Arts District, and a hangar at Alameda Point. Real sun, real hours, the lights on at night, the microphone on the desk and the speaker on the machine. Rendered in the browser from a data file anybody can copy. Apache-2.0, self-hostable."
/>
<link rel="canonical" href="https://office.lumbridgecorp.com/" />
@@ -53,9 +53,17 @@ function twoDoors(): Plugin {
<meta property="og:image:type" content="image/png" />
<meta property="og:image:width" content="1200" />
<meta property="og:image:height" content="630" />
<!--
Describes the card as it is actually composed, which is not the same thing
as describing the app. FURNITURE.BARE takes the plan view off the share
card — the card supplies its own typography and the app's panels shrunk to
1200x630 are unreadable furniture — so an alt that promises "the plan drawn
beside it" is describing a screenshot nobody is looking at. Re-read it
against public/og-office.png whenever capture.mjs changes the framing.
-->
<meta
property="og:image:alt"
content="A studio seen from above as a cutaway model: desks, seating and planting laid out across one floor, the plan drawn beside it, people at their seats."
content="A studio interior rendered as an open-topped model and seen from above: two desks of monitors, chairs, shelving, planting, a kitchen counter and floor-to-ceiling glazing, with a humanoid standing on the floor beside the bench."
/>
<meta name="twitter:card" content="summary_large_image" />