Files
Epicnabbo-Catalogus-Updated…/src/components/top-header.tsx
T

222 lines
5.8 KiB
TypeScript

import Image from "next/image";
import Link from "next/link";
import { auth, signOut } from "@/lib/auth";
import { avatarImageUrl } from "@/lib/format";
import { prisma } from "@/lib/prisma";
import { siteSettings } from "@/lib/services/site-settings";
function Currency({
icon,
amount,
label,
}: {
icon: string;
amount: number;
label: string;
}) {
return (
<div className="flex gap-x-1 sm:gap-x-2 items-center">
<div
className={`h-[20px] w-[20px] sm:h-[25px] sm:w-[25px] rounded-full outline-offset-[3px] ${icon}`}
/>
<div
style={{
color:
"var(--color-navbar-text-readable, var(--color-navbar-text, var(--color-text-muted)))",
}}
>
<span
className="font-semibold text-xs sm:text-sm"
style={{
color:
"var(--color-navbar-text-readable, var(--color-navbar-text, var(--color-text)))",
}}
>
{amount.toLocaleString()}
</span>{" "}
<span className="hidden sm:inline text-xs">{label}</span>
</div>
</div>
);
}
export async function TopHeader() {
const session = await auth();
if (!session?.user?.id) return null;
const id = Number(session.user.id);
let credits = 0;
let duckets = 0;
let diamonds = 0;
let look = "";
try {
const [user, currencies] = await Promise.all([
prisma.user.findUnique({
where: { id },
select: { credits: true, look: true },
}),
prisma.usersCurrency.findMany({ where: { userId: id } }),
]);
credits = user?.credits ?? 0;
look = user?.look ?? "";
for (const c of currencies) {
if (c.type === 0) duckets = c.amount;
if (c.type === 5) diamonds = c.amount;
}
} catch {
// render without live balances
}
const imager =
(await siteSettings.get(
"habbo_imaging_url",
"https://www.habbo.com/habbo-imaging/avatarimage",
)) ?? "";
const avatar = avatarImageUrl(imager, look, { headOnly: true, direction: 2 });
const isStaff = (session.user.rank ?? 0) >= 7;
return (
<div style={{ backgroundColor: "var(--color-navbar)" }}>
<div className="max-w-7xl min-h-[44px] sm:min-h-[60px] px-2 sm:px-4 flex items-center justify-between mx-auto">
<div className="flex flex-wrap gap-x-2 sm:gap-x-6">
<Currency icon="nav-credit-icon" amount={credits} label="Credits" />
<Currency icon="nav-ducket-icon" amount={duckets} label="Duckets" />
<Currency
icon="nav-diamond-icon"
amount={diamonds}
label="Diamonds"
/>
</div>
<div className="flex items-center gap-x-1 sm:gap-x-3">
{isStaff ? (
<details className="relative">
<summary
className="list-none cursor-pointer font-semibold text-xs sm:text-sm [&::-webkit-details-marker]:hidden"
style={{
color:
"var(--color-navbar-text-readable, var(--color-navbar-text, var(--color-text)))",
}}
>
<span className="hidden sm:inline">Administration</span>
<span className="sm:hidden">Admin</span>
</summary>
<div
role="menu"
className="dropdown-menu absolute right-0 top-full mt-0.5 min-w-[180px] rounded-xl z-50 py-2"
>
<Link href="/admin" className="dropdown-item" role="menuitem">
Admin panel
</Link>
<Link
href="/admin/commandocentrum"
className="dropdown-item"
role="menuitem"
>
Commandocentrum
</Link>
<Link
href="/admin/logs"
className="dropdown-item"
role="menuitem"
>
Logs
</Link>
<Link href="/logo" className="dropdown-item" role="menuitem">
Logo generator
</Link>
</div>
</details>
) : null}
<details className="relative">
<summary
aria-label="User menu"
className="list-none cursor-pointer flex items-center [&::-webkit-details-marker]:hidden"
>
<Image
className="bg-no-repeat bg-center"
src={avatar}
alt=""
width={54}
height={62}
unoptimized
/>
<span
className="hidden sm:inline -ml-2 font-semibold"
style={{
color:
"var(--color-navbar-text-readable, var(--color-navbar-text, var(--color-text)))",
}}
>
{session.user.name}
</span>
</summary>
<div
role="menu"
className="dropdown-menu fixed sm:absolute right-2 sm:right-0 top-auto sm:top-full mt-0.5 min-w-[200px] rounded-xl z-50 py-2"
>
<Link href="/me" className="dropdown-item" role="menuitem">
My dashboard
</Link>
<Link
href={`/u/${session.user.name}`}
className="dropdown-item"
role="menuitem"
>
My profile
</Link>
<Link href="/settings" className="dropdown-item" role="menuitem">
User settings
</Link>
<Link
href="/settings/2fa"
className="dropdown-item"
role="menuitem"
>
Two-factor
</Link>
<Link
href="/settings/sessions"
className="dropdown-item"
role="menuitem"
>
Login activity
</Link>
<div
className="h-px my-1 mx-3"
style={{
backgroundColor:
"color-mix(in srgb, var(--color-text-muted) 12%, transparent)",
}}
/>
<form
action={async () => {
"use server";
await signOut({ redirectTo: "/" });
}}
>
<button
type="submit"
role="menuitem"
className="dropdown-item w-full text-center mx-1 rounded-lg"
style={{
backgroundColor:
"color-mix(in srgb, var(--button-danger-color) 12%, transparent)",
color: "var(--button-danger-color)",
border: "none",
cursor: "pointer",
width: "calc(100% - 8px)",
}}
>
Logout
</button>
</form>
</div>
</details>
</div>
</div>
</div>
);
}