teecup/frontend/components/tournament-card.tsx

87 lines
3 KiB
TypeScript
Raw Normal View History

import Link from "next/link"
import { Calendar, ChevronRight } from "lucide-react"
import { TournamentStatusBadge, type TournamentStatus } from "@/components/tournament-status-badge"
export type Tournament = {
id: string
name: string
status: TournamentStatus
startDate?: string
endDate?: string
}
const dateFormatter = new Intl.DateTimeFormat("no-NO", {
day: "numeric",
month: "short",
year: "numeric",
})
function formatDate(value?: string) {
if (!value) return null
const parsed = new Date(value)
if (Number.isNaN(parsed.getTime())) return null
return dateFormatter.format(parsed)
}
function formatDateRange(start?: string, end?: string) {
const from = formatDate(start)
const to = formatDate(end)
if (from && to) return from === to ? from : `${from} ${to}`
return from ?? to ?? null
}
export function TournamentCard({
tournament,
orgId,
organizer = false,
}: {
tournament: Tournament
// Satt (dashbordet, innlogget) -> lenker til den innloggede detaljsiden.
// Utelatt (klubb-landingsside, offentlig) -> lenker til den offentlige
// /t/{id}-ruten i stedet. Samme kort, to kontekster.
orgId?: string
// Vis en "Arrangør"-merkelapp (dashbordets slåtte-sammen "Kommende
// turneringer"-liste, 2026-07-25 -- deltaker- og arrangør-turneringer i
// ÉN liste, merkelappen skiller dem visuelt).
organizer?: boolean
}) {
const dateRange = formatDateRange(tournament.startDate, tournament.endDate)
const href = orgId
? `/tournaments/${tournament.id}?org=${orgId}&name=${encodeURIComponent(tournament.name)}`
: `/t/${tournament.id}`
return (
<Link
href={href}
className="group flex w-full items-center gap-4 rounded-2xl border border-border bg-card p-4 text-left shadow-sm shadow-black/5 transition-colors hover:border-primary/50 hover:bg-accent/50 sm:p-5"
>
<div className="flex min-w-0 flex-1 flex-col gap-2">
<div className="flex flex-wrap items-center gap-x-3 gap-y-2">
<h3 className="truncate text-base font-bold text-foreground sm:text-lg">
{tournament.name}
</h3>
<TournamentStatusBadge status={tournament.status} />
{organizer && (
<span className="inline-flex items-center gap-1.5 rounded-full bg-brand-orange/15 px-2.5 py-1 text-xs font-semibold text-foreground">
<span aria-hidden="true" className="size-1.5 rounded-full bg-brand-orange" />
Arrangør
</span>
)}
</div>
{dateRange ? (
<div className="flex items-center gap-1.5 text-sm text-muted-foreground">
<Calendar aria-hidden="true" className="size-4 shrink-0" />
<span className="tabular-nums">{dateRange}</span>
</div>
) : (
<span className="text-sm text-muted-foreground">Ingen datoer satt</span>
)}
</div>
<ChevronRight
aria-hidden="true"
className="size-5 shrink-0 text-muted-foreground transition-transform group-hover:translate-x-0.5 group-hover:text-foreground"
/>
</Link>
)
}