Porta il profilo in alto a destra e lascia quattro voci nella barra

La barra aveva cinque voci e la quinta era il profilo, che non è una
destinazione di pari livello con Oggi, Calendario, Squadra e Classifica: è la
propria scheda, e su iOS si cerca in alto a destra. Toglierla dalla barra
restituisce anche un quinto di larghezza alle altre quattro.

`LinkProfilo` mostra l'avatar del giocatore e porta a `/profilo`. Sta in
`PageHeader`, quindi compare su calendario, squadra, classifica e profilo, più
l'hero della home che ha un'intestazione propria. Se l'avatar non è stato
caricato `Avatar` ricade sulle iniziali; se il giocatore non c'è ancora (primo
render) resta il logo, così il posto non resta vuoto.

Sulla pagina del profilo l'avatar sarebbe un link a sé stessa: `PageHeader`
prende una prop `azione` e lì si passa il logo della squadra.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
2026-09-05 19:22:08 +02:00
co-authored by Claude Opus 5
parent fabee4df1d
commit 383643392a
4 changed files with 53 additions and 9 deletions
+4 -3
View File
@@ -1,12 +1,13 @@
import { Link } from "@tanstack/react-router";
import { CalendarDays, Home, Trophy, User, Users } from "lucide-react";
import { CalendarDays, Home, Trophy, Users } from "lucide-react";
// Quattro voci e non cinque: il profilo sta in alto a destra
// nell'intestazione di ogni pagina, dove lo cerca chi arriva da iOS.
const items = [
{ to: "/", label: "Oggi", icon: Home },
{ to: "/calendario", label: "Calendario", icon: CalendarDays },
{ to: "/squadra", label: "Squadra", icon: Users },
{ to: "/classifica", label: "Classifica", icon: Trophy },
{ to: "/profilo", label: "Profilo", icon: User },
] as const;
export function BottomNav() {
@@ -25,7 +26,7 @@ export function BottomNav() {
di sistema. Prima l'altezza dipendeva dai padding delle voci e nessuno
poteva saperla da fuori.
*/}
<div className="materiale pointer-events-auto mx-auto grid h-[var(--altezza-nav)] max-w-md grid-cols-5 overflow-hidden rounded-full border border-border/60 px-1 shadow-lg">
<div className="materiale pointer-events-auto mx-auto grid h-[var(--altezza-nav)] max-w-md grid-cols-4 overflow-hidden rounded-full border border-border/60 px-1 shadow-lg">
{items.map(({ to, label, icon: Icon }) => (
<Link
key={to}
+33 -2
View File
@@ -1,7 +1,10 @@
import { useId, useState, type ComponentPropsWithoutRef, type ReactNode } from "react";
import { Link } from "@tanstack/react-router";
import { ChevronDown } from "lucide-react";
import { cn } from "@/lib/utils";
import { statoMeta, type Stato } from "@/lib/crapp-data";
import { useIo } from "@/lib/rosa";
import { Avatar } from "@/components/crapp/Avatar";
import { Reveal } from "@/components/motion/Reveal";
import { Numero } from "@/components/motion/Numero";
@@ -33,7 +36,35 @@ export function Card({
return <Tag className={cn("premi rounded-3xl bg-card p-4 shadow-card", className)} {...props} />;
}
export function PageHeader({ titolo, sottotitolo }: { titolo: string; sottotitolo?: string }) {
/**
* Accesso al profilo in alto a destra: la BottomNav ha quattro voci e questa è
* l'unica porta verso `/profilo`. Sulla pagina del profilo si passa `azione` a
* `PageHeader` per rimetterci il logo — sarebbe un link a sé stessa.
*/
export function LinkProfilo() {
const g = useIo();
if (!g) return <TeamLogo className="h-11 w-11" />;
return (
<Link
to="/profilo"
aria-label="Il tuo profilo"
className="premi shrink-0 rounded-2xl ring-2 ring-primary-foreground/30"
>
<Avatar id={g.id} fallback={g.iniziali} className="h-11 w-11 text-lg" />
</Link>
);
}
export function PageHeader({
titolo,
sottotitolo,
azione,
}: {
titolo: string;
sottotitolo?: string;
/** Sostituisce il link al profilo in alto a destra. */
azione?: ReactNode;
}) {
return (
<header className="bg-hero px-5 pb-8 pt-7 text-primary-foreground">
<div className="grid grid-cols-[minmax(0,1fr)_auto] items-center gap-4">
@@ -43,7 +74,7 @@ export function PageHeader({ titolo, sottotitolo }: { titolo: string; sottotitol
<p className="mt-1 truncate text-sm text-primary-foreground/80">{sottotitolo}</p>
) : null}
</div>
<TeamLogo className="h-11 w-11" />
{azione ?? <LinkProfilo />}
</div>
</header>
);