first commit

This commit is contained in:
2026-04-26 21:27:00 +07:00
commit 3ce6f0510b
48 changed files with 9700 additions and 0 deletions
+55
View File
@@ -0,0 +1,55 @@
import { NavLink } from "react-router-dom";
import { Film, Settings2, Video } from "lucide-react";
import type { ReactNode } from "react";
function NavItem({
to,
label,
icon,
}: {
to: string;
label: string;
icon: ReactNode;
}) {
return (
<NavLink
to={to}
className={({ isActive }) =>
[
"inline-flex items-center gap-2 rounded-md px-3 py-2 text-sm font-medium transition",
isActive
? "bg-zinc-800 text-zinc-50"
: "text-zinc-300 hover:bg-zinc-900 hover:text-zinc-50",
].join(" ")
}
>
<span className="inline-flex h-4 w-4 items-center justify-center">{icon}</span>
<span>{label}</span>
</NavLink>
);
}
export default function TopNav() {
return (
<header className="border-b border-zinc-800 bg-zinc-950/70 backdrop-blur">
<div className="mx-auto flex w-full max-w-7xl items-center justify-between gap-4 px-4 py-3 md:px-6">
<div className="flex items-center gap-3">
<div className="flex h-9 w-9 items-center justify-center rounded-lg bg-zinc-900 ring-1 ring-zinc-800">
<Video className="h-5 w-5" />
</div>
<div className="leading-tight">
<div className="text-sm font-semibold">IPCam Dashboard</div>
<div className="text-xs text-zinc-400">MediaMTX + Orange Pi</div>
</div>
</div>
<nav className="flex items-center gap-1">
<NavItem to="/live" label="Live" icon={<Video className="h-4 w-4" />} />
<NavItem to="/playback" label="Playback" icon={<Film className="h-4 w-4" />} />
<NavItem to="/settings" label="Settings" icon={<Settings2 className="h-4 w-4" />} />
</nav>
</div>
</header>
);
}