Files
vkv/resources/js/components/AppBreadcrumbs.tsx
Zdeněk Burda 41e3ce6f25 Initial commit
2026-01-09 21:26:40 +01:00

85 lines
2.7 KiB
TypeScript

import React from "react";
import { Breadcrumbs, BreadcrumbItem } from "@heroui/react";
import { useContestStore } from "@/stores/contestStore";
import { useLanguageStore } from "@/stores/languageStore";
import { useNavigate } from "react-router-dom";
type AppBreadcrumbsProps = {
extra?: { label: string; href?: string }[];
};
export default function AppBreadcrumbs({ extra = [] }: AppBreadcrumbsProps) {
const selectedContest = useContestStore((s) => s.selectedContest);
const selectedRound = useContestStore((s) => s.selectedRound);
const setSelectedRound = useContestStore((s) => s.setSelectedRound);
const clearSelection = useContestStore((s) => s.clearSelection);
const setSelectedContest = useContestStore((s) => s.setSelectedContest);
const locale = useLanguageStore((s) => s.locale);
const navigate = useNavigate();
const resolveLabel = (value: any): string => {
if (!value) return "";
if (typeof value === "string") return value;
if (typeof value === "object") {
if (value[locale]) return value[locale];
if (value["en"]) return value["en"];
const first = Object.values(value)[0];
return typeof first === "string" ? first : "";
}
return String(value);
};
const crumbs = [
{ label: "Home", href: "/", level: "home" as const },
{ label: "Závody", href: "/contests", level: "contests" as const },
...(selectedContest
? [{
label: resolveLabel(selectedContest.name),
href: `/contests/${selectedContest.id}`,
level: "contest" as const,
contest: selectedContest,
}]
: []),
...(selectedRound
? [{
label: resolveLabel(selectedRound.name),
href: `/contests/${selectedContest?.id ?? ""}/rounds/${selectedRound.id}`,
level: "round" as const,
}]
: []),
...extra,
];
const handleNavigate = (href?: string, level?: "home" | "contests" | "contest" | "round", contest?: any) => {
if (!href) return;
// při kliknutí na vyšší úroveň vyčisti nižší selekce
if (level === "home") {
clearSelection();
} else if (level === "contests") {
setSelectedRound(null);
} else if (level === "contest") {
setSelectedRound(null);
if (contest) {
setSelectedContest(contest);
}
}
navigate(href);
};
return (
<Breadcrumbs aria-label="Breadcrumb" variant="solid" className="mb-2">
{crumbs.map((c, idx) => (
<BreadcrumbItem
key={`${c.label}-${idx}`}
href={c.href}
onPress={() => handleNavigate(c.href, c.level as any, (c as any).contest)}
>
{c.label}
</BreadcrumbItem>
))}
</Breadcrumbs>
);
}