//! What a frontend draws and what it can ask the core to do. //! //! The core owns state and navigation; adapters map input to `Command` and //! render `View`. Terminal text lives in [`crate::client::tui`], not here. use crate::client::games::roulette::{Cursor, Direction}; use crate::client::games::traits::GameState; use crate::roulette::{BetTarget, Bets}; #[derive(Debug, Clone, Copy, PartialEq, Eq)] pub enum RoulettePhase { Placing, Spinning, Result, } #[derive(Debug, Clone, PartialEq, Eq)] pub struct RouletteView { pub bet_amount: u64, pub balance: Option, pub chip: u64, pub bets: Bets, pub cursor: Cursor, pub phase: RoulettePhase, pub number: Option, pub color: Option, pub winnings: Option, pub error: Option, } impl RouletteView { pub fn from_state(state: &GameState) -> Self { let bets = state .data .get("bets") .and_then(|raw| Bets::from_json(raw).ok()) .unwrap_or_default(); let chip = state .data .get("chip") .and_then(|value| value.parse().ok()) .unwrap_or(10); let cursor = state .data .get("cursor") .map(|raw| Cursor::parse(raw)) .unwrap_or_default(); let phase = match state.data.get("status").map(String::as_str) { Some("spinning") => RoulettePhase::Spinning, Some("result") => RoulettePhase::Result, _ => RoulettePhase::Placing, }; let number = state.data.get("number").and_then(|value| value.parse().ok()); let color = state.data.get("color").cloned(); let winnings = state .data .get("winnings") .and_then(|value| value.parse().ok()); let balance = state .data .get("balance") .and_then(|value| value.parse().ok()); let error = state .data .get("error") .cloned() .filter(|message| !message.is_empty()); Self { bet_amount: state.bet_amount, balance, chip, bets, cursor, phase, number, color, winnings, error, } } } /// Everything a frontend can draw. `Text` is the bridge for games that have /// not been ported to a structured view yet. #[derive(Debug, Clone, PartialEq, Eq)] pub enum View { Roulette(RouletteView), Text(Vec), } /// Semantic input. Frontends turn keys and clicks into these. #[derive(Debug, Clone, PartialEq, Eq)] pub enum Command { MoveCursor(Direction), PlaceBet, PlaceBetAt(BetTarget), ClearBets, SetChip(u64), AdjustChip(i64), Spin, Leave, }