clay-borg/workplans/CB-WP-0036-interactive-mode.md
tegwick bd9e168af5
Some checks failed
ci / check (push) Failing after 4s
CB-WP-0036 done: the pace flag and the first ornament declarations
--pace speed|interactive, defaulting to Speed. Nothing reads it yet, and
that is the point: it is the seam clay-animate attaches to, and a seam is
cheap now where a retrofit would not be. A misspelt pace is refused rather
than defaulting, because quietly falling back to Speed would look exactly
like the renderer being broken.

I3 is asserted rather than intended: the same scripted game at both paces
must produce a byte-identical serialised recording and the same end state
hash. Mutation-proven — leak the pace into the seed and it fails with "the
recording differs by pace, so a renderer has become mechanism".

specs/OrnamentRegister.md carries four declarations. This reverses the
reasoning written in T03 earlier, which said the first declarations would
come from F18's unvendored files: instances already existed. Hand order is
what prompted the category, and "who deals" was the maintainer's own
example. O3 is the interesting one — seat ORDER is mechanism because
GR-R08 rotates Lead, while where a seat is drawn is not.

I5 is executable: check_ornament_falsifier fails any row still declared
that names no falsifier, mutation-proven red on O1. Presence, never
adequacy, and the finding text says so.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-07 22:15:38 +02:00

7 KiB

id kind title status state_hub_workstream_id
CB-WP-0036 product Pace and ornamentation done 698651ed-cccd-46f2-84cc-07b0bdb85ad0

Purpose

structural tier  M   (a driver parameter and a declared vocabulary; the
                      animation architecture that made this L has moved
                      out of this repo)
chaos            d8 = 7  → no override
declared tier    M

Re-declared 2026-08-07, declaration 8 of chaos window 3.

Why this was rewritten, and what it used to say

Declared on 2026-08-07 as tier L, covering an animation layer, Rust-computed transitions over the journal delta, and a client/server interaction able to animate other players' moves. Chaos was d8 = 7, no override. No code was written, and the tier-L adversarial review was never run — which is the only reason this could be re-scoped rather than unwound.

The maintainer moved the animation out of clay-borg, and the reasoning is now specs/Ornamentation.md:

the basic simulator should have the relevant concepts of simulation and interaction, feedback mechanisms etc. with very simple ui concepts and frontend, backend interactions to keep the focus on the game and simulation core

So movement, timing and layering belong to a later, separate clay-animate; material behaviour to clay-physics beyond that. What stays here is the vocabulary, the boundary and the pace knob — and the invariants that keep the boundary real once something downstream exists to test it.

Two terms changed and the change is not cosmetic. "Ritual" became ornamentation, because half the category is material rather than ceremonial — card stock, a typeface, the drift of a discard. And the test is no longer "does it have a decision in it": choosing who deals is a decision and is ornamental. The test is whether the state hash moves, which is executable, and which settles the open question the previous version of this workplan left for a reviewer.

Task: the concept, in the spec that governs structure

id: CB-WP-0036-T01
status: done
priority: high
state_hub_task_id: "e7602796-cdb7-44cf-a39d-697b1e8e2a7f"

Controls:

  • the boundary has a falsifier, not just a diagram;
  • ornamentation is defined by a test something can run, not by taste;
  • it says what is deliberately not built and why.

Done 2026-08-07. specs/Ornamentation.md.

§1.1 makes the line executable by reusing state_hash — the same instrument that binds a trial note to a position (ADR-0019 D3).

§2 is the part that earns its place in this repo rather than a renderer's stylesheet. Calling something ornamentation is a claim that it does not matter, and this project's register is a list of times that claim was wrong — quantity in Tokens.csv, F18's four unread files, SOLVE offered where it could not act. So a declaration carries a falsifier, and provisional is a state it must be able to say out loud.

§3.1 restates ADR-0007 D5 one level up: downstream may read, may not decide. §3.2 refuses to design the port, because no consumer exists and an interface built against an imagined client is the same defect as a gate that cannot go red.

§5 gives five invariants, four of them checkable today. I3 — the same seed and decisions produce a byte-identical recording at any pace, through any renderer — is the falsifier for the whole split.

Task: the pace parameter

id: CB-WP-0036-T02
status: done
priority: medium
state_hub_task_id: "e978b93b-fcbd-4853-a27d-5eca00f9ca19"

--pace speed | interactive, defaulting to speed, and not --mode (taken by ScoringMode).

Controls:

  • I4 measured, not asserted: sim, trials and the benchmarks are unaffected — nothing, not little;
  • prefers-reduced-motion behaves as speed;
  • the flag exists before anything reads it, and that is deliberate: it is the seam clay-animate will attach to, and a seam is cheap while a retrofit is not.

Done 2026-08-07. --pace speed|interactive, Pace::Speed the Default.

I3 is asserted, not intended. pace_cannot_change_the_game plays the same scripted game at both paces and compares the serialised recording byte for byte, plus the end state hash. Mutation-proven: leak the pace into the seed and it fails with "the recording differs by pace, so a renderer has become mechanism".

A misspelt pace is refused rather than defaulting. --pace cinematic errors and names both values. Quietly falling back to Speed would look exactly like clay-animate being broken, and that is the seam this flag exists to be.

I4 needs no measurement yet and that is worth saying plainly: nothing reads pace, so the cost to sim, trials and the benchmarks is zero by construction rather than by benchmark. The measurement becomes real when something reads it.

Task: declarations, once there are any to make

id: CB-WP-0036-T03
status: done
priority: low
state_hub_task_id: "bf2a68b0-5985-40ff-b4f5-33c40d92cff0"

Ornamentation declarations per §2.1 — what is ornamented, why it does not bind, what would falsify it.

Done 2026-08-07. specs/OrnamentRegister.md, four declarations.

This reverses the reasoning written here earlier, which said the first declarations would come from F18's unvendored files and that vendoring was the trigger. That was wrong: instances already existed. Hand order is the one that prompted the whole category — the request to drag cards between slots — and "who deals" was the maintainer's own example. Waiting for F18 would have left the register empty while its instances sat in the conversation that created it.

The four: O1 hand order (provisional), O2 who shuffles and deals (provisional), O3 where a seat is drawn (rule-grounded — seat order is mechanism, GR-R08 rotates Lead; the drawn position is not), O4 typography and illustration (provisional, and nothing may be declared about Player_Mats or Glossary until they are read — F18).

I5 is executable: check_ornament_falsifier in loop-lint fails any row still declared that names no falsifier. Mutation-proven on O1 — strip its falsifier and the lint goes red. Three self-test controls: it catches a bare declaration, clears one that names a falsifier, and skips refuted rows as history. Presence, never adequacy, and the finding text says so — the same split as ADR-0018 D5.

No longer in this repo

  • the animation layer, transitions over the journal delta, cards summoned larger beside a seat and shrinking toward a target, discards drifting — clay-animate;
  • material simulationclay-physics;
  • hand sorting, which was T05 here: it is presentation of a hand whose contents are mechanism, so it goes with the renderer. The constraint survives the move and is now I1: sorting must not move state_hash, because a hash that moved would break every trial note's binding.