refactor(admin): align admin ui with app design language

- dashboard: card grid replaced by status strip + nav-tile section + list
- nav-tile promoted to shared component
- stat tiles and usage screen de-carded, sections divided like settings
- hub run tournament back to a list row
- telemetry link restored in tools list
This commit is contained in:
2026-08-25 22:24:36 -07:00
parent 895737febc
commit 1cc75591fa
22 changed files with 511 additions and 799 deletions
@@ -1,5 +1,5 @@
import { useTournament } from "../queries";
import { Box, List } from "@mantine/core";
import { List } from "@mantine/core";
import ListButton from "@/components/list-button";
import Sheet from "@/components/sheet/sheet";
import TournamentForm from "./tournament-form";
@@ -12,9 +12,7 @@ import {
import { useSheet } from "@/hooks/use-sheet";
import ListLink from "@/components/list-link";
import EditRules from "./edit-rules";
import Button from "@/components/button";
import { Trans, useLingui } from "@lingui/react/macro";
import { useNavigate } from "@tanstack/react-router";
import { useLingui } from "@lingui/react/macro";
interface ManageTournamentProps {
tournamentId: string;
@@ -22,7 +20,6 @@ interface ManageTournamentProps {
const ManageTournament = ({ tournamentId }: ManageTournamentProps) => {
const { t } = useLingui();
const navigate = useNavigate();
const { data: tournament } = useTournament(tournamentId);
if (!tournament) throw new Error("Tournament not found.");
@@ -39,18 +36,12 @@ const ManageTournament = ({ tournamentId }: ManageTournamentProps) => {
return (
<>
<Box px="md" py="md">
<Button
leftSection={<TreeStructureIcon weight="bold" size={20} />}
onClick={() =>
navigate({ to: `/admin/tournaments/run/${tournamentId}` })
}
>
<Trans>Run Tournament</Trans>
</Button>
</Box>
<List p="0">
<ListLink
label={t`Run Tournament`}
Icon={TreeStructureIcon}
to={`/admin/tournaments/run/${tournamentId}`}
/>
<ListLink
label={t`Enrollment & Teams`}
Icon={UsersThreeIcon}
@@ -30,28 +30,9 @@ const RulesContent = lazy(
() => import("../../upcoming-tournament/rules-content")
);
interface NavTileProps {
label: string;
Icon: Icon;
onClick?: () => void;
disabled?: boolean;
}
import { NavTile } from "@/components/nav-tile";
/** A single square-ish nav tile with icon-over-label and press feedback. */
export const NavTile = ({ label, Icon, onClick, disabled }: NavTileProps) => (
<UnstyledButton
className={`${classes.tile} flxn-tile`}
onClick={onClick}
disabled={disabled}
>
<span className={`${classes.icon} flxn-tile-icon`}>
<Icon size={22} weight="bold" />
</span>
<Text size="xs" fw={600} lineClamp={2} lh={1.2}>
{label}
</Text>
</UnstyledButton>
);
export { NavTile };
interface NavGridProps {
tournament: Tournament;