Board layers

This commit is contained in:
2026-06-15 23:35:18 -05:00
parent d1d0824d37
commit 01cd73ca3b
29 changed files with 2166 additions and 2051 deletions
+22 -14
View File
@@ -143,21 +143,29 @@ fn run(
continue;
}
let size = terminal.size()?;
match current_input_mode(mode, ui) {
InputMode::Board | InputMode::Frozen => {
if let Mode::Play(game) = mode {
handle_board_input(event, ui.log.open, size.height, game, ui);
}
// Each Mode only produces a subset of input modes (Editor only in Edit;
// Board/Scroll/Frozen only in Play; Menu/Ignore in either). Match on Mode
// first so each handler gets the right `game`/`ed` without re-checking,
// and assert the impossible combinations away with `unreachable!`.
let input_mode = current_input_mode(mode, ui);
if matches!(input_mode, InputMode::Menu) {
handle_menu_input(event, ui)
} else if !matches!(input_mode, InputMode::Ignore) {
// If input_mode is ignore, an animation is running and claiming no input mode — discard all events.
match mode {
Mode::Play(game) => match input_mode {
InputMode::Board | InputMode::Frozen => {
handle_board_input(event, ui.log.open, size.height, game, ui);
}
InputMode::Scroll => handle_scroll_input(event, game, ui),
_ => unreachable!("Menu and Ignore handled above; Editor input mode only occurs in Edit mode"),
},
Mode::Edit(ed) => match input_mode {
InputMode::Editor => handle_editor_input(event, size.width, ed, ui),
_ => unreachable!("Menu and Ignore handled above; Board/Scroll/Frozen input modes only occur in Play mode")
},
}
InputMode::Menu => handle_menu_input(event, ui),
InputMode::Scroll => {
if let Mode::Play(game) = mode { handle_scroll_input(event, game, ui); }
}
InputMode::Editor => {
if let Mode::Edit(ed) = mode { handle_editor_input(event, size.width, ed, ui); }
}
// Animation running and claiming no input mode — discard all events.
InputMode::Ignore => {}
}
}
+13 -5
View File
@@ -107,13 +107,21 @@ impl Ui {
return; // no mode tick during any animation (even when just ended)
}
// The game only advances during normal play (InputMode::Board). While a
// scroll or menu overlay is open the input mode is Scroll/Menu, so the game
// is paused — otherwise `game.tick` would call `handle_scroll`, clearing the
// scroll the instant its open animation finished.
let input_mode = crate::input::current_input_mode(mode, self);
match mode {
// Play: tick the game, then check whether a scroll overlay appeared.
// Play: tick the game (only in Board mode), then check whether a scroll
// overlay appeared as a result of this tick.
Mode::Play(game) => {
game.tick(dt);
if let Some(scroll) = &game.active_scroll {
let lines = scroll.lines.clone();
self.active_animation = Some(Box::new(ScrollOpenAnimation::new(lines)));
if matches!(input_mode, crate::input::InputMode::Board) {
game.tick(dt);
if let Some(scroll) = &game.active_scroll {
let lines = scroll.lines.clone();
self.active_animation = Some(Box::new(ScrollOpenAnimation::new(lines)));
}
}
}
// Edit: only the cursor blink advances; the game does not exist here.