gh_UserManager/apps/web/components/sections/hero.tsx
bermooda-company 54d5891edf user
2026-08-23 23:59:14 +03:30

123 lines
4.9 KiB
TypeScript

"use client";
import { ArrowRight, ArrowLeft, ShieldCheck, UserCircle2 } from "lucide-react";
import Link from "next/link";
import { useLanguage } from "@/components/language-provider";
import { Button, buttonVariants } from "@/components/ui/button";
import { Badge } from "@/components/ui/badge";
import { PRODUCTS } from "@/lib/content";
import { cn } from "@/lib/utils";
export function Hero() {
const { t, lang, dir } = useLanguage();
const Arrow = lang === "fa" ? ArrowLeft : ArrowRight;
return (
<section id="top" className="relative overflow-hidden bg-white dark:bg-ink">
<div className="pointer-events-none absolute inset-0 bg-grid-faint opacity-[0.03] dark:opacity-100 [mask-image:radial-gradient(ellipse_at_top,black,transparent_70%)]" />
<div className="pointer-events-none absolute -top-40 left-1/2 h-[36rem] w-[36rem] -translate-x-1/2 rounded-full bg-brand-600/10 dark:bg-brand-600/20 blur-3xl" />
<div className="container-x relative grid items-center gap-16 py-24 lg:grid-cols-2 lg:py-32">
<div className="animate-fade-up">
<Badge>
<ShieldCheck className="h-3.5 w-3.5" />
{t.hero.badge}
</Badge>
<h1 className="mt-6 text-4xl font-bold leading-[1.1] tracking-tight text-slate-900 dark:text-white sm:text-5xl lg:text-6xl">
<span className="gradient-text">{t.hero.title}</span>
</h1>
<p className="mt-6 max-w-xl text-lg leading-relaxed text-slate-600 dark:text-slate-400">
{t.hero.subtitle}
</p>
<div className="mt-9 flex flex-wrap gap-3">
<Link href="/login" className={cn(buttonVariants({ size: "lg" }))}>
{t.hero.ctaPrimary}
<Arrow className="h-5 w-5 rtl:rotate-180" />
</Link>
<Link href="/account" className={cn(buttonVariants({ size: "lg", variant: "secondary" }))}>
<UserCircle2 className="h-5 w-5" />
{t.hero.ctaSecondary}
</Link>
</div>
<p className="mt-6 text-sm text-slate-500 dark:text-slate-500">{t.hero.note}</p>
</div>
<div className="relative flex items-center justify-center">
<HubVisual />
</div>
</div>
</section>
);
}
function HubVisual() {
const { lang } = useLanguage();
return (
<div className="relative h-80 w-full max-w-md" dir="ltr">
<div className="absolute left-1/2 top-1/2 h-28 w-28 -translate-x-1/2 -translate-y-1/2 rounded-3xl bg-brand-gradient shadow-2xl shadow-brand-900/50 ring-4 ring-white/10">
<div className="flex h-full w-full flex-col items-center justify-center text-white">
<ShieldCheck className="h-8 w-8" />
<span className="mt-1 text-xs font-semibold">
{lang === "fa" ? "هاب مرکزی" : "Central Hub"}
</span>
</div>
</div>
{PRODUCTS.map((p, i) => {
const angle = (Math.PI * 2 * i) / PRODUCTS.length - Math.PI / 2;
const radius = 130;
const x = 50 + (Math.cos(angle) * radius) / 3.2;
const y = 50 + (Math.sin(angle) * radius) / 3.2;
return (
<div
key={p.key}
className="absolute h-20 w-20 -translate-x-1/2 -translate-y-1/2 rounded-2xl border border-slate-200 bg-white p-3 text-center shadow-sm backdrop-blur dark:border-white/10 dark:bg-white/[0.04] dark:shadow-none"
style={{ left: `${x}%`, top: `${y}%` }}
>
<div className="flex h-full flex-col items-center justify-center gap-1">
<span className="text-sm font-semibold text-slate-900 dark:text-white">{p.name}</span>
<span
className={
"rounded-full px-2 py-0.5 text-[10px] " +
(p.status === "connected"
? "bg-emerald-500/15 text-emerald-700 dark:text-emerald-300"
: "bg-slate-100 text-slate-500 dark:bg-white/10 dark:text-slate-400")
}
>
{p.status === "connected"
? lang === "fa"
? "متصل"
: "Live"
: lang === "fa"
? "آینده"
: "Soon"}
</span>
</div>
</div>
);
})}
<svg className="absolute inset-0 h-full w-full" viewBox="0 0 100 100" preserveAspectRatio="none">
{PRODUCTS.map((_, i) => {
const angle = (Math.PI * 2 * i) / PRODUCTS.length - Math.PI / 2;
const radius = 130;
const x = 50 + (Math.cos(angle) * radius) / 3.2;
const y = 50 + (Math.sin(angle) * radius) / 3.2;
return (
<line
key={i}
x1="50"
y1="50"
x2={x}
y2={y}
stroke="rgba(129,140,248,0.35)"
strokeWidth="0.4"
strokeDasharray="2 2"
/>
);
})}
</svg>
</div>
);
}