ai-chatbot/components/agents/AgentCanvasTopNavDark.tsx
2026-07-08 15:23:05 +08:00

126 lines
4.2 KiB
TypeScript

"use client";
import type { ReactNode } from "react";
import { ArrowLeft, Images, Layers, LayoutGrid, Wand2 } from "lucide-react";
import { Button } from "@/components/ui/button";
import { cn } from "@/lib/utils";
interface AgentCanvasTopNavDarkProps {
siteName?: string | null;
siteLogo?: string | null;
siteLogoDark?: string | null;
onBack?: () => void;
rightSlot?: ReactNode;
activeKey?: "featured" | "agent" | "canvas" | "gallery";
batchProcessingEnabled?: boolean;
}
const NAV_ITEMS = [
{
key: "featured" as const,
label: "批量处理",
icon: Layers,
onClick: () => window.location.assign(`/canvas/${crypto.randomUUID()}?batch=1`),
},
{
key: "agent" as const,
label: "风格化",
icon: Wand2,
onClick: () => window.location.assign("/canvas?mode=agent"),
},
{
key: "canvas" as const,
label: "无限画布",
icon: LayoutGrid,
onClick: () => window.location.assign(`/canvas/${crypto.randomUUID()}`),
},
{
key: "gallery" as const,
label: "我的图册",
icon: Images,
onClick: () => window.location.assign("/gallery"),
},
];
export function AgentCanvasTopNavDark({
siteName = "AI Chatbot",
siteLogo,
siteLogoDark,
onBack,
rightSlot = null,
activeKey = "agent",
batchProcessingEnabled = true,
}: AgentCanvasTopNavDarkProps) {
const resolvedSiteName = String(siteName || "AI Chatbot").trim() || "AI Chatbot";
const displayLogo = siteLogoDark?.trim() || siteLogo?.trim() || "";
return (
<header className="fixed top-0 left-0 right-0 z-50 border-b border-white/5 bg-black/80 backdrop-blur-xl">
<div className="mx-auto max-w-[1480px] px-6 lg:px-8 xl:px-10">
<div className="flex h-16 items-center justify-between gap-4">
<div className="flex min-w-0 items-center gap-3">
{onBack ? (
<button
type="button"
onClick={onBack}
className="flex h-9 w-9 shrink-0 items-center justify-center rounded-lg bg-white/5 text-white/60 transition-colors hover:bg-white/10 hover:text-white"
aria-label="返回上一步"
>
<ArrowLeft className="h-5 w-5" />
</button>
) : null}
<button
type="button"
onClick={() => window.location.assign("/")}
className="flex min-w-0 items-center gap-2.5 transition-opacity hover:opacity-80"
>
{displayLogo ? (
<img
src={displayLogo}
alt={resolvedSiteName}
className="h-8 w-8 shrink-0 object-contain"
/>
) : (
<div className="flex h-8 w-8 shrink-0 items-center justify-center rounded-lg bg-white/10">
<Wand2 className="h-4 w-4 text-white" />
</div>
)}
<span className="truncate text-base font-semibold text-white">{resolvedSiteName}</span>
</button>
</div>
<div className="ml-auto flex shrink-0 items-center gap-3">
<nav className="hidden items-center gap-2 md:flex">
{NAV_ITEMS.filter(
(item) => item.key !== "featured" || batchProcessingEnabled
).map((item) => {
const Icon = item.icon;
const isActive = item.key === activeKey;
return (
<button
key={item.key}
type="button"
onClick={item.onClick}
className={cn(
"flex items-center gap-2 rounded-full px-4 py-2 text-sm font-medium transition-all duration-300",
isActive
? "bg-white text-black"
: "bg-white/5 text-white/60 hover:bg-white/10 hover:text-white"
)}
>
<Icon className="h-4 w-4" />
{item.label}
</button>
);
})}
</nav>
{rightSlot ? <div className="flex items-center justify-end">{rightSlot}</div> : null}
</div>
</div>
</div>
</header>
);
}