import { XPEventType } from '../events'; import { Action, Condition, FlagValue, RehearsalPlan, Scenario } from './types'; import { ScenarioStrings } from './strings'; /** * A hint rung for a puzzle's anti-stuck ladder (M12). A rung reveals its `text` * (as a tray balloon) once the player looks stuck: after `afterFails` * `password:fail`s, or `afterIdles` `user:idle` periods — whichever comes first. * Prefer the {@link ladder} helper over writing rungs by hand. */ export interface PuzzleHint { /** Inline balloon body (quick prototyping); `textKey` wins when both are set. */ text?: string; /** String-table key for the body (#207); resolves over `text`. */ textKey?: string; /** Balloon title (default `'Hint'`). */ title?: string; /** String-table key for the title (#207); resolves over `title`. */ titleKey?: string; /** Reveal after this many `password:fail` events (journal count ≥). */ afterFails?: number; /** Reveal after this many `user:idle` periods (journal count ≥). */ afterIdles?: number; } /** The cadence options shared by {@link ladder} and {@link ladderKeys}. */ interface LadderCadence { fails?: number; idles?: number; } /** * Build an escalating hint ladder (M12): each text becomes a rung, and `fails` / * `idles` set the base cadence so rung *i* unlocks at `base * (i + 1)` — e.g. * `ladder({ fails: 2 }, a, b)` shows `a` after 2 fails, `b` after 4. Give both * `fails` and `idles` to reveal on either channel. Compiles (via * {@link compilePuzzleGraph}) to `password:fail` / `user:idle` count triggers. * * Inline text is for prototyping; prefer {@link ladderKeys} once a string table * exists so the hints localize with the rest of the beat text (#207). */ export declare const ladder: (opts: LadderCadence & { title?: string; }, ...texts: string[]) => PuzzleHint[]; /** * Like {@link ladder}, but each rung references a string-table key (#207) * instead of an inline literal, so the hint ladder localizes with the rest of * the beat text. `titleKey` names the shared balloon title key. */ export declare const ladderKeys: (opts: LadderCadence & { titleKey?: string; }, ...textKeys: string[]) => PuzzleHint[]; /** One node in the dependency graph. */ export interface PuzzleNode { /** Stable id (referenced by other nodes' `requires`). */ id: string; /** Puzzle ids that must be solved before this one can be solved. */ requires?: string[]; /** * Event type(s) that re-check `solvedWhen`. Derived from `solvedWhen`'s * `happened`/`count` types when omitted; required when `solvedWhen` only reads * flags/FS/the triggering event's payload. */ on?: XPEventType | XPEventType[]; /** The condition that marks this puzzle solved. */ solvedWhen: Condition; /** Actions performed once, when the puzzle is solved (reveals, unlocks). */ grants?: Action[]; /** Hint ladder (M12 anti-stuck contract; checked by the linter). */ hints?: PuzzleHint[]; /** Marks an act bottleneck: everything "after" it must transitively require it. */ gate?: boolean; } /** A complete puzzle dependency graph. */ export interface PuzzleGraph { /** Scenario id of the compiled output. */ id: string; initialFlags?: Record; puzzles: PuzzleNode[]; /** Per-locale beat-text tables (#207), passed through to the compiled scenario. */ strings?: ScenarioStrings; /** Canonical walkthrough for rehearsal/seek + solver CI (#207), passed through. */ rehearsal?: RehearsalPlan; } /** The flag a solved puzzle sets (and that dependents gate on). */ export declare const solvedFlag: (puzzleId: string) => string; export declare const compilePuzzleGraph: (graph: PuzzleGraph) => Scenario; export interface GraphLintIssue { puzzle?: string; level: 'error' | 'warn' | 'info'; message: string; } export interface PuzzleGraphReport { issues: GraphLintIssue[]; /** Count of puzzles at each dependency depth (0 = roots). Pacing/"bushiness". */ bushiness: number[]; /** The widest level — the most puzzles a player can juggle at once. */ maxParallel: number; /** True when there are no error-level issues. */ ok: boolean; } /** * Statically analyse a puzzle graph. Errors (missing requires, cycles, * unreachable, no trigger event) mean the graph can't run correctly; warnings * (no hint ladder, gate bypass) are design smells. Also computes bushiness. */ export declare const lintPuzzleGraph: (graph: PuzzleGraph) => PuzzleGraphReport; export {};