Skip to content

BDSP AutoStory: segments 00 and 01 on the shared story steps, simulated end to end - #124

Closed
dayfine wants to merge 20 commits into
bdsp/mvp-v3from
bdsp/story-steps
Closed

dayfine wants to merge 20 commits into
bdsp/mvp-v3from
bdsp/story-steps

Conversation

@dayfine

@dayfine dayfine commented Nov 1, 2026

Copy link
Copy Markdown
Owner

Depends on #121 and the shared story steps in #122 (merged in). Not for console yet; the MVP branches stay as they are.

#121's segments 00 and 01 were rows of wrapped functions; they are now one table of shared story steps (PokemonBDSP_AutoStory_StoryTable) that reads like #120's, with 00.04b to 00.04d fully declarative and every other step calling its old function through a registered variant. Retries come from the shared policy and options (attempts per checkpoint, default 3 where the table had 20; stop at the first failure); the checkpoint_reattempt_loop: attempt N failed line is still logged for each failed step. A new PokemonBDSP::AutoStory - Simulation suite runs 00.00 to Floaroma against a fake game that plans every route and walk on the built-in JSON maps: order and saves, start/end ranges, a blackout in 00.04b's training resetting to its save, three attempts then a stop, start poses chaining, the door exit's first not-a-room look; the Mart lady events test gains the Lab sign re-anchor case. Nothing was run on a Switch.

🤖 Generated with Claude Code

https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E

dayfine and others added 20 commits November 1, 2026 09:53
A story checkpoint as a list of StorySteps (route, legs, step onto a
trigger, talk, YES/NO, scene, battle, train, heal, shop, save, ready for
a boss, and a game-only step), plain data, built into engine events by
build_story_checkpoint(). Each event asks the game's StoryStepExecutor
to do its step: one virtual per kind, failing as unsupported unless the
game overrides it. Poses are the game's (TilePose); skip_if names
conditions the executor answers.

Tests run tables against a fake executor: event order, skip_if, pose
propagation, failure naming, unsupported kinds, a segment with a reload,
and lint.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
SegmentPolicy is now where retries are set: attempts per checkpoint
(default 3), stop at the first failure (no reload; the game stays where
it failed), and in-place recoveries per event (SegmentHooks::recover,
then the event again) before a checkpoint is reloaded, default 0.
run_segment reports each checkpoint's attempts and recoveries and logs
"[Checkpoint] 00.07: passed on attempt 2 (1 reset)" and "[Segment] 00:
2 of 3 checkpoints one-shot", so the one-shot rate can be tracked.

StoryRunOptions is the program-option group both AutoStory programs
embed: "Attempts per checkpoint" and "Stop at the first failure". A
story step's skip_if condition is a run flag unless the game overrides
holds(). Tests: the policy against the fake executor (attempts then
fail, stop at first failure, recover in place, one-shot report).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
00.04b (after the catch, to Dawn in Jubilife) was one function; it is now
a table of the shared story steps (Data/PokemonBDSP_AutoStory_Segment00Steps):
find the save, to the catch grass, train 3, into Sandgem, below the
Center's sign, taps to its door, heal, Potions, back to Route 202 through
the signs' gap, save, north past the trainers, the stairs, Dawn's scene.
Steps 2-8 skip on the "has_potions" flag and 9-10 on "potions_saved", set
by the steps that know (the Bag on resume, the Mart lady's own save).
ConsoleStoryExecutor (Utils) does the kinds BDSP has (route with trainer
sight and named plan costs, D-pad legs, train, heal, save, mash) and runs
each step through the table's runner, so failures keep their screenshot
and the "checkpoint_reattempt_loop: attempt N failed: <id>: ..." line the
lab watcher reads. Segment 00 registers its own variants (Mart lady or
clerk, the signs' gap, the Jubilife stairs). The other rows stay wrapped.

Retries: the lab's STOP_AT_FIRST_FAILURE option is replaced by the shared
StoryRunOptions group (attempts per checkpoint, default 3; stop at the
first failure). The story tables (segments 00 and 01) run with that
policy instead of 20 attempts; checkpoint_reattempt_loop() for the other
segments still has its 20 and follows the stop option.

A new test lints 00.04b and plans each of its routes on the story maps
from where the step before leaves the player, the clerk's way.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
build_story_checkpoint() calls StoryStepExecutor::begin_attempt() before
building, once per attempt, so a game can start the attempt afresh (BDSP:
the trainers who can see us again; the row's failure mode).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
Segment_00.cpp takes bdsp/mvp-v3's: its 00.04b/c/d rows replace this
branch's one-row 00.04b, which the next commit rewrites as story steps.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
…o end in tests

The table (PokemonBDSP_AutoStory_StoryTable) now reads like FRLG's: rows of
the shared StorySteps, 00.00 to 01.11, plain data. 00.04b to 00.04d (from
bdsp/mvp-v3's split) are declarative: route to the catch grass, train 3,
into Sandgem (robust costs), to the Center's sign (town costs), taps west
(one short is fine), heal; the Potions shop; north past Route 202's
trainers, up the stairs, Dawn's scene. Every other step calls its old
function through a variant the segment registers (segment_00_variants(),
segment_01_variants()). story_table_segment() builds rows the way the old
StoryCheckpointSpec rows were built: save first unless the row stops on
failure, then the steps through ConsoleStoryExecutor, which goes through
the runner so failures keep their screenshot and attempt log line. The
console-action alias is renamed StoryAction, apart from Pokemon::StoryStep.

leave_door_south()'s stop decision is door_walk_stops(), so it can be
tested.

Tests: Test_StorySimulation runs both segments end to end against a fake
game (routes and legs planned on the built-in maps): checkpoint order and
saves, start/end ranges, a blackout in 00.04b's training resetting to its
save, a step failing three times then stopping (and stop-at-first-failure),
start poses chaining, every called function registered, and the door
exit's looks. Test_MartLadyEvents gains the Lab sign re-anchor case.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
…l initializer

Windows clang: missing field 'policy' initializer (-Wmissing-field-initializers).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
…r Fast)

StoryChecks: THOROUGH steps read the screen to confirm what they did
(purchases, the Bag, status after battles, position); FAST trusts counts
and timings. Each game decides what its steps check at each level. The
executor carries it (checks(), set_checks(); THOROUGH by default), and
StoryRunOptions gains a "Checks" dropdown, Thorough by default, read with
checks(). Tests: the level reaches a step; the option group's defaults.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
AutoStoryOptions carries it; ConsoleStoryExecutor sets it before each
step. Nothing reads it yet.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
…eed it

StoryRunOptions gains "Game language" (any language the games have,
English by default, never refused for lacking a reader), and the executor
carries it (language(), set_language()) for the few reads that need text:
item names in a shop or the Bag. The header states the rule: steps never
match dialogue or menu text, and a game with no reader for the language
falls back to language-free checks. Tests: the option's choices and the
executor's language.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
BDSP AutoStory's route lines (the plan, each leg as it starts, a replan
where the player was seen, a trainer stopping us, the arrival), lifted
from PokemonBDSP_AutoStory_RouteWalk.cpp so that every game's walker logs
the same lines, with what other games need: tiles of named maps rather
than BDSP's world tiles, one tile or a set, legs onto a warp, Surf and
turns, and two new lines: where a leg ended and how that is known
(walked, assumed after an interrupt, unknown), and where the player was
found again after a stop.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
The program's language now comes from the shared StoryRunOptions
(g_story_language, AutoStoryOptions::language, the executor), and
story_reads_text() says whether the text reads have a reader for it
(English only, so far). Without one:
- the location banner and the save card read as UNREAD_LOCATION, which
  location_banner_matches() takes as a match: the banner's box showing is
  the check, and the walk's tiles say where we are;
- signs and talks are checked by their box opening and closing, unread;
- a Bag search takes the pocket's cursor row if the pocket has one;
- battle move names go unread (an unread move counts as a plain attack);
- 00.04c keeps to the Mart lady: the clerk's list is found by item names.
Still English-only and outside 00.00-01.11's table steps: activate_repel's
names, buy_items' hover detector, the outside-help battle's names; PP
reads are digits only.

Tests: the simulation runs its executor with Japanese; a new case checks
the no-reader rules; the Mart lady events pass with every box unread.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
… size limits

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
The route walker's plan, leg, replan, trainer and arrival lines now come
from Pokemon_RouteLog.h, which they were lifted into, word for word but
for the "taps before the battle" replan's punctuation. New: a line for
each leg that reached its planned tiles, saying how that is known (an open
leg with a wild battle on the way counts its taps, so its end is assumed).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01AKYzhrMnPK61XHWEch4a6E
@dayfine

dayfine commented Nov 1, 2026

Copy link
Copy Markdown
Owner Author

Superseded by #128, BDSP v4's story table on the shared steps (with #148 for its actions).

@dayfine dayfine closed this Nov 1, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant