CB-WP-0046: the rule the placement encodes, and a log that names its rules
Some checks failed
ci / check (push) Failing after 4s
Some checks failed
ci / check (push) Failing after 4s
CB-WP-0045 left "nothing explains what a scope does" open and gave a FALSE reason: that scoping is our Variant so no printed sentence exists. The H2 package ships Rules_Text.csv -- twenty-two passages of player-facing rules -- and nothing in clay-borg had ever read the file. A wrong reason for an open item is worse than an open item; it retires the question. Filed as F26 against ground-game: a package that adds a FILE is invisible where one that adds a column is not. The scope rule now renders under the table in the edition's own words, only when a non-global scope is in play, matched by heading rather than row number, and absent (never paraphrased) if the edition drops it. The trial log stamps its variant on the begin marker -- a session property, not an eighth column -- read off state.variant rather than the --variant flag, because a bare `state.variant = v` leaves H2 inert and a flag-stamped log would put false provenance on real player words. An unstamped log reports `unrecorded`, never `ground-darvo-r0`. Six mutations, six red. The sixth is the finding: every trials.py fixture built its marker out of BEGIN, so nine checks followed BEGIN away from what hotseat.rs writes and stayed green while real logs broke. A fixture built from the constant under test cannot test the constant -- the control is now a literal, asserted from both sides. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
parent
df65e2dee1
commit
de25c4cae0
10 changed files with 986 additions and 12 deletions
|
|
@ -1306,6 +1306,25 @@ fn body(s: &mut String, view: &GroundView) {
|
|||
s.push_str("<div class=\"card\">no problems in play</div>");
|
||||
}
|
||||
s.push_str(&table_svg(view));
|
||||
// CB-WP-0046: the placement is legible, the RULE it encodes was not.
|
||||
//
|
||||
// Shown only when a non-global scope is actually on the table — under
|
||||
// the baseline every Problem is everyone's, and an explanation of a
|
||||
// distinction that is not in play is noise. Same discipline as the
|
||||
// GROUND modes: at the thing it explains, and closable.
|
||||
if view.problem_markers.values().any(|m| {
|
||||
m.scope
|
||||
.is_some_and(|x| x != games_ground::edition::StressScope::Global)
|
||||
}) {
|
||||
if let Some(rule) = stress_scope_rule_text() {
|
||||
let _ = write!(
|
||||
s,
|
||||
"<details class=\"card\"><summary>what a Problem\u{2019}s scope does\
|
||||
</summary>{}</details>",
|
||||
esc(&rule)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
s.push_str("<h2>seats</h2><div class=\"row\">");
|
||||
for (id, p) in &view.players {
|
||||
|
|
@ -1490,6 +1509,20 @@ fn ground_modes_text() -> Option<String> {
|
|||
.map(|c| c.rules_text)
|
||||
}
|
||||
|
||||
/// What a scope DOES, in the edition's words (CB-WP-0046).
|
||||
///
|
||||
/// CB-WP-0045 left this open and gave the wrong reason: *"the scope rule
|
||||
/// is ours (a Variant), so there is no vendored sentence to render."* The
|
||||
/// H2 package ships `Rules_Text.csv` and its `Problems / Stress scope`
|
||||
/// passage is exactly the rule. Nothing read the file.
|
||||
///
|
||||
/// **The placement was legible and the rule it encodes was not** — a
|
||||
/// player could see a card sitting on their Bond lines and have no way to
|
||||
/// learn that its Stress presses everyone on those lines.
|
||||
fn stress_scope_rule_text() -> Option<String> {
|
||||
games_ground::edition::stress_scope_rule()
|
||||
}
|
||||
|
||||
/// A GROUND sub-choice, in words, naming whoever it touches.
|
||||
fn ground_choice_label(c: &games_ground::GroundChoice) -> String {
|
||||
use games_ground::GroundChoice as G;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue