docs: update docs

This commit is contained in:
hypercross 2026-04-04 01:03:12 +08:00
parent 6c8d6e0790
commit a89aac9c21
2 changed files with 59 additions and 6 deletions

View File

@ -48,13 +48,13 @@ tests/ # Mirrors src/ structure with *.test.ts files
- Trailing commas in multi-line objects/arrays
### Naming Conventions
- **Types/Interfaces**: `PascalCase``Part`, `Region`, `Command`, `IGameContext`
- **Classes**: `PascalCase``MutableSignal`, `AsyncQueue`, `Mulberry32RNG`
- **Functions**: `camelCase`, verb-first — `createGameContext`, `parseCommand`, `isValidMove`
- **Types/Interfaces**: `PascalCase``Part`, `Region`, `Command`, `IGameContext`, `GameHost`
- **Classes**: `PascalCase``MutableSignal`, `AsyncQueue`, `Mulberry32RNG`, `GameHost`
- **Functions**: `camelCase`, verb-first — `createGameContext`, `createGameHost`, `parseCommand`, `isValidMove`
- **Variables**: `camelCase`
- **Constants**: `UPPER_SNAKE_CASE``BOARD_SIZE`, `WINNING_LINES`
- **Test files**: `*.test.ts` mirroring `src/` structure under `tests/`
- **Factory functions**: prefix with `create` or `mutable``createGameContext`, `mutableSignal`
- **Factory functions**: prefix with `create` or `mutable``createGameContext`, `createGameHost`, `mutableSignal`
### Types
- **Strict TypeScript** is enabled — no `any`
@ -84,9 +84,10 @@ tests/ # Mirrors src/ structure with *.test.ts files
- **Reactivity**: `MutableSignal<T>` extends Preact Signal — access state via `.value`, mutate via `.produce(draft => ...)`
- **Command system**: CLI-style parsing with schema validation via `inline-schema`
- **Prompt system**: Commands prompt for input via `PromptEvent` with `resolve`/`reject`; `tryCommit` accepts `Command | string` and validates against schema before custom validator
- **Prompt system**: Commands prompt for input via `PromptEvent` with `resolve`/`reject`; `tryCommit` accepts `Command | string` and validates against schema before custom validator; `promptEnd` event fires when prompt completes (success or cancel)
- **GameHost**: Lifecycle manager for game sessions — provides `setup()`, `onInput()`, `dispose()`, reactive `state`/`status`/`activePromptSchema` signals
- **Barrel exports**: `src/index.ts` is the single public API surface
- **Game modules**: export `registry` and `createInitialState` for use with `createGameContextFromModule`
- **Game modules**: export `registry` and `createInitialState` for use with `createGameContextFromModule` or `createGameHost`
- **Region system**: plain `Region` type with `createRegion()` factory; `parts` are stored as `Record<string, Part>` keyed by ID, with `partMap` in regions mapping position keys to part IDs
- **Part collections**: Game state uses `Record<string, Part<TMeta>>` (not arrays) for O(1) lookup by ID. Use `Object.values(parts)` when iteration is needed, `Object.keys(parts)` for count/IDs
- **Mutative**: used for immutable state updates inside `MutableSignal.produce()`

View File

@ -10,6 +10,7 @@ Build turn-based board games with reactive state, entity collections, spatial re
- **Type Safe**: Full TypeScript support with strict mode and generic context extension
- **Region System**: Spatial management with multi-axis positioning, alignment, and shuffling
- **Command System**: CLI-style command parsing with schema validation, type coercion, and prompt support
- **Game Lifecycle Management**: `GameHost` class provides clean setup/reset/dispose lifecycle for game sessions
- **Deterministic RNG**: Seeded pseudo-random number generator (Mulberry32) for reproducible game states
## Installation
@ -124,6 +125,52 @@ If the player needs to cancel instead of committing:
promptEvent.cancel('player quit');
```
### Managing Game Lifecycle with GameHost
For a cleaner game lifecycle (setup, reset, dispose), use `GameHost`:
```ts
import { createGameHost } from 'boardgame-core';
import { registry, createInitialState } from './my-game';
// Create a game host with a setup command
const host = createGameHost(
{ registry, createInitialState },
'setup' // command to run when setting up/resetting the game
);
// Reactive state — use in effects or computed values
console.log(host.state.value.currentPlayer);
console.log(host.status.value); // 'created' | 'running' | 'disposed'
// Check if a prompt is active and what schema it expects
const schema = host.activePromptSchema.value;
if (schema) {
console.log('Waiting for:', schema.name, schema.params);
}
// Submit player input to the active prompt
const error = host.onInput('play X 1 2');
if (error) {
console.log('Invalid move:', error);
}
// Reset the game (cancels active prompt, resets state, runs setup)
await host.setup('setup');
// Dispose when done (cleans up listeners, cancels active prompts)
host.dispose();
```
The `GameHost` provides:
- **`state`**: `ReadonlySignal<TState>` — reactive game state
- **`status`**: `ReadonlySignal<'created' | 'running' | 'disposed'>` — lifecycle status
- **`activePromptSchema`**: `ReadonlySignal<CommandSchema | null>` — reactive current prompt schema
- **`onInput(input)`**: Submit input to active prompt, returns error or null
- **`setup(command)`**: Reset and reinitialize the game
- **`dispose()`**: Clean up all resources
- **`on(event, listener)`**: Listen to `'setup'` or `'dispose'` events
## Sample Games
### Tic-Tac-Toe
@ -189,6 +236,10 @@ rng.setSeed(999); // reseed
| `IGameContext` | Base interface for the game context (state, commands) |
| `createGameContext(registry, initialState?)` | Create a game context instance. `initialState` can be an object or factory function |
| `createGameCommandRegistry<TState>()` | Create a command registry with fluent `.add()` API |
| `GameHost<TState>` | Game lifecycle manager class with setup/reset/dispose |
| `createGameHost(module, setupCommand, options?)` | Create a GameHost instance from a game module |
| `GameHostStatus` | Type: `'created' \| 'running' \| 'disposed'` |
| `GameHostOptions` | Options: `{ autoStart?: boolean }` |
### Parts
@ -239,6 +290,7 @@ rng.setSeed(999); // reseed
| `runCommandParsed(registry, context, command)` | Run a pre-parsed command |
| `createCommandRunnerContext(registry, context)` | Create a command runner context |
| `PromptEvent` | Event dispatched when a command prompts for input |
| `CommandRunnerEvents` | Event types: `prompt` (when prompt starts), `promptEnd` (when prompt completes) |
### Utilities