• v0.14.0 — replay pipeline + Quat bug fixes + UX tail

    funman300 released this 2026-05-05 19:44:03 +00:00 | 475 commits to master since this release

    Largest release since the card-theme system. Three threads land
    together: the v0.13.0-era UX candidate tail (theme thumbnails,
    daily-challenge calendar, Time Attack auto-save, per-mode bests,
    time-bonus slider), Quat smoke-test bug fixes (multi-card move
    validation, softlock detection, deal-tween information leak), and
    the entire replay pipeline (record → persist → upload → web viewer).

    Added

    • Theme-picker thumbnails. Each Settings → Cosmetic chip renders an
      Ace + back preview pair via the existing rasterize_svg path.
    • 14-day daily-challenge calendar in the Profile modal. PlayerProgress
      gains daily_challenge_history (capped at 365) and
      daily_challenge_longest_streak.
    • Time Attack session auto-save to time_attack_session.json sibling
      next to game_state.json. 30 s cadence + on AppExit. Sessions whose
      10-min window expired in real time during a closed launch are
      discarded.
    • Per-mode best-score and fastest-win readouts in Stats. Six new
      #[serde(default)] StatsSnapshot fields (Classic / Zen / Challenge
      × best_score + fastest_win_seconds).
    • Time-bonus multiplier slider in Settings → Gameplay (0.0–2.0,
      default 1.0). Cosmetic; doesn't affect achievement thresholds.
    • Win-replay recording + storage. Every successful move appends to
      a RecordingReplay; GameWonEvent freezes it into a Replay and
      persists to latest_replay.json. Single-slot.
    • "Watch replay" button in Stats overlay (full in-engine playback
      is the next iteration; the button surfaces an InfoToastEvent for
      now).
    • Replay upload + fetch endpoints on the server, JWT-gated. Engine
      uploads winning replays automatically when cloud sync is on.
    • New solitaire_wasm crate compiling replay-relevant solitaire_core
      types to WebAssembly. Browser-side replay re-execution.
    • Web replay viewer served from the server. GET /replays/:id returns
      HTML + CSS + wasm bundle. Card-flight animations included.
    • E2E test coverage for the full upload → fetch path.

    Fixed

    • Multi-card lift validation. solitaire_core::rules::is_valid_
      tableau_sequence rejects stacks whose adjacent cards don't form a
      descending alternating-colour run. Wired into move_cards.
    • Softlock detection. has_legal_moves walks every potential move
      source against every destination instead of early-returning on
      non-empty stock. GameOverScreen now actually fires.
    • Deal-tween information leak. New-game snaps every card sprite to
      the stock position before writing StateChangedEvent so all 52
      cards animate from a single deck point during the deal.

    By the numbers: 1134 passing tests (was 1053 at v0.13.0), zero
    clippy warnings under --workspace --all-targets -- -D warnings.

    Downloads