HardYards/web/world/js
type-two 19c39acc8d Lane B S14: collateral exposure on the card + the night-5 invoice line (pool item)
COLLATERAL ON THE CARD. 'Winnable at $80' is an incomplete sentence on a yard
where letting a corner go also bills $180 of carport, so the card now prices
it — through world.collateralFor(), the one resolver (A's structKey fix), never
a second copy of that lookup in a panel. Deduped per STRUCTURE the way main.js
bills ('two beams letting go is one carport gone'): site_02's four carport
anchors read $180 total, not $720. The bill also rides on the margin-flag line
itself, because 'knife-edge' and 'knife-edge AND $180' are different authoring
decisions. An unpriced label renders UNPRICED — not scored, in red, never
'free' — which is the gutter bug's shape and the lie the card exists to prevent.

Verified A's structKey fix rather than assuming it: an editor-shaped carport
(id s1 + collateralKey) prices to $180, a second one (s2) also $180, and the
negative control (id s1, no collateralKey) reads null = not scored. My first
test reported a false alarm because I renamed a SHIPPED spec's id without the
palette's collateralKey — A's editor writes that field explicitly, so the
editor path was never broken.

THE NIGHT-5 INVOICE LINE (pool item, offered S13, accepted). Night 5's garden
is beyond saving by design, and the job sheet was the last surface still
dangling 'up to $45 / paid on what's left of the bed at dawn' — a maximum
nobody can earn, phrased as a rigging problem the player could solve.

NO ECONOMY CHANGE, deliberately. week.js's own comment forbids quote and settle
diverging ('the job sheet promises a number the invoice doesn't pay'), and
zeroing the quote would break that in the opposite direction — settle really
does pay the bonus proportionally. So the NUMBER stays and its CONDITION tells
the truth, which is the job sheet's own idiom:
  nights 1-4  'paid on what's left of the bed at dawn'        (unchanged)
  night 5     'scales with the bed at dawn — and tonight the ice takes it
               whatever you rig'
and the ledger names it too, because an unexplained small number next to
'night lost' reads as the player's failure:
  night 4  'garden bonus — 18% of the bed          +$8'
  night 5  'garden bonus — 18% of the bed, beyond saving from the start  +$8'

Verified in the running game on all five nights: flag fires on 5 only, every
quoted and paid figure identical (garden $45, total $136, bonus $8).

Selftest 374 passed / 0 failed / 0 skipped.
2026-07-18 16:29:41 +10:00
..
tests Lane B S14 gate 2.3: pin the editor's scored wind to the game's played wind 2026-07-18 16:16:29 +10:00
broom.js Lane D: calibrate the douse to B's real ponds; fix the sagging-belly refusal 2026-07-17 09:23:17 +10:00
camera.js Sprint 13 gate 2.5: two camera fixes — spawn framing, aftermath cloth-swallow 2026-07-18 01:18:29 +10:00
contracts.js Sprint 11 gate 1: three rulings — enum widened, carport priced, venturi reconciled 2026-07-17 17:20:11 +10:00
debris.js Lane C S13 gate 2.3 + D's sliver: ambient leaves from 30 km/h; hail pool hides at zero 2026-07-18 11:51:26 +10:00
editor_score.js Lane B S14: collateral exposure on the card + the night-5 invoice line (pool item) 2026-07-18 16:29:41 +10:00
garden.js Sprint 13: garden model exported as garden.js (B's gate-1.2 blocker) + applyMute(sky,on) as a value 2026-07-18 12:44:37 +10:00
hud.js Lane B S14: collateral exposure on the card + the night-5 invoice line (pool item) 2026-07-18 16:29:41 +10:00
interact.js Lane D: calibrate the douse to B's real ponds; fix the sagging-belly refusal 2026-07-17 09:23:17 +10:00
ladder.js Lane D: ladder survives a mid-carry knockdown, and the prompt names the right bracket 2026-07-18 01:00:01 +10:00
main.js Sprint 13 gate 1.4: NIGHT 5 RULED — the garden is beyond saving BY DESIGN, and the verdict teaches it 2026-07-18 14:11:58 +10:00
player.js Lane D: the player leans into the wind (gate 2.4 — as a root pose, not a clip) 2026-07-18 01:33:47 +10:00
player.sim.js Lane D: the player leans into the wind (gate 2.4 — as a root pose, not a clip) 2026-07-18 01:33:47 +10:00
rigging.js Lane B S13: consumable spares — close D's free-infinite-spares hole (count half) 2026-07-18 01:09:51 +10:00
rigging.selftest.js Lane B S13: consumable spares — close D's free-infinite-spares hole (count half) 2026-07-18 01:09:51 +10:00
sail.js Lane B S13: gate-3 smalls — rig.t was a determinism bug, + prep readouts 2026-07-18 01:04:02 +10:00
sail.selftest.js Lane B S13: gate-3 smalls — rig.t was a determinism bug, + prep readouts 2026-07-18 01:04:02 +10:00
skyfx.js Lane C S13 gate 2.3 + D's sliver: ambient leaves from 30 km/h; hail pool hides at zero 2026-07-18 11:51:26 +10:00
testkit.js Gate 0: name the harness dispute's cause; make skips real (testkit) 2026-07-17 10:21:01 +10:00
weather.core.js Add validateSiteWind — the site JSON's wind block fails loud (SPRINT10) 2026-07-17 15:30:00 +10:00
weather.js Lane C S13 correction: the bench flew site_02 funnel-OFF and tree-FROZEN; wild-night headline dies 2026-07-18 13:08:21 +10:00
week.js Lane B S14: collateral exposure on the card + the night-5 invoice line (pool item) 2026-07-18 16:29:41 +10:00
world.js Rule the gutter $90 (E's proposal adopted); teach collateralFor/wreckStructure the house; action B's effective-rating flag 2026-07-17 20:45:49 +10:00