Add Tailwind v4 @theme tokens for surfaces, accents, text, borders,
and status colors. Self-host Geist Sans/Mono variable fonts. Redesign
nav with backdrop blur and active states, home page with gradient hero.
Migrate all 50+ components from ad-hoc gray/blue Tailwind classes to
semantic theme tokens (surface-*, text-*, border-*, accent-*, status-*).
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Show colored pill badges (Mega, G-Max, D-Max, Tera) on boss Pokemon
in BossDefeatModal and BossTeamPreview. Starter-dependent condition
labels are ignored. Follows EncounterMethodBadge pattern.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Add missing tsconfig strictness flags (noUncheckedIndexedAccess,
exactOptionalPropertyTypes, noImplicitOverride,
noPropertyAccessFromIndexSignature) and fix all resulting type errors
- Replace ESLint/Prettier with oxlint 1.48.0 and oxfmt 0.33.0
- Pin all frontend and backend dependencies to exact versions
- Pin GitHub Actions to SHA hashes with persist-credentials: false
- Fix CI Python version mismatch (3.12 -> 3.14) and ruff target-version
- Add vitest 4.0.18 with jsdom environment for frontend testing
- Add ty 0.0.17 for Python type checking (non-blocking in CI)
- Add actionlint and zizmor CI job for workflow linting and security audit
- Add Dependabot config for npm, pip, and github-actions
- Update CLAUDE.md and pre-commit hooks to reflect new tooling
- Ignore Claude Code sandbox artifacts in gitignore
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Set up pre-commit framework with ruff (backend) and ESLint/Prettier/tsc
(frontend) hooks to catch issues locally before CI. Auto-format all
frontend files with Prettier to comply with the new check.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Genlockes can now select a naming scheme at creation time, which is
automatically applied to every leg's run. When catching a pokemon whose
evolution family appeared in a previous leg, the system suggests the
original nickname with a roman numeral suffix (e.g., "Heracles II").
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Reviewed-on: TheFurya/nuzlocke-tracker#20
Co-authored-by: Julian Tabel <juliantabel.jt@gmail.com>
Co-committed-by: Julian Tabel <juliantabel.jt@gmail.com>
Visually indent child routes under their parent with tree connectors,
and make dragging a parent move all its children as a unit.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add clickable suggestion chips below the nickname input in the encounter
modal. Chips are fetched from GET /runs/{id}/name-suggestions via React
Query, shown only when a naming scheme is set. Clicking a chip fills in
the nickname; a regenerate button fetches a fresh random batch. Completes
the Name Generation epic.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add a nullable naming_scheme column to NuzlockeRun so users can pick a
themed word category for nickname suggestions. Includes Alembic migration,
updated Pydantic schemas, a GET /runs/naming-categories endpoint backed by
a cached dictionary loader, and frontend dropdowns in both the NewRun
creation flow and the RunDashboard for mid-run changes.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Include mime.types at the server block level to ensure .webp files
are served with the correct Content-Type (image/webp).
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Replace Vite defaults with Nuzlocke Tracker branding: custom pokeball-
skull favicon (SVG + PNG + ICO), page title, meta description, Open
Graph tags, theme-color, web manifest, and package.json name.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Backend: installs non-editable, runs uvicorn without reload.
Frontend: multi-stage build, serves static files via nginx with
API proxy to the backend service and SPA fallback routing.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add postGameCompletion toggle to nuzlocke rules so players can indicate
whether a run ends after the Champion or continues into post-game. Adds
a new "Completion" category section in rules configuration with a green
badge color.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add sort dropdown to RunEncounters (the encounters page with the
expandable team section) and move all useMemo hooks before early
returns in both RunDashboard and RunEncounters to fix React hook
ordering violations.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add a dropdown to sort Active Team and Graveyard by route order,
catch level, species name, or national dex number.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add optional error prop to DeleteConfirmModal and wire it into AdminRuns
so the backend's rejection message is displayed to the user.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Implement read-only lineage view that traces Pokemon across genlocke legs
via existing transfer records. Backend walks transfer chains to build
lineage entries; frontend renders them as cards with a column-aligned
timeline grid so leg dots line up vertically across all lineages.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Move alive and hofTeam into useMemo hooks above early returns to fix
React hook ordering violation. Include transfer and shiny encounters
in alive so they appear in the team section and can be selected for
the Hall of Fame.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Transfer modal now only appears when a Hall of Fame team is selected,
using the existing hofTeam data instead of the survivors endpoint.
Without a HoF selection, advance proceeds directly with no transfer step.
Transferred encounters are now a separate category: they appear in their
own "Transferred Pokemon" section, don't occupy route slots in the
encounter map, and don't block the route-lock check (excluded via
genlocke_transfers subquery). The run detail endpoint returns
transferEncounterIds so the frontend can distinguish them.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Run deletion now properly cleans up boss_results, genlocke_transfers,
and genlocke_leg references before deleting the run. Also fix
showTransferModal being referenced before initialization in
RunEncounters by moving its useState declaration above useLegSurvivors.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When advancing to the next genlocke leg, users can now select surviving
Pokemon to transfer. Transferred Pokemon are bred down to their base
evolutionary form and appear as level-1 egg encounters in the next leg.
A GenlockeTransfer record links source and target encounters for lineage tracking.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Aggregates all fainted encounters across every leg of a genlocke into a
unified graveyard view. Backend serves GET /genlockes/{id}/graveyard with
per-entry leg/game context and summary stats (total deaths, deaths per
leg, deadliest leg). Frontend adds a toggle button on the genlocke detail
page that reveals a filterable/sortable grid of grayscale Pokemon cards.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Backend: PATCH/DELETE genlocke, POST/DELETE legs with order
re-numbering. Frontend: admin list page with status filter,
detail page with inline editing, legs table, and stats display.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add GET /genlockes and GET /genlockes/{id} endpoints with aggregate
encounter/death stats per leg, and a frontend list page at /genlockes
plus a detail page at /genlockes/:genlockeId showing progress timeline,
cumulative stats, configuration, retired families, and quick actions.
Update nav link to point to the list page instead of /genlockes/new.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Move hofTeam useMemo before early returns to comply with Rules of Hooks.
It was placed after the loading/error guards, causing a "rendered more
hooks than during the previous render" crash.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
After marking a run as completed, a modal prompts the player to select
which Pokemon (up to 6) entered the Hall of Fame. The selection is stored
as hof_encounter_ids on the run, displayed in the victory banner, and
can be edited later. This lays the foundation for scoping genlocke
retireHoF to only the actual HoF team.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When retireHoF is enabled, surviving HoF Pokemon and their evolutionary
families are retired at leg advancement and treated as duplicates in all
subsequent legs — both in the encounter modal and bulk randomize.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When a run belonging to a genlocke is completed or failed, the genlocke
status updates accordingly. The run detail API now includes genlocke
context (leg order, total legs, genlocke name). A new advance endpoint
creates the next leg's run, and the frontend shows genlocke-aware UI
including a "Leg X of Y" banner, advance button, and contextual
messaging in the end-run modal.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Implements the genlocke creation feature end-to-end: Genlocke and
GenlockeLeg models with migration, POST /genlockes endpoint that
creates the genlocke with all legs and auto-starts the first run,
and a 4-step wizard UI (Name, Select Games with preset templates,
Rules, Confirm) at /genlockes/new.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add `category` field (original/remake/enhanced/sequel/spinoff) to the
Game model and tag all 38 games. Create regions.json with generation
mapping, ordering, and genlocke preset defaults per region. Add
GET /games/by-region endpoint returning games grouped by region.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Egg hatches can now be logged at any location without consuming the
route's encounter slot. Adds an EggEncounterModal with pokemon search
and a "Log Egg" button on the run encounters page.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The seed export command now downloads badge images and boss sprites
from remote URLs and stores them in frontend/public/, rewriting the
JSON URLs to local paths. Sprites are namespaced by game version
(e.g. /boss-sprites/red/brock.png) so each generation can have
its own sprite style.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When evolving Nincada, a confirmation prompt now offers to also add
Shedinja as a new encounter on the same route. The Shedinja encounter
uses a "shed_evolution" origin to bypass route-locking.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When a run has a starter Pokemon, automatically match its species name
against boss battle condition labels (e.g., "charmander" matches "Chose
Charmander"). If exactly one variant matches, pre-select it and hide the
pill selector. Falls back to showing pills when no match is found.
Fixes starter lookup to use game routes data (which has encounterMethods
populated) instead of the run detail route (which defaults to empty).
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>