fix some bug in some blocks

This commit is contained in:
mr.sabri
2026-07-23 06:55:21 +03:30
parent 89fbd6d158
commit edb3e10469
65 changed files with 1565 additions and 1476 deletions
+23 -16
View File
@@ -11,34 +11,41 @@ interface Feature109Props {
const Feature109 = ({ className }: Feature109Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="grid place-items-center gap-10 lg:grid-cols-2">
<div className="flex flex-col gap-5 text-start">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<div className="grid min-w-0 place-items-center gap-10 lg:grid-cols-2">
<div className="flex min-w-0 flex-col gap-5 text-start">
<Badge variant="outline" className="w-fit bg-background">
کمپین
</Badge>
<h3 className="text-3xl font-semibold lg:text-2xll">
<h3 className="text-balance text-3xl font-semibold lg:text-2xll">
ردیابی UTM
</h3>
<p className="text-muted-foreground lg:text-lg">
<p className="text-balance text-muted-foreground lg:text-lg">
گزارش ROI
</p>
<Button className="mt-2.5 w-fit gap-2" size="lg">
<Button
className="mt-2.5 h-auto max-w-full gap-2 whitespace-normal text-balance"
size="lg"
>
با سگمنت‌بندی دقیق، پیام مناسب را به مخاطب مناسب برسانید. داده رفتاری نشان می‌دهد کدام محتوا بیشترین تأثیر را روی تبدیل دارد.
<Menu className="h-auto w-4" />
<Menu className="h-auto w-4 shrink-0" />
</Button>
</div>
<div className="relative rounded-xl">
<div className="relative w-full min-w-0 overflow-hidden rounded-xl">
<img
src="/block-media/external/unsplash/photo-1567320743368-9db24e12ebf0.jpg"
alt="تحلیل عملکرد کمپین"
className="rounded-xl object-cover md:aspect-video lg:aspect-auto"
className="max-w-full rounded-xl object-cover md:aspect-video lg:aspect-auto"
/>
<div className="absolute inset-0 rounded-xl bg-linear-to-t from-primary via-transparent to-transparent" />
<div className="absolute top-0 flex h-full w-full flex-col justify-between p-7">
<span className="ms-auto flex w-fit items-center gap-2 rounded-full bg-background/30 px-4 py-2.5 text-sm font-semibold backdrop-blur-sm">
<Avatar className="size-7 rounded-full">
<div className="absolute inset-0 flex h-full w-full min-w-0 flex-col justify-between p-7">
<span className="ms-auto flex w-fit max-w-full items-center gap-2 rounded-full bg-background/30 px-4 py-2.5 text-sm font-semibold backdrop-blur-sm">
<Avatar className="size-7 shrink-0 rounded-full">
<AvatarImage
src="/block-media/shadcnblocks/block/avatar-1.webp"
alt="نمودار ROI"
@@ -46,13 +53,13 @@ const Feature109 = ({ className }: Feature109Props) => {
</Avatar>
رشد برند
</span>
<div className="flex flex-col gap-5 text-background">
<h4 className="text-lg font-semibold lg:text-3xl">
<div className="flex min-w-0 flex-col gap-5 text-background">
<h4 className="text-balance text-lg font-semibold lg:text-3xl">
مدیریت کمپین
</h4>
<a href="#" className="flex items-center gap-1 font-medium">
سگمنت‌بندی مخاطب
<ChevronRight className="h-auto w-4 rtl:rotate-180" />
<ChevronRight className="h-auto w-4 shrink-0 rtl:rotate-180" />
</a>
</div>
</div>
+2 -2
View File
@@ -11,7 +11,7 @@ const team = [
alt: "صف اولویت سرنخ‌ها",
},
{
name: "Michael Lee",
name: "عملکرد فروش",
role: "سرنخ‌های با بالاترین احتمال تبدیل را در بالای صف کار روزانه قرار دهید.",
avatar: "/block-media/shadcnblocks/block/avatar-2.webp",
alt: "داشبورد عملکرد فروش",
@@ -66,7 +66,7 @@ const Feature120 = ({ className }: Feature120Props) => {
</div>
))}
</div>
<Button className="w-fit">با یادآورهای هوشمند و اولویت‌بندی سرنخ، زمان تیم روی معاملات با احتمال بیشتر صرف می‌شود و چرخه فروش کوتاه‌تر می‌شود.</Button>
<Button className="w-fit">شروع کنید</Button>
</div>
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
+14 -10
View File
@@ -101,9 +101,13 @@ interface Feature154Props {
const Feature154 = ({ className }: Feature154Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="mx-auto flex max-w-3xl flex-col items-center justify-center gap-6 text-center">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<div className="mx-auto flex max-w-3xl min-w-0 flex-col items-center justify-center gap-6 text-center">
<Badge variant="outline">ERP</Badge>
<h1 className="text-xl font-semibold text-balance md:text-2xll">
عملیات سازمان را یکپارچه کنید
@@ -112,12 +116,12 @@ const Feature154 = ({ className }: Feature154Props) => {
گزارش‌های یکپارچه نشان می‌دهد کدام بخش بیشترین تأثیر را روی سودآوری دارد.
</p>
</div>
<div className="relative mt-10">
<div className="relative mt-10 w-full min-w-0 overflow-hidden">
<Marquee className="[--duration:30s]">
{badges.map((badge) => (
{badges.map((badge, index) => (
<div
key={badge.title}
className="flex items-center gap-2 rounded-full bg-muted px-4 py-2"
key={`row1-${badge.title}-${index}`}
className="flex shrink-0 items-center gap-2 rounded-full bg-muted px-4 py-2"
>
{badge.icon}
{badge.title}
@@ -125,10 +129,10 @@ const Feature154 = ({ className }: Feature154Props) => {
))}
</Marquee>
<Marquee reverse className="[--duration:30s]">
{badges.map((badge) => (
{badges.map((badge, index) => (
<div
key={badge.title}
className="flex items-center gap-2 rounded-full bg-muted px-4 py-2"
key={`row2-${badge.title}-${index}`}
className="flex shrink-0 items-center gap-2 rounded-full bg-muted px-4 py-2"
>
{badge.icon}
{badge.title}
+12 -8
View File
@@ -60,10 +60,14 @@ interface Feature183Props {
const Feature183 = ({ className }: Feature183Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="w-full shrink-0">
<div className="relative mx-auto h-96 w-full rounded-3xl bg-muted bg-cover bg-center bg-no-repeat sm:h-96">
<section
dir="rtl"
lang="fa"
className={cn("w-full min-w-0 overflow-x-clip pb-32", className)}
>
<div className="container min-w-0">
<div className="w-full min-w-0 shrink-0 pt-32">
<div className="relative mx-auto h-96 w-full min-w-0 rounded-3xl bg-muted bg-cover bg-center bg-no-repeat sm:h-96">
<svg
xmlns="http://www.w3.org/2000/svg"
width="100%"
@@ -104,7 +108,7 @@ const Feature183 = ({ className }: Feature183Props) => {
</defs>
</svg>
<div className="absolute -top-32 start-1/2 bottom-0 z-10 mt-12 w-[12.5rem] -translate-x-1/2 transform overflow-hidden sm:w-[18.75rem]">
<div className="absolute -top-32 start-1/2 bottom-0 z-10 mt-12 w-[12.5rem] max-w-[calc(100%-2rem)] -translate-x-1/2 transform overflow-hidden sm:w-[18.75rem]">
<img
src="/block-media/shadcnblocks/block/hero108/iphone.png"
alt="گزارش مالی یکپارچه"
@@ -117,7 +121,7 @@ const Feature183 = ({ className }: Feature183Props) => {
/>
</div>
<div className="absolute top-12 end-1/4 z-20 hidden w-60 transform rounded-2xl border bg-background p-4 text-start shadow-md md:-rotate-12 lg:block">
<div className="absolute top-12 end-[max(1rem,12%)] z-20 hidden w-60 max-w-[min(15rem,42%)] transform rounded-2xl border bg-background p-4 text-start shadow-md md:-rotate-12 lg:block">
<div className="flex flex-row">
<h3 className="text-lg font-semibold">گردش تأیید</h3>
<Badge variant="secondary" className="ms-auto rounded-sm">
@@ -131,7 +135,7 @@ const Feature183 = ({ className }: Feature183Props) => {
</div>
</div>
<div className="absolute top-12 start-1/4 z-20 hidden w-60 transform rounded-lg border bg-background p-4 text-start shadow-md lg:block">
<div className="absolute top-12 start-[max(1rem,12%)] z-20 hidden w-60 max-w-[min(15rem,42%)] transform rounded-lg border bg-background p-4 text-start shadow-md lg:block">
<div className="flex flex-row border-b pb-4">
<h3 className="text-lg font-semibold">ERP</h3>
<div className="relative ms-auto">
@@ -168,7 +172,7 @@ const Feature183 = ({ className }: Feature183Props) => {
</div>
</div>
<div className="mt-14 flex flex-col items-center justify-center gap-x-24 gap-y-8 lg:flex-row">
<div className="mt-14 flex min-w-0 flex-col items-center justify-center gap-x-24 gap-y-8 lg:flex-row">
{DATA.map((item) => (
<StatCard key={item.title} {...item} />
))}
+17 -13
View File
@@ -66,24 +66,28 @@ const Feature197 = ({
const [activeImage, setActiveImage] = useState(features[0].image);
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container mx-auto">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full min-w-0 overflow-hidden py-32", className)}
>
<div className="container mx-auto min-w-0">
<h2 className="mb-12 text-3xl font-semibold text-balance md:text-xl">
عملیات سازمان را یکپارچه کنید
</h2>
<div className="flex w-full items-start justify-between gap-12">
<div className="w-full md:w-1/2">
<div className="flex w-full min-w-0 flex-col items-stretch justify-between gap-8 md:flex-row md:items-start md:gap-12">
<div className="w-full min-w-0 md:w-1/2">
<Accordion
type="single"
collapsible
className="w-full"
className="w-full min-w-0"
defaultValue="item-1"
>
{features.map((tab) => (
<AccordionItem
key={tab.id}
value={`item-${tab.id}`}
className="transition-opacity hover:opacity-80"
className="min-w-0 transition-opacity hover:opacity-80"
>
<AccordionTrigger
onClick={() => {
@@ -94,7 +98,7 @@ const Feature197 = ({
>
<span
className={cn(
"text-xl",
"min-w-0 text-xl text-balance break-words",
tab.id === activeTabId
? "text-foreground"
: "text-muted-foreground",
@@ -104,14 +108,14 @@ const Feature197 = ({
</span>
</AccordionTrigger>
<AccordionContent className="pb-2">
<p className="text-base text-pretty text-muted-foreground">
<p className="text-base text-pretty break-words text-muted-foreground">
{tab.description}
</p>
<div className="mt-4 md:hidden">
<div className="mt-4 overflow-hidden rounded-md md:hidden">
<img
src={tab.image}
alt={tab.imageAlt}
className="h-full max-h-80 w-full rounded-md object-cover"
className="h-full max-h-80 w-full object-cover"
/>
</div>
</AccordionContent>
@@ -119,15 +123,15 @@ const Feature197 = ({
))}
</Accordion>
</div>
<div className="relative hidden w-1/2 overflow-hidden rounded-xl bg-muted md:block">
<div className="relative aspect-4/3">
<div className="relative hidden w-full min-w-0 overflow-hidden rounded-xl bg-muted md:block md:w-1/2">
<div className="relative aspect-4/3 w-full">
{features.map((feature) => (
<img
key={feature.id}
src={feature.image}
alt={feature.imageAlt}
className={cn(
"absolute inset-0 h-full w-full rounded-md object-cover transition-opacity duration-500",
"absolute inset-0 size-full object-cover transition-opacity duration-500",
activeImage === feature.image ? "opacity-100" : "opacity-0",
)}
/>
+33 -38
View File
@@ -16,27 +16,23 @@ const DATA: DataItem[] = [
{
id: "simplify-workflow",
title: "سطح دسترسی",
description:
"گزارش سفارشی را بدون SQL بسازید و سریع منتشر کنید.",
description: "گزارش سفارشی را بدون SQL بسازید و سریع منتشر کنید.",
icon: <Workflow />,
className: "absolute top-0.5 cursor-pointer",
className: "lg:mt-0",
},
{
id: "eliminate-clunky-tools",
title: "تحلیل پیش‌بین",
description:
"ابعاد مختلف را بچرخانید و الگوی پنهان را پیدا کنید.",
description: "ابعاد مختلف را بچرخانید و الگوی پنهان را پیدا کنید.",
icon: <Wrench />,
className:
"absolute -end-4 top-5 cursor-pointer xl:end-5 xl:top-0",
className: "lg:mt-10",
},
{
id: "connect-workflows",
title: "اشتراک گزارش",
description:
"نمای اجرایی برای تصمیم‌های سریع طراحی کنید.",
description: "نمای اجرایی برای تصمیم‌های سریع طراحی کنید.",
icon: <Cable />,
className: "absolute bottom-2 start-[25%] cursor-pointer",
className: "lg:mt-4",
},
];
@@ -52,15 +48,20 @@ const CardComponent = ({
className?: string;
}) => {
return (
<div className={className}>
<Card className="flex max-w-lg transform items-center gap-4 rounded-2xl p-6 text-start shadow-lg transition-transform hover:scale-105">
<div className="shrink-0 rounded-full bg-muted p-3.5">{icon}</div>
<div className="font-semibold">
<p>{title}</p>
<p className="text-pretty text-muted-foreground">{description}</p>
</div>
</Card>
</div>
<Card
className={cn(
"flex w-full max-w-lg transform items-center gap-4 rounded-2xl p-6 text-start shadow-lg transition-transform hover:scale-105",
className,
)}
>
<div className="shrink-0 rounded-full bg-muted p-3.5">{icon}</div>
<div className="min-w-0 font-semibold">
<p className="text-balance break-words">{title}</p>
<p className="text-pretty break-words text-muted-foreground">
{description}
</p>
</div>
</Card>
);
};
@@ -70,30 +71,24 @@ interface Feature198Props {
const Feature198 = ({ className }: Feature198Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="relative py-20 md:py-24 lg:py-28">
<h2 className="mx-auto max-w-5xl text-center text-2xll font-medium text-balance sm:text-2xll lg:text-2xll xl:text-[85px]">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full min-w-0 overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<div className="relative flex w-full min-w-0 flex-col gap-12 py-12 md:gap-16 md:py-16 lg:py-20">
<h2 className="mx-auto max-w-5xl text-center text-3xl font-medium text-balance sm:text-4xl md:text-5xl lg:text-6xl xl:text-7xl">
<span className="text-muted-foreground">
ابزارهای شما باید با کسب‌وکار شما سازگار شوند.{" "}
</span>
<span>داشبوردهای تعاملی به تیم‌ها اجازه می‌دهد سؤال جدید بپرسند بدون اینکه هر بار به تیم داده وابسته باشند.</span>
<span>
داشبوردهای تعاملی به تیم‌ها اجازه می‌دهد سؤال جدید بپرسند بدون
اینکه هر بار به تیم داده وابسته باشند.
</span>
</h2>
<div className="lg:hidden">
<div className="grid translate-y-4 justify-items-center gap-2">
{DATA.map((card) => (
<CardComponent
key={card.id}
title={card.title}
description={card.description}
icon={card.icon}
/>
))}
</div>
</div>
<div className="absolute inset-0 max-lg:hidden">
<div className="mx-auto grid w-full min-w-0 max-w-6xl justify-items-center gap-4 sm:gap-6 lg:grid-cols-3 lg:items-start lg:gap-8">
{DATA.map((card) => (
<CardComponent
key={card.id}
+18 -11
View File
@@ -24,37 +24,44 @@ interface Feature204Props {
const Feature204 = ({ className }: Feature204Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="flex flex-col items-center gap-10 md:gap-24 lg:flex-row lg:items-stretch">
<div className="grid w-full max-w-lg place-items-center rounded-2xl bg-[url('/block-media/shadcnblocks/block/photos/ivan-bandura-hqnUYXsN5oY-unsplash.jpg')] bg-cover bg-center bg-no-repeat px-8 py-10 sm:px-16 sm:py-20">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<div className="flex min-w-0 flex-col items-center gap-10 md:gap-24 lg:flex-row lg:items-stretch">
<div className="grid w-full max-w-lg min-w-0 place-items-center overflow-hidden rounded-2xl bg-[url('/block-media/shadcnblocks/block/photos/ivan-bandura-hqnUYXsN5oY-unsplash.jpg')] bg-cover bg-center bg-no-repeat px-8 py-10 sm:px-16 sm:py-20">
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
alt="گزارش عملکرد"
className="rounded-2xl"
className="max-w-full rounded-2xl"
/>
</div>
<div className="flex max-w-2xl flex-col justify-between gap-10">
<div className="text-center lg:text-start">
<div className="flex w-full min-w-0 max-w-2xl flex-col justify-between gap-10">
<div className="min-w-0 text-center lg:text-start">
<h2 className="text-2xll font-medium text-balance lg:text-2xll">
داده پراکنده را به تصمیم تبدیل کنید
</h2>
<p className="mt-6 text-lg text-pretty text-muted-foreground">
گزارش‌های بصری نشان می‌دهند کدام اقدام بیشترین اثر را روی درآمد و نگهداشت مشتری داشته است.
</p>
<Button size="lg" className="mt-8 gap-2">
<Button
size="lg"
className="mt-8 h-auto max-w-full gap-2 whitespace-normal text-balance"
>
داده فروش، بازاریابی و پشتیبانی در داشبوردهای یکپارچه جمع می‌شود. مدیران بدون انتظار گزارش دستی، وضعیت واقعی کسب‌وکار را می‌بینند.
<Zap className="size-4" />
<Zap className="size-4 shrink-0" />
</Button>
</div>
<div className="grid gap-7 sm:grid-cols-2">
<div className="grid min-w-0 gap-7 sm:grid-cols-2">
{FEATURES.map((feature) => {
const Icon = feature.icon;
return (
<div
key={feature.id}
className="text-center lg:text-start"
className="min-w-0 text-center lg:text-start"
>
<Icon className="mx-auto size-8 lg:ms-0 lg:me-auto" />
<h3 className="mt-4 mb-2 text-lg font-semibold">
+23 -18
View File
@@ -151,6 +151,7 @@ interface Feature216Props {
const Feature216 = ({ className }: Feature216Props) => {
const [buttonPosition, setButtonPosition] = useState<number>(0);
// Rightmost tab in RTL (`justify-start`) is the first item.
const [tabValue, setTabValue] = useState<TabValue>(TAB_ITEMS[0].value);
const triggerRefs = useRef<HTMLButtonElement[]>([]);
const imageRef = useRef<HTMLDivElement | null>(null);
@@ -198,6 +199,8 @@ const Feature216 = ({ className }: Feature216Props) => {
setTabValue(value as TabValue);
};
const currentIndex = getCurrentTabIndex();
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
@@ -205,7 +208,7 @@ const Feature216 = ({ className }: Feature216Props) => {
شاخص‌های کلیدی را یکجا ببینید
</h2>
<Tabs value={tabValue} onValueChange={onValueChange} className="w-full">
<TabsList className="hidden !h-auto w-full items-end gap-12 bg-transparent pb-10 xl:flex">
<TabsList className="hidden !h-auto w-full !justify-start items-end gap-12 bg-transparent pb-10 xl:flex">
{TAB_ITEMS.map((trigger, index) => {
const Icon = trigger.icon;
@@ -259,32 +262,34 @@ const Feature216 = ({ className }: Feature216Props) => {
</p>
</TabsContent>
))}
<div
className="absolute start-0 translate-y-1/2"
style={{ bottom: buttonPosition }}
>
<Button
variant="secondary"
disabled={getCurrentTabIndex() === 0}
onClick={() => handleTabNavigation("prev")}
size="lg"
className="size-12 -translate-x-1/2 rounded-full border shadow-lg rtl:translate-x-1/2"
>
<ArrowLeft className="rtl:rotate-180" />
</Button>
</div>
{/* Physical left (end in RTL): previous — moves toward rightmost tabs */}
<div
className="absolute end-0 translate-y-1/2"
style={{ bottom: buttonPosition }}
>
<Button
variant="secondary"
disabled={getCurrentTabIndex() === TAB_ITEMS.length - 1}
onClick={() => handleTabNavigation("next")}
disabled={currentIndex <= 0}
onClick={() => handleTabNavigation("prev")}
size="lg"
className="size-12 translate-x-1/2 rounded-full border shadow-lg rtl:-translate-x-1/2"
>
<ArrowRight className="rtl:rotate-180" />
<ArrowRight />
</Button>
</div>
{/* Physical right (start in RTL): next — moves toward leftmost tabs */}
<div
className="absolute start-0 translate-y-1/2"
style={{ bottom: buttonPosition }}
>
<Button
variant="secondary"
disabled={currentIndex >= TAB_ITEMS.length - 1}
onClick={() => handleTabNavigation("next")}
size="lg"
className="size-12 -translate-x-1/2 rounded-full border shadow-lg rtl:translate-x-1/2"
>
<ArrowLeft />
</Button>
</div>
</div>
+49 -19
View File
@@ -1,6 +1,6 @@
"use client";
import { ChevronRight, Plus } from "lucide-react";
import { ChevronLeft, ChevronRight, Plus } from "lucide-react";
import React from "react";
import { Button } from "@/components/ui/button";
@@ -9,8 +9,6 @@ import {
Carousel,
CarouselContent,
CarouselItem,
CarouselNext,
CarouselPrevious,
} from "@/components/ui/carousel";
import { cn } from "@/lib/utils";
@@ -49,7 +47,11 @@ const TESTIMONIALS = [
},
] as const;
const Feature242 = () => {
interface Feature242Props {
className?: string;
}
const Feature242 = ({ className }: Feature242Props) => {
const [api, setApi] = React.useState<CarouselApi>();
const [current, setCurrent] = React.useState(0);
const [count, setCount] = React.useState(0);
@@ -71,9 +73,13 @@ const Feature242 = () => {
value.toLocaleString("fa-IR", { minimumIntegerDigits: 2 });
return (
<section dir="rtl" lang="fa" className="overflow-hidden py-32">
<div className="relative container flex flex-col items-center md:px-0 lg:pt-8">
<div className="relative z-10 w-full items-center justify-between text-start lg:flex">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="relative container flex min-w-0 flex-col items-center md:px-0 lg:pt-8">
<div className="relative z-10 w-full min-w-0 items-center justify-between text-start lg:flex">
<h1 className="max-w-2xl text-2xll font-semibold tracking-tighter text-balance md:text-2xll">
با هوش مصنوعی سریع‌تر تصمیم بگیرید
</h1>
@@ -89,30 +95,31 @@ const Feature242 = () => {
</span>
</p>
</div>
<DottedDiv className="mt-8 flex w-full items-center justify-center px-2 py-10">
<DottedDiv className="mt-8 flex w-full min-w-0 items-center justify-center px-2 py-10">
<Carousel
opts={{
align: "center",
loop: true,
direction: "rtl",
}}
className="w-full"
className="w-full min-w-0"
setApi={setApi}
>
<CarouselContent className="m-0 flex w-full">
{/* Override -ml-4 — breaks RTL track sizing */}
<CarouselContent className="-ml-0! m-0 flex w-full">
{TESTIMONIALS.map((item) => (
<CarouselItem
key={item.id}
className="px-2 md:basis-1/2 lg:basis-1/3"
className="min-w-0 pl-0! px-2 md:basis-1/2 lg:basis-1/3"
>
<div className="group relative flex h-full max-h-96 w-full flex-col items-start justify-between rounded-3xl bg-muted p-5 text-ellipsis">
<div className="group relative flex h-full max-h-96 w-full min-w-0 flex-col items-start justify-between rounded-3xl bg-muted p-5 text-ellipsis">
<img
className="max-h-72 w-full opacity-100 transition-all ease-in-out group-hover:scale-90 group-hover:opacity-60"
className="max-h-72 w-full max-w-full opacity-100 transition-all ease-in-out group-hover:scale-90 group-hover:opacity-60"
src={item.imgSrc}
alt={item.imageAlt}
/>
<div className="flex w-full items-center justify-between gap-4">
<h5 className="text-xl leading-7 font-medium tracking-tighter text-balance transition-all ease-in-out group-hover:translate-x-4 rtl:group-hover:-translate-x-4">
<div className="flex w-full min-w-0 items-center justify-between gap-4">
<h5 className="min-w-0 text-xl leading-7 font-medium tracking-tighter text-balance transition-all ease-in-out group-hover:translate-x-4 rtl:group-hover:-translate-x-4">
{item.title}
</h5>
<a
@@ -142,9 +149,32 @@ const Feature242 = () => {
</span>
</div>
<div className="relative me-10 flex gap-2">
<CarouselPrevious className="size-10" />
<CarouselNext variant="default" className="size-10" />
{/*
Embla RTL: scrollNext/scrollPrev are index-based, so default
ChevronLeft→prev / ChevronRight→next feels reversed visually.
Match arrow direction to movement by swapping handlers.
*/}
<div className="relative z-10 flex gap-2">
<Button
type="button"
variant="outline"
size="icon"
className="size-10 rounded-full"
onClick={() => api?.scrollNext()}
aria-label="اسلاید بعدی"
>
<ChevronLeft className="size-4" />
</Button>
<Button
type="button"
variant="default"
size="icon"
className="size-10 rounded-full"
onClick={() => api?.scrollPrev()}
aria-label="اسلاید قبلی"
>
<ChevronRight className="size-4" />
</Button>
</div>
</div>
</Carousel>
@@ -163,7 +193,7 @@ const DottedDiv = ({
children: React.ReactNode;
className?: string;
}) => (
<div className={cn("relative", className)}>
<div className={cn("relative min-w-0 overflow-hidden", className)}>
<div className="absolute top-4 -start-[12.5px] h-px w-[110%] bg-muted md:-start-20" />
<div className="absolute bottom-4 -start-[12.5px] h-px w-[110%] bg-muted md:-start-20" />
<div className="absolute -top-4 start-0 h-[110%] w-px bg-muted" />
+15 -11
View File
@@ -18,9 +18,13 @@ interface Feature246Props {
const Feature246 = ({ className }: Feature246Props) => {
return (
<section dir="rtl" lang="fa" className={cn("bg-background", className)}>
<div className="container flex flex-col justify-between overflow-hidden py-32 lg:flex-row">
<div className="flex w-full flex-col items-start gap-20 text-start lg:me-2">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden bg-background", className)}
>
<div className="container flex min-w-0 flex-col justify-between overflow-hidden py-32 lg:flex-row lg:items-center">
<div className="flex w-full min-w-0 flex-col items-start gap-20 text-start lg:me-2 lg:max-w-xl">
<h1 className="text-2xll font-semibold tracking-tighter text-balance text-foreground md:text-2xll">
ERP
<br />
@@ -28,9 +32,9 @@ const Feature246 = ({ className }: Feature246Props) => {
</h1>
<div className="space-y-5">
{BENEFITS.map((benefit) => (
<div key={benefit.id} className="flex items-center gap-4">
<div className="flex size-7 items-center justify-center">
<BadgeCheck className="h-20" />
<div key={benefit.id} className="flex min-w-0 items-center gap-4">
<div className="flex size-7 shrink-0 items-center justify-center">
<BadgeCheck className="size-7" />
</div>
<span className="text-xl tracking-tight text-foreground">
{benefit.label}
@@ -38,22 +42,22 @@ const Feature246 = ({ className }: Feature246Props) => {
</div>
))}
</div>
<div className="flex w-full items-center overflow-hidden rounded-full border border-border p-2">
<div className="flex w-full min-w-0 items-center gap-1 overflow-hidden rounded-full border border-border p-2">
<Input
type="email"
dir="rtl"
className="h-full border-none ps-6 text-start text-lg! tracking-tight shadow-none outline-none focus-visible:ring-0 focus-visible:outline-none"
className="h-full min-w-0 flex-1 border-none ps-6 text-start text-lg! tracking-tight shadow-none outline-none focus-visible:ring-0 focus-visible:outline-none"
placeholder="عملیات سازمان را یکپارچه کنید"
/>
<Button className="h-15 shrink-0 rounded-full bg-foreground px-10 text-lg font-medium tracking-tight text-background transition-all ease-in-out hover:px-12">
<Button className="h-15 shrink-0 rounded-full bg-foreground px-6 text-lg font-medium tracking-tight text-background transition-all ease-in-out sm:px-10 hover:sm:px-12">
ثبت‌نام
</Button>
</div>
</div>
<div className="relative flex h-auto w-full items-center justify-end rounded-none">
<div className="relative mt-10 flex h-auto w-full min-w-0 items-center justify-center overflow-hidden rounded-none lg:mt-0 lg:max-w-xl lg:justify-end">
<img
src="/block-media/shadcnblocks/block/illustrations/tokyo-letters-and-arrows-flying-out-of-a-black-hole.svg"
className="start-40 scale-x-[-1] object-fit rtl:scale-x-100 lg:absolute"
className="max-h-[28rem] w-full max-w-full scale-x-[-1] object-contain rtl:scale-x-100"
alt="گزارش مالی یکپارچه"
/>
</div>
+19 -12
View File
@@ -13,20 +13,26 @@ interface Feature249Props {
const Feature249 = ({ className }: Feature249Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full min-w-0 overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<ContainerScroll
titleComponent={
<>
<p className="mx-auto mb-4 text-pretty text-muted-foreground md:text-xl">
<p className="mx-auto mb-4 max-w-3xl text-pretty text-muted-foreground md:text-xl">
با یادآورهای هوشمند و اولویت‌بندی سرنخ، زمان تیم روی معاملات با احتمال بیشتر صرف می‌شود و چرخه فروش کوتاه‌تر می‌شود.
</p>
<h1 className="text-2xll font-semibold tracking-tighter text-balance md:text-8xl xl:text-[10rem]">
<span className="pe-6 text-muted-foreground/40">پیش‌بینی درآمد را دقیق‌تر کنید</span>
<h1 className="text-3xl font-semibold tracking-tighter text-balance break-words sm:text-4xl md:text-5xl lg:text-6xl xl:text-7xl">
<span className="pe-2 text-muted-foreground/40 sm:pe-4 md:pe-6">
پیش‌بینی درآمد را دقیق‌تر کنید
</span>
<AuroraText
colors={["#ff6449", "#ff6449", "#6248fe", "#6248fe"]}
>
چرخه فروش را از سرنخ تا قرارداد در یک مسیر مشخص پیش ببرید. مدیران می‌توانند گلوگاه‌ها را ببینند و تیم‌ها با اولویت درست روی معاملات ارزشمند تمرکز کنند.
چرخه فروش را از سرنخ تا قرارداد در یک مسیر مشخص پیش ببرید
</AuroraText>
</h1>
</>
@@ -78,7 +84,8 @@ export const ContainerScroll = ({
}, []);
const scaleDimensions = () => {
return isMobile ? [0.7, 0.9] : [1.05, 1];
// Keep scale ≤ 1 so the 3D card never bleeds past the preview frame.
return isMobile ? [0.7, 0.9] : [0.95, 1];
};
const rotate = useTransform(scrollYProgress, [0, 1], [20, 0]);
@@ -87,11 +94,11 @@ export const ContainerScroll = ({
return (
<div
className="relative flex h-[60rem] items-center justify-center"
className="relative flex h-[40rem] w-full min-w-0 items-center justify-center overflow-hidden md:h-[50rem] lg:h-[60rem]"
ref={containerRef}
>
<div
className="relative w-full"
className="relative w-full min-w-0"
style={{
perspective: "1000px",
}}
@@ -117,7 +124,7 @@ export const Header = ({
style={{
translateY: translate,
}}
className="div mx-auto max-w-5xl text-center"
className="mx-auto w-full min-w-0 max-w-5xl px-2 text-center sm:px-4"
>
{titleComponent}
</motion.div>
@@ -140,9 +147,9 @@ export const Card = ({
rotateX: rotate,
scale,
}}
className="-4 mx-auto -mt-12 h-[30rem] w-full max-w-5xl rounded-[30px] p-2 shadow-2xl md:h-[40rem] md:p-6"
className="mx-auto -mt-12 h-[24rem] w-full min-w-0 max-w-5xl overflow-hidden rounded-[30px] p-2 shadow-2xl md:h-[36rem] md:p-6 lg:h-[40rem]"
>
<div className="size-full overflow-hidden rounded-2xl bg-gray-100 md:rounded-2xl md:p-4 dark:bg-zinc-900">
<div className="size-full min-w-0 overflow-hidden rounded-2xl bg-gray-100 md:rounded-2xl md:p-4 dark:bg-zinc-900">
{children}
</div>
</motion.div>
+30 -25
View File
@@ -14,12 +14,16 @@ interface Feature250Props {
const Feature250 = ({ className }: Feature250Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full min-w-0 overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<p className="mx-auto mb-4 max-w-sm text-center text-pretty text-muted-foreground md:text-xl">
با سگمنت‌بندی دقیق، پیام مناسب را به مخاطب مناسب برسانید. داده رفتاری نشان می‌دهد کدام محتوا بیشترین تأثیر را روی تبدیل دارد.
</p>
<h1 className="mx-auto -mb-12 max-w-3xl text-center text-xl font-medium tracking-tighter text-balance md:text-2xll lg:mb-5 lg:text-2xll">
<h1 className="mx-auto mb-2 max-w-3xl text-center text-xl font-medium tracking-tighter text-balance break-words md:text-2xll lg:mb-5 lg:text-2xll">
کمپین‌هایی بسازید که واقعاً تبدیل می‌شوند
</h1>
<AnimatedBeamIllustration />
@@ -44,14 +48,15 @@ function AnimatedBeamIllustration() {
const div7Ref = useRef<HTMLDivElement>(null);
return (
<div
className="relative flex w-full items-center justify-center overflow-hidden p-10"
className="relative flex w-full min-w-0 max-w-full items-center justify-center overflow-hidden p-6 sm:p-10"
ref={containerRef}
>
<div className="flex w-full flex-col items-center justify-between gap-10 lg:flex-row">
<div className="relative z-10 flex h-100 w-full items-center justify-center rounded-3xl lg:w-0">
<div className="flex w-full min-w-0 flex-col items-center justify-between gap-10 lg:flex-row">
{/* Reserve width on lg so absolute nodes/beams stay inside the frame (avoid lg:w-0 bleed). */}
<div className="relative z-10 flex h-100 w-full min-w-0 items-center justify-center rounded-3xl lg:w-56 lg:shrink-0">
<div
ref={div1Ref}
className="absolute start-0 top-40 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-0 lg:top-1/2"
className="absolute start-2 top-40 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-2 lg:top-1/2"
>
<div className="flex size-10 items-center justify-center rounded-lg border border-border bg-background p-[5px]">
<div className="flex size-full items-center justify-center rounded-md border border-border bg-muted">
@@ -61,7 +66,7 @@ function AnimatedBeamIllustration() {
</div>
<div
ref={div2Ref}
className="absolute end-0 top-40 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-20 lg:top-20"
className="absolute end-2 top-40 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-16 lg:top-20"
>
<div className="flex size-10 items-center justify-center rounded-lg border border-border bg-background p-[5px]">
<div className="flex size-full items-center justify-center rounded-md border border-border bg-muted">
@@ -71,7 +76,7 @@ function AnimatedBeamIllustration() {
</div>
<div
ref={div3Ref}
className="absolute start-6 bottom-0 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-20 lg:bottom-2"
className="absolute start-6 bottom-4 z-10 flex size-18 items-center justify-center rounded-full bg-background p-1 lg:start-16 lg:bottom-4"
>
<div className="flex size-10 items-center justify-center rounded-lg border border-border bg-background p-[5px]">
<div className="flex size-full items-center justify-center rounded-md border border-border bg-muted">
@@ -81,7 +86,7 @@ function AnimatedBeamIllustration() {
</div>
<div
ref={div4Ref}
className="absolute end-6 bottom-0 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-50 lg:top-0"
className="absolute end-6 bottom-4 z-10 flex size-18 items-center justify-center rounded-full bg-background p-1 lg:start-36 lg:top-4"
>
<div className="flex size-10 items-center justify-center rounded-lg border border-border bg-background p-[5px]">
<div className="flex size-full items-center justify-center rounded-md border border-border bg-muted">
@@ -91,7 +96,7 @@ function AnimatedBeamIllustration() {
</div>
<div
ref={div5Ref}
className="absolute top-20 z-10 flex size-18 -translate-y-1/2 items-center justify-center rounded-full bg-background p-1 lg:start-50 lg:top-100"
className="absolute start-1/2 top-20 z-10 flex size-18 -translate-x-1/2 items-center justify-center rounded-full bg-background p-1 rtl:translate-x-1/2 lg:start-36 lg:top-auto lg:bottom-4 lg:translate-x-0 rtl:lg:translate-x-0"
>
<div className="flex size-10 items-center justify-center rounded-lg border border-border bg-background p-[5px]">
<div className="flex size-full items-center justify-center rounded-md border border-border bg-muted">
@@ -102,7 +107,7 @@ function AnimatedBeamIllustration() {
</div>
<div
ref={div6Ref}
className="z-10 flex size-32 items-center justify-center rounded-3xl border bg-muted lg:size-42"
className="z-10 flex size-32 shrink-0 items-center justify-center rounded-3xl border bg-muted lg:size-42"
>
<img
src="/block-media/shadcnblocks/block/block-1.svg"
@@ -112,7 +117,7 @@ function AnimatedBeamIllustration() {
</div>
<div
ref={div7Ref}
className="z-10 mt-40 flex size-15 items-center justify-center rounded-xl border bg-muted lg:mt-0"
className="z-10 mt-24 flex size-15 shrink-0 items-center justify-center rounded-xl border bg-muted lg:mt-0"
>
<Zap fill="currentColor" />
</div>
@@ -180,10 +185,10 @@ function AnimatedBeamIllustration() {
reverse={REVERSE}
/>
<AnimatedBeam
endYOffset={-30}
endXOffset={60}
endYOffset={-24}
endXOffset={24}
duration={DURATION}
curvature={-140}
curvature={-80}
containerRef={containerRef}
fromRef={div2Ref}
toRef={div6Ref}
@@ -191,8 +196,8 @@ function AnimatedBeamIllustration() {
/>
<AnimatedBeam
duration={DURATION}
endYOffset={30}
curvature={140}
endYOffset={24}
curvature={80}
containerRef={containerRef}
fromRef={div3Ref}
toRef={div6Ref}
@@ -200,9 +205,9 @@ function AnimatedBeamIllustration() {
/>
<AnimatedBeam
duration={DURATION}
endYOffset={-30}
endXOffset={-60}
curvature={-180}
endYOffset={-24}
endXOffset={-24}
curvature={-100}
containerRef={containerRef}
fromRef={div4Ref}
toRef={div6Ref}
@@ -211,9 +216,9 @@ function AnimatedBeamIllustration() {
<AnimatedBeam
duration={DURATION}
endXOffset={-60}
endYOffset={30}
curvature={180}
endXOffset={-24}
endYOffset={24}
curvature={100}
containerRef={containerRef}
fromRef={div5Ref}
toRef={div6Ref}
@@ -386,7 +391,7 @@ const AnimatedBeam: React.FC<AnimatedBeamProps> = ({
height={svgDimensions.height}
xmlns="http://www.w3.org/2000/svg"
className={cn(
"pointer-events-none absolute start-0 top-0 transform-gpu stroke-2",
"pointer-events-none absolute start-0 top-0 max-w-full overflow-hidden transform-gpu stroke-2",
className,
)}
viewBox={`0 0 ${svgDimensions.width} ${svgDimensions.height}`}
+21 -9
View File
@@ -10,11 +10,18 @@ interface Feature252Props {
const Feature252 = ({ className }: Feature252Props) => {
return (
<section dir="rtl" lang="fa" className={cn("bg-muted py-32", className)}>
<div className="container">
<div className="relative h-92 w-full overflow-hidden rounded-4xl border bg-background p-4">
<section
dir="rtl"
lang="fa"
className={cn(
"relative w-full min-w-0 overflow-hidden bg-muted py-32",
className,
)}
>
<div className="container min-w-0">
<div className="relative h-92 w-full min-w-0 max-w-full overflow-hidden rounded-4xl border bg-background p-4">
<svg
className="absolute start-0 top-0 size-full p-4"
className="absolute start-0 top-0 size-full max-w-full p-4"
fill="none"
xmlns="http://www.w3.org/2000/svg"
aria-hidden="true"
@@ -29,23 +36,28 @@ const Feature252 = ({ className }: Feature252Props) => {
strokeDasharray="7 12"
/>
</svg>
<div className="relative flex size-full items-center justify-center overflow-hidden rounded-3xl text-center">
<div className="flex flex-col items-center gap-4">
<div className="relative flex size-full min-w-0 items-center justify-center overflow-hidden rounded-3xl text-center">
<div className="relative z-10 flex min-w-0 flex-col items-center gap-4 px-2">
<p className="mx-auto max-w-sm text-pretty text-muted-foreground lg:text-xl">
گزارش‌های بصری نشان می‌دهند کدام اقدام بیشترین اثر را روی درآمد و نگهداشت مشتری داشته است.
</p>
<h1 className="text-2xll font-medium tracking-tighter text-balance lg:text-2xll">
<h1 className="text-xl font-medium tracking-tighter text-balance break-words sm:text-2xl md:text-2xll">
داده پراکنده را به تصمیم تبدیل کنید
</h1>
<Button
variant="secondary"
className="relative z-99 mb-20 w-fit rounded-none! border px-10"
className="relative z-10 mb-16 w-fit rounded-none! border px-10 sm:mb-20"
>
شروع کنید
</Button>
</div>
<Ripple mainCircleSize={550} className="absolute -bottom-220" />
{/* Keep ripple circles inside the card: smaller radius + milder offset */}
<Ripple
mainCircleSize={280}
numCircles={6}
className="absolute inset-x-0 -bottom-32 top-auto h-64 overflow-hidden"
/>
</div>
</div>
</div>
+13 -8
View File
@@ -11,11 +11,15 @@ interface Feature253Props {
const Feature253 = ({ className }: Feature253Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="relative flex h-92 w-full flex-col justify-between overflow-hidden rounded-4xl border bg-muted p-8 md:flex-row">
<div className="flex h-full max-w-lg flex-col justify-center gap-4 text-start">
<h1 className="text-xl font-medium tracking-tighter text-balance md:text-2xll">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full min-w-0 overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<div className="relative flex h-92 w-full min-w-0 max-w-full flex-col justify-between overflow-hidden rounded-4xl border bg-muted p-6 sm:p-8 md:flex-row">
<div className="relative z-10 flex h-full min-w-0 max-w-lg flex-col justify-center gap-4 text-start">
<h1 className="text-xl font-medium tracking-tighter text-balance break-words md:text-2xll">
زمان حل مسئله را کوتاه کنید
</h1>
<p className="text-pretty text-muted-foreground/70">
@@ -23,14 +27,15 @@ const Feature253 = ({ className }: Feature253Props) => {
</p>
<Button
variant="default"
className="group relative z-99 w-fit rounded-full! border border-none bg-background px-10 tracking-tighter text-foreground shadow-none! hover:bg-background"
className="group relative z-10 w-fit rounded-full! border border-none bg-background px-10 tracking-tighter text-foreground shadow-none! hover:bg-background"
>
تیکت
<ArrowRight className="ms-2 -rotate-45 rounded-full bg-foreground p-px text-background transition-all ease-in-out group-hover:rotate-0 rtl:rotate-[135deg] rtl:group-hover:rotate-180" />
</Button>
</div>
<div className="relative size-full">
<Globe className="absolute top-0 md:-end-100 md:top-10 md:scale-150" />
<div className="relative mt-6 min-h-40 min-w-0 w-full flex-1 overflow-hidden md:mt-0 md:max-w-md">
{/* Keep globe peek inside the card — avoid -end-100 / scale-150 bleed */}
<Globe className="absolute end-0 top-0 size-full max-w-none origin-top md:-end-8 md:top-6 md:scale-110" />
</div>
</div>
</div>
+70 -63
View File
@@ -75,70 +75,77 @@ interface Feature254Props {
const Feature254 = ({ className }: Feature254Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="relative">
<div className="flex w-full items-center justify-center">
<div className="absolute z-99 flex size-full flex-col items-center justify-center gap-4">
<div className="pointer-events-none absolute inset-y-0 top-1/2 left-1/2 h-1/3 w-full max-w-2xl -translate-x-1/2 -translate-y-1/2 bg-background blur-2xl" />
<h1 className="z-10 text-center text-2xll font-medium tracking-tighter text-balance sm:text-2xll">
با هوش مصنوعی سریع‌تر تصمیم بگیرید
</h1>
<p className="z-10 max-w-2xl text-center text-pretty text-muted-foreground/70">
مدل‌های هوشمند الگوهای پنهان در داده فروش و پشتیبانی را پیدا می‌کنند. تیم‌ها با پیشنهادهای عملی، سریع‌تر اقدام می‌کنند.
</p>
<section
dir="rtl"
lang="fa"
className={cn(
"relative w-full min-w-0 overflow-hidden py-32",
className,
)}
>
<div className="relative mx-auto flex w-full min-w-0 max-w-5xl items-center justify-center px-4">
<div className="absolute inset-0 z-10 flex flex-col items-center justify-center gap-4 px-4">
<div className="pointer-events-none absolute top-1/2 left-1/2 h-1/3 w-full max-w-2xl -translate-x-1/2 -translate-y-1/2 bg-background blur-2xl" />
<h1 className="relative z-10 max-w-xl text-center text-2xl font-medium tracking-tighter text-balance break-words sm:text-3xl md:text-2xll">
با هوش مصنوعی سریع‌تر تصمیم بگیرید
</h1>
<p className="relative z-10 max-w-2xl text-center text-pretty text-muted-foreground/70">
مدل‌های هوشمند الگوهای پنهان در داده فروش و پشتیبانی را پیدا می‌کنند.
تیم‌ها با پیشنهادهای عملی، سریع‌تر اقدام می‌کنند.
</p>
<Button
variant="default"
className="group relative z-10 w-fit gap-2 rounded-full! px-10 tracking-tighter shadow-none!"
>
اتوماسیون AI
<ArrowRight className="-rotate-45 transition-all ease-in-out group-hover:rotate-0 rtl:rotate-[135deg] rtl:group-hover:rotate-180" />
</Button>
</div>
<div className="relative flex h-[620px] w-full flex-col items-center justify-center overflow-hidden">
<OrbitingCircles iconSize={40} radius={130} speed={2}>
{CIRCLE_1_IMAGES.map((item) => (
<div
key={item.id}
className="size-10 overflow-hidden rounded-full"
>
<img
src={item.src}
className="size-full object-cover"
alt={item.imageAlt}
/>
</div>
))}
</OrbitingCircles>
<OrbitingCircles iconSize={40} radius={200} reverse speed={2}>
{CIRCLE_2_IMAGES.map((item) => (
<div
key={item.id}
className="size-10 overflow-hidden rounded-full"
>
<img
src={item.src}
className="size-full object-cover"
alt={item.imageAlt}
/>
</div>
))}
</OrbitingCircles>
<OrbitingCircles iconSize={40} radius={280} speed={1}>
{CIRCLE_3_IMAGES.map((item) => (
<div
key={item.id}
className="size-10 overflow-hidden rounded-full"
>
<img
src={item.src}
className="size-full object-cover"
alt={item.imageAlt}
/>
</div>
))}
</OrbitingCircles>
</div>
<Button
variant="default"
className="group relative z-10 w-fit gap-2 rounded-full! px-10 tracking-tighter shadow-none!"
>
اتوماسیون AI
<ArrowRight className="-rotate-45 transition-all ease-in-out group-hover:rotate-0 rtl:rotate-[135deg] rtl:group-hover:rotate-180" />
</Button>
</div>
<div className="relative flex h-[32rem] w-full min-w-0 max-w-full flex-col items-center justify-center overflow-hidden sm:h-[36rem] md:h-[40rem]">
<OrbitingCircles iconSize={40} radius={100} speed={2}>
{CIRCLE_1_IMAGES.map((item) => (
<div
key={item.id}
className="size-10 overflow-hidden rounded-full border border-border/40 shadow-sm sm:size-11"
>
<img
src={item.src}
className="size-full object-cover"
alt={item.imageAlt}
/>
</div>
))}
</OrbitingCircles>
<OrbitingCircles iconSize={40} radius={170} reverse speed={2}>
{CIRCLE_2_IMAGES.map((item) => (
<div
key={item.id}
className="size-10 overflow-hidden rounded-full border border-border/40 opacity-90 shadow-sm sm:size-11"
>
<img
src={item.src}
className="size-full object-cover"
alt={item.imageAlt}
/>
</div>
))}
</OrbitingCircles>
<OrbitingCircles iconSize={48} radius={250} speed={1}>
{CIRCLE_3_IMAGES.map((item) => (
<div
key={item.id}
className="size-11 overflow-hidden rounded-full border border-border/40 opacity-80 shadow-sm sm:size-12"
>
<img
src={item.src}
className="size-full object-cover"
alt={item.imageAlt}
/>
</div>
))}
</OrbitingCircles>
</div>
</div>
</section>
+15 -8
View File
@@ -73,16 +73,16 @@ interface Feature257Props {
}
const ToolCard = ({ tool }: { tool: ToolItem }) => (
<CardSpotlight className="group flex h-96 flex-col items-start justify-between rounded-md border border-border bg-background p-2 text-start transition-all duration-300 hover:bg-black hover:text-white md:p-4">
<div className="z-10 rounded-md border border-border px-2 py-1 text-xs font-medium transition-colors duration-300 group-hover:border-white md:px-4 md:py-2 md:text-sm">
<CardSpotlight className="group flex h-96 min-w-0 flex-col items-start justify-between overflow-hidden rounded-md border border-border bg-background p-2 text-start transition-all duration-300 hover:bg-black hover:text-white md:p-4">
<div className="z-10 max-w-full rounded-md border border-border px-2 py-1 text-xs font-medium text-balance transition-colors duration-300 group-hover:border-white md:px-4 md:py-2 md:text-sm">
{tool.category}
</div>
<img
src={tool.logo}
alt={tool.imageAlt}
className="mx-auto mb-4 h-24 object-contain [filter:brightness(0)] transition-all duration-300 group-hover:[filter:brightness(1)_invert(1)] dark:invert"
className="mx-auto mb-4 h-24 max-w-full object-contain [filter:brightness(0)] transition-all duration-300 group-hover:[filter:brightness(1)_invert(1)] dark:invert"
/>
<h2 className="z-10 text-xl font-normal transition-colors duration-300 lg:text-3xl">
<h2 className="z-10 max-w-full text-xl font-normal text-balance transition-colors duration-300 lg:text-3xl">
{tool.name}
</h2>
</CardSpotlight>
@@ -90,14 +90,21 @@ const ToolCard = ({ tool }: { tool: ToolItem }) => (
const Feature257 = ({ className }: Feature257Props) => {
return (
<section dir="rtl" lang="fa" className={cn("bg-muted py-16 sm:py-32", className)}>
<div className="container">
<div className="grid grid-cols-1 gap-4 md:grid-cols-2">
<section
dir="rtl"
lang="fa"
className={cn(
"relative w-full overflow-hidden bg-muted py-16 sm:py-32",
className,
)}
>
<div className="container min-w-0">
<div className="grid min-w-0 grid-cols-1 gap-4 md:grid-cols-2">
{TOOLS.slice(0, 2).map((tool) => (
<ToolCard key={tool.id} tool={tool} />
))}
</div>
<div className="mt-4 grid grid-cols-1 gap-4 md:grid-cols-2 lg:grid-cols-3">
<div className="mt-4 grid min-w-0 grid-cols-1 gap-4 md:grid-cols-2 lg:grid-cols-3">
{TOOLS.slice(2, 9).map((tool) => (
<ToolCard key={tool.id} tool={tool} />
))}
+18 -15
View File
@@ -29,41 +29,44 @@ const Feature267 = ({ className }: Feature267Props) => {
dir="rtl"
lang="fa"
className={cn(
"relative h-full w-screen overflow-hidden py-32",
"relative h-full w-full min-w-0 overflow-hidden py-32",
className,
)}
>
<div className="container grid grid-cols-1 items-center gap-5 lg:grid-cols-2">
<div className="flex h-full flex-col justify-center text-start">
<div className="flex items-center gap-2">
<Sparkles className="size-5 fill-foreground" />
<p className="w-fit rounded-full py-1 font-medium tracking-tight">
<div className="container grid min-w-0 grid-cols-1 items-center gap-5 lg:grid-cols-2">
<div className="flex h-full min-w-0 flex-col justify-center text-start">
<div className="flex min-w-0 items-start gap-2">
<Sparkles className="mt-1 size-5 shrink-0 fill-foreground" />
<p className="min-w-0 flex-1 text-pretty font-medium tracking-tight">
تمام تعاملات، سرنخ‌ها و قراردادها در یک فضای کاری متمرکز جمع می‌شود. تیم فروش بدون جابجایی بین ابزارها، سریع‌تر پیش‌بینی می‌کند و معاملات بیشتری می‌بندد.
</p>
</div>
<h1 className="mt-3 mb-8 max-w-xl text-2xll font-semibold tracking-tighter text-balance lg:max-w-3xl lg:text-2xll">
<h1 className="mt-3 mb-8 max-w-xl text-2xl font-semibold tracking-tighter text-balance break-words sm:text-3xl lg:max-w-3xl lg:text-2xll">
فروش تیم‌تان را یکجا مدیریت کنید
</h1>
<p className="max-w-xl text-pretty text-muted-foreground">
از اولین تماس تا تمدید قرارداد، هر مرحله فروش قابل ردیابی است. گزارش‌های لحظه‌ای به مدیران کمک می‌کند گلوگاه‌ها را قبل از از دست دادن درآمد شناسایی کنند.
</p>
<div className="mt-10 gap-4">
<div className="flex h-15 w-full max-w-md items-center rounded-full border p-1">
<div className="mt-10 min-w-0">
<div className="flex h-15 w-full min-w-0 max-w-md items-center rounded-full border p-1">
<Input
type="email"
dir="rtl"
className="w-full rounded-full border-none text-start shadow-none ring-0 focus-visible:ring-0 focus-visible:outline-none active:ring-0 active:outline-0"
placeholder="هر سرنخ را تا قرارداد دنبال کنید"
className="min-w-0 flex-1 rounded-full border-none text-start shadow-none ring-0 focus-visible:ring-0 focus-visible:outline-none active:ring-0 active:outline-0"
placeholder="ایمیل کاری"
/>
<Button className="h-full shrink-0 rounded-full">
روابط مشتری را در یک نگاه ببینید
<Button className="h-full shrink-0 rounded-full px-4 sm:px-6">
شروع کنید
</Button>
</div>
</div>
</div>
<div className="items-center justify-center">
<ThreeDMarquee className="rounded-none" images={MARQUEE_IMAGES} />
<div className="min-w-0 max-w-full overflow-hidden">
<ThreeDMarquee
className="w-full max-w-full rounded-none"
images={MARQUEE_IMAGES}
/>
</div>
</div>
</section>
+20 -17
View File
@@ -49,32 +49,35 @@ const Feature268 = ({ className }: Feature268Props) => {
<section
dir="rtl"
lang="fa"
className={cn("h-full w-screen overflow-hidden py-32", className)}
className={cn(
"relative h-full w-full min-w-0 overflow-hidden py-32",
className,
)}
>
<div className="relative container flex h-full flex-col items-start justify-between gap-10 lg:flex-row">
<div className="w-full space-y-5 text-start lg:w-3/5">
<div className="relative container flex h-full min-w-0 flex-col items-start justify-between gap-10 lg:flex-row">
<div className="w-full min-w-0 space-y-5 text-start lg:w-3/5">
<h1 className="mt-3 w-full max-w-2xl text-2xll font-semibold tracking-tighter text-balance lg:text-2xll">
پیش‌بینی درآمد را دقیق‌تر کنید
</h1>
<p className="max-w-xl text-pretty text-muted-foreground">
<p className="max-w-xl text-pretty break-words text-muted-foreground">
با یادآورهای هوشمند و اولویت‌بندی سرنخ، زمان تیم روی معاملات با احتمال بیشتر صرف می‌شود و چرخه فروش کوتاه‌تر می‌شود.
</p>
<div className="mt-10 mb-29 flex gap-2">
<div className="mt-10 mb-29 flex min-w-0 flex-wrap gap-2">
<Button className="rounded-full">شروع کنید</Button>
<Button variant="secondary" className="rounded-full">
بیشتر بدانید
</Button>
</div>
<ul className="space-y-4">
<li className="mb-3">
<p className="font-semibold tracking-tight opacity-50">
<ul className="min-w-0 space-y-4">
<li className="mb-3 min-w-0">
<p className="font-semibold tracking-tight text-pretty break-words opacity-50">
چرخه فروش را از سرنخ تا قرارداد در یک مسیر مشخص پیش ببرید. مدیران می‌توانند گلوگاه‌ها را ببینند و تیم‌ها با اولویت درست روی معاملات ارزشمند تمرکز کنند.
</p>
</li>
{FEATURES.map((feature) => (
<li key={feature.id} className="flex gap-4 lg:items-center">
<li key={feature.id} className="flex min-w-0 gap-4 lg:items-center">
<Check className="size-4 shrink-0" />
<p className="font-medium tracking-tight text-pretty">
<p className="min-w-0 font-medium tracking-tight text-pretty break-words">
{feature.title}
<span className="ps-2 opacity-30">{feature.description}</span>
</p>
@@ -83,10 +86,10 @@ const Feature268 = ({ className }: Feature268Props) => {
</ul>
</div>
<CardContainer
className="w-full"
containerClassName="h-full w-full p-0 m-0 lg:w-2/5"
className="w-full min-w-0 max-w-full"
containerClassName="h-full w-full min-w-0 max-w-full p-0 m-0 lg:w-2/5"
>
<CardBody className="group/card flex h-full w-full! flex-col items-center justify-center rounded-3xl bg-muted/70 px-5 py-15">
<CardBody className="group/card flex h-full w-full! max-w-full min-w-0 flex-col items-center justify-center rounded-3xl bg-muted/70 px-5 py-15">
<CardItem
translateZ="60"
className="mb-2 max-w-xs text-center text-3xl leading-none font-semibold tracking-tight text-balance"
@@ -96,22 +99,22 @@ const Feature268 = ({ className }: Feature268Props) => {
<CardItem
as="p"
translateZ="25"
className="my-4 flex w-full max-w-sm items-center justify-center text-sm tracking-tight"
className="my-4 flex w-full max-w-sm min-w-0 items-center justify-center text-sm tracking-tight"
>
<span className="ms-2 opacity-50">تیم فروش</span>
<span className="font-semibold">بستن معامله</span>
</CardItem>
<CardItem translateZ="60" className="mt-4 w-full max-w-[1000px]">
<CardItem translateZ="60" className="mt-4 w-full min-w-0 max-w-full">
<img
src="/block-media/shadcnblocks/block/guri3/img27.jpeg"
height="1000"
width="1000"
className="h-82 w-full rounded-3xl object-cover group-hover/card:shadow-xl lg:h-60"
className="h-82 w-full max-w-full rounded-3xl object-cover group-hover/card:shadow-xl lg:h-60"
alt="صف اولویت سرنخ‌ها"
/>
</CardItem>
<div className="flex w-full flex-col items-center justify-center">
<div className="flex w-full min-w-0 flex-col items-center justify-center">
<CardItem translateZ="100">
<Button
variant="ghost"
+25 -20
View File
@@ -32,23 +32,28 @@ const Feature269 = ({ className }: Feature269Props) => {
<section
dir="rtl"
lang="fa"
className={cn("h-full w-screen overflow-hidden py-32", className)}
className={cn(
"relative h-full w-full overflow-hidden py-32",
className,
)}
>
<div className="relative container flex h-full flex-col items-start justify-between gap-10 lg:flex-row">
<div className="w-full space-y-5 text-start lg:w-3/5">
<div className="relative container flex h-full min-w-0 flex-col items-start justify-between gap-10 lg:flex-row">
<div className="w-full min-w-0 space-y-5 text-start lg:w-3/5">
<h1 className="mx-auto mb-15 w-full max-w-lg text-center text-2xll font-semibold tracking-tighter text-balance lg:mx-0 lg:text-start lg:text-2xll">
کمپین‌هایی بسازید که واقعاً تبدیل می‌شوند
کمپین‌هایی بسازید که واقعاً تبدیل می‌شوند؟
</h1>
<div className="mb-18 flex items-center gap-4 px-5 lg:max-w-md">
<span className="h-px w-full bg-muted-foreground/20" />
<p className="text-sm text-muted-foreground/50">با سگمنت‌بندی دقیق، پیام مناسب را به مخاطب مناسب برسانید. داده رفتاری نشان می‌دهد کدام محتوا بیشترین تأثیر را روی تبدیل دارد.</p>
<span className="h-px w-full bg-muted-foreground/20" />
<div className="mb-18 flex w-full min-w-0 max-w-md items-center gap-4 px-5 lg:px-0">
<span className="h-px min-w-0 flex-1 bg-muted-foreground/20" />
<p className="shrink-0 text-sm tracking-wide text-muted-foreground/50">
ویژگی‌ها
</p>
<span className="h-px min-w-0 flex-1 bg-muted-foreground/20" />
</div>
<ul className="grid grid-cols-2 gap-3 lg:max-w-md">
<ul className="grid w-full min-w-0 grid-cols-2 gap-3 lg:max-w-md">
{FEATURES.map((feature) => (
<li key={feature.id} className="flex gap-2 lg:items-center">
<li key={feature.id} className="flex min-w-0 gap-2 lg:items-center">
<BadgeCheck className="size-4 shrink-0 text-muted-foreground/80" />
<p className="tracking-tight text-pretty text-muted-foreground/80">
<p className="min-w-0 tracking-tight text-pretty text-muted-foreground/80">
{feature.label}
</p>
</li>
@@ -56,30 +61,30 @@ const Feature269 = ({ className }: Feature269Props) => {
</ul>
</div>
<CardContainer
className="w-full"
containerClassName="h-full w-full p-0 m-0 lg:w-2/5"
className="w-full min-w-0"
containerClassName="h-full w-full min-w-0 p-0 m-0 lg:w-2/5"
>
<CardBody className="group/card flex h-full w-full! flex-col items-center justify-center rounded-3xl bg-muted/70 p-5">
<CardBody className="group/card flex h-full w-full! min-w-0 flex-col items-center justify-center rounded-3xl bg-muted/70 p-5">
<CardItem
translateZ="60"
className="mt-10 mb-2 max-w-xs text-center text-3xl leading-none font-semibold tracking-tighter text-balance"
className="mt-10 mb-2 max-w-xs text-center text-2xl leading-none font-semibold tracking-tighter text-balance sm:text-3xl"
>
ببینید کدام کانال بیشترین سرنخ با کیفیت را می‌آورد.
ببینید کدام کانال بیشترین سرنخ با کیفیت را می‌آورد
</CardItem>
<CardItem
as="p"
translateZ="25"
className="my-4 flex w-full max-w-sm items-center justify-center text-sm tracking-tight"
className="my-4 flex w-full max-w-sm items-center justify-center gap-2 text-sm tracking-tight"
>
<span className="ms-2 opacity-50">کمپین</span>
<span className="opacity-50">خوش آمدید به</span>
<span className="font-semibold">رشد برند</span>
</CardItem>
<CardItem translateZ="60" className="mt-4 w-full max-w-[1000px]">
<CardItem translateZ="60" className="mt-4 w-full min-w-0 max-w-full">
<img
src="/block-media/shadcnblocks/block/guri3/img7.jpeg"
height="1000"
width="1000"
className="h-70 w-full rounded-3xl object-cover group-hover/card:shadow-xl"
className="h-70 w-full max-w-full rounded-3xl object-cover group-hover/card:shadow-xl"
alt="تحلیل عملکرد کمپین"
/>
</CardItem>
+29 -19
View File
@@ -40,48 +40,56 @@ const FEATURES = [
},
] as const;
const Feature270 = () => {
interface Feature270Props {
className?: string;
}
const Feature270 = ({ className }: Feature270Props) => {
return (
<section
dir="rtl"
lang="fa"
className="h-full w-screen overflow-hidden py-32"
className={cn(
"relative h-full w-full min-w-0 overflow-hidden py-32",
className,
)}
>
<div className="relative container">
<div className="w-full space-y-5 text-start lg:w-3/5">
<div className="relative container min-w-0">
<div className="w-full min-w-0 space-y-5 text-start lg:w-3/5">
<h1 className="mb-6 w-full max-w-lg text-2xll font-semibold tracking-tighter text-balance lg:text-2xll">
فرایندها را استاندارد و سریع کنید
</h1>
<p className="max-w-2xl text-pretty opacity-50 md:mb-20">
<p className="max-w-2xl text-pretty break-words opacity-50 md:mb-20">
قوانین ساده تعریف کنید تا وظایف تکراری بدون دخالت دست انجام شود. تیم روی تصمیم‌های مهم تمرکز می‌کند و سرعت اجرا بالاتر می‌رود.
</p>
</div>
<div className="relative grid h-[95rem] items-center justify-between gap-3 md:h-[68rem] md:grid-cols-2 lg:h-[32rem] lg:grid-cols-3">
<div className="relative grid h-[95rem] min-w-0 items-center justify-between gap-3 md:h-[68rem] md:grid-cols-2 lg:h-[32rem] lg:grid-cols-3">
{FEATURES.map((feature) => (
<PinContainer
key={feature.id}
title="بیشتر بدانید"
href="https://www.ShadcnBlocks/blocks"
className="w-full rounded-3xl bg-muted/70! p-4"
className="w-full min-w-0 rounded-3xl bg-muted/70! p-4"
containerClassName="w-full min-w-0 max-w-full"
>
<div className="flex flex-col text-start">
<div className={feature.imageOrder}>
<div className="flex min-w-0 flex-col text-start">
<div className={cn("min-w-0", feature.imageOrder)}>
<img
src={feature.image}
height="1000"
width="1000"
className="h-70 w-full rounded-3xl object-cover group-hover/card:shadow-xl"
className="h-70 w-full max-w-full rounded-3xl object-cover group-hover/card:shadow-xl"
alt={feature.imageAlt}
/>
</div>
<div className={cn("mt-4 w-full p-3", feature.contentOrder)}>
<div className={cn("mt-4 w-full min-w-0 p-3", feature.contentOrder)}>
<p className="leading-none tracking-tighter opacity-50">
{feature.number}
</p>
<h2 className="my-3 text-3xl leading-none font-semibold tracking-tighter text-balance">
<h2 className="my-3 text-3xl leading-none font-semibold tracking-tighter text-balance break-words">
{feature.title}
</h2>
<p className="text-pretty leading-5 opacity-50">
<p className="text-pretty break-words leading-5 opacity-50">
{feature.description}
</p>
</div>
@@ -128,7 +136,7 @@ export const PinContainer = ({
return (
<a
className={cn(
"group/pin relative z-50 cursor-pointer",
"group/pin relative z-50 block w-full min-w-0 max-w-full cursor-pointer",
containerClassName,
)}
onMouseEnter={onMouseEnter}
@@ -140,15 +148,17 @@ export const PinContainer = ({
perspective: "1000px",
transform: "rotateX(70deg) translateZ(0deg)",
}}
className="absolute top-1/2 left-1/2 mt-4 ml-[0.09375rem] w-full -translate-x-1/2 -translate-y-1/2"
className="absolute top-1/2 left-1/2 mt-4 ml-[0.09375rem] w-full max-w-full -translate-x-1/2 -translate-y-1/2"
>
<div
style={{
transform: transform,
}}
className="absolute top-1/2 left-1/2 flex w-full items-start justify-start overflow-hidden rounded-2xl transition duration-700"
className="absolute top-1/2 left-1/2 flex w-full max-w-full items-start justify-start overflow-hidden rounded-2xl transition duration-700"
>
<div className={cn("relative z-50", className)}>{children}</div>
<div className={cn("relative z-50 min-w-0 w-full", className)}>
{children}
</div>
</div>
</div>
<PinPerspective title={title} />
@@ -163,8 +173,8 @@ export const PinPerspective = ({
href?: string;
}) => {
return (
<motion.div className="pointer-events-none z-[60] flex h-80 w-96 items-center justify-center opacity-0 transition duration-500 group-hover/pin:opacity-100">
<div className="inset-0 -mt-7 h-full w-full flex-none">
<motion.div className="pointer-events-none z-[60] flex h-80 w-full max-w-full items-center justify-center opacity-0 transition duration-500 group-hover/pin:opacity-100">
<div className="inset-0 -mt-7 h-full w-full min-w-0 flex-none overflow-hidden">
<div className="absolute inset-x-0 top-0 flex justify-center">
<span className="relative z-10 flex items-center gap-2 rounded-full bg-zinc-950 px-4 py-0.5 ring-1 ring-white/10">
<span className="relative z-20 inline-block py-0.5 text-xs font-bold text-white">
+46 -46
View File
@@ -29,11 +29,11 @@ const Feature271 = ({ className }: Feature271Props) => {
<section
dir="rtl"
lang="fa"
className={cn("h-full w-screen overflow-hidden", className)}
className={cn("relative h-full w-full overflow-hidden", className)}
>
<AuroraBackground>
<div className="relative container flex h-full flex-col items-center justify-center gap-15 text-center">
<div className="flex flex-col items-center justify-center">
<div className="relative container flex h-full min-w-0 flex-col items-center justify-center gap-15 text-center">
<div className="flex min-w-0 flex-col items-center justify-center">
<Badge
variant="outline"
className="mb-5 w-fit rounded-full bg-background/70 px-4 py-1 text-sm tracking-tight"
@@ -44,16 +44,19 @@ const Feature271 = ({ className }: Feature271Props) => {
داده پراکنده را به تصمیم تبدیل کنید
</h1>
</div>
<div className="flex w-full max-w-lg items-center gap-4 px-5">
<span className="h-px w-full bg-muted-foreground/20" />
<p className="text-sm text-muted-foreground/50">گزارش‌های بصری نشان می‌دهند کدام اقدام بیشترین اثر را روی درآمد و نگهداشت مشتری داشته است.</p>
<span className="h-px w-full bg-muted-foreground/20" />
<div className="flex w-full min-w-0 max-w-lg items-center gap-4 px-5">
<span className="h-px min-w-0 flex-1 bg-muted-foreground/20" />
<p className="min-w-0 max-w-[14rem] shrink text-sm text-balance text-muted-foreground/50 sm:max-w-xs">
گزارش‌های بصری نشان می‌دهند کدام اقدام بیشترین اثر را روی درآمد و
نگهداشت مشتری داشته است.
</p>
<span className="h-px min-w-0 flex-1 bg-muted-foreground/20" />
</div>
<ul className="grid grid-cols-2 gap-3 text-start">
<ul className="grid w-full min-w-0 max-w-lg grid-cols-2 gap-3 px-2 text-start">
{FEATURES.map((feature) => (
<li key={feature.id} className="flex gap-2 lg:items-center">
<li key={feature.id} className="flex min-w-0 gap-2 lg:items-center">
<BadgeCheck className="size-4 shrink-0 text-primary" />
<p className="tracking-tight text-pretty text-muted-foreground/80">
<p className="min-w-0 tracking-tight text-pretty text-muted-foreground/80">
{feature.label}
</p>
</li>
@@ -83,46 +86,43 @@ export const AuroraBackground = ({
...props
}: AuroraBackgroundProps) => {
return (
<main>
<div
className={cn(
"transition-bg relative flex h-full min-h-[32rem] w-full min-w-0 flex-col items-center justify-center overflow-hidden bg-zinc-50 text-slate-950 dark:bg-zinc-900",
className,
)}
{...props}
>
<div
className={cn(
"transition-bg relative flex h-[100vh] flex-col items-center justify-center bg-zinc-50 text-slate-950 dark:bg-zinc-900",
className,
)}
{...props}
className="absolute inset-0 overflow-hidden"
style={
{
"--aurora":
"repeating-linear-gradient(100deg,#000_10%,#666_15%,#ccc_20%,#fff_25%,#333_30%)",
"--dark-gradient":
"repeating-linear-gradient(100deg,#000_0%,#000_7%,transparent_10%,transparent_12%,#000_16%)",
"--white-gradient":
"repeating-linear-gradient(100deg,#fff_0%,#fff_7%,transparent_10%,transparent_12%,#fff_16%)",
"--gray-200": "#ccc",
"--gray-400": "#666",
"--gray-800": "#333",
"--black": "#000",
"--white": "#fff",
"--transparent": "transparent",
} as React.CSSProperties
}
>
<div
className="absolute inset-0 overflow-hidden"
style={
{
"--aurora":
"repeating-linear-gradient(100deg,#000_10%,#666_15%,#ccc_20%,#fff_25%,#333_30%)",
"--dark-gradient":
"repeating-linear-gradient(100deg,#000_0%,#000_7%,transparent_10%,transparent_12%,#000_16%)",
"--white-gradient":
"repeating-linear-gradient(100deg,#fff_0%,#fff_7%,transparent_10%,transparent_12%,#fff_16%)",
className={cn(
`pointer-events-none absolute -inset-[10px] [background-image:var(--white-gradient),var(--aurora)] [background-size:300%,_200%] [background-position:50%_50%,50%_50%] opacity-50 blur-[10px] invert filter will-change-transform [--aurora:repeating-linear-gradient(100deg,var(--black)_10%,var(--gray-400)_15%,var(--gray-200)_20%,var(--white)_25%,var(--gray-800)_30%)] [--dark-gradient:repeating-linear-gradient(100deg,var(--black)_0%,var(--black)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--black)_16%)] [--white-gradient:repeating-linear-gradient(100deg,var(--white)_0%,var(--white)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--white)_16%)] after:absolute after:inset-0 after:animate-aurora-background after:[background-image:var(--white-gradient),var(--aurora)] after:[background-size:200%,_100%] after:mix-blend-difference after:content-[""] dark:[background-image:var(--dark-gradient),var(--aurora)] dark:invert-0 after:dark:[background-image:var(--dark-gradient),var(--aurora)]`,
"--gray-200": "#ccc",
"--gray-400": "#666",
"--gray-800": "#333",
"--black": "#000",
"--white": "#fff",
"--transparent": "transparent",
} as React.CSSProperties
}
>
<div
// I'm sorry but this is what peak developer performance looks like // trigger warning
className={cn(
`pointer-events-none absolute -inset-[10px] [background-image:var(--white-gradient),var(--aurora)] [background-size:300%,_200%] [background-position:50%_50%,50%_50%] opacity-50 blur-[10px] invert filter will-change-transform [--aurora:repeating-linear-gradient(100deg,var(--black)_10%,var(--gray-400)_15%,var(--gray-200)_20%,var(--white)_25%,var(--gray-800)_30%)] [--dark-gradient:repeating-linear-gradient(100deg,var(--black)_0%,var(--black)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--black)_16%)] [--white-gradient:repeating-linear-gradient(100deg,var(--white)_0%,var(--white)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--white)_16%)] after:absolute after:inset-0 after:animate-aurora-background after:[background-image:var(--white-gradient),var(--aurora)] after:[background-size:200%,_100%] after:[background-attachment:fixed] after:mix-blend-difference after:content-[""] dark:[background-image:var(--dark-gradient),var(--aurora)] dark:invert-0 after:dark:[background-image:var(--dark-gradient),var(--aurora)]`,
showRadialGradient &&
`[mask-image:radial-gradient(ellipse_at_100%_0%,black_10%,var(--transparent)_70%)]`,
)}
></div>
</div>
{children}
showRadialGradient &&
`[mask-image:radial-gradient(ellipse_at_100%_0%,black_10%,var(--transparent)_70%)]`,
)}
/>
</div>
</main>
{children}
</div>
);
};
+8 -8
View File
@@ -34,12 +34,12 @@ const Feature272 = ({ className }: Feature272Props) => {
dir="rtl"
lang="fa"
className={cn(
"dark h-full w-screen overflow-hidden bg-background py-32 text-foreground",
"dark relative h-full w-full overflow-hidden bg-background py-32 text-foreground",
className,
)}
>
<div className="relative z-20 container flex h-full flex-col items-center justify-center gap-10">
<p className="text-sm tracking-wide text-muted-foreground">
<div className="relative z-20 container flex h-full min-w-0 flex-col items-center justify-center gap-10">
<p className="max-w-3xl text-center text-sm tracking-wide text-balance text-muted-foreground">
پاسخ‌های آماده و پایگاه دانش، زمان پاسخ را کم می‌کند و کیفیت را در کل تیم یکسان نگه می‌دارد.
</p>
<h2 className="text-center text-2xll font-semibold tracking-tighter text-balance lg:text-2xll">
@@ -48,11 +48,11 @@ const Feature272 = ({ className }: Feature272Props) => {
<p className="max-w-3xl text-center text-pretty text-muted-foreground">
رضایت مشتری و زمان حل را پیگیری کنید تا نقاط ضعف فرایند پشتیبانی را بهبود دهید.
</p>
<div className="relative grid grid-cols-1 md:grid-cols-3">
<div className="relative grid w-full min-w-0 grid-cols-1 md:grid-cols-3">
{STEPS.map((step, index) => (
<div
key={step.id}
className="relative space-y-5 border p-10 text-start"
className="relative min-w-0 space-y-5 border p-10 text-start"
>
<h3 className="text-xl font-semibold tracking-tighter">
{step.title}
@@ -61,14 +61,14 @@ const Feature272 = ({ className }: Feature272Props) => {
{step.description}
</p>
{index < STEPS.length - 1 && (
<div className="absolute start-1/2 -bottom-5 z-10 flex size-10 translate-x-1/2 rotate-90 items-center justify-center gap-2 rounded-full border bg-background md:top-1/2 md:-end-5 md:translate-x-0 md:-translate-y-1/2 md:rotate-0">
<div className="absolute start-1/2 -bottom-5 z-10 flex size-10 -translate-x-1/2 rotate-90 items-center justify-center gap-2 rounded-full border bg-background rtl:translate-x-1/2 md:top-1/2 md:-end-5 md:start-auto md:translate-x-0 md:-translate-y-1/2 md:rotate-0 rtl:md:translate-x-0">
<ArrowRight className="size-6 rtl:rotate-180" />
</div>
)}
</div>
))}
<div className="absolute start-0 z-99 h-full w-10 bg-gradient-to-r from-background to-transparent rtl:bg-gradient-to-l" />
<div className="absolute end-0 z-99 h-full w-10 bg-gradient-to-l from-background to-transparent rtl:bg-gradient-to-r" />
<div className="pointer-events-none absolute start-0 z-10 h-full w-10 bg-gradient-to-r from-background to-transparent rtl:bg-gradient-to-l" />
<div className="pointer-events-none absolute end-0 z-10 h-full w-10 bg-gradient-to-l from-background to-transparent rtl:bg-gradient-to-r" />
</div>
</div>
<BackgroundBeams className="dark bg-background text-foreground" />
+16 -11
View File
@@ -83,31 +83,36 @@ const Feature280 = ({ className }: Feature280Props) => {
<section
dir="rtl"
lang="fa"
className={cn("h-full w-screen overflow-hidden py-32", className)}
className={cn(
"relative h-full w-full overflow-hidden py-32",
className,
)}
>
<div className="container flex w-full max-w-6xl flex-col items-center justify-between lg:flex-row">
<div className="relative flex h-full flex-col items-center justify-center gap-15 text-center lg:items-start lg:text-start">
<div className="container flex w-full min-w-0 max-w-6xl flex-col items-center justify-between gap-12 lg:flex-row lg:gap-8">
<div className="relative flex h-full w-full min-w-0 flex-col items-center justify-center gap-15 text-center lg:items-start lg:text-start">
<h1 className="w-full max-w-md text-2xll font-semibold tracking-tighter text-balance lg:text-2xll">
تصمیم استراتژیک را داده‌محور کنید
</h1>
<div className="flex w-full max-w-lg items-center gap-4 px-5">
<span className="h-px w-full bg-muted-foreground/20" />
<p className="text-sm text-muted-foreground/50">هشدارهای هوشمند زمانی که شاخص از مسیر هدف خارج می‌شود، مدیران را به‌موقع مطلع می‌کند.</p>
<span className="h-px w-full bg-muted-foreground/20" />
<div className="flex w-full min-w-0 max-w-lg items-center gap-4 px-5">
<span className="h-px min-w-4 flex-1 bg-muted-foreground/20" />
<p className="max-w-[min(100%,16rem)] shrink text-center text-sm text-balance text-muted-foreground/50 sm:max-w-xs">
هشدارهای هوشمند زمانی که شاخص از مسیر هدف خارج می‌شود، مدیران را به‌موقع مطلع می‌کند.
</p>
<span className="h-px min-w-4 flex-1 bg-muted-foreground/20" />
</div>
<ul className="grid grid-cols-2 gap-3 text-start">
<ul className="grid w-full min-w-0 max-w-lg grid-cols-2 gap-3 text-start">
{FEATURES.map((feature) => (
<li key={feature.id} className="flex gap-2 lg:items-center">
<li key={feature.id} className="flex min-w-0 gap-2 lg:items-center">
<BadgeCheck className="size-4 shrink-0 text-muted-foreground/80" />
<p className="tracking-tight text-pretty text-muted-foreground/80">
<p className="min-w-0 tracking-tight text-pretty text-muted-foreground/80">
{feature.label}
</p>
</li>
))}
</ul>
</div>
<div className="mt-24 flex items-center justify-center lg:mt-0">
<div className="mt-24 flex w-full min-w-0 max-w-96 items-center justify-center overflow-hidden lg:mt-0 lg:shrink-0">
<CardStack items={CARDS} />
</div>
</div>
+19 -14
View File
@@ -120,10 +120,13 @@ const Feature281 = ({ className }: Feature281Props) => {
<section
dir="rtl"
lang="fa"
className={cn("h-full w-screen overflow-hidden py-32", className)}
className={cn(
"relative h-full w-full overflow-hidden py-32",
className,
)}
>
<div className="container flex w-full max-w-6xl flex-col items-center justify-center">
<div className="relative flex h-full flex-col items-center justify-center gap-8 text-center">
<div className="container flex w-full min-w-0 max-w-6xl flex-col items-center justify-center">
<div className="relative flex h-full min-w-0 flex-col items-center justify-center gap-8 text-center">
<p className="rounded-full bg-muted px-4 py-1 text-xs font-medium">
ارتباط با مشتری
</p>
@@ -131,7 +134,7 @@ const Feature281 = ({ className }: Feature281Props) => {
پایپ‌لاین فروش
</h1>
</div>
<div className="mt-24 flex items-center justify-center">
<div className="mt-24 flex w-full min-w-0 items-center justify-center px-2">
<CardStack items={CARDS} />
</div>
<Button variant="ghost" className="group/btn mt-8 w-fit" asChild>
@@ -187,13 +190,13 @@ const CardStack = ({
}, [startFlipping]);
return (
<div className="relative h-60 w-96">
<div className="relative h-60 w-full max-w-96 min-w-0">
{cards.map((card, index) => {
const CompanyIcon = card.companyIcon;
return (
<motion.div
key={card.id}
className="absolute flex h-60 w-96 flex-col justify-between rounded-3xl border border-neutral-200 bg-white p-4 text-start shadow-xl shadow-black/[0.1] dark:border-white/[0.1] dark:bg-black dark:shadow-white/[0.05]"
className="absolute inset-x-0 flex h-60 w-full max-w-96 flex-col justify-between overflow-hidden rounded-3xl border border-neutral-200 bg-white p-4 text-start shadow-xl shadow-black/[0.1] dark:border-white/[0.1] dark:bg-black dark:shadow-white/[0.05]"
style={{
transformOrigin: "top center",
}}
@@ -208,20 +211,22 @@ const CardStack = ({
bounce: 0.3,
}}
>
<div className="font-normal text-neutral-700 dark:text-neutral-200">
<div className="min-w-0 overflow-hidden font-normal text-neutral-700 dark:text-neutral-200">
{card.content}
</div>
<div className="flex items-center justify-between">
<div className="flex items-center gap-2">
<Avatar key={index} className="size-12">
<div className="mt-3 flex min-w-0 items-center justify-between gap-2">
<div className="flex min-w-0 items-center gap-2">
<Avatar key={index} className="size-12 shrink-0">
<AvatarImage src={card.userImage} alt={card.name} />
</Avatar>
<div>
<p className="font-medium">{card.name}</p>
<p className="text-muted-foreground/80">{card.designation}</p>
<div className="min-w-0">
<p className="truncate font-medium">{card.name}</p>
<p className="truncate text-muted-foreground/80">
{card.designation}
</p>
</div>
</div>
<div className="flex size-10 items-center justify-center rounded-full bg-muted-foreground/15">
<div className="flex size-10 shrink-0 items-center justify-center rounded-full bg-muted-foreground/15">
<CompanyIcon className="size-5" />
</div>
</div>
+12 -12
View File
@@ -16,29 +16,29 @@ const Feature282 = ({ className }: Feature282Props) => {
<section
dir="rtl"
lang="fa"
className={cn("w-screen overflow-hidden py-32", className)}
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="container grid h-full w-full grid-cols-1 gap-12 md:grid-cols-2">
<div>
<div className="mx-auto flex h-full w-full flex-col gap-4 rounded-lg border border-primary/20 bg-primary p-4 md:max-w-sm">
<div className="h-full w-full rounded-md border border-border/50 bg-background p-4">
<div className="container grid h-full w-full min-w-0 grid-cols-1 gap-12 md:grid-cols-2">
<div className="min-w-0">
<div className="mx-auto flex h-full w-full min-w-0 flex-col gap-4 overflow-hidden rounded-lg border border-primary/20 bg-primary p-4 md:max-w-sm">
<div className="h-full w-full min-w-0 overflow-hidden rounded-md border border-border/50 bg-background p-4">
<EvervaultCard
text="یادآور پیگیری خودکار"
className="w-full text-center text-xl font-medium tracking-tight"
className="w-full max-w-full text-center text-xl font-medium tracking-tight text-balance"
/>
</div>
<div className="space-y-2 p-4 text-start">
<p className="font-mono text-sm text-muted-foreground">
<div className="min-w-0 space-y-2 p-4 text-start">
<p className="font-mono text-sm text-balance text-muted-foreground">
با یادآورهای هوشمند و اولویت‌بندی سرنخ، زمان تیم روی معاملات با احتمال بیشتر صرف می‌شود و چرخه فروش کوتاه‌تر می‌شود.
</p>
<p className="text-lg font-semibold text-primary-foreground">
<p className="text-lg font-semibold text-balance text-primary-foreground">
چرخه فروش را از سرنخ تا قرارداد در یک مسیر مشخص پیش ببرید. مدیران می‌توانند گلوگاه‌ها را ببینند و تیم‌ها با اولویت درست روی معاملات ارزشمند تمرکز کنند.
</p>
</div>
</div>
</div>
<div className="text-start">
<p className="mb-2 font-mono text-sm text-muted-foreground">
<div className="min-w-0 text-start">
<p className="mb-2 font-mono text-sm text-balance text-muted-foreground">
الگوهای موفق فروش را در کل سازمان تکرار کنید. داده لحظه‌ای نشان می‌دهد کدام مرحله بیشترین افت تبدیل را دارد.
</p>
<h2 className="text-3xl font-semibold tracking-tight text-balance md:max-w-lg">
@@ -52,7 +52,7 @@ const Feature282 = ({ className }: Feature282Props) => {
</p>
<ul className="mt-8 space-y-3">
{SECURITY_FEATURES.map((feature) => (
<li key={feature.id} className="flex items-center gap-3">
<li key={feature.id} className="flex min-w-0 items-center gap-3">
<div className="size-2 shrink-0 rounded-full bg-primary" />
<span className="font-mono text-sm text-muted-foreground">
{feature.label}
+19 -15
View File
@@ -13,42 +13,42 @@ const IMAGES = [
src: "/block-media/shadcnblocks/block/guri3/img11.jpeg",
imageAlt: "تحلیل عملکرد کمپین",
className:
"absolute -start-10 top-1/2 h-52 w-40 -translate-y-1/2 translate-x-full overflow-hidden rounded-2xl",
"absolute -start-6 top-1/2 hidden h-40 w-32 -translate-y-1/2 translate-x-3/4 overflow-hidden rounded-2xl sm:block md:-start-10 md:h-52 md:w-40 md:translate-x-full",
},
{
id: "corner-start-top",
src: "/block-media/shadcnblocks/block/guri3/img1.jpeg",
imageAlt: "نمودار ROI",
className:
"absolute -top-3 start-10 size-28 -translate-y-full translate-x-full overflow-hidden rounded-2xl",
"absolute -top-3 start-6 hidden size-20 -translate-y-3/4 translate-x-1/2 overflow-hidden rounded-2xl sm:block md:start-10 md:size-28 md:-translate-y-full md:translate-x-full",
},
{
id: "corner-start-bottom",
src: "/block-media/shadcnblocks/block/guri3/img7.jpeg",
imageAlt: "داشبورد بازاریابی دیجیتال",
className:
"absolute -bottom-3 start-10 size-32 translate-x-full translate-y-full overflow-hidden rounded-2xl",
"absolute -bottom-3 start-6 hidden size-24 translate-x-1/2 translate-y-3/4 overflow-hidden rounded-2xl sm:block md:start-10 md:size-32 md:translate-x-full md:translate-y-full",
},
{
id: "side-end-main",
src: "/block-media/shadcnblocks/block/guri3/img12.jpeg",
imageAlt: "تحلیل عملکرد کمپین",
className:
"absolute -end-10 top-1/2 h-52 w-45 -translate-x-full -translate-y-1/2 overflow-hidden rounded-2xl",
"absolute -end-6 top-1/2 hidden h-40 w-36 -translate-x-3/4 -translate-y-1/2 overflow-hidden rounded-2xl sm:block md:-end-10 md:h-52 md:w-45 md:-translate-x-full",
},
{
id: "corner-end-top",
src: "/block-media/shadcnblocks/block/guri3/img13.jpeg",
imageAlt: "نمودار ROI",
className:
"absolute -top-3 end-10 size-28 -translate-x-full -translate-y-full overflow-hidden rounded-2xl",
"absolute -top-3 end-6 hidden size-20 -translate-x-1/2 -translate-y-3/4 overflow-hidden rounded-2xl sm:block md:end-10 md:size-28 md:-translate-x-full md:-translate-y-full",
},
{
id: "corner-end-bottom",
src: "/block-media/shadcnblocks/block/guri3/img3.jpeg",
imageAlt: "داشبورد بازاریابی دیجیتال",
className:
"absolute -bottom-3 end-10 size-32 -translate-x-full translate-y-full overflow-hidden rounded-2xl",
"absolute -bottom-3 end-6 hidden size-24 -translate-x-1/2 translate-y-3/4 overflow-hidden rounded-2xl sm:block md:end-10 md:size-32 md:-translate-x-full md:translate-y-full",
},
] as const;
@@ -63,24 +63,28 @@ const Feature283 = ({ className }: Feature283Props) => {
<section
dir="rtl"
lang="fa"
className={cn("h-screen overflow-hidden py-32", className)}
className={cn(
"relative h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden py-32",
className,
)}
>
<div className="container flex h-full w-full flex-col items-center justify-center px-4">
<div className="relative flex flex-col items-center justify-center">
<h2 className="relative py-2 text-center font-sans text-xl font-semibold tracking-tighter text-balance md:text-2xll">
<div className="container flex h-full w-full min-w-0 flex-col items-center justify-center px-4">
<div className="relative flex w-full min-w-0 max-w-4xl flex-col items-center justify-center overflow-x-clip px-8 py-16 sm:px-16 sm:py-24">
<h2 className="relative z-10 py-2 text-center font-sans text-xl font-semibold tracking-tighter text-balance md:text-2xll">
کمپین‌هایی بسازید که واقعاً تبدیل می‌شوند
</h2>
<p className="mx-auto mt-2 max-w-xl px-5 text-center text-pretty text-sm text-muted-foreground/50 md:text-base">
<p className="relative z-10 mx-auto mt-2 max-w-xl px-5 text-center text-pretty text-sm text-muted-foreground/50 md:text-base">
با سگمنت‌بندی دقیق، پیام مناسب را به مخاطب مناسب برسانید. داده رفتاری نشان می‌دهد کدام محتوا بیشترین تأثیر را روی تبدیل دارد.
</p>
<Button className="mt-10 h-10 gap-2 rounded-xl">
<Button className="relative z-10 mt-10 h-auto max-w-full gap-2 rounded-xl whitespace-normal text-balance">
گزارش لحظه‌ای هزینه، کلیک و تبدیل به شما کمک می‌کند بودجه را از کانال‌های ضعیف به کانال‌های پربازده منتقل کنید.
<Forward className="size-4 rtl:rotate-180" />
<Forward className="size-4 shrink-0 rtl:rotate-180" />
</Button>
<div>
<div className="pointer-events-none absolute inset-0 sm:pointer-events-auto">
{IMAGES.map((image, index) => (
<motion.div
drag
dragConstraints={{ left: -40, right: 40, top: -40, bottom: 40 }}
key={image.id}
initial={{ y: "50%", opacity: 0, scale: 0.8 }}
whileInView={{ y: 0, opacity: 1, scale: 1 }}
@@ -103,7 +107,7 @@ const Feature283 = ({ className }: Feature283Props) => {
}}
onHoverStart={() => setHoveredIndex(index)}
onHoverEnd={() => setHoveredIndex(null)}
className={image.className}
className={cn("pointer-events-auto", image.className)}
>
<img
src={image.src}
+12 -9
View File
@@ -14,11 +14,14 @@ const Feature292 = ({ className }: Feature292Props) => {
<section
dir="rtl"
lang="fa"
className={cn("relative grid w-screen overflow-hidden py-32", className)}
className={cn(
"relative grid w-full overflow-hidden py-32",
className,
)}
>
<div className="relative z-10 container h-full grid-cols-1 items-center justify-center gap-6 lg:grid lg:grid-cols-2">
<div className="flex flex-col items-center justify-center text-center lg:items-start lg:text-start">
<div className="mb-12 flex items-center justify-center gap-3 rounded-full bg-muted-foreground/5 p-1 pe-4 text-sm font-medium tracking-tight text-muted-foreground">
<div className="relative z-10 container grid h-full min-w-0 grid-cols-1 items-center justify-center gap-6 lg:grid-cols-2">
<div className="flex min-w-0 flex-col items-center justify-center text-center lg:items-start lg:text-start">
<div className="mb-12 flex max-w-full min-w-0 flex-wrap items-center justify-center gap-3 rounded-full bg-muted-foreground/5 p-1 pe-4 text-sm font-medium tracking-tight text-muted-foreground lg:justify-start">
<div className="flex items-center gap-3 rounded-full bg-muted-foreground/10 px-4 py-1.5">
<span className="inline-block size-2 shrink-0 rounded-full bg-blue-500" />
<span>ترافیک ارگانیک</span>
@@ -39,24 +42,24 @@ const Feature292 = ({ className }: Feature292Props) => {
گزارش رتبه و ترافیک نشان می‌دهد کدام اقدام بیشترین اثر را روی دیده‌شدن داشته است.
</p>
<div className="mt-10 flex w-full max-w-lg gap-2">
<div className="mt-10 flex w-full min-w-0 max-w-lg flex-wrap gap-2 sm:flex-nowrap">
<Input
type="email"
dir="rtl"
className="h-13 w-full rounded-full"
className="h-13 min-w-0 flex-1 rounded-full"
placeholder="رتبه کلمات کلیدی را پیگیری کنید"
/>
<Button className="h-13 gap-2 rounded-full">
<Button className="h-13 shrink-0 gap-2 rounded-full">
شروع کنید
<ArrowRight className="-rotate-45 rtl:rotate-[135deg]" />
</Button>
</div>
</div>
<div className="relative mt-10 flex h-[80vh] w-full items-center justify-center overflow-hidden rounded-4xl border lg:mt-0 lg:h-[70vh]">
<div className="relative mt-10 flex h-[80vh] w-full min-w-0 items-center justify-center overflow-hidden rounded-4xl border lg:mt-0 lg:h-[70vh]">
<img
src="/block-media/shadcnblocks/block/guri3/img7.jpeg"
alt="داشبورد SEO"
className="size-full object-cover"
className="size-full max-w-full object-cover"
/>
</div>
</div>
+7 -7
View File
@@ -15,32 +15,32 @@ const Feature293 = ({ className }: Feature293Props) => {
dir="rtl"
lang="fa"
className={cn(
"dark relative h-screen w-screen overflow-hidden bg-background py-32 text-foreground",
"dark relative h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden bg-background py-32 text-foreground",
className,
)}
>
<div className="relative container flex h-full flex-col items-center justify-center">
<div className="w-full max-w-lg text-center">
<div className="relative container flex h-full min-w-0 flex-col items-center justify-center">
<div className="w-full min-w-0 max-w-lg text-center">
<h1 className="relative z-20 text-center text-2xll font-semibold tracking-tighter text-balance md:text-2xll lg:text-2xll">
از خرید تا فروش در یک سیستم
</h1>
<p className="mt-4 text-pretty text-muted-foreground/50">
گزارش‌های یکپارچه نشان می‌دهد کدام بخش بیشترین تأثیر را روی سودآوری دارد.
</p>
<div className="mt-10 flex w-full max-w-lg gap-2">
<div className="mt-10 flex w-full min-w-0 max-w-lg flex-wrap gap-2 sm:flex-nowrap">
<Input
type="email"
dir="rtl"
className="h-11 w-full rounded-2xl border-none lg:h-13"
className="h-11 min-w-0 flex-1 rounded-2xl border-none lg:h-13"
placeholder="عملیات سازمان را یکپارچه کنید"
/>
<Button className="h-11 gap-2 rounded-2xl !px-4 lg:h-13">
<Button className="h-11 shrink-0 gap-2 rounded-2xl !px-4 lg:h-13">
یکپارچگی
<ArrowRight className="size-4 shrink-0 rtl:rotate-180" />
</Button>
</div>
</div>
<div className="relative mt-5 h-40 w-[40rem]">
<div className="relative mt-5 h-40 w-full max-w-[40rem] min-w-0 overflow-hidden">
<div className="absolute inset-x-20 top-0 h-[2px] w-3/4 bg-gradient-to-r from-transparent via-indigo-500 to-transparent blur-sm" />
<div className="absolute inset-x-20 top-0 h-px w-3/4 bg-gradient-to-r from-transparent via-indigo-500 to-transparent" />
<div className="absolute inset-x-60 top-0 h-[5px] w-1/4 bg-gradient-to-r from-transparent via-sky-500 to-transparent blur-sm" />
+7 -7
View File
@@ -49,12 +49,12 @@ const Feature294 = ({ className }: Feature294Props) => {
dir="rtl"
lang="fa"
className={cn(
"dark relative w-screen overflow-hidden bg-background py-32 text-foreground",
"dark relative w-full overflow-hidden bg-background py-32 text-foreground",
className,
)}
>
<div className="relative container flex h-full flex-col items-center justify-center">
<div className="w-full max-w-lg text-center">
<div className="relative container flex h-full min-w-0 flex-col items-center justify-center">
<div className="w-full min-w-0 max-w-lg text-center">
<h1 className="relative z-20 text-center text-2xll font-semibold tracking-tighter text-balance md:text-2xll lg:text-2xll">
تصمیم استراتژیک را داده‌محور کنید
</h1>
@@ -62,7 +62,7 @@ const Feature294 = ({ className }: Feature294Props) => {
داشبوردهای تعاملی به تیم‌ها اجازه می‌دهد سؤال جدید بپرسند بدون اینکه هر بار به تیم داده وابسته باشند.
</p>
</div>
<div className="relative mt-5 mb-10 h-40 w-[40rem]">
<div className="relative mt-5 mb-10 h-40 w-full max-w-[40rem] min-w-0 overflow-hidden">
<div className="absolute inset-x-20 top-0 h-[2px] w-3/4 bg-gradient-to-r from-transparent via-indigo-500 to-transparent blur-sm" />
<div className="absolute inset-x-20 top-0 h-px w-3/4 bg-gradient-to-r from-transparent via-indigo-500 to-transparent" />
<div className="absolute inset-x-60 top-0 h-[5px] w-1/4 bg-gradient-to-r from-transparent via-sky-500 to-transparent blur-sm" />
@@ -80,13 +80,13 @@ const Feature294 = ({ className }: Feature294Props) => {
<div className="absolute inset-0 h-full w-full bg-background [mask-image:radial-gradient(350px_130px_at_top,transparent_20%,white)]" />
</div>
<div className="grid w-full max-w-5xl grid-cols-1 gap-15 md:grid-cols-2 lg:grid-cols-3">
<div className="grid w-full min-w-0 max-w-5xl grid-cols-1 gap-15 md:grid-cols-2 lg:grid-cols-3">
{FEATURES.map((feature) => {
const IconComponent = feature.icon;
return (
<div key={feature.id} className="flex gap-4 text-start">
<div key={feature.id} className="flex min-w-0 gap-4 text-start">
<IconComponent className="w-12 shrink-0 stroke-1 text-sky-500" />
<div className="space-y-2">
<div className="min-w-0 space-y-2">
<h3 className="text-xl font-medium">{feature.title}</h3>
<p className="text-pretty text-muted-foreground/30">
{feature.description}
+93 -150
View File
@@ -4,21 +4,14 @@ import type { MotionValue } from "framer-motion";
import {
AnimatePresence,
motion,
useMotionValueEvent,
useScroll,
useTransform,
} from "framer-motion";
import React, { useEffect, useRef, useState } from "react";
import React, { useRef, useState } from "react";
import { cn } from "@/lib/utils";
const getAnimationRange = (index: number, totalFeatures: number) => {
const cardPosition = index / totalFeatures;
const range = [0, cardPosition, 1];
return range;
};
interface Statistics {
value: string;
label: string;
@@ -39,52 +32,15 @@ interface Testimonial {
designation: string;
}
interface AnimationWrapperProps {
children: React.ReactNode;
delay?: number;
className?: string;
duration?: number;
}
const AnimationWrapper = ({
children,
delay = 0,
className,
duration = 0.3,
}: AnimationWrapperProps) => {
return (
<motion.div
initial={{
x: -10,
opacity: 0,
}}
animate={{
x: 0,
opacity: 1,
}}
exit={{
x: 10,
opacity: 0,
}}
transition={{
duration: duration,
ease: "easeOut",
delay: delay,
}}
className={className}
>
{children}
</motion.div>
);
};
interface TestimonialCardProps {
testimonial: Testimonial;
}
const TestimonialCard = ({ testimonial }: TestimonialCardProps) => {
return (
<div className="hidden h-96 flex-1/2 shrink-0 flex-col items-start justify-end rounded-lg border bg-muted p-6 text-start sm:flex lg:h-full">
<div
className="hidden h-96 min-w-[14rem] flex-[1/2] shrink-0 flex-col items-start justify-end rounded-lg border bg-muted p-6 text-start sm:flex lg:h-full lg:min-w-[16rem]"
>
<img
src={testimonial.companyLogo}
alt={testimonial.author}
@@ -94,7 +50,7 @@ const TestimonialCard = ({ testimonial }: TestimonialCardProps) => {
«{testimonial.quote}»
</p>
<p className="mt-4 text-sm font-medium">
{testimonial.author}{" "}
{testimonial.author}{" "}
<span className="font-light">{testimonial.designation}</span>
</p>
</div>
@@ -112,18 +68,13 @@ const ScrollProgressIndicator = ({
activeIndex,
scrollYProgress,
}: ScrollProgressIndicatorProps) => {
const range = getAnimationRange(
Math.max(0, activeIndex - 0.5),
totalFeatures,
const segmentStart = activeIndex / totalFeatures;
const segmentEnd = (activeIndex + 1) / totalFeatures;
const width = useTransform(
scrollYProgress,
[segmentStart, segmentEnd],
["0%", "100%"],
);
const nextRange = getAnimationRange(
Math.min(totalFeatures, activeIndex + 0.5),
totalFeatures,
);
const currentRange = [range[1], nextRange[1]];
const width = useTransform(scrollYProgress, currentRange, ["0%", "100%"]);
return (
<div className="mt-14 hidden w-fit items-center justify-center gap-3 rounded-full bg-muted px-6 py-4 lg:flex">
@@ -137,14 +88,12 @@ const ScrollProgressIndicator = ({
activeIndex > index && "bg-foreground",
)}
>
{activeIndex === index && (
{activeIndex === index ? (
<motion.div
style={{
width,
}}
className="absolute top-0 start-0 h-full rounded-full bg-foreground"
style={{ width }}
className="absolute start-0 top-0 h-full rounded-full bg-foreground"
/>
)}
) : null}
</div>
);
})}
@@ -168,19 +117,13 @@ const FeatureCard = ({
scrollYProgress,
}: FeatureCardProps) => {
return (
<div
className={cn(
"flex w-full flex-col-reverse justify-between gap-8 px-10 py-4 text-start lg:absolute lg:top-1/2 lg:start-1/2 lg:h-full lg:-translate-x-1/2 lg:-translate-y-1/2 lg:flex-row lg:items-center lg:border-s",
)}
>
<div className="flex flex-2/5 flex-col gap-8 lg:h-full lg:gap-0">
<div className="flex flex-col gap-1">
<AnimationWrapper>
<p className="text-xl font-semibold">{feature.title}</p>
</AnimationWrapper>
<AnimationWrapper delay={0.15}>
<p className="font-light text-pretty">{feature.subtitle}</p>
</AnimationWrapper>
<div className="flex w-full min-w-0 flex-col-reverse justify-between gap-8 px-4 py-4 text-start sm:px-10 lg:min-h-[28rem] lg:flex-row lg:items-stretch lg:border-s">
<div className="flex min-w-0 flex-[2/5] flex-col gap-8 lg:gap-0">
<div className="flex min-w-0 flex-col gap-1">
<p className="text-xl font-semibold text-balance break-words">
{feature.title}
</p>
<p className="font-light text-pretty">{feature.subtitle}</p>
</div>
<ScrollProgressIndicator
@@ -190,30 +133,23 @@ const FeatureCard = ({
/>
<div className="flex flex-col gap-1 lg:mt-auto">
<AnimationWrapper delay={0.3}>
<p className="text-2xll font-medium">{feature.statistics.value}</p>
</AnimationWrapper>
<AnimationWrapper delay={0.45}>
<p className="text-sm font-light">{feature.statistics.label}</p>
</AnimationWrapper>
<p className="text-2xl font-medium">{feature.statistics.value}</p>
<p className="text-sm font-light">{feature.statistics.label}</p>
</div>
</div>
<AnimationWrapper
duration={0.6}
className="flex h-96 w-full flex-3/5 items-center gap-6 lg:h-full"
>
<div className="flex h-96 w-full min-w-[18rem] flex-[3/5] items-center gap-6 sm:min-w-[24rem] lg:h-[28rem]">
<img
src={feature.visual}
alt={feature.title}
className={cn(
"h-96 w-full overflow-hidden rounded-lg border object-cover lg:h-full",
index === 0 && "flex-1/2",
"h-full w-full min-w-0 overflow-hidden rounded-lg border object-cover",
index === 0 && "flex-[1/2]",
)}
/>
{index === 0 && <TestimonialCard testimonial={testimonial} />}
</AnimationWrapper>
{index === 0 ? <TestimonialCard testimonial={testimonial} /> : null}
</div>
</div>
);
};
@@ -280,81 +216,88 @@ const DEFAULT_TESTIMONIAL: Testimonial = {
designation: "با هوش مصنوعی سریع‌تر تصمیم بگیرید",
};
function getActiveFeatureIndex(progress: number, total: number) {
if (total <= 0) return 0;
if (progress >= 1) return total - 1;
return Math.min(total - 1, Math.floor(progress * total));
}
const Feature322 = ({
className,
features = DEFAULT_FEATURES,
testimonial = DEFAULT_TESTIMONIAL,
}: Feature322Props) => {
const ref = useRef<HTMLDivElement>(null);
const scrollRef = useRef<HTMLElement>(null);
const { scrollYProgress } = useScroll({
container: ref,
container: scrollRef,
});
const [activeIndex, setActiveIndex] = useState(0);
useEffect(() => {
const unsubscribe = scrollYProgress.on("change", (latest) => {
let minDistance = Infinity;
let temp = 0;
features.forEach((_, index) => {
const range = getAnimationRange(index, features.length);
const position = range[1];
const distance = Math.abs(latest - position);
if (distance < minDistance) {
minDistance = distance;
temp = index;
}
});
setActiveIndex(temp);
});
useMotionValueEvent(scrollYProgress, "change", (latest) => {
const nextIndex = getActiveFeatureIndex(latest, features.length);
setActiveIndex((prev) => (prev === nextIndex ? prev : nextIndex));
});
return () => unsubscribe();
}, [features, scrollYProgress]);
const activeFeature = features[activeIndex] ?? features[0];
return (
<section
ref={ref}
ref={scrollRef}
dir="rtl"
lang="fa"
className={cn("h-screen overflow-y-auto", className)}
className={cn(
"relative h-svh w-full min-w-[20rem] max-w-full overflow-x-clip overflow-y-auto sm:min-w-[36rem] lg:min-w-[64rem]",
className,
)}
>
<div className="container">
<div className="sticky top-0 hidden h-screen w-full flex-col items-center justify-center gap-10 lg:flex">
<div className="relative h-full w-full lg:h-1/2">
<AnimatePresence mode="popLayout">
<FeatureCard
key={features[activeIndex]?.id ?? `feature-${activeIndex}`}
index={activeIndex}
feature={features[activeIndex]}
testimonial={testimonial}
totalFeatures={features.length}
scrollYProgress={scrollYProgress}
/>
</AnimatePresence>
</div>
</div>
<div className="flex w-full flex-col items-center justify-center gap-10 overflow-y-auto py-32 lg:hidden">
<div className="relative h-full w-full lg:h-1/2">
{features.map((feature, index) => {
return (
<FeatureCard
key={feature.id}
index={index}
feature={feature}
testimonial={testimonial}
totalFeatures={features.length}
scrollYProgress={scrollYProgress}
/>
);
})}
<div className="container min-w-0 w-full max-w-full">
{/* Desktop: sticky stage + scroll spacer */}
<div className="relative hidden lg:block">
<div className="sticky top-0 flex h-svh w-full min-w-0 flex-col items-center justify-center">
<div className="relative w-full min-w-0 max-w-full">
<AnimatePresence mode="wait" initial={false}>
{activeFeature ? (
<motion.div
key={activeFeature.id}
initial={{ opacity: 0, x: -12 }}
animate={{ opacity: 1, x: 0 }}
exit={{ opacity: 0, x: 12 }}
transition={{ duration: 0.35, ease: "easeOut" }}
className="w-full min-w-0"
>
<FeatureCard
index={activeIndex}
feature={activeFeature}
testimonial={testimonial}
totalFeatures={features.length}
scrollYProgress={scrollYProgress}
/>
</motion.div>
) : null}
</AnimatePresence>
</div>
</div>
<div
style={{ height: `${Math.max(features.length, 1) * 75}vh` }}
className="pointer-events-none w-full"
aria-hidden
/>
</div>
<div
style={{
height: `${features.length * 75}vh`,
}}
className="hidden lg:block"
/>
{/* Mobile / tablet: stacked cards, no crossfade thrash */}
<div className="flex w-full min-w-0 flex-col items-center justify-center gap-10 py-16 lg:hidden">
{features.map((feature, index) => (
<FeatureCard
key={feature.id}
index={index}
feature={feature}
testimonial={testimonial}
totalFeatures={features.length}
scrollYProgress={scrollYProgress}
/>
))}
</div>
</div>
</section>
);
+27 -23
View File
@@ -90,7 +90,7 @@ const FeatureCard = ({ feature, isActive, onClick }: FeatureCardProps) => {
style={{
borderRadius: "24px",
}}
className="flex cursor-pointer items-start gap-4 overflow-hidden bg-background text-start md:w-fit md:max-w-sm"
className="flex min-w-0 max-w-full cursor-pointer items-start gap-4 overflow-hidden bg-background text-start md:w-fit md:max-w-sm"
onClick={onClick}
>
{isActive ? (
@@ -106,7 +106,7 @@ const FeatureCard = ({ feature, isActive, onClick }: FeatureCardProps) => {
delay: 0.3,
ease: "easeOut",
}}
className="p-6 text-sm md:p-8 md:text-base"
className="min-w-0 p-6 text-sm md:p-8 md:text-base"
>
<p className="text-pretty">
<span className="font-semibold">{feature.title}.</span>{" "}
@@ -136,7 +136,7 @@ const FeatureCard = ({ feature, isActive, onClick }: FeatureCardProps) => {
}}
>
<PlusCircle strokeWidth={1.5} className="shrink-0" />
<p className="shrink-0 font-semibold">{feature.title}</p>
<p className="min-w-0 font-semibold">{feature.title}</p>
</motion.div>
)}
</motion.div>
@@ -164,14 +164,14 @@ const FeaturesDesktop = ({
isNextDisabled,
}: FeaturesDesktopProps) => {
return (
<div className="relative z-10 hidden items-center gap-8 md:flex">
<div className="relative z-10 hidden min-w-0 items-center gap-8 md:flex">
<Controls
handleNext={handleNext}
handlePrevious={handlePrevious}
isPrevioIRRisabled={isPrevioIRRisabled}
isNextDisabled={isNextDisabled}
/>
<div className="flex flex-col gap-4">
<div className="flex min-w-0 flex-col gap-4">
{features.map((feature, index) => {
return (
<FeatureCard
@@ -209,8 +209,8 @@ const FeaturesMobile = ({
const variants = {
initial: (dir: 1 | -1) => ({
opacity: 0,
scale: 0.6,
x: `${dir * -50}%`,
scale: 0.9,
x: `${dir * -20}%`,
}),
animate: {
opacity: 1,
@@ -219,17 +219,17 @@ const FeaturesMobile = ({
},
exit: (dir: 1 | -1) => ({
opacity: 0,
scale: 0.6,
x: `${dir * 50}%`,
scale: 0.9,
x: `${dir * 20}%`,
}),
};
return (
<div className="absolute bottom-6 start-0 z-10 flex w-full items-end justify-between gap-6 px-6 md:hidden">
<div className="absolute inset-x-0 bottom-6 z-10 flex w-full min-w-0 items-end justify-between gap-3 px-4 sm:gap-6 sm:px-6 md:hidden">
<Button
variant="outline"
size="icon"
className="rounded-full !bg-background/100 [&_svg:not([class*='size-'])]:size-6"
className="shrink-0 rounded-full !bg-background/100 [&_svg:not([class*='size-'])]:size-6"
onClick={handlePrevious}
disabled={isPrevioIRRisabled}
>
@@ -247,7 +247,7 @@ const FeaturesMobile = ({
duration: 0.2,
ease: "easeOut",
}}
className="h-full w-full object-cover"
className="h-full min-w-0 flex-1 object-cover"
>
<FeatureCard
feature={features[activeIndex]}
@@ -260,7 +260,7 @@ const FeaturesMobile = ({
<Button
variant="outline"
size="icon"
className="rounded-full !bg-background/100 [&_svg:not([class*='size-'])]:size-6"
className="shrink-0 rounded-full !bg-background/100 [&_svg:not([class*='size-'])]:size-6"
onClick={handleNext}
disabled={isNextDisabled}
>
@@ -356,9 +356,9 @@ const Feature323 = ({
setActiveIndex(index);
};
const xOffset = !isMobile ? 50 : 15;
const yOffset = !isMobile ? 15 : 5;
const scale = !isMobile ? 0.6 : 0.8;
const xOffset = !isMobile ? 20 : 10;
const yOffset = !isMobile ? 10 : 5;
const scale = !isMobile ? 0.85 : 0.9;
const variants = {
initial: (dir: 1 | -1) => ({
@@ -385,14 +385,18 @@ const Feature323 = ({
};
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container space-y-20">
<div className="relative start-1/2 max-w-5xl -translate-x-1/2">
<h2 className="text-xl font-semibold text-balance sm:text-2xll">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full min-w-0 overflow-hidden py-32", className)}
>
<div className="container min-w-0 space-y-20">
<div className="mx-auto w-full min-w-0 max-w-5xl">
<h2 className="text-xl font-semibold text-balance break-words sm:text-2xll">
{heading}
</h2>
</div>
<div className="relative h-full min-h-[60vh] w-full overflow-hidden rounded-4xl bg-muted px-8 py-8 md:min-h-full md:py-20">
<div className="relative h-full min-h-[60vh] w-full min-w-0 max-w-full overflow-hidden rounded-4xl bg-muted px-4 py-8 sm:px-8 md:min-h-full md:py-20">
<FeaturesDesktop
features={features}
handleNext={handleNext}
@@ -412,7 +416,7 @@ const Feature323 = ({
isNextDisabled={activeIndex === features.length - 1}
/>
<div className="absolute top-0 end-0 z-0 flex h-full w-full items-center justify-center lg:w-2/3 lg:mask-[linear-gradient(to_left,_transparent,_black_30%,_black)]">
<div className="absolute inset-0 z-0 flex h-full w-full min-w-0 items-center justify-center overflow-hidden lg:inset-y-0 lg:end-0 lg:start-auto lg:w-2/3 lg:mask-[linear-gradient(to_left,_transparent,_black_30%,_black)]">
<AnimatePresence mode="popLayout" custom={direction}>
<motion.img
key={`feature-image-${features[activeIndex]?.id}`}
@@ -427,7 +431,7 @@ const Feature323 = ({
}}
src={features[activeIndex].image}
alt={features[activeIndex].title}
className="h-full w-full object-cover"
className="h-full w-full max-w-full object-cover"
/>
</AnimatePresence>
</div>
+16 -12
View File
@@ -37,31 +37,35 @@ interface Feature82Props {
const Feature82 = ({ className }: Feature82Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div className="container">
<div className="grid place-items-center items-center gap-4 lg:grid-cols-5 lg:gap-16">
<h1 className="text-center text-xl font-semibold text-balance lg:col-span-2 lg:text-start lg:text-2xll">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="container min-w-0">
<div className="grid min-w-0 place-items-center items-center gap-4 lg:grid-cols-5 lg:gap-16">
<h1 className="min-w-0 text-center text-xl font-semibold text-balance lg:col-span-2 lg:text-start lg:text-2xll">
فرایندها را استاندارد و سریع کنید
</h1>
<p className="text-center text-lg text-muted-foreground lg:col-span-2 lg:text-start">
<p className="min-w-0 text-center text-lg text-balance text-muted-foreground lg:col-span-2 lg:text-start">
قوانین ساده تعریف کنید تا وظایف تکراری بدون دخالت دست انجام شود. تیم روی تصمیم‌های مهم تمرکز می‌کند و سرعت اجرا بالاتر می‌رود.
</p>
<Button className="mx-auto w-fit lg:mx-0 lg:ms-auto">
<Button className="mx-auto h-auto max-w-full whitespace-normal text-balance lg:mx-0 lg:ms-auto">
فرایندهای بین‌تیمی را در یک بوم بصری طراحی کنید. هر مرحله قابل ردیابی است و گلوگاه‌ها قبل از تأخیر جدی مشخص می‌شوند.
</Button>
</div>
<Separator className="mt-8 mb-12" />
<ul className="grid grid-cols-1 gap-10 md:grid-cols-2 lg:grid-cols-4 lg:gap-20">
<ul className="grid min-w-0 grid-cols-1 gap-10 md:grid-cols-2 lg:grid-cols-4 lg:gap-20">
{integrations.map((integration) => (
<li key={integration.title}>
<div>
<li key={integration.title} className="min-w-0">
<div className="min-w-0">
<img
src={integration.image}
alt={`لوگوی ${integration.title}`}
className="h-auto w-16"
/>
<h3 className="my-2 text-xl font-bold">{integration.title}</h3>
<p className="text-sm text-muted-foreground">
<p className="text-sm text-balance text-muted-foreground">
{integration.description}
</p>
</div>
@@ -70,10 +74,10 @@ const Feature82 = ({ className }: Feature82Props) => {
</ul>
<a
href="#"
className="mt-12 flex items-center justify-center gap-1 text-lg font-semibold underline"
className="mt-12 flex flex-wrap items-center justify-center gap-1 text-lg font-semibold underline"
>
اتوماسیون را در کل سازمان یکپارچه کنید
<ArrowRight className="h-auto w-4 rtl:rotate-180" />
<ArrowRight className="h-auto w-4 shrink-0 rtl:rotate-180" />
</a>
</div>
</section>
+27 -18
View File
@@ -37,25 +37,34 @@ interface Feature98Props {
const Feature98 = ({ className }: Feature98Props) => {
return (
<section dir="rtl" lang="fa" className={cn("py-32", className)}>
<div>
<div className="container">
<div className="grid gap-8 lg:grid-cols-5 lg:gap-20">
<div className="lg:col-span-3">
<p className="text-lg text-muted-foreground">
<section
dir="rtl"
lang="fa"
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="min-w-0">
<div className="container min-w-0">
<div className="grid min-w-0 gap-8 lg:grid-cols-5 lg:gap-20">
<div className="min-w-0 lg:col-span-3">
<p className="text-balance text-lg text-muted-foreground">
گزارش‌های بصری نشان می‌دهند کدام اقدام بیشترین اثر را روی درآمد و نگهداشت مشتری داشته است.
</p>
<h2 className="mt-6 text-xl lg:text-2xll">
<h2 className="mt-6 text-balance text-xl lg:text-2xll">
داده پراکنده را به تصمیم تبدیل کنید
</h2>
</div>
<div className="lg:col-span-2">
<p className="text-lg text-muted-foreground">
<div className="min-w-0 lg:col-span-2">
<p className="text-balance text-lg text-muted-foreground">
داده فروش، بازاریابی و پشتیبانی در داشبوردهای یکپارچه جمع می‌شود. مدیران بدون انتظار گزارش دستی، وضعیت واقعی کسب‌وکار را می‌بینند.
</p>
<div className="mt-10 flex gap-2">
<Button size="lg">شاخص‌های مهم را شخصی‌سازی کنید و تغییرات غیرعادی را زودتر تشخیص دهید. تیم‌ها با دید مشترک، سریع‌تر هم‌راستا می‌شوند.</Button>
<Button size="lg" variant="secondary">
<div className="mt-10 flex min-w-0 flex-wrap gap-2">
<Button
size="lg"
className="h-auto max-w-full whitespace-normal text-balance"
>
شاخص‌های مهم را شخصی‌سازی کنید و تغییرات غیرعادی را زودتر تشخیص دهید. تیم‌ها با دید مشترک، سریع‌تر هم‌راستا می‌شوند.
</Button>
<Button size="lg" variant="secondary" className="shrink-0">
تحلیل داده
</Button>
</div>
@@ -63,17 +72,17 @@ const Feature98 = ({ className }: Feature98Props) => {
</div>
</div>
<Separator className="mt-24 mb-6" />
<div className="container grid gap-8 lg:grid-cols-3">
<div className="container grid min-w-0 gap-8 lg:grid-cols-3">
{cards.map((card) => (
<a
key={card.title}
href={card.href}
className="group relative grid overflow-hidden sm:grid-cols-2 lg:grid-cols-1"
className="group relative grid min-w-0 overflow-hidden sm:grid-cols-2 lg:grid-cols-1"
>
<div className="absolute start-0 top-0 z-20 flex w-full justify-between gap-2 p-6 text-background sm:bottom-0 sm:start-1/2 sm:w-1/2 sm:flex-col lg:bottom-auto lg:start-0 lg:w-full lg:flex-row lg:items-center">
<div>
<div className="absolute start-0 top-0 z-20 flex w-full min-w-0 justify-between gap-2 p-6 text-background sm:bottom-0 sm:start-1/2 sm:w-1/2 sm:flex-col lg:bottom-auto lg:start-0 lg:w-full lg:flex-row lg:items-center">
<div className="min-w-0">
<h3 className="text-lg font-medium">{card.title}</h3>
<p>{card.description}</p>
<p className="text-balance">{card.description}</p>
</div>
<span className="flex size-12 shrink-0 items-center justify-center rounded-full bg-background text-primary sm:self-end lg:size-14 lg:self-auto">
<ArrowRight className="rtl:rotate-180" />
@@ -82,7 +91,7 @@ const Feature98 = ({ className }: Feature98Props) => {
<img
src={card.image}
alt={card.imageAlt}
className="scale-105 transition-all duration-500 group-hover:scale-[1.1]"
className="max-w-full scale-105 transition-all duration-500 group-hover:scale-[1.1]"
/>
<div className="z-10 bg-primary" />
</a>
+18 -18
View File
@@ -11,44 +11,44 @@ const Hero145 = ({ className }: Hero145Props) => {
return (
<section
className={cn(
"dark relative h-svh max-h-[1400px] w-full bg-[url(/block-media/shadcnblocks/block/full-width-backgrounds/andrew-kliatskyi-uBg4k82xnI4-unsplash.jpg)] bg-cover bg-[100%] bg-no-repeat before:absolute before:top-0 before:left-0 before:size-full before:bg-[radial-gradient(circle_at_100%_-100%,transparent_40%,rgba(0,0,0,.75)_85%)] before:content-['']",
"dark relative h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden bg-[url(/block-media/shadcnblocks/block/full-width-backgrounds/andrew-kliatskyi-uBg4k82xnI4-unsplash.jpg)] bg-cover bg-[100%] bg-no-repeat before:absolute before:inset-0 before:bg-[radial-gradient(circle_at_100%_-100%,transparent_40%,rgba(0,0,0,.75)_85%)] before:content-['']",
className,
)}
>
<div className="relative z-10 container flex size-full max-w-[103.125rem] flex-col justify-between pt-24 pb-14 md:justify-end">
<div className="flex h-full flex-col justify-between gap-6 md:justify-end">
<h1 className="text-xl leading-[2.25rem] font-bold text-foreground lg:text-2xll lg:leading-[3rem]! xl:text-2xll xl:leading-[5.5rem]!">
<div className="relative z-10 container flex size-full min-w-0 max-w-[103.125rem] flex-col justify-between pt-24 pb-14 md:justify-end">
<div className="flex h-full min-w-0 flex-col justify-between gap-6 md:justify-end">
<h1 className="min-w-0 text-xl leading-[2.25rem] font-bold text-balance break-words text-foreground lg:text-2xll lg:leading-[3rem]! xl:text-2xll xl:leading-[5.5rem]!">
<div className="mb-2">به استخدام برترین</div>
<div className="relative h-[calc(2.25rem*3)] md:h-[2.25rem] lg:h-[3rem] xl:h-[5.5rem]">
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_0s] will-change-[opacity]">
<div className="relative h-[calc(2.25rem*3)] w-full min-w-0 overflow-hidden md:h-[2.25rem] lg:h-[3rem] xl:h-[5.5rem]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_0s] will-change-[opacity]">
نمایندگان فروش امنیت سایبری
</div>
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_2s] opacity-0 will-change-[opacity]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_2s] opacity-0 will-change-[opacity]">
تست‌کنندگان نفوذ
</div>
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_4s] opacity-0 will-change-[opacity]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_4s] opacity-0 will-change-[opacity]">
مهندسان فروش
</div>
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_6s] opacity-0 will-change-[opacity]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_6s] opacity-0 will-change-[opacity]">
معماران IAM
</div>
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_8s] opacity-0 will-change-[opacity]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_8s] opacity-0 will-change-[opacity]">
مدیران ارشد امنیت اطلاعات
</div>
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_10s] opacity-0 will-change-[opacity]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_10s] opacity-0 will-change-[opacity]">
مهندسان امنیت ابری
</div>
<div className="absolute top-0 left-0 animate-[show-text_14s_ease-in-out_infinite_12s] opacity-0 will-change-[opacity]">
<div className="absolute inset-x-0 top-0 w-full animate-[show-text_14s_ease-in-out_infinite_12s] opacity-0 will-change-[opacity]">
مهندسان امنیت اپلیکیشن
</div>
</div>
</h1>
<div className="flex flex-col gap-8">
<p className="text-lg text-foreground lg:text-xl">
<div className="flex min-w-0 flex-col gap-8">
<p className="text-balance text-lg text-foreground lg:text-xl">
فرآیند جذب نیرو را سریع‌تر و هدفمندتر انجام دهید.
</p>
<div className="flex flex-wrap items-center justify-between gap-5">
<div className="flex flex-wrap items-center gap-5">
</p>
<div className="flex min-w-0 flex-wrap items-center justify-between gap-5">
<div className="flex min-w-0 flex-wrap items-center gap-5">
<Button
asChild
className="h-fit w-fit rounded-full px-7 py-3.5 text-xs font-semibold text-nowrap uppercase lg:px-9 lg:py-5 lg:text-base"
@@ -65,7 +65,7 @@ const Hero145 = ({ className }: Hero145Props) => {
</div>
<Button
variant="link"
className="flex h-fit w-fit items-center gap-2 text-xs font-semibold text-nowrap uppercase hover:no-underline lg:text-base"
className="flex h-fit w-fit shrink-0 items-center gap-2 text-xs font-semibold text-nowrap uppercase hover:no-underline lg:text-base"
>
<div>برای مشاهده بیشتر اسکرول کنید</div>
<ArrowDown className="size-3! stroke-white lg:size-4!" />
+1 -1
View File
@@ -74,7 +74,7 @@ const Hero159 = ({ className }: Hero159Props) => {
</div>
</div>
</div>
<div className="absolute -top-36 right-0 hidden w-1/2 rounded-bl-[1.875rem] md:block md:h-[34.375rem] xl:h-[41.5625rem]">
<div className="absolute -top-36 end-0 hidden w-1/2 rounded-es-[1.875rem] md:block md:h-[34.375rem] xl:h-[41.5625rem]">
<img
src="/block-media/shadcnblocks/block/placeholder-8-wide.svg"
alt="تصویر نمونه"
+15 -12
View File
@@ -11,16 +11,19 @@ interface Hero167Props {
const Hero167 = ({ className }: Hero167Props) => {
return (
<section
className={cn("overflow-hidden bg-background py-20 font-sans", className)}
className={cn(
"relative w-full overflow-hidden bg-background py-20 font-sans",
className,
)}
>
<div className="container">
<div className="container min-w-0">
<div className="grid grid-cols-1 gap-x-10 gap-y-16 lg:grid-cols-2">
<div className="flex flex-col gap-12">
<div className="max-w-[31.25rem]">
<h1 className="mb-8 font-sans text-2xll font-semibold text-foreground md:text-2xll">
<div className="flex min-w-0 flex-col gap-12">
<div className="max-w-[31.25rem] min-w-0">
<h1 className="mb-8 font-sans text-2xll font-semibold text-balance break-words text-foreground md:text-2xll">
توانایی مراقبت را گسترش دهید
</h1>
<p className="text-xl text-muted-foreground">
<p className="text-balance text-xl text-muted-foreground">
ناکارآمدی‌ها را حذف و مراقبت از بیمار را با سیستم جامع بهداشت
و درمانی که گردش‌کار شما را یکپارچه و بهینه می‌کند، ارتقا دهید.
</p>
@@ -29,7 +32,7 @@ const Hero167 = ({ className }: Hero167Props) => {
<Button
asChild
variant="outline"
className="group inline-flex h-fit w-fit flex-wrap items-center gap-2 rounded-full border border-black px-5 py-3 transition-all hover:bg-black hover:shadow-[0_2px_15px_2px_var(--color-muted-foreground)]"
className="group inline-flex h-fit w-fit max-w-full flex-wrap items-center gap-2 rounded-full border border-black px-5 py-3 transition-all hover:bg-black hover:shadow-[0_2px_15px_2px_var(--color-muted-foreground)]"
>
<a href="#">
<p className="text-sm font-medium text-black transition-colors group-hover:text-white">
@@ -41,7 +44,7 @@ const Hero167 = ({ className }: Hero167Props) => {
<Button
asChild
variant="outline"
className="group inline-flex h-fit w-fit flex-wrap items-center gap-2 rounded-full border border-black px-5 py-3 transition-all hover:bg-black hover:shadow-[0_2px_15px_2px_var(--color-muted-foreground)]"
className="group inline-flex h-fit w-fit max-w-full flex-wrap items-center gap-2 rounded-full border border-black px-5 py-3 transition-all hover:bg-black hover:shadow-[0_2px_15px_2px_var(--color-muted-foreground)]"
>
<a href="#">
<p className="text-sm font-medium text-black transition-colors group-hover:text-white">
@@ -52,9 +55,9 @@ const Hero167 = ({ className }: Hero167Props) => {
</Button>
</div>
</div>
<div className="">
<div className="relative -me-8 h-[25rem] min-w-[50vw] rounded-lg bg-linear-to-b from-[#fbf7ec] to-[#e2f1ee] md:h-[45.625rem]">
<div className="absolute top-16 left-24 w-[26.25rem] overflow-hidden rounded-lg shadow-lg md:top-32 md:left-40 md:w-[42.5rem] md:rounded-xl lg:left-24 lg:w-[46.25rem]">
<div className="min-w-0">
<div className="relative h-[25rem] w-full min-w-0 overflow-hidden rounded-lg bg-linear-to-b from-[#fbf7ec] to-[#e2f1ee] md:h-[45.625rem]">
<div className="absolute top-16 start-6 w-[min(100%-1.5rem,26.25rem)] overflow-hidden rounded-lg shadow-lg md:top-32 md:start-10 md:w-[min(100%-2.5rem,42.5rem)] md:rounded-xl lg:start-6 lg:w-[min(100%-1.5rem,46.25rem)]">
<AspectRatio ratio={1.466424682 / 1}>
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
@@ -64,7 +67,7 @@ const Hero167 = ({ className }: Hero167Props) => {
</AspectRatio>
</div>
<div className="absolute bottom-4 left-32 w-full max-w-[8.75rem] overflow-hidden rounded-md shadow-xl md:left-72 md:max-w-[16.5625rem] md:rounded-xl lg:bottom-10 lg:left-52 xl:left-32">
<div className="absolute bottom-4 start-8 w-full max-w-[8.75rem] overflow-hidden rounded-md shadow-xl md:start-16 md:max-w-[16.5625rem] md:rounded-xl lg:bottom-10 lg:start-12 xl:start-8">
<AspectRatio ratio={1.698717949 / 1}>
<img
src="/block-media/shadcnblocks/block/placeholder-dark-4.svg"
+15 -15
View File
@@ -9,45 +9,45 @@ interface Hero168Props {
const Hero168 = ({ className }: Hero168Props) => {
return (
<section className={cn("overflow-hidden py-32", className)}>
<div className="container">
<div className="flex flex-col items-start justify-between gap-8 md:flex-row xl:gap-20">
<div className="flex w-full flex-col items-start text-start">
<h1 className="mb-8 text-xl font-normal text-pretty md:text-2xll">
<section className={cn("relative w-full overflow-hidden py-32", className)}>
<div className="container min-w-0">
<div className="flex min-w-0 flex-col items-start justify-between gap-8 md:flex-row xl:gap-20">
<div className="flex w-full min-w-0 flex-col items-start text-start">
<h1 className="mb-8 text-xl font-normal text-pretty text-balance break-words md:text-2xll">
راهکارهای هوشمند برای رشد کسب‌وکار
</h1>
<p className="mb-12 max-w-[70%] text-xl font-normal text-muted-foreground">
</h1>
<p className="mb-12 max-w-[70%] text-balance text-xl font-normal text-muted-foreground">
با استفاده از ابزارهای یکپارچه و هوشمند، بهره‌وری تیم را افزایش دهید و فرایندهای کاری را ساده‌تر کنید.
</p>
</p>
<div className="flex w-full justify-start md:justify-start">
<Button className="px-5 py-3" variant="outline">
شروع رایگان <ArrowRight className="ms-2 size-4 rtl:rotate-180" />
</Button>
</div>
</div>
<div className="relative flex h-[600px] w-full rounded-md sm:h-[750px]">
<div className="absolute flex h-[600px] w-screen rounded-md bg-linear-to-b from-muted/50 to-muted sm:h-[750px]">
<div className="relative flex h-[600px] w-full min-w-0 overflow-hidden rounded-md sm:h-[750px]">
<div className="absolute inset-0 flex rounded-md bg-linear-to-b from-muted/50 to-muted">
<img
src="/block-media/shadcnblocks/block/placeholder-dark-1.svg"
alt="تصویر نمونه"
className="my-auto ms-20 block h-4/6 w-auto rounded-md object-cover md:w-2/5"
className="my-auto ms-8 block h-4/6 w-auto max-w-[min(100%,20rem)] rounded-md object-cover md:ms-20 md:max-w-none md:w-2/5"
/>
<div className="absolute top-1/2 -left-5 md:-left-20 lg:-left-44">
<div className="absolute top-1/2 start-2 md:start-4 lg:start-8">
<img
src="/block-media/shadcnblocks/block/placeholder-dark-2.svg"
alt="تصویر نمونه"
className="mb-6 h-[134px] w-[230px] rounded-lg object-cover shadow-md lg:h-[142px] lg:w-[265px]"
className="mb-6 h-[134px] w-[230px] max-w-full rounded-lg object-cover shadow-md lg:h-[142px] lg:w-[265px]"
/>
<img
src="/block-media/shadcnblocks/block/placeholder-dark-3.svg"
alt="تصویر نمونه"
className="h-[115px] w-[230px] rounded-lg bg-muted shadow-md lg:h-[122px] lg:w-[265px]"
className="h-[115px] w-[230px] max-w-full rounded-lg bg-muted shadow-md lg:h-[122px] lg:w-[265px]"
/>
</div>
<img
src="/block-media/shadcnblocks/block/placeholder-dark-3.svg"
alt="تصویر نمونه"
className="absolute bottom-[70%] -left-5 h-[146px] w-[230px] rounded-lg bg-muted shadow-md md:bottom-10 md:left-1/4 lg:h-[156px] lg:w-[265px] 2xl:left-32"
className="absolute bottom-[70%] start-2 h-[146px] w-[230px] max-w-full rounded-lg bg-muted shadow-md md:bottom-10 md:start-1/4 lg:h-[156px] lg:w-[265px] 2xl:start-32"
/>
</div>
</div>
+1 -1
View File
@@ -19,7 +19,7 @@ const Hero178 = ({ className }: Hero178Props) => {
<p className="font-mono text-[clamp(0.875rem,0.875vw,1rem)] text-muted-foreground">
پشتیبانی مشتری
</p>
<h1 className="text-[clamp(3.5rem,calc(6.5vw+2.3rem),9.5rem)] leading-[0.85] tracking-[-0.03em] text-foreground">
<h1 className="text-[clamp(2.25rem,calc(3.5vw+1.25rem),5.5rem)] leading-[0.95] tracking-[-0.03em] text-foreground">
تجربه
<br />
پشتیبانی مشتری را متحول کنید
+1 -1
View File
@@ -16,7 +16,7 @@ const Hero179 = ({ className }: Hero179Props) => {
<p className="font-mono text-[clamp(0.875rem,0.875vw,1rem)] text-muted-foreground">
صندوق ورودی مشترک
</p>
<h1 className="text-[clamp(3.5rem,calc(6.5vw+2.3rem),9.5rem)] leading-[0.85] tracking-[-0.03em] text-foreground">
<h1 className="text-[clamp(2.25rem,calc(3.5vw+1.25rem),5.5rem)] leading-[0.95] tracking-[-0.03em] text-foreground">
صندوق ورودی تیمی
<br />
را سازمان‌دهی کنید
+2 -2
View File
@@ -81,10 +81,10 @@ const Hero195 = ({
<div className="container">
<div className="border-x border-border py-20">
<div className="relative mx-auto max-w-2xl p-2">
<h1 className="mx-1 mt-6 text-center text-2xll font-bold tracking-tighter md:text-2xll">
<h1 className="mx-1 mt-6 text-center text-2xll font-bold tracking-tighter md:text-2xll [mask-image:linear-gradient(to_right,transparent_0%,black_35%)] [-webkit-mask-image:linear-gradient(to_right,transparent_0%,black_35%)]">
{title}
</h1>
<p className="mx-2 mt-6 max-w-xl text-center text-lg font-medium text-muted-foreground md:text-xl">
<p className="mx-2 mt-6 max-w-xl text-center text-lg font-medium text-muted-foreground md:text-xl [mask-image:linear-gradient(to_right,transparent_0%,black_35%)] [-webkit-mask-image:linear-gradient(to_right,transparent_0%,black_35%)]">
{description}
</p>
<div className="mx-2 mt-6 flex justify-center gap-2">
+1 -1
View File
@@ -46,7 +46,7 @@ const Hero202 = ({ className }: Hero202Props) => {
</Button>
</div>
</div>
<div className="absolute -right-70 -bottom-70 -rotate-45 transition-all ease-in-out group-hover:-rotate-0">
<div className="absolute -left-70 -bottom-70 -rotate-45 transition-all ease-in-out group-hover:-rotate-0">
<img
src="/block-media/shadcnblocks/block/illustrations/tokyo-solar-system-around-a-smiley.svg"
className="size-150 md:size-220"
+27 -22
View File
@@ -13,35 +13,40 @@ interface Hero204Props {
const Hero204 = ({ className }: Hero204Props) => {
return (
<section className={cn("bg-background py-32", className)}>
<div className="container flex flex-col items-center justify-center gap-4 text-center">
<h2 className="flex text-xl tracking-tighter text-foreground">
<section
className={cn(
"relative w-full overflow-hidden bg-background py-32",
className,
)}
>
<div className="container flex min-w-0 flex-col items-center justify-center gap-4 text-center">
<h2 className="flex items-center text-xl tracking-tighter text-foreground">
<Sparkle className="ms-3" /> کتابخانه کامپوننت
</h2>
<h1 className="font-playfair max-w-xl text-xl tracking-tighter text-foreground md:text-2xll">
</h2>
<h1 className="font-playfair max-w-xl text-balance text-xl tracking-tighter text-foreground md:text-2xll">
کامپوننت‌های آماده برای توسعه سریع رابط کاربری
</h1>
<p className="mt-7 max-w-xl text-xl tracking-tight text-muted-foreground">
</h1>
<p className="mt-7 max-w-xl text-balance text-xl tracking-tight text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
</p>
<div className="mt-10 flex w-full max-w-xl items-center justify-center rounded-full border p-1">
<div className="mt-10 flex w-full max-w-xl min-w-0 items-center justify-center rounded-full border p-1">
<Input
placeholder="ایمیل خود را وارد کنید"
className="w-full border-none ps-5 text-xl! tracking-tight shadow-none outline-none focus-visible:ring-0 focus-visible:outline-none"
className="w-full min-w-0 border-none ps-5 text-xl! tracking-tight shadow-none outline-none focus-visible:ring-0 focus-visible:outline-none"
/>
<Button className="rounded-full px-10 py-7 text-lg text-background transition-all ease-in-out hover:px-12">
<Button className="shrink-0 rounded-full px-10 py-7 text-lg text-background transition-all ease-in-out hover:px-12">
شروع رایگان
</Button>
</Button>
</div>
{/* Iphone mockup with content */}
<div className="relative mt-12 flex h-[450px] w-screen justify-center overflow-hidden border-b-2 border-border">
{/* Iphone mockup with content — centered in preview frame */}
<div className="relative mt-12 flex h-[450px] w-full min-w-0 justify-center overflow-hidden border-b-2 border-border">
<motion.div
initial={{ opacity: 0, y: 200, scale: 0.8 }}
animate={{ opacity: 100, y: 0, scale: 1 }}
animate={{ opacity: 1, y: 0, scale: 1 }}
transition={{ ease: [0, 0.51, 0.2, 1.01], duration: 0.8 }}
className="absolute mx-auto mt-6 me-58 hidden h-[850px] w-[400px] -rotate-18 items-center justify-center rounded-[75px] bg-black md:mt-12 md:flex md:h-[840px] md:w-[400px]"
className="absolute top-0 left-1/2 z-0 mt-6 hidden h-[850px] w-[400px] -translate-x-[calc(50%+7.25rem)] -rotate-18 items-center justify-center rounded-[75px] bg-black md:mt-12 md:flex md:h-[840px]"
>
<img
className="absolute z-2 scale-105 object-cover"
@@ -52,12 +57,12 @@ const Hero204 = ({ className }: Hero204Props) => {
<div className="mt-20 flex justify-between px-0">
<h1 className="flex items-end gap-2 px-12 text-2xll font-semibold tracking-tight text-background md:text-2xll">
کامپوننت‌های رابط کاربری
<div className="mb-2 size-3 rounded-full bg-red-500 md:size-5" />
<div className="mb-2 size-3 rounded-full bg-red-500 md:size-5" />
</h1>
<div className="mt-2 me-8 flex flex-col items-end">
<p className="text-lg tracking-tighter text-muted-foreground md:text-xl">
آخرین به‌روزرسانی
</p>
</p>
<p className="-mt-1 text-xl font-semibold tracking-tighter text-muted-foreground/50 md:text-xl">
2025
</p>
@@ -72,12 +77,12 @@ const Hero204 = ({ className }: Hero204Props) => {
</motion.div>
<motion.div
initial={{ opacity: 0, y: 200, scale: 0.8 }}
animate={{ opacity: 100, y: 0, scale: 1 }}
animate={{ opacity: 1, y: 0, scale: 1 }}
transition={{
ease: [0, 0.71, 0.2, 1.01],
duration: 0.8,
}}
className="absolute mx-auto mt-6 flex h-[850px] w-[400px] items-center justify-center rounded-[75px] bg-background md:mt-24 md:ms-58 md:h-[840px] md:w-[400px] md:rotate-20"
className="absolute top-0 left-1/2 z-10 mt-6 flex h-[850px] w-[400px] -translate-x-1/2 items-center justify-center rounded-[75px] bg-background md:mt-24 md:-translate-x-[calc(50%-7.25rem)] md:h-[840px] md:rotate-20"
>
<img
className="absolute z-2 scale-105 object-cover"
@@ -88,12 +93,12 @@ const Hero204 = ({ className }: Hero204Props) => {
<div className="mt-20 flex justify-between px-0">
<h1 className="flex items-end gap-2 px-12 text-2xll font-semibold tracking-tight text-foreground md:text-2xll">
بلاک‌های صفحات
<div className="mb-2 size-3 rounded-full bg-red-500 md:size-5" />
<div className="mb-2 size-3 rounded-full bg-red-500 md:size-5" />
</h1>
<div className="mt-2 me-8 flex flex-col items-end">
<p className="text-lg tracking-tighter text-muted-foreground md:text-xl">
به‌روزرسانی جدید
</p>
</p>
<p className="-mt-1 text-xl font-semibold tracking-tighter text-muted-foreground/50 md:text-xl">
2025
</p>
+129 -169
View File
@@ -1,7 +1,7 @@
"use client";
import { AnimatePresence, motion } from "framer-motion";
import { ArrowRight } from "lucide-react";
import { ArrowUpRight } from "lucide-react";
import React, { useEffect, useState } from "react";
import { Button } from "@/components/ui/button";
@@ -11,156 +11,134 @@ interface Hero214Props {
className?: string;
}
const Hero214 = ({ className }: Hero214Props) => {
const images = [
{
src: "/block-media/shadcnblocks/block/lummi/bw12.jpeg",
alt: "تصویر پرتره",
name: "Joanna Doe",
},
{
src: "/block-media/shadcnblocks/block/lummi/bw13.jpeg",
alt: "تصویر پرتره",
name: "مریم چناری",
},
{
src: "/block-media/shadcnblocks/block/lummi/bw14.jpeg",
alt: "تصویر پرتره",
name: "Joanna Doe",
},
];
const IMAGES = [
{
src: "/block-media/shadcnblocks/block/lummi/landscape1.jpeg",
alt: "نمای معماری مدرن",
},
{
src: "/block-media/shadcnblocks/block/lummi/landscape2.jpeg",
alt: "فضای معماری مینیمال",
},
{
src: "/block-media/shadcnblocks/block/lummi/highRise.jpg",
alt: "ساختمان مرتفع معاصر",
},
] as const;
const Hero214 = ({ className }: Hero214Props) => {
const [currentIndex, setCurrentIndex] = useState(0);
const secondaryA = IMAGES[(currentIndex + 1) % IMAGES.length];
const secondaryB = IMAGES[(currentIndex + 2) % IMAGES.length];
useEffect(() => {
const timer = setTimeout(() => {
setCurrentIndex((prevIndex) => (prevIndex + 1) % images.length);
setCurrentIndex((prev) => (prev + 1) % IMAGES.length);
}, 2500);
return () => clearTimeout(timer);
}, [currentIndex, images.length]);
}, [currentIndex]);
return (
<section className={cn("py-32", className)}>
<div className="container">
<div className="mb-5 max-w-2xl lg:mb-0">
<h1 className="font-playfair text-start text-2xll tracking-tighter lg:text-2xll">
خانه ایده‌آل خود را در <br className="hidden md:block" /> شهر خود پیدا کنید
</h1>
</div>
<div className="relative lg:-translate-y-4">
<MaskedDiv maskType="type-5">
<AnimatePresence mode="popLayout">
<motion.img
key={currentIndex}
className="h-full w-full object-cover"
src={images[currentIndex].src}
alt={images[currentIndex].alt}
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.5 }}
/>
</AnimatePresence>
</MaskedDiv>
<section
className={cn("relative w-full overflow-hidden bg-background py-20 md:py-28", className)}
>
<div className="container min-w-0">
{/*
Composition matches the reference:
title → top-left cutout, thumbs → top-right cutout, CTA → bottom-left notch.
Physical left/right align with the LTR SVG mask.
*/}
<div className="relative w-full min-w-0">
<h1 className="relative z-20 mb-6 max-w-[18rem] text-left font-sans text-3xl leading-[1.15] font-semibold tracking-tight text-foreground sm:max-w-xs sm:text-4xl md:mb-0 md:absolute md:top-0 md:left-0 md:max-w-[22rem] lg:max-w-[26rem] lg:text-5xl xl:text-[3.25rem]">
بلاک‌های آماده با رابط کاربری و Tailwind
</h1>
<div className="absolute -top-26 right-0 flex gap-6">
<motion.div
initial={{ opacity: 0, y: 30, scale: 0.9 }}
animate={{ opacity: 1, y: 0, scale: 1 }}
exit={{ opacity: 0, y: 30, scale: 0.9 }}
transition={{ duration: 0.3, ease: "easeOut" }}
className="hidden size-44 -translate-y-4 overflow-hidden rounded-4xl xl:block xl:-translate-0"
>
<AnimatePresence mode="popLayout">
<div className="relative z-10 mt-2 w-full md:mt-10 lg:mt-14">
<MaskedDiv maskType="type-5">
<AnimatePresence mode="wait" initial={false}>
<motion.img
key={currentIndex}
className="absolute inset-0 size-full object-cover"
src={IMAGES[currentIndex].src}
alt={IMAGES[currentIndex].alt}
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.5 }}
src={
images[currentIndex + 1]?.src || images[currentIndex].src
}
alt={
images[currentIndex + 1]?.alt || images[currentIndex].alt
}
className="h-full w-full object-cover"
transition={{ duration: 1.2 }}
/>
</AnimatePresence>
</motion.div>
<motion.div
initial={{ opacity: 0, y: -30, scale: 0.9 }}
animate={{ opacity: 1, y: 0, scale: 1 }}
exit={{ opacity: 0, y: 30, scale: 0.9 }}
transition={{ duration: 0.3, ease: "easeOut" }}
className="hidden size-44 -translate-y-4 overflow-hidden rounded-4xl lg:block xl:-translate-0"
>
<AnimatePresence mode="popLayout">
<motion.img
key={currentIndex}
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.5 }}
src={
images[currentIndex + 2]?.src || images[currentIndex].src
}
alt={
images[currentIndex + 2]?.alt || images[currentIndex].alt
}
className="h-full w-full object-cover"
/>
</AnimatePresence>
</motion.div>
</div>
</MaskedDiv>
<div className="mt-5 flex w-full gap-6 lg:hidden">
<div className="relative h-44 w-full overflow-hidden rounded-4xl">
<AnimatePresence mode="popLayout">
<motion.img
key={currentIndex}
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.5 }}
src={
images[currentIndex + 1]?.src || images[currentIndex].src
}
alt={
images[currentIndex + 1]?.alt || images[currentIndex].alt
}
className="h-full w-full object-cover"
/>
</AnimatePresence>
</div>{" "}
<div className="relative h-44 w-full overflow-hidden rounded-4xl">
<AnimatePresence mode="popLayout">
<motion.img
key={currentIndex}
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.5 }}
src={
images[currentIndex + 2]?.src || images[currentIndex].src
}
alt={
images[currentIndex + 2]?.alt || images[currentIndex].alt
}
className="h-full w-full object-cover"
/>
</AnimatePresence>
{/* Top-right secondary thumbs (sit in the mask cutout) */}
<div className="absolute top-0 right-0 z-20 hidden gap-4 md:flex lg:gap-5 xl:gap-6">
<motion.div
initial={{ opacity: 0, y: 24, scale: 0.94 }}
animate={{ opacity: 1, y: 0, scale: 1 }}
transition={{ duration: 0.35, ease: "easeOut" }}
className="size-28 overflow-hidden rounded-[1.75rem] lg:size-36 xl:size-44 xl:rounded-[2rem]"
>
<AnimatePresence mode="wait" initial={false}>
<motion.img
key={secondaryA.src}
src={secondaryA.src}
alt={secondaryA.alt}
className="size-full object-cover"
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.2 }}
/>
</AnimatePresence>
</motion.div>
<motion.div
initial={{ opacity: 0, y: -24, scale: 0.94 }}
animate={{ opacity: 1, y: 0, scale: 1 }}
transition={{ duration: 0.35, ease: "easeOut" }}
className="size-28 overflow-hidden rounded-[1.75rem] lg:size-36 xl:size-44 xl:rounded-[2rem]"
>
<AnimatePresence mode="wait" initial={false}>
<motion.img
key={secondaryB.src}
src={secondaryB.src}
alt={secondaryB.alt}
className="size-full object-cover"
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
transition={{ duration: 1.2 }}
/>
</AnimatePresence>
</motion.div>
</div>
</div>
<Button
variant="secondary"
className="group -bottom-5 left-0 mt-3 flex items-center justify-center rounded-full bg-muted px-6 py-2 tracking-tight hover:gap-4 lg:absolute lg:bottom-0 lg:mt-0 xl:bottom-3"
>
تماس با ما{" "}
<ArrowRight className="size-4 -rotate-45 transition-all duration-300 ease-out group-hover:rotate-0 rtl:rotate-[135deg] rtl:group-hover:rotate-0" />
</Button>
{/* Mobile thumbs */}
<div className="mt-4 flex w-full gap-4 md:hidden">
<div className="relative h-36 w-full overflow-hidden rounded-[1.75rem]">
<img
src={secondaryA.src}
alt={secondaryA.alt}
className="size-full object-cover"
/>
</div>
<div className="relative h-36 w-full overflow-hidden rounded-[1.75rem]">
<img
src={secondaryB.src}
alt={secondaryB.alt}
className="size-full object-cover"
/>
</div>
</div>
{/* Bottom-left CTA in the mask notch */}
<Button
variant="secondary"
className="group relative z-20 mt-5 h-auto rounded-full bg-muted px-5 py-2.5 text-sm font-medium tracking-tight text-foreground hover:bg-muted/80 md:absolute md:bottom-1 md:left-0 md:mt-0 lg:bottom-2 xl:bottom-3"
>
مشاهده کامپوننت‌ها
<ArrowUpRight className="ms-1.5 size-4 transition-transform duration-300 group-hover:translate-x-0.5 group-hover:-translate-y-0.5" />
</Button>
</div>
</div>
</div>
</section>
@@ -175,10 +153,10 @@ interface SvgPath {
width: number;
}
type MaskType = "type-1" | "type-2" | "type-3" | "type-4" | "type-5";
type MaskType = "type-5";
interface MaskedDivProps {
children: React.ReactElement<HTMLImageElement | HTMLVideoElement>;
children: React.ReactNode;
maskType?: MaskType;
className?: string;
backgroundColor?: string;
@@ -186,67 +164,49 @@ interface MaskedDivProps {
}
const svgPaths: Record<MaskType, SvgPath> = {
"type-1": {
path: "M0.928955 40.9769C0.928955 18.9149 18.7917 1.01844 40.8536 0.976903L289.97 0.507853C308.413 0.473128 323.521 15.1483 324.022 33.5845L324.886 65.4007C325.955 104.745 358.022 136.159 397.38 136.417L432.98 136.65C447.818 136.748 459.797 148.799 459.803 163.637L459.982 550.982C459.992 573.08 442.08 591 419.982 591H40.9289C18.8376 591 0.928955 573.091 0.928955 551V40.9769Z",
height: 591,
width: 460,
},
"type-2": {
path: "M0.811768 77.2118C0.811768 60.4225 14.4222 46.8121 31.2115 46.8121H180.95C192.496 46.8121 201.855 37.4527 201.855 25.9073V25.9073C201.855 11.9565 213.164 0.647217 227.115 0.647217H529.273C548.014 0.647217 563.206 15.8395 563.206 34.5802V34.5802C563.206 50.0897 575.779 62.6626 591.289 62.6626H820.388C837.177 62.6626 850.787 76.273 850.787 93.0623V350.953C850.787 367.742 837.177 381.353 820.388 381.353H366.165C349.852 381.353 336.627 368.128 336.627 351.814V351.814C336.627 335.501 323.402 322.276 307.089 322.276H31.2114C14.4222 322.276 0.811768 308.666 0.811768 291.876V77.2118Z",
height: 381,
width: 850,
},
"type-3": {
path: "M0.680664 112.659C0.680664 50.805 50.823 0.662672 112.677 0.662672H413.07C456.315 0.662672 497.495 19.1588 526.221 51.4846V51.4846C554.948 83.8104 596.128 102.307 639.373 102.307H711.793C752.427 102.307 790.787 83.5522 815.744 51.4846V51.4846C840.7 19.417 879.06 0.662644 919.695 0.662597L1225.01 0.66224C1286.86 0.662168 1337.01 50.8046 1337.01 112.658V652.815C1337.01 714.668 1286.86 764.811 1225.01 764.811L670 764.811H335.34H278.376C217.423 764.811 168.01 715.399 168.01 654.446V626.747C168.01 580.208 130.283 542.48 83.7437 542.48V542.48C37.8692 542.48 0.680664 505.292 0.680664 459.417V382.737V112.659Z",
height: 889,
width: 1340,
},
"type-4": {
path: "M0.811768 34.5451C0.811768 15.7441 16.053 0.502808 34.8541 0.502808H816.745C835.546 0.502808 850.787 15.7441 850.787 34.5452V242.977C850.787 261.778 835.546 277.019 816.745 277.019H638.293H550.537C527.035 277.019 504.789 266.407 490.001 248.141L486.211 243.46C453.263 202.765 390.688 204.378 359.881 246.717V246.717C346.027 265.756 323.901 277.019 300.355 277.019H213.306H34.8541C16.0531 277.019 0.811768 261.778 0.811768 242.977V34.5451Z",
height: 278,
width: 851,
},
// Notched organic frame: title pocket (top-left), thumbs pocket (top-right), CTA notch (bottom-left)
"type-5": {
path: "M0.589399 112.279C0.589402 82.1213 25.037 57.6738 55.1946 57.6738H335.688C350.06 57.6738 361.712 46.0226 361.712 31.6502C361.712 14.2835 375.79 0.205078 393.157 0.205078H949.833C983.496 0.205078 1010.78 27.4941 1010.78 61.1568C1010.78 89.0156 1033.37 111.6 1061.23 111.6H1472.74C1502.9 111.6 1527.35 136.047 1527.35 166.205V629.438C1527.35 659.596 1502.9 684.044 1472.74 684.044H639.176C619.635 684.044 603.794 668.203 603.794 648.662C603.794 629.122 587.954 613.281 568.413 613.281H55.1945C25.0369 613.281 0.589358 588.833 0.58936 558.676L0.589399 112.279Z",
height: 700,
height: 684,
width: 1528,
},
};
function buildMaskDataUrl(mask: SvgPath): string {
return `data:image/svg+xml,%3Csvg width='${mask.width}' height='${mask.height}' viewBox='0 0 ${mask.width} ${mask.height}' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath fill-rule='evenodd' clip-rule='evenodd' d='${mask.path}' fill='%23D9D9D9'/%3E%3C/svg%3E`;
}
const MaskedDiv: React.FC<MaskedDivProps> = ({
children,
maskType = "type-1",
maskType = "type-5",
className = "",
backgroundColor = "transparent",
size = 1,
}) => {
const selectedMask = svgPaths[maskType];
const svgString = `${selectedMask.width}${selectedMask.height}${selectedMask.width} ${selectedMask.height}${selectedMask.path}`;
const maskUrl = buildMaskDataUrl(selectedMask);
const containerStyle: React.CSSProperties = {
aspectRatio: `${selectedMask.width}/${selectedMask.height}`,
aspectRatio: `${selectedMask.width} / ${selectedMask.height}`,
backgroundColor,
maskImage: `url("${svgString}")`,
WebkitMaskImage: `url("${svgString}")`,
maskImage: `url("${maskUrl}")`,
WebkitMaskImage: `url("${maskUrl}")`,
maskRepeat: "no-repeat",
WebkitMaskRepeat: "no-repeat",
maskSize: "contain",
WebkitMaskSize: "contain",
maskSize: "100% 100%",
WebkitMaskSize: "100% 100%",
maskPosition: "center",
WebkitMaskPosition: "center",
width: `${size * 100}%`,
maxWidth: "100%",
margin: "0 auto",
};
return (
<section
className={`pointer-events-none relative ${className}`}
<div
className={cn("relative w-full min-w-0 overflow-hidden", className)}
style={containerStyle}
>
{React.cloneElement(children, {
className: `w-full h-full object-cover transition-all duration-300 ${children.props.className || ""
}`,
})}
</section>
{children}
</div>
);
};
+1 -1
View File
@@ -27,7 +27,7 @@ const Hero215 = ({ className }: Hero215Props) => {
<ArrowRight className="size-4 -rotate-45 transition-all ease-out group-hover:rotate-0 rtl:rotate-180" />
</Button>
</div>
<div className="absolute -top-20 right-0 w-[27rem] max-w-xl">
<div className="absolute -top-20 left-0 w-[27rem] max-w-xl">
<img
src="/block-media/shadcnblocks/block/lummi/highRise.jpg"
className="animate-fade-in rounded-2xl object-cover"
+18 -18
View File
@@ -14,28 +14,28 @@ const Hero220 = ({ className }: Hero220Props) => {
return (
<section
className={cn(
"relative flex min-h-screen flex-col items-center justify-center overflow-hidden py-32",
"relative flex h-svh max-h-[1400px] min-h-[600px] w-full flex-col items-center justify-center overflow-hidden",
className,
)}
>
<div className="container">
<div className="absolute top-0 left-0 h-screen w-full overflow-hidden bg-[url('/block-media/shadcnblocks/block/lummi/landscape6.jpeg')] bg-cover bg-top bg-no-repeat opacity-20" />
<div className="flex flex-col items-center justify-center gap-4">
<motion.div
initial={{ opacity: 0, scale: 1.1 }}
animate={{ opacity: 1, scale: 1 }}
transition={{ duration: 0.3 }}
className="relative flex h-[250px] w-full items-center"
<div className="absolute inset-0 bg-[url('/block-media/shadcnblocks/block/lummi/landscape6.jpeg')] bg-cover bg-top bg-no-repeat opacity-20" />
<div className="relative z-10 container flex w-full flex-col items-center justify-center">
<motion.div
initial={{ opacity: 0, scale: 1.1 }}
animate={{ opacity: 1, scale: 1 }}
transition={{ duration: 0.3, ease: "easeOut" }}
className="relative flex h-[220px] w-full max-w-5xl items-center sm:h-[250px]"
>
<VideoText
src="/block-media/shadcnblocks/block/landscape.mp4"
className="font-bold tracking-tighter"
fontFamily="IRANSansX, Tahoma, sans-serif"
fontWeight={700}
fontSize={18}
>
<VideoText
src="/block-media/shadcnblocks/block/landscape.mp4"
className="font-playfair text-[15rem] font-bold tracking-tighter"
fontFamily="Playfair Display"
>
کامپوننت‌ها
</VideoText>
</motion.div>
</div>
کامپوننت‌ها
</VideoText>
</motion.div>
</div>
</section>
);
+34 -36
View File
@@ -78,10 +78,12 @@ const Hero226 = ({ className }: Hero226Props) => {
>
<Carousel
setApi={setApi}
className="w-full"
className="w-full min-w-0 overflow-hidden"
opts={{
loop: true,
align: "start",
slidesToScroll: 1,
direction: "rtl",
}}
plugins={[
Autoplay({
@@ -91,51 +93,47 @@ const Hero226 = ({ className }: Hero226Props) => {
}),
]}
>
<CarouselContent className="flex w-full gap-4">
{/* Override -ml-4 / pl-4 — they break RTL single-slide sizing */}
<CarouselContent className="-ml-0!">
{Images.map((img, index) => (
<CarouselItem key={index} className="w-full basis-[91%]">
<div className="p-1">
<div
key={index}
className="relative flex h-166 flex-col items-end justify-between bg-muted p-8"
>
<div className="pointer-events-none absolute top-0 left-0 h-full w-full">
<img
src={img.image}
alt="تصویر نمونه"
className="h-full w-full object-cover"
/>
</div>
<div className="z-10 mt-42 text-white">
<h1 className="max-w-lg text-end text-2xll font-medium tracking-tight">
{img.title}
</h1>
<p className="my-6 max-w-lg text-end text-lg">
{img.description}
</p>
</div>
<div className="bg-muted00 z-10 flex w-full justify-between">
<a href={img.link}>
<Button
variant="outline"
className="text-md group flex w-fit items-center justify-center gap-2 rounded-full px-4 py-1 tracking-tight"
>
شروع رایگان
<ArrowRight className="size-4 -rotate-45 transition-all ease-out group-hover:ms-3 group-hover:rotate-0 rtl:rotate-[135deg] rtl:group-hover:rotate-0" />
</Button>
</a>
</div>
<CarouselItem key={index} className="basis-full pl-0!">
<div className="relative flex h-166 w-full min-w-0 flex-col items-end justify-between overflow-hidden bg-muted p-8">
<div className="pointer-events-none absolute inset-0">
<img
src={img.image}
alt="تصویر نمونه"
className="size-full object-cover"
/>
</div>
<div className="z-10 mt-42 text-white">
<h1 className="max-w-lg text-end text-2xll font-medium tracking-tight">
{img.title}
</h1>
<p className="my-6 max-w-lg text-end text-lg">
{img.description}
</p>
</div>
<div className="z-10 flex w-full justify-between">
<a href={img.link}>
<Button
variant="outline"
className="text-md group flex w-fit items-center justify-center gap-2 rounded-full px-4 py-1 tracking-tight"
>
شروع رایگان
<ArrowRight className="size-4 -rotate-45 transition-all ease-out group-hover:ms-3 group-hover:rotate-0 rtl:rotate-[135deg] rtl:group-hover:rotate-0" />
</Button>
</a>
</div>
</div>
</CarouselItem>
))}
</CarouselContent>
{/* Navigation Dots */}
<div className="mt-4 flex justify-center gap-2">
{Array.from({ length: 5 }).map((_, index) => (
{Images.map((_, index) => (
<button
key={index}
type="button"
onClick={() => api?.scrollTo(index)}
className={`h-2.5 w-2.5 rounded-full transition-all ${
current === index
+94 -80
View File
@@ -2,8 +2,7 @@
import Autoplay from "embla-carousel-autoplay";
import { AnimatePresence, motion } from "framer-motion";
import React, { useMemo } from "react";
import { useCallback } from "react";
import React, { useCallback, useMemo } from "react";
import {
Carousel,
@@ -18,6 +17,44 @@ interface Hero228Props {
className?: string;
}
const TESTIMONIALS = [
{
id: 1,
image: "/block-media/shadcnblocks/block/lummi/person1.jpeg",
name: "علی رضایی",
},
{
id: 2,
image: "/block-media/shadcnblocks/block/lummi/person2.jpeg",
name: "سارا محمدی",
},
{
id: 3,
image: "/block-media/shadcnblocks/block/lummi/person3.jpeg",
name: "رضا کریمی",
},
{
id: 4,
image: "/block-media/shadcnblocks/block/lummi/person4.jpeg",
name: "نرگس حسینی",
},
{
id: 5,
image: "/block-media/shadcnblocks/block/lummi/person5.jpeg",
name: "امیر نوری",
},
{
id: 6,
image: "/block-media/shadcnblocks/block/lummi/bw3.jpeg",
name: "الهام کاظمی",
},
{
id: 7,
image: "/block-media/shadcnblocks/block/lummi/bw11.jpeg",
name: "کیان موسوی",
},
] as const;
const Hero228 = ({ className }: Hero228Props) => {
const [api, setApi] = React.useState<CarouselApi>();
const [current, setCurrent] = React.useState(0);
@@ -31,59 +68,33 @@ const Hero228 = ({ className }: Hero228Props) => {
}, [api]);
const isMobile = useIsMobile();
const slideCount = isMobile
? TESTIMONIALS.length
: TESTIMONIALS.length + 2;
const testimonials = [
{
id: 1,
image:
"/block-media/shadcnblocks/block/lummi/person1.jpeg",
name: "جان دو",
},
{
id: 2,
image:
"/block-media/shadcnblocks/block/lummi/person2.jpeg",
name: "جین اسمیت",
},
{
id: 3,
image:
"/block-media/shadcnblocks/block/lummi/person3.jpeg",
name: "جان جانسون",
},
{
id: 4,
image:
"/block-media/shadcnblocks/block/lummi/person4.jpeg",
name: "سارا ویلیام",
},
{
id: 5,
image:
"/block-media/shadcnblocks/block/lummi/person5.jpeg",
name: "مایکل براون",
},
{
id: 6,
image:
"/block-media/shadcnblocks/block/lummi/bw3.jpeg",
name: "امیلی دیویس",
},
{
id: 7,
image:
"/block-media/shadcnblocks/block/lummi/bw11.jpeg",
name: "جیسون وایت",
},
];
const activeName =
TESTIMONIALS[current % TESTIMONIALS.length]?.name ?? TESTIMONIALS[0].name;
const getImageSrc = useCallback((index: number) => {
if (index === TESTIMONIALS.length) return TESTIMONIALS[0].image;
if (index === TESTIMONIALS.length + 1) return TESTIMONIALS[1].image;
if (index === TESTIMONIALS.length + 2) return TESTIMONIALS[2].image;
return TESTIMONIALS[index]?.image ?? TESTIMONIALS[0].image;
}, []);
// RTL track: current is on the physical right, then center, then left
const getRotation = useCallback(
(index: number) => {
if (index === current)
return "md:-rotate-45 md:translate-x-40 md:scale-75 md:relative";
if (index === current + 1) return "md:rotate-0 md:z-10 md:relative";
if (index === current + 2)
return "md:rotate-45 md:-translate-x-40 md:scale-75 md:relative";
if (index === current) {
return "md:relative md:z-0 md:translate-x-40 md:scale-75 md:rotate-45";
}
if (index === current + 1) {
return "md:relative md:z-10 md:rotate-0";
}
if (index === current + 2) {
return "md:relative md:z-0 md:-translate-x-40 md:scale-75 md:-rotate-45";
}
return "";
},
[current],
);
@@ -94,7 +105,7 @@ const Hero228 = ({ className }: Hero228Props) => {
<motion.div
key={item}
initial={{
opacity: item % 5 === 0 ? 0.2 : 0.2,
opacity: 0.2,
filter: "blur(1px)",
}}
animate={{
@@ -107,7 +118,7 @@ const Hero228 = ({ className }: Hero228Props) => {
ease: "easeOut",
}}
className={cn(
"w-[1px] bg-black",
"w-px bg-foreground",
item % 5 === 0 ? "h-[15px]" : "h-[10px]",
)}
/>
@@ -116,18 +127,24 @@ const Hero228 = ({ className }: Hero228Props) => {
);
return (
<section className={cn("bg-background py-32", className)}>
<div className="container flex flex-col items-center justify-center gap-4 text-center">
<h1 className="max-w-3xl text-2xll font-medium tracking-tighter text-foreground md:px-9 md:text-2xll">
<section className={cn("relative w-full overflow-hidden bg-background py-32", className)}>
<div className="container flex min-w-0 flex-col items-center justify-center gap-4 text-center">
<h1 className="max-w-3xl text-balance text-2xll font-medium tracking-tighter text-foreground md:px-9 md:text-2xll">
<span className="font-playfair italic">همه</span> ابزارهای لازم برای{" "}
<span className="font-playfair italic">خلاق و</span> توسعه سریع
</h1>
<p className="mt-5 max-w-xl text-muted-foreground/80">
</h1>
<p className="mt-5 max-w-xl text-balance text-muted-foreground/80">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
</p>
<Carousel
className="max-w-5xl"
className="relative w-full min-w-0 max-w-5xl overflow-hidden"
opts={{
loop: true,
align: "start",
slidesToScroll: 1,
direction: "rtl",
}}
plugins={[
Autoplay({
delay: 1000,
@@ -136,43 +153,40 @@ const Hero228 = ({ className }: Hero228Props) => {
]}
setApi={setApi}
>
<CarouselContent>
{Array.from({
length: isMobile ? testimonials.length : testimonials.length + 2,
}).map((_, index) => (
<CarouselItem key={index} className="my-10 md:basis-1/3">
{/* Override -ml-4 / pl-4 — they break RTL track sizing */}
<CarouselContent className="-ml-0!">
{Array.from({ length: slideCount }).map((_, index) => (
<CarouselItem
key={index}
className="my-10 basis-full pl-0! md:basis-1/3"
>
<div
className={`h-105 w-full transition-transform duration-500 ease-in-out ${getRotation(index)}`}
className={cn(
"h-105 w-full min-w-0 overflow-hidden transition-transform duration-500 ease-in-out",
getRotation(index),
)}
>
<img
src={
index == testimonials.length
? testimonials[0].image
: index == testimonials.length + 1
? testimonials[1].image
: index == testimonials.length + 2
? testimonials[2].image
: testimonials[index].image
}
className="h-full w-full object-cover"
alt="تصویر نمونه"
src={getImageSrc(index)}
className="size-full object-cover"
alt={activeName}
/>
</div>
</CarouselItem>
))}
</CarouselContent>
<div className="absolute right-0 bottom-0 flex w-full translate-y-full flex-col items-center justify-center gap-2">
<div className="absolute inset-x-0 bottom-0 flex w-full translate-y-full flex-col items-center justify-center gap-2">
<div className="flex gap-2">{scrollbarBars}</div>
<AnimatePresence mode="popLayout" initial={false}>
<motion.p
key={current}
key={activeName}
className="w-full text-lg font-medium"
initial={{ opacity: 0, y: 20, scale: 0.9, filter: "blur(5px)" }}
animate={{ opacity: 1, y: 0, scale: 1, filter: "blur(0px)" }}
exit={{ opacity: 0, y: -20, scale: 0.9, filter: "blur(5px)" }}
transition={{ duration: 0.5 }}
>
{testimonials[current]?.name}
{activeName}
</motion.p>
</AnimatePresence>
<div className="flex gap-2">{scrollbarBars}</div>
+11 -11
View File
@@ -15,11 +15,11 @@ const Hero229 = ({ className }: Hero229Props) => {
return (
<section
className={cn(
"relative h-[100dvh] w-[100dvw] overflow-hidden border bg-background py-32",
"relative h-[100dvh] max-h-[1400px] min-h-[600px] w-full overflow-hidden border bg-background py-32",
className,
)}
>
<div className="relative z-20 container flex flex-col items-center justify-center gap-4 text-center">
<div className="relative z-20 container flex min-w-0 flex-col items-center justify-center gap-4 text-center">
<Button
variant="secondary"
className="text-md group mt-42 flex w-fit items-center justify-center gap-3 rounded-full bg-muted/60 px-5 py-1 tracking-tight"
@@ -27,13 +27,13 @@ const Hero229 = ({ className }: Hero229Props) => {
<span className="size-2 rounded-full bg-foreground" />
<span>مشاهده پلن‌ها</span>
</Button>
<h1 className="max-w-3xl text-2xll font-medium tracking-tighter text-foreground md:text-2xll">
<h1 className="max-w-3xl text-balance text-2xll font-medium tracking-tighter text-foreground md:text-2xll">
مجموعه بلاک‌های آماده <br /> برای رابط کاربری و استایل‌دهی مدرن
</h1>
<p className="mt-5 max-w-xl text-muted-foreground/80">
</h1>
<p className="mt-5 max-w-xl text-balance text-muted-foreground/80">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<div className="flex gap-4">
</p>
<div className="flex min-w-0 flex-wrap items-center justify-center gap-4">
<Button
variant="secondary"
className="text-md group flex w-fit items-center justify-center gap-2 rounded-full px-4 py-1 tracking-tight"
@@ -55,25 +55,25 @@ const Hero229 = ({ className }: Hero229Props) => {
initial={{ opacity: 0, y: -100 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 1, ease: [0, 0, 0, 1.12] }}
className="absolute top-0 left-1/2 -translate-x-1/2"
className="pointer-events-none absolute top-0 left-1/2 max-w-full -translate-x-1/2"
/>
<Illustration1
initial={{ opacity: 0, y: -100 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 1, ease: [0, 0, 0, 1.12] }}
className="absolute bottom-0 left-1/2 -translate-x-1/2 scale-y-[-1]"
className="pointer-events-none absolute bottom-0 left-1/2 max-w-full -translate-x-1/2 scale-y-[-1]"
/>
<Illustration2
initial={{ opacity: 0, x: -100 }}
animate={{ opacity: 1, x: 0 }}
transition={{ duration: 1, ease: [0, 0, 0, 1.12] }}
className="absolute top-1/2 left-0 z-99 hidden -translate-y-1/2 md:block"
className="pointer-events-none absolute top-1/2 left-0 z-10 hidden max-w-[30%] -translate-y-1/2 md:block"
/>
<Illustration2
initial={{ opacity: 0, x: -100 }}
animate={{ opacity: 1, x: 0 }}
transition={{ duration: 1, ease: [0, 0, 0, 1.12] }}
className="absolute top-1/2 right-0 z-99 hidden -translate-y-1/2 scale-x-[-1] md:block"
className="pointer-events-none absolute top-1/2 right-0 z-10 hidden max-w-[30%] -translate-y-1/2 scale-x-[-1] md:block"
/>
</section>
);
+18 -3
View File
@@ -1,7 +1,6 @@
"use client";
import AutoScroll from "embla-carousel-auto-scroll";
import Autoplay from "embla-carousel-autoplay";
import { ArrowRight } from "lucide-react";
import React from "react";
@@ -186,7 +185,15 @@ const Hero230 = ({ className }: Hero230Props) => {
<div className="relative mx-auto flex items-center justify-center">
<Carousel
plugins={[AutoScroll({ playOnInit: true })]}
plugins={[
AutoScroll({
speed: 1,
startDelay: 0,
playOnInit: true,
stopOnInteraction: false,
stopOnMouseEnter: false,
}),
]}
opts={{ loop: true, align: "start" }}
>
<CarouselContent className="ms-0">
@@ -211,7 +218,15 @@ const Hero230 = ({ className }: Hero230Props) => {
</div>
<div className="relative mx-auto -mt-12 flex items-center justify-center">
<Carousel
plugins={[Autoplay({ delay: 1500 })]}
plugins={[
AutoScroll({
speed: 1,
startDelay: 0,
playOnInit: true,
stopOnInteraction: false,
stopOnMouseEnter: false,
}),
]}
opts={{ loop: true, align: "start" }}
>
<CarouselContent>
+10 -10
View File
@@ -16,12 +16,12 @@ const Hero232 = ({ className }: Hero232Props) => {
return (
<section
className={cn(
"relative h-screen w-screen bg-background py-32",
"relative h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden bg-background py-32",
className,
)}
>
<div className="relative z-20 container flex items-center justify-center">
<div className="flex w-fit flex-col items-center justify-center gap-4 bg-background pb-3 text-center">
<div className="relative z-20 container flex min-w-0 items-center justify-center">
<div className="flex w-full min-w-0 max-w-4xl flex-col items-center justify-center gap-4 bg-background pb-3 text-center">
<Button
variant="secondary"
className="text-md group mt-24 flex w-fit items-center justify-center gap-3 rounded-full bg-muted/60 px-5 py-1 tracking-tight"
@@ -29,8 +29,8 @@ const Hero232 = ({ className }: Hero232Props) => {
<span className="size-2 rounded-full bg-foreground" />
<span>پلن مناسب برای هر تیم</span>
</Button>
<div className="relative flex max-w-4xl items-center justify-center text-center text-2xll font-medium tracking-tight md:text-2xll">
<h1 className="relative z-10 tracking-tighter">
<div className="relative flex w-full min-w-0 max-w-4xl items-center justify-center text-center text-2xll font-medium tracking-tight md:text-2xll">
<h1 className="relative z-10 text-balance break-words tracking-tighter">
<span className="ms-3 text-muted-foreground/50">
تنها اپی که برای ماندن
</span>
@@ -40,10 +40,10 @@ const Hero232 = ({ className }: Hero232Props) => {
</h1>
<div className="absolute z-9 h-[105%] w-[85%] bg-background" />
</div>
<p className="mt-5 max-w-xl bg-background text-muted-foreground/80">
<p className="mt-5 max-w-xl text-balance bg-background text-muted-foreground/80">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<div className="flex gap-4">
</p>
<div className="flex min-w-0 flex-wrap items-center justify-center gap-4">
<Button
variant="secondary"
className="text-md group flex w-fit items-center justify-center gap-2 rounded-full px-4 py-1 tracking-tight"
@@ -66,14 +66,14 @@ const Hero232 = ({ className }: Hero232Props) => {
initial={{ opacity: 0, y: -100 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 1, ease: [0, 0, 0, 1.12] }}
className="absolute top-6 left-0 hidden text-orange-500 lg:block"
className="pointer-events-none absolute top-6 left-0 hidden max-w-[40%] text-orange-500 lg:block"
/>
<Illustration1
initial={{ opacity: 0, y: -100 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 1, ease: [0, 0, 0, 1.12] }}
className="absolute top-32 right-0 hidden scale-x-[-1] scale-y-[-1] text-orange-500 lg:block"
className="pointer-events-none absolute top-32 right-0 hidden max-w-[40%] scale-x-[-1] scale-y-[-1] text-orange-500 lg:block"
/>
</section>
);
+9 -9
View File
@@ -19,11 +19,11 @@ const Hero233 = ({ className }: Hero233Props) => {
return (
<section
className={cn(
"relative h-screen w-screen overflow-hidden bg-background py-32",
"relative h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden bg-background py-32",
className,
)}
>
<div className="relative z-20 container flex flex-col items-center justify-center gap-4 py-10 text-center md:mt-22">
<div className="relative z-20 container flex min-w-0 flex-col items-center justify-center gap-4 py-10 text-center md:mt-22">
<div className="absolute -z-1 size-full max-w-3xl bg-background blur-xl" />
<Button
variant="secondary"
@@ -32,8 +32,8 @@ const Hero233 = ({ className }: Hero233Props) => {
<span className="size-2 rounded-full bg-foreground" />
<span>پلن مناسب برای هر تیم</span>
</Button>
<div className="relative flex max-w-4xl items-center justify-center text-center text-2xll font-medium tracking-tight md:text-2xll">
<h1 className="relative z-10">
<div className="relative flex w-full min-w-0 max-w-4xl items-center justify-center text-center text-2xll font-medium tracking-tight md:text-2xll">
<h1 className="relative z-10 text-balance break-words">
<span className="ms-3 text-muted-foreground/50">
تنها اپی که برای ماندن
</span>
@@ -43,10 +43,10 @@ const Hero233 = ({ className }: Hero233Props) => {
</h1>
</div>
<p className="mt-5 max-w-xl bg-background text-muted-foreground/80">
<p className="mt-5 max-w-xl text-balance bg-background text-muted-foreground/80">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<div className="my-5 flex gap-4">
</p>
<div className="my-5 flex min-w-0 flex-wrap items-center justify-center gap-4">
<Button
variant="secondary"
className="text-md group flex w-fit items-center justify-center gap-2 rounded-full px-4 py-1 tracking-tight"
@@ -64,7 +64,7 @@ const Hero233 = ({ className }: Hero233Props) => {
</div>
</div>
<div className="absolute top-0 flex size-full justify-center">
<div className="pointer-events-none absolute inset-0 z-0 flex justify-center overflow-hidden">
{Array.from({ length: isMobile ? 7 : 18 }).map((_, i) => (
<motion.div
key={i}
@@ -75,7 +75,7 @@ const Hero233 = ({ className }: Hero233Props) => {
delay: i * 0.05,
ease: "easeOut",
}}
className="w-24 border-l bg-gradient-to-b to-transparent transition-all ease-in-out hover:scale-110 hover:from-black/2"
className="w-24 shrink-0 border-s bg-gradient-to-b to-transparent transition-all ease-in-out hover:scale-110 hover:from-black/2"
/>
))}
</div>
+12 -14
View File
@@ -66,27 +66,27 @@ const Hero236 = ({ className }: Hero236Props) => {
return (
<section
className={cn("relative w-screen overflow-hidden py-32", className)}
className={cn("relative w-full overflow-hidden py-32", className)}
>
<div className="container flex flex-col lg:flex-row">
<div className="mt-10 space-y-12 lg:w-1/2">
<div className="container mx-auto flex min-w-0 flex-col items-center lg:flex-row lg:items-center lg:justify-between">
<div className="mt-10 w-full min-w-0 space-y-12 lg:w-1/2">
<p className="w-fit rounded-full bg-muted px-4 py-1 text-sm uppercase">
چرا ما؟
</p>
<h1 className="font-calSans mt-3 max-w-lg text-2xll font-medium lg:text-2xll">
<h1 className="font-calSans mt-3 max-w-lg text-balance text-2xll font-medium lg:text-2xll">
<span className="opacity-30">همه کامپوننت‌هایی</span> که نیاز دارید
</h1>
<p className="max-w-lg text-lg text-muted-foreground">
<p className="max-w-lg text-balance text-lg text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
</p>
<ul className="mt-18 flex flex-wrap gap-9">
{stats.map((stat, index) => (
<li key={stat.title} className="flex items-center gap-4">
<div className="flex size-12 items-center justify-center rounded-2xl border md:size-18">
<li key={stat.title} className="flex min-w-0 items-center gap-4">
<div className="flex size-12 shrink-0 items-center justify-center rounded-2xl border md:size-18">
{stat.icon}
</div>
<div>
<div className="min-w-0">
<h2 className="font-calSans text-xl font-medium md:text-3xl">
{stat.title}
</h2>
@@ -99,10 +99,8 @@ const Hero236 = ({ className }: Hero236Props) => {
))}
</ul>
</div>
<div className="flex h-[500px] w-full items-center justify-center overflow-hidden lg:w-1/2">
<div className="absolute flex h-full w-full items-center justify-center">
<IconCloud images={images} />
</div>
<div className="relative flex h-[500px] w-full min-w-0 items-center justify-center overflow-hidden lg:w-1/2">
<IconCloud images={images} />
</div>
</div>
</section>
@@ -431,7 +429,7 @@ export function IconCloud({ icons, images }: IconCloudProps) {
onMouseMove={handleMouseMove}
onMouseUp={handleMouseUp}
onMouseLeave={handleMouseUp}
className="rounded-lg"
className="max-h-full max-w-full rounded-lg"
aria-label="ابر آیکون سه‌بعدی تعاملی"
role="img"
/>
+41 -33
View File
@@ -62,42 +62,16 @@ const Hero237 = ({ className }: Hero237Props) => {
return (
<section
className={cn(
"relative w-screen overflow-hidden border border-b py-32",
"relative w-full overflow-hidden border border-b py-32",
className,
)}
>
<div className="relative container flex flex-col lg:flex-row">
<div className="mt-10 space-y-12 lg:w-1/2">
<p className="w-fit rounded-full bg-muted px-4 py-1 text-sm uppercase">
چرا ما؟
</p>
<h1 className="font-calSans mt-3 max-w-lg text-2xll font-medium lg:text-2xll">
<span className="opacity-30">همه کامپوننت‌هایی</span> که نیاز دارید
</h1>
<p className="max-w-lg text-lg text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<ul className="mt-18 flex flex-wrap gap-9">
{stats.map((stat, index) => (
<li key={stat.title} className="flex items-center gap-4">
<div className="flex size-12 items-center justify-center rounded-2xl border md:size-18">
{stat.icon}
</div>
<div>
<h2 className="font-calSans text-xl font-medium md:text-3xl">
{stat.title}
</h2>
<p className="text-sm md:text-base">{stat.description}</p>
</div>
{index !== stats.length - 1 && (
<div className="ms-4 h-full w-px bg-gradient-to-t from-black via-border to-transparent" />
)}
</li>
))}
</ul>
</div>
<div className="relative h-112 lg:w-1/2">
{/* dir=ltr keeps visual: orbits left, text right; text column stays rtl */}
<div
dir="ltr"
className="relative container flex min-w-0 flex-col lg:flex-row lg:items-center"
>
<div className="relative order-2 h-112 w-full min-w-0 overflow-hidden lg:order-1 lg:w-1/2">
<div className="relative -left-35 flex h-[1100px] w-[1500px] flex-col items-center justify-center lg:absolute lg:left-0">
<OrbitingCircles iconSize={40} radius={310} speed={2}>
{circle1Images.map((src, index) => (
@@ -129,6 +103,40 @@ const Hero237 = ({ className }: Hero237Props) => {
</OrbitingCircles>
</div>
</div>
<div
dir="rtl"
className="order-1 mt-10 w-full min-w-0 space-y-12 text-start lg:order-2 lg:w-1/2"
>
<p className="w-fit rounded-full bg-muted px-4 py-1 text-sm uppercase">
چرا ما؟
</p>
<h1 className="font-calSans mt-3 max-w-lg text-balance text-2xll font-medium lg:text-2xll">
<span className="opacity-30">همه کامپوننت‌هایی</span> که نیاز دارید
</h1>
<p className="max-w-lg text-balance text-lg text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<ul className="mt-18 flex flex-wrap gap-9">
{stats.map((stat, index) => (
<li key={stat.title} className="flex min-w-0 items-center gap-4">
<div className="flex size-12 shrink-0 items-center justify-center rounded-2xl border md:size-18">
{stat.icon}
</div>
<div className="min-w-0">
<h2 className="font-calSans text-xl font-medium md:text-3xl">
{stat.title}
</h2>
<p className="text-sm md:text-base">{stat.description}</p>
</div>
{index !== stats.length - 1 && (
<div className="ms-4 h-full w-px bg-gradient-to-t from-black via-border to-transparent" />
)}
</li>
))}
</ul>
</div>
</div>
</section>
);
+49 -49
View File
@@ -33,43 +33,46 @@ const Hero238 = ({ className }: Hero238Props) => {
return (
<section
className={cn("h-full w-screen overflow-hidden lg:h-screen", className)}
className={cn(
"relative h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden",
className,
)}
>
<AuroraBackground>
<div className="relative container flex h-full flex-col py-32 lg:flex-row">
<div className="mt-auto space-y-12 lg:w-1/2">
<h1 className="mt-3 max-w-xl text-2xll font-medium font-semibold tracking-tighter lg:text-2xll">
<AuroraBackground className="h-full min-h-0 w-full">
<div className="relative container flex h-full min-w-0 flex-col py-32 lg:flex-row">
<div className="mt-auto min-w-0 space-y-12 lg:w-1/2">
<h1 className="mt-3 max-w-xl text-balance break-words text-2xll font-medium font-semibold tracking-tighter lg:text-2xll">
با یک بار خرید به تمام کامپوننت‌های حرفه‌ای دسترسی داشته باشید
</h1>
<div className="flex items-center gap-4">
</h1>
<div className="flex min-w-0 flex-wrap items-center gap-4">
<Button>شروع رایگان</Button>
<Button variant="ghost">
مشاهده امکانات <ArrowRight className="rtl:rotate-180" />
</Button>
</div>
<ul className="mt-20 flex flex-wrap gap-4">
<ul className="mt-20 flex min-w-0 flex-wrap gap-4">
{benefits.map((benifit, index) => {
const Icon = benifit.icon;
return (
<li key={benifit.title} className="flex items-center gap-2">
<div className="size-">
<li key={benifit.title} className="flex min-w-0 items-center gap-2">
<div className="size-4 shrink-0">
<Icon className="size-4" />
</div>
<span className="text-sm">{benifit.title}</span>
{index !== benefits.length - 1 && (
<div className="ms-2 size-1 rounded-full bg-foreground" />
<div className="ms-2 size-1 shrink-0 rounded-full bg-foreground" />
)}
</li>
);
})}
</ul>
</div>
<div className="relative flex h-[500px] w-full items-center justify-center overflow-hidden lg:w-1/2">
<div className="relative flex h-[500px] w-full min-w-0 items-center justify-center overflow-hidden lg:w-1/2">
<motion.div
initial={{ opacity: 0, y: "50%" }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 0.2, ease: "easeOut" }}
className="absolute right-0 bottom-0 w-[210px] rounded-2xl bg-primary p-4 text-sm text-secondary"
className="absolute right-0 bottom-0 max-w-full w-[210px] rounded-2xl bg-primary p-4 text-sm text-secondary"
>
<span className="ms-3 inline-block size-2 rounded-full bg-orange-500" />
<span className="font-semibold">ری یو آی</span>
@@ -102,46 +105,43 @@ export const AuroraBackground = ({
...props
}: AuroraBackgroundProps) => {
return (
<main>
<div
className={cn(
"transition-bg relative flex h-full min-h-0 w-full flex-col items-center justify-center overflow-hidden bg-zinc-50 text-slate-950 dark:bg-zinc-900",
className,
)}
{...props}
>
<div
className={cn(
"transition-bg relative flex h-[100vh] flex-col items-center justify-center bg-zinc-50 text-slate-950 dark:bg-zinc-900",
className,
)}
{...props}
className="absolute inset-0 overflow-hidden"
style={
{
"--aurora":
"repeating-linear-gradient(100deg,#000_10%,#666_15%,#ccc_20%,#fff_25%,#333_30%)",
"--dark-gradient":
"repeating-linear-gradient(100deg,#000_0%,#000_7%,transparent_10%,transparent_12%,#000_16%)",
"--white-gradient":
"repeating-linear-gradient(100deg,#fff_0%,#fff_7%,transparent_10%,transparent_12%,#fff_16%)",
"--gray-200": "#ccc",
"--gray-400": "#666",
"--gray-800": "#333",
"--black": "#000",
"--white": "#fff",
"--transparent": "transparent",
} as React.CSSProperties
}
>
<div
className="absolute inset-0 overflow-hidden"
style={
{
"--aurora":
"repeating-linear-gradient(100deg,#000_10%,#666_15%,#ccc_20%,#fff_25%,#333_30%)",
"--dark-gradient":
"repeating-linear-gradient(100deg,#000_0%,#000_7%,transparent_10%,transparent_12%,#000_16%)",
"--white-gradient":
"repeating-linear-gradient(100deg,#fff_0%,#fff_7%,transparent_10%,transparent_12%,#fff_16%)",
className={cn(
`pointer-events-none absolute inset-0 [background-image:var(--white-gradient),var(--aurora)] [background-size:300%,_200%] [background-position:50%_50%,50%_50%] opacity-50 blur-[10px] invert filter will-change-transform [--aurora:repeating-linear-gradient(100deg,var(--black)_10%,var(--gray-400)_15%,var(--gray-200)_20%,var(--white)_25%,var(--gray-800)_30%)] [--dark-gradient:repeating-linear-gradient(100deg,var(--black)_0%,var(--black)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--black)_16%)] [--white-gradient:repeating-linear-gradient(100deg,var(--white)_0%,var(--white)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--white)_16%)] after:absolute after:inset-0 after:animate-aurora-background after:[background-image:var(--white-gradient),var(--aurora)] after:[background-size:200%,_100%] after:mix-blend-difference after:content-[""] dark:[background-image:var(--dark-gradient),var(--aurora)] dark:invert-0 after:dark:[background-image:var(--dark-gradient),var(--aurora)]`,
"--gray-200": "#ccc",
"--gray-400": "#666",
"--gray-800": "#333",
"--black": "#000",
"--white": "#fff",
"--transparent": "transparent",
} as React.CSSProperties
}
>
<div
// I'm sorry but this is what peak developer performance looks like // trigger warning
className={cn(
`pointer-events-none absolute -inset-[10px] [background-image:var(--white-gradient),var(--aurora)] [background-size:300%,_200%] [background-position:50%_50%,50%_50%] opacity-50 blur-[10px] invert filter will-change-transform [--aurora:repeating-linear-gradient(100deg,var(--black)_10%,var(--gray-400)_15%,var(--gray-200)_20%,var(--white)_25%,var(--gray-800)_30%)] [--dark-gradient:repeating-linear-gradient(100deg,var(--black)_0%,var(--black)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--black)_16%)] [--white-gradient:repeating-linear-gradient(100deg,var(--white)_0%,var(--white)_7%,var(--transparent)_10%,var(--transparent)_12%,var(--white)_16%)] after:absolute after:inset-0 after:animate-aurora-background after:[background-image:var(--white-gradient),var(--aurora)] after:[background-size:200%,_100%] after:[background-attachment:fixed] after:mix-blend-difference after:content-[""] dark:[background-image:var(--dark-gradient),var(--aurora)] dark:invert-0 after:dark:[background-image:var(--dark-gradient),var(--aurora)]`,
showRadialGradient &&
`[mask-image:radial-gradient(ellipse_at_100%_0%,black_10%,var(--transparent)_70%)]`,
)}
></div>
</div>
{children}
showRadialGradient &&
`[mask-image:radial-gradient(ellipse_at_100%_0%,black_10%,var(--transparent)_70%)]`,
)}
></div>
</div>
</main>
{children}
</div>
);
};
+12 -9
View File
@@ -50,26 +50,29 @@ const Hero239 = ({ className }: Hero239Props) => {
];
return (
<section className={cn("relative py-32", className)}>
<div className="container flex flex-col items-center justify-center gap-5 text-center">
<section className={cn("relative w-full overflow-hidden py-32", className)}>
<div className="container flex min-w-0 flex-col items-center justify-center gap-5 text-center">
<p className="w-fit rounded-full bg-muted px-4 py-1 text-sm uppercase">
ری یو آی
</p>
<h1 className="mt-3 max-w-xl text-2xll font-medium font-semibold tracking-tighter lg:max-w-3xl lg:text-2xll">
<h1 className="mt-3 max-w-xl text-balance break-words text-2xll font-medium font-semibold tracking-tighter lg:max-w-3xl lg:text-2xll">
با یک بار خرید به تمام کامپوننت‌های حرفه‌ای دسترسی داشته باشید
</h1>
<p className="max-w-xl text-muted-foreground">
</h1>
<p className="max-w-xl text-balance text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<div className="flex items-center gap-4">
</p>
<div className="flex min-w-0 flex-wrap items-center justify-center gap-4">
<Button>شروع رایگان</Button>
<Button variant="ghost">
مشاهده امکانات <ArrowRight className="rtl:rotate-180" />
</Button>
</div>
<div className="mt-15 flex h-full w-full items-center justify-center">
<ThreeDMarquee className="rounded-none" images={images} />
<div className="mt-15 flex h-full w-full min-w-0 items-center justify-center overflow-hidden">
<ThreeDMarquee
className="w-full min-w-0 max-w-full rounded-none"
images={images}
/>
</div>
</div>
</section>
+31 -16
View File
@@ -51,37 +51,52 @@ const Hero240 = ({ className }: Hero240Props) => {
return (
<section
dir="rtl"
lang="fa"
className={cn(
"relative h-full w-screen overflow-hidden py-32",
className,
// After `className` so injected `w-screen` / `100vw` cannot win in the merge
"relative w-full max-w-full min-w-0 overflow-x-clip overflow-hidden py-32",
)}
>
<div className="container flex flex-col items-center justify-center gap-5 text-center">
<div className="flex items-center gap-2">
<Zap className="size-5" />
<div className="container flex w-full min-w-0 max-w-full flex-col items-stretch justify-center gap-5 text-center">
<div className="flex min-w-0 items-center justify-center gap-2">
<Zap className="size-5 shrink-0" />
<p className="w-fit rounded-full py-1 font-medium tracking-tight">
کتابخانه کامپوننت
</p>
</p>
</div>
<h1 className="mt-3 max-w-xl text-2xll font-medium font-semibold tracking-tighter lg:max-w-3xl lg:text-2xll">
<h1 className="mx-auto mt-3 max-w-xl text-balance break-words text-2xl font-semibold tracking-tighter sm:text-3xl lg:max-w-3xl lg:text-2xll">
کامپوننت‌های آماده برای توسعه سریع‌تر محصولات
</h1>
<p className="max-w-xl text-muted-foreground">
</h1>
<p className="mx-auto max-w-xl text-balance text-pretty text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<div className="mt-10 flex w-full max-w-2xl items-center justify-center gap-4">
<div className="flex w-full max-w-md rounded-full border p-1">
</p>
<div className="mx-auto mt-10 flex w-full min-w-0 max-w-2xl items-center justify-center gap-4">
<div className="flex h-12 w-full min-w-0 max-w-md items-center rounded-full border p-1">
<Input
className="w-full rounded-full border-none shadow-none ring-0 focus-visible:ring-0 focus-visible:outline-none active:ring-0 active:outline-0"
className="min-w-0 flex-1 rounded-full border-none shadow-none ring-0 focus-visible:ring-0 focus-visible:outline-none active:ring-0 active:outline-0"
placeholder="ایمیل خود را وارد کنید"
/>
<Button className="rounded-full">عضویت رایگان</Button>
<Button className="h-full shrink-0 rounded-full px-4 sm:px-6">
عضویت رایگان
</Button>
</div>
</div>
<div className="mt-15 flex h-full w-full items-center justify-center">
<ThreeDMarquee className="rounded-none" images={images} />
<div className="absolute bottom-0 left-0 h-1/3 w-full bg-gradient-to-t from-background via-background to-transparent" />
{/*
ThreeDMarquee uses an internal 1720px stage. Keep this wrapper
width-bound + overflow-x-clip so it cannot widen #preview-frame.
*/}
<div
className="relative isolate mt-15 h-[360px] w-full min-w-0 max-w-full self-stretch overflow-x-clip overflow-hidden sm:h-[480px] md:h-[600px]"
style={{ contain: "inline-size" }}
>
<ThreeDMarquee
className="!mx-0 !h-full !w-full !max-w-full min-w-0 rounded-none"
images={images}
/>
<div className="pointer-events-none absolute inset-x-0 bottom-0 h-1/3 bg-gradient-to-t from-background via-background to-transparent" />
</div>
</div>
</section>
+12 -12
View File
@@ -13,18 +13,18 @@ const Hero241 = ({ className }: Hero241Props) => {
return (
<section
className={cn(
"relative h-full min-h-screen w-screen overflow-hidden py-32",
"relative min-h-svh max-h-[1400px] w-full overflow-hidden py-32",
className,
)}
>
<div className="static z-10 container flex flex-col items-center justify-center gap-10 text-center">
<h1 className="font-playfair mt-10 text-2xll font-medium tracking-tight lg:text-2xll">
<div className="static z-10 container flex min-w-0 flex-col items-center justify-center gap-10 text-center">
<h1 className="font-playfair mt-10 max-w-full text-balance break-words text-2xll font-medium tracking-tight lg:text-2xll">
سریع‌ترین مسیر برای <br /> رابط‌های کاربری آماده استفاده
</h1>
<p className="max-w-xl leading-5 font-medium">
</h1>
<p className="max-w-xl text-balance leading-5 font-medium">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<div className="flex items-center gap-4">
</p>
<div className="flex min-w-0 flex-wrap items-center justify-center gap-4">
<Button className="text-md rounded-xl font-serif">
مشاهده مستندات <ArrowRight className="-rotate-45 rtl:rotate-180" />{" "}
</Button>
@@ -32,19 +32,19 @@ const Hero241 = ({ className }: Hero241Props) => {
شروع رایگان <ArrowRight className="-rotate-45 rtl:rotate-180" />{" "}
</Button>
</div>
<div className="absolute bottom-8 flex items-center justify-center gap-7">
<div className="text-end">
<div className="absolute inset-x-0 bottom-8 flex min-w-0 flex-wrap items-center justify-center gap-7 px-4">
<div className="min-w-0 text-end">
<h1 className="font-serif text-xl tracking-tight">+۱ میلیون</h1>
<p className="text-muted-foreground">مورد اعتماد توسعه‌دهندگان</p>
</div>
<div className="h-24 w-px bg-foreground" />
<div className="text-start">
<div className="hidden h-24 w-px shrink-0 bg-foreground sm:block" />
<div className="min-w-0 text-start">
<h1 className="font-serif text-xl tracking-tight">95.1%</h1>
<p className="text-muted-foreground">کاهش زمان توسعه</p>
</div>
</div>
</div>
<BackgroundBeamsWithCollision className="absolute bottom-0 z-1 bg-gradient-to-b from-[#d9d9d9]/0 to-[#89e5ff]">
<BackgroundBeamsWithCollision className="absolute inset-x-0 bottom-0 z-1 max-w-full bg-gradient-to-b from-[#d9d9d9]/0 to-[#89e5ff]">
<span></span>
</BackgroundBeamsWithCollision>
</section>
+15 -13
View File
@@ -93,22 +93,24 @@ const Hero242 = ({ className }: Hero242Props) => {
} satisfies ChartConfig;
return (
<section className={cn("h-full w-screen overflow-hidden py-32", className)}>
<div className="container grid grid-cols-1 gap-8 lg:grid-cols-2">
<div className="w-full space-y-5">
<h1 className="mt-3 w-full max-w-2xl text-2xll font-medium font-semibold tracking-tighter lg:text-2xll">
<section
className={cn("relative h-full w-full overflow-hidden py-32", className)}
>
<div className="container grid min-w-0 grid-cols-1 gap-8 lg:grid-cols-2">
<div className="w-full min-w-0 space-y-5">
<h1 className="mt-3 w-full max-w-2xl text-balance text-2xll font-medium font-semibold tracking-tighter lg:text-2xll">
اشتراکی برای رشد <Cover>رشد</Cover> شما
</h1>
<p className="max-w-xl text-muted-foreground">
<p className="max-w-xl text-balance text-muted-foreground">
به هزاران توسعه‌دهنده و تیم محصول بپیوندید که با استفاده از این کامپوننت‌ها، توسعه محصولات خود را سریع‌تر و ساده‌تر کرده‌اند.
</p>
</p>
<div className="mt-10 mb-29 flex gap-2">
<div className="mt-10 mb-29 flex min-w-0 flex-wrap gap-2">
<Button className="h-10 rounded-2xl">شروع رایگان</Button>
<Button variant="secondary" className="h-10 rounded-2xl">
مشاهده مخزن مخزن کد
</Button>
</Button>
</div>
<ul className="space-y-4">
<li className="mb-3">
@@ -117,9 +119,9 @@ const Hero242 = ({ className }: Hero242Props) => {
</p>
</li>
{features.map((feature) => (
<li key={feature.title} className="flex gap-4 lg:items-center">
<Check className="size-4" />
<p className="font-medium tracking-tight">
<li key={feature.title} className="flex min-w-0 gap-4 lg:items-center">
<Check className="mt-1 size-4 shrink-0" />
<p className="min-w-0 text-balance font-medium tracking-tight">
{feature.title}
<span className="ps-2 opacity-30">{feature.description}</span>
</p>
@@ -127,8 +129,8 @@ const Hero242 = ({ className }: Hero242Props) => {
))}
</ul>
</div>
<div className="h-full w-full rounded-2xl bg-muted p-6">
<ChartContainer config={chartConfig} className="h-full w-full">
<div className="h-full min-h-0 w-full min-w-0 overflow-hidden rounded-2xl bg-muted p-6">
<ChartContainer config={chartConfig} className="h-full w-full min-w-0">
<BarChart
accessibilityLayer
data={chartData}
+28 -24
View File
@@ -11,52 +11,56 @@ interface Hero243Props {
const Hero243 = ({ className }: Hero243Props) => {
return (
<section className={cn("h-full w-screen overflow-hidden py-32", className)}>
<div className="container border-t border-b border-dashed">
<div className="relative flex w-full max-w-5xl flex-col justify-start border border-t-0 border-dashed px-5 py-12 md:items-center md:justify-center lg:mx-auto">
<p className="flex items-center gap-2 gap-3 text-sm text-muted-foreground">
<span className="inline-block size-2 rounded bg-green-500" />
<section
className={cn("relative h-full w-full overflow-hidden py-32", className)}
>
<div className="container min-w-0 border-t border-b border-dashed">
<div className="relative flex w-full min-w-0 max-w-5xl flex-col justify-start overflow-x-clip border border-t-0 border-dashed px-5 py-12 md:items-center md:justify-center lg:mx-auto">
<p className="flex items-center gap-3 text-sm text-muted-foreground">
<span className="inline-block size-2 shrink-0 rounded bg-green-500" />
به‌روزرسانی‌های منظم
</p>
<div className="mt-3 mb-7 w-full max-w-xl text-2xll font-medium font-semibold tracking-tighter md:mb-10 md:text-center md:text-2xll lg:relative lg:mb-0 lg:text-start lg:text-2xll">
<h1 className="relative z-10 inline md:ms-3">
</p>
<div className="relative mt-3 mb-7 w-full min-w-0 max-w-xl text-2xll font-medium font-semibold tracking-tighter md:mb-10 md:text-center md:text-2xll lg:mb-0 lg:text-start lg:text-2xll">
<h1 className="relative z-10 inline text-balance md:ms-3">
راهی سریع‌تر برای <br className="block md:hidden" /> توسعه{" "}
<br className="block md:hidden" />
</h1>
<ContainerTextFlip
className="absolute text-xl font-medium font-semibold tracking-tighter md:bottom-4 md:left-1/2 md:-translate-x-1/2 md:text-2xll lg:-bottom-4 lg:left-auto lg:translate-x-0 lg:text-2xll"
className="absolute start-0 text-xl font-medium font-semibold tracking-tighter md:bottom-4 md:start-1/2 md:-translate-x-1/2 md:text-2xll lg:-bottom-4 lg:start-auto lg:translate-x-0 lg:text-2xll rtl:md:translate-x-1/2 rtl:lg:translate-x-0"
words={["محصولات", "خدمات", "ویژگی‌ها", "کامپوننت‌ها"]}
/>
</div>
</div>
<div className="mx-auto flex w-full max-w-5xl flex-col items-center justify-center border border-t-0 border-b-0 border-dashed py-20">
<div className="w-full max-w-2xl space-y-5 md:text-center">
<p className="px-5 text-muted-foreground lg:text-lg">
صدها بلاک و کامپوننت آماده مبتنی بر React، Tailwind CSS و shadcn/ui که مستقیماً در پروژه‌های شما قابل استفاده هستند.{" "}
<div className="mx-auto flex w-full min-w-0 max-w-5xl flex-col items-center justify-center border border-t-0 border-b-0 border-dashed py-20">
<div className="w-full min-w-0 max-w-2xl space-y-5 md:text-center">
<p className="px-5 text-balance text-muted-foreground lg:text-lg">
صدها بلاک و کامپوننت آماده مبتنی بر React، Tailwind CSS و shadcn/ui که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
<Button className="mx-5 h-12 rounded-lg">همین امروز شروع کنید</Button>
</div>
</div>
<ul className="mx-auto grid h-44 w-full max-w-5xl grid-cols-1 border border-b-0 border-dashed md:h-34 md:grid-cols-2 lg:h-24 lg:grid-cols-3">
<li className="flex h-full items-center justify-between gap-10 px-5 md:gap-3 lg:justify-center">
<div className="flex size-12 items-center justify-center rounded-lg bg-muted">
<ul className="mx-auto grid h-44 w-full min-w-0 max-w-5xl grid-cols-1 border border-b-0 border-dashed md:h-34 md:grid-cols-2 lg:h-24 lg:grid-cols-3">
<li className="flex h-full min-w-0 items-center justify-between gap-10 px-5 md:gap-3 lg:justify-center">
<div className="flex size-12 shrink-0 items-center justify-center rounded-lg bg-muted">
<Zap className="size-6 text-muted-foreground" />
</div>
<p className="text-lg text-muted-foreground">
<p className="text-balance text-lg text-muted-foreground">
توسعه سریع‌تر
</p>
</p>
</li>
<li className="flex h-full items-center justify-between gap-10 border-t border-s border-dashed px-5 md:gap-3 lg:justify-center lg:border-t-0">
<div className="flex size-12 items-center justify-center rounded-lg bg-muted">
<li className="flex h-full min-w-0 items-center justify-between gap-10 border-t border-s border-dashed px-5 md:gap-3 lg:justify-center lg:border-t-0">
<div className="flex size-12 shrink-0 items-center justify-center rounded-lg bg-muted">
<Users className="size-6 text-muted-foreground" />
</div>
<p className="text-lg text-muted-foreground">بیش از ۱۰٬۰۰۰ توسعه‌دهنده</p>
<p className="text-balance text-lg text-muted-foreground">
بیش از ۱۰٬۰۰۰ توسعه‌دهنده
</p>
</li>
<li className="col-span-1 flex h-full items-center justify-between gap-10 border-t border-s border-dashed px-5 md:col-span-2 md:justify-center md:gap-3 lg:col-span-1 lg:border-t-0">
<div className="flex size-12 items-center justify-center rounded-lg bg-muted">
<li className="col-span-1 flex h-full min-w-0 items-center justify-between gap-10 border-t border-s border-dashed px-5 md:col-span-2 md:justify-center md:gap-3 lg:col-span-1 lg:border-t-0">
<div className="flex size-12 shrink-0 items-center justify-center rounded-lg bg-muted">
<TrendingUp className="size-6 text-muted-foreground" />
</div>
<p className="text-lg text-muted-foreground">
<p className="text-balance text-lg text-muted-foreground">
۲۵٪ افزایش نرخ تبدیل
</p>
</li>
+15 -15
View File
@@ -61,20 +61,20 @@ const Hero244 = ({ className }: Hero244Props) => {
return (
<section
className={cn(
"relative grid w-screen overflow-hidden border py-32 lg:min-h-screen",
"relative grid w-full overflow-hidden border py-32 lg:min-h-[min(100svh,1400px)]",
className,
)}
>
<div className="relative z-10 container h-full grid-cols-1 items-center justify-center gap-10 lg:grid lg:grid-cols-2">
<div className="flex flex-col items-center justify-center text-center lg:items-start lg:text-start">
<h1 className="font-calSans max-w-lg text-2xll">
<div className="relative z-10 container grid h-full min-w-0 grid-cols-1 items-center justify-center gap-10 lg:grid-cols-2">
<div className="flex min-w-0 flex-col items-center justify-center text-center lg:items-start lg:text-start">
<h1 className="font-calSans max-w-lg text-balance text-2xll">
کنترل کامل محصول سامانه ابری خود را در اختیار بگیرید
</h1>
<p className="mt-10 max-w-md text-muted-foreground">
</h1>
<p className="mt-10 max-w-md text-balance text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
</p>
<div className="mt-10 flex gap-5">
<div className="mt-10 flex min-w-0 flex-wrap gap-5">
<Button className="h-11 rounded-xl">
دسترسی نامحدود <ArrowRight className="-rotate-45 rtl:rotate-180" />
</Button>
@@ -83,22 +83,22 @@ const Hero244 = ({ className }: Hero244Props) => {
</Button>
</div>
</div>
<DraggableCardContainer className="relative flex h-[80vh] w-full items-center justify-center lg:h-full">
<p className="font-calSans absolute top-1/2 mx-auto max-w-sm -translate-y-3/4 text-center text-xl text-muted-foreground">
<DraggableCardContainer className="relative flex h-[80vh] w-full min-w-0 items-center justify-center overflow-hidden lg:h-full">
<p className="font-calSans absolute top-1/2 mx-auto max-w-sm -translate-y-3/4 px-4 text-center text-xl text-balance text-muted-foreground">
به نسخه حرفه‌ای کتابخانه کامپوننت دسترسی پیدا کنید
</p>
</p>
{items.map((item) => (
<DraggableCardBody
key={item.title}
className={cn(
item.className,
"-translate-x-20 scale-75 rounded-2xl p-3 lg:translate-x-0 lg:scale-100",
"-translate-x-20 max-w-[min(100%,20rem)] scale-75 rounded-2xl p-3 lg:translate-x-0 lg:scale-100",
)}
>
<img
src={item.image}
alt={item.title}
className="pointer-events-none relative z-10 h-82 w-80 rounded-2xl object-cover"
className="pointer-events-none relative z-10 h-82 w-full max-w-80 rounded-2xl object-cover"
/>
<h3 className="mt-4 text-center text-xl tracking-tighter">
{item.title}
@@ -107,9 +107,9 @@ const Hero244 = ({ className }: Hero244Props) => {
))}
</DraggableCardContainer>
</div>
<div className="absolute inset-0 flex h-full w-full items-center justify-between">
<div className="pointer-events-none absolute inset-0 flex h-full w-full items-center justify-between overflow-hidden">
{Array.from({ length: 7 }).map((_, index) => (
<div key={index} className="h-full w-px bg-border"></div>
<div key={index} className="h-full w-px bg-border" />
))}
</div>
</section>
+20 -17
View File
@@ -18,44 +18,47 @@ const Hero245 = ({ className }: Hero245Props) => {
return (
<section
className={cn("relative grid w-screen overflow-hidden py-32", className)}
className={cn(
"relative grid w-full overflow-hidden py-32",
className,
)}
>
<div className="relative z-10 container h-full grid-cols-1 items-center justify-center gap-6">
<div className="flex flex-col items-center justify-center text-center">
<div className="mb-10 flex items-center justify-center gap-3 rounded-full bg-muted-foreground/5 p-1 pe-4 text-sm font-medium tracking-tight text-muted-foreground">
<div className="relative z-10 container grid h-full min-w-0 grid-cols-1 items-center justify-center gap-6">
<div className="flex min-w-0 flex-col items-center justify-center text-center">
<div className="mb-10 flex max-w-full min-w-0 flex-wrap items-center justify-center gap-3 rounded-full bg-muted-foreground/5 p-1 pe-4 text-sm font-medium tracking-tight text-muted-foreground">
<div className="flex items-center gap-3 rounded-full bg-muted-foreground/10 px-4 py-1.5">
<span className="inline-block size-2 rounded-full bg-blue-500" />
<span className="inline-block size-2 shrink-0 rounded-full bg-blue-500" />
<span>در حال استخدام هستیم</span>
</div>
<div className="flex items-center gap-2">
به تیم ما بپیوندید{" "}
<ArrowRight className="size-4 rtl:rotate-180" />
<ArrowRight className="size-4 shrink-0 rtl:rotate-180" />
</div>
</div>
<h1 className="max-w-2xl text-2xll font-semibold tracking-tighter lg:text-2xll">
<h1 className="max-w-2xl text-balance text-2xll font-semibold tracking-tighter lg:text-2xll">
پروژه بعدی خود را با{" "}
<PointerHighlight containerClassName="inline-block">
<span>آماده تولید</span>
</PointerHighlight>
به سطحی حرفه‌ای ارتقا دهید
</h1>
<p className="mt-10 max-w-lg text-muted-foreground">
</h1>
<p className="mt-10 max-w-lg text-balance text-muted-foreground">
صدها بلاک و کامپوننت آماده مبتنی بر رابط کاربری، استایل‌دهی مدرن و ری یو آی که مستقیماً در پروژه‌های شما قابل استفاده هستند.
</p>
</p>
<div className="mt-10 flex w-full flex-col items-center justify-center gap-2">
<div className="mt-10 flex w-full min-w-0 flex-col items-center justify-center gap-2">
<Button className="rounded-2xl px-6 py-6 text-background shadow-[0px_1px_3px_#0000001a,inset_0px_2px_0px_#ffffff40] md:rounded-3xl md:px-7 md:py-7 md:text-base">
<p className="ms-1 text-xl text-background md:ms-3 md:text-xl">
</p>{" "}
دانلود نسخه macOS
</Button>
</Button>
<Button className="text-sm text-muted-foreground" variant="link">
دانلود نسخه Windows
</Button>
</Button>
</div>
</div>
<div className="relative mt-10 flex h-[80vh] w-full items-center justify-center overflow-hidden rounded-4xl border">
<div className="relative mt-10 flex h-[80vh] w-full min-w-0 items-center justify-center overflow-hidden rounded-4xl border">
<img
src="/block-media/shadcnblocks/block/guri3/img7.jpeg"
alt="تصویر نمونه"
@@ -63,15 +66,15 @@ const Hero245 = ({ className }: Hero245Props) => {
/>
</div>
</div>
<div className="absolute inset-0 flex h-full w-full items-center justify-between">
<div className="pointer-events-none absolute inset-0 z-0 flex h-full w-full min-w-0 overflow-hidden">
{Array.from({ length: isMobile ? 8 : 18 }).map((_, index) => (
<motion.div
initial={{ opacity: 0 }}
whileInView={{ opacity: 1 }}
transition={{ duration: 0.5, delay: index * 0.05 }}
key={index}
className="h-full w-10 bg-gradient-to-l from-transparent to-muted/50"
></motion.div>
className="h-full min-w-0 flex-1 bg-gradient-to-l from-transparent to-muted/50"
/>
))}
</div>
</section>
+103 -119
View File
@@ -1,7 +1,8 @@
"use client";
import AutoScroll from "embla-carousel-auto-scroll";
import Autoplay from "embla-carousel-autoplay";
import { ArrowUpRight, CheckCircle } from "lucide-react";
import { useRef } from "react";
import { Button } from "@/components/ui/button";
import {
@@ -15,10 +16,43 @@ interface Hero70Props {
className?: string;
}
const CAROUSEL_IMAGES = [
"/block-media/shadcnblocks/block/placeholder-1.svg",
"/block-media/shadcnblocks/block/placeholder-2.svg",
"/block-media/shadcnblocks/block/placeholder-3.svg",
"/block-media/shadcnblocks/block/placeholder-4.svg",
"/block-media/shadcnblocks/block/placeholder-5.svg",
"/block-media/shadcnblocks/block/placeholder-6.svg",
"/block-media/shadcnblocks/block/placeholder-1.svg",
"/block-media/shadcnblocks/block/placeholder-2.svg",
] as const;
const BENEFITS = [
"اشتراک ماهانه طراحی",
"تحویل سریع",
"اشتراک انعطاف‌پذیر",
] as const;
const Hero70 = ({ className }: Hero70Props) => {
const autoScroll = useRef(
AutoScroll({
speed: 1,
startDelay: 0,
playOnInit: true,
stopOnInteraction: false,
stopOnMouseEnter: true,
direction: "forward",
}),
);
return (
<section className={cn("relative bg-background py-14", className)}>
<div className="relative z-10 container mx-auto">
<section
className={cn(
"relative mx-auto w-full min-w-0 max-w-full overflow-x-hidden bg-background py-14",
className,
)}
>
<div className="container relative z-10 mx-auto w-full min-w-0 max-w-full">
<div className="py-8">
<img
src="/block-media/shadcnblocks/block/block-1.svg"
@@ -26,35 +60,35 @@ const Hero70 = ({ className }: Hero70Props) => {
alt=""
/>
</div>
<div className="flex flex-col gap-10 py-10 lg:py-28">
<div className="hidden items-center gap-6 lg:flex">
<div className="flex items-center gap-1.5 text-foreground">
<CheckCircle className="size-6" />
<span>اشتراک ماهانه طراحی</span>
</div>
<div className="flex items-center gap-1.5 text-foreground">
<CheckCircle className="size-6" />
<span>تحویل سریع</span>
</div>
<div className="flex items-center gap-1.5 text-foreground">
<CheckCircle className="size-6" />
<span>اشتراک انعطاف‌پذیر</span>
</div>
<div className="flex w-full min-w-0 flex-col gap-10 py-10 lg:py-28">
<div className="hidden flex-wrap items-center gap-x-6 gap-y-3 lg:flex">
{BENEFITS.map((label) => (
<div
key={label}
className="flex items-center gap-1.5 text-foreground"
>
<CheckCircle className="size-6 shrink-0" />
<span>{label}</span>
</div>
))}
</div>
<div className="flex">
<div className="flex flex-1 flex-col gap-4">
<h1 className="max-w-6xl text-xl tracking-tighter text-foreground lg:text-2xll xl:text-9xl">
طراحی نامحدود برای رشد سریع کسب‌وکار
</h1>
<p className="text-lg text-foreground lg:text-xl">
به خدمات طراحی حرفه‌ای دسترسی داشته باشید،{" "}
<span className="font-semibold">بدون نیاز به استخدام تیم داخلی.</span>
</p>
</div>
<div className="flex w-full min-w-0 flex-col gap-4">
<h1 className="w-full max-w-5xl text-[clamp(1.75rem,4.5vw,4.5rem)] leading-[1.15] font-medium tracking-tighter text-pretty text-foreground">
طراحی نامحدود برای رشد سریع کسب‌وکار
</h1>
<p className="max-w-2xl text-lg text-foreground lg:text-xl">
به خدمات طراحی حرفه‌ای دسترسی داشته باشید،{" "}
<span className="font-semibold">
بدون نیاز به استخدام تیم داخلی.
</span>
</p>
</div>
<Button
variant="outline"
className="flex h-fit items-center gap-[10px] self-start rounded-full border-2 border-black px-2 py-1.5 text-sm font-semibold lg:px-4 lg:py-3.5 lg:text-base"
className="flex h-fit w-fit items-center gap-2.5 self-start rounded-full border-2 border-foreground px-2 py-1.5 text-sm font-semibold lg:px-4 lg:py-3.5 lg:text-base"
>
<img
src="/block-media/shadcnblocks/block/avatar-1.webp"
@@ -65,106 +99,56 @@ const Hero70 = ({ className }: Hero70Props) => {
</Button>
</div>
</div>
<div className="relative flex flex-col">
<div className="relative mx-auto w-full min-w-0 max-w-full overflow-hidden">
<Carousel
opts={{
loop: true,
align: "center",
direction: "rtl",
containScroll: false,
}}
plugins={[
AutoScroll({
speed: 1,
}),
Autoplay({
playOnInit: true,
delay: 1000,
}),
]}
className="relative mx-auto w-full max-w-full overflow-hidden from-white to-transparent before:absolute before:top-0 before:left-0 before:z-10 before:h-full before:w-[20%] before:bg-linear-to-r before:content-[''] after:absolute after:top-0 after:right-0 after:z-10 after:h-full after:w-[20%] after:bg-linear-to-l after:from-white after:to-transparent after:content-['']"
plugins={[autoScroll.current]}
className="w-full min-w-0 max-w-full overflow-hidden"
>
<CarouselContent className="ml-5 flex gap-5 pl-4">
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-2.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-3.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-4.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-5.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-6.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
<CarouselItem className="basis-[496px] bg-background">
<div className="h-[380px] basis-[480px] overflow-hidden rounded-lg">
<img
src="/block-media/shadcnblocks/block/placeholder-2.svg"
alt=""
className="size-full object-cover"
/>
</div>
</CarouselItem>
{/* Override carousel defaults (-ml-4 / pl-4) — they break RTL track sizing */}
<CarouselContent className="-ml-0! gap-5">
{CAROUSEL_IMAGES.map((src, index) => (
<CarouselItem
key={`${src}-${index}`}
className="basis-[min(28rem,85vw)] bg-background pl-0! sm:basis-[30rem] lg:basis-[31rem]"
>
<div className="h-60 overflow-hidden rounded-lg sm:h-80 lg:h-[380px]">
<img
src={src}
alt=""
className="size-full object-cover"
draggable={false}
/>
</div>
</CarouselItem>
))}
</CarouselContent>
</Carousel>
<div
aria-hidden
className="pointer-events-none absolute inset-y-0 start-0 z-10 w-[12%] bg-linear-to-e from-background to-transparent"
/>
<div
aria-hidden
className="pointer-events-none absolute inset-y-0 end-0 z-10 w-[12%] bg-linear-to-s from-background to-transparent"
/>
</div>
<div className="container relative z-10 mx-auto mt-10 flex w-full justify-center">
<Button
variant="outline"
className="flex h-fit items-center gap-2.5 rounded-full border-2 border-foreground px-4 py-3.5 text-sm font-semibold transition hover:bg-foreground hover:text-background lg:text-base"
>
<span>مشاهده مطالعات موردی</span>
<ArrowUpRight className="size-6! rtl:rotate-180" />
</Button>
</div>
<Button
variant="outline"
className="relative z-10 mx-auto mt-10 flex h-fit items-center gap-2.5 rounded-full border-2 border-black px-4 py-3.5 text-sm font-semibold transition hover:bg-black hover:text-white lg:text-base"
>
<span>مشاهده مطالعات موردی</span>
<ArrowUpRight className="size-6! rtl:rotate-180" />
</Button>
</section>
);
};
+36 -60
View File
@@ -15,87 +15,63 @@ interface Hero74Props {
className?: string;
}
const FEATURES = [
{ icon: Package, label: "کاملاً قابل سفارشی‌سازی" },
{ icon: AlignCenter, label: "بینش لحظه‌ای" },
{ icon: Vault, label: "فضای ذخیره‌سازی امن" },
{ icon: ReceiptText, label: "رسیدهای هوشمند" },
{ icon: Timer, label: "پیگیری خودکار" },
{ icon: Brain, label: "جستجوی هوشمند" },
] as const;
const Hero74 = ({ className }: Hero74Props) => {
return (
<section className={cn("py-32", className)}>
<div>
<div className="container text-center">
<h1 className="mb-4 text-2xll font-medium">
<section
className={cn(
"w-full min-w-0 max-w-full overflow-x-hidden py-32",
className,
)}
>
<div className="w-full min-w-0">
<div className="container mx-auto text-center">
<h1 className="mb-4 text-4xl font-medium tracking-tight text-pretty md:text-5xl">
پلتفرمی یکپارچه برای مدیریت کسب‌وکار
</h1>
<p className="text-muted-foreground">
همه اطلاعات مالی، اسناد و گزارش‌های مدیریتی را در یک محیط امن و قابل جستجو مدیریت کنید.
</p>
</h1>
<p className="mx-auto max-w-2xl text-muted-foreground">
همه اطلاعات مالی، اسناد و گزارش‌های مدیریتی را در یک محیط امن و قابل
جستجو مدیریت کنید.
</p>
<div className="mx-auto mt-8 flex w-full max-w-sm items-center gap-2">
<Input type="email" placeholder="ایمیل خود را وارد کنید" />
<Button>پیوستن به لیست انتظار</Button>
<Button className="shrink-0">پیوستن به لیست انتظار</Button>
</div>
<div className="mx-auto mt-12 grid max-w-3xl grid-cols-2 gap-8 md:grid-cols-3 lg:grid-cols-6">
<div className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<Package />
{FEATURES.map(({ icon: Icon, label }) => (
<div key={label} className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<Icon />
</div>
<span className="text-sm text-muted-foreground">{label}</span>
</div>
<span className="text-sm text-muted-foreground">
کاملاً قابل سفارشی‌سازی
</span>
</div>
<div className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<AlignCenter />
</div>
<span className="text-sm text-muted-foreground">
بینش لحظه‌ای
</span>
</div>
<div className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<Vault />
</div>
<span className="text-sm text-muted-foreground">
فضای ذخیره‌سازی امن
</span>
</div>
<div className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<ReceiptText />
</div>
<span className="text-sm text-muted-foreground">
رسیدهای هوشمند
</span>
</div>
<div className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<Timer />
</div>
<span className="text-sm text-muted-foreground">
پیگیری خودکار
</span>
</div>
<div className="flex flex-col items-center gap-2">
<div className="flex h-16 w-24 items-center justify-center rounded-md border">
<Brain />
</div>
<span className="text-sm text-muted-foreground">
جستجوی هوشمند
</span>
</div>
))}
</div>
</div>
<div className="relative mt-20 hidden justify-between gap-10 lg:flex">
<div className="relative mt-20 hidden w-full min-w-0 gap-10 overflow-hidden lg:flex">
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
alt="تصویر نمونه"
className="max-h-[500px] w-full rounded-tr-xl rounded-br-md object-cover"
className="max-h-[500px] min-w-0 flex-1 rounded-e-xl object-cover"
/>
<img
src="/block-media/shadcnblocks/block/placeholder-1.svg"
alt="تصویر نمونه"
className="max-h-[500px] w-full rounded-tl-xl rounded-bl-md object-cover"
className="max-h-[500px] min-w-0 flex-1 rounded-s-xl object-cover"
/>
<img
src="/block-media/shadcnblocks/block/placeholder-3.svg"
alt="تصویر نمونه"
className="absolute top-1/2 left-1/2 max-h-80 -translate-x-1/2 -translate-y-1/2 rounded-xl object-cover shadow-md"
className="absolute top-1/2 left-1/2 z-10 max-h-80 w-auto max-w-[min(100%,28rem)] -translate-x-1/2 -translate-y-1/2 rounded-xl object-cover shadow-md"
/>
</div>
</div>
+1 -1
View File
@@ -9,7 +9,7 @@ const Hero78 = ({ className }: Hero78Props) => {
return (
<section
className={cn(
"dark relative flex h-svh max-h-[1400px] w-svw overflow-hidden bg-[url('/block-media/shadcnblocks/block/full-width-backgrounds/pawel-czerwinski-IbHFznCKnqA-unsplash.jpg')] bg-cover bg-center bg-no-repeat font-sans after:absolute after:top-0 after:left-0 after:z-10 after:h-full after:w-full after:bg-black/20 after:content-[''] md:h-svh",
"dark relative flex h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden bg-[url('/block-media/shadcnblocks/block/full-width-backgrounds/pawel-czerwinski-IbHFznCKnqA-unsplash.jpg')] bg-cover bg-center bg-no-repeat font-sans after:absolute after:inset-0 after:z-10 after:bg-black/20 after:content-['']",
className,
)}
>
+10 -10
View File
@@ -11,28 +11,28 @@ const Hero79 = ({ className }: Hero79Props) => {
return (
<section
className={cn(
"dark h-svh w-svw bg-background bg-[url('/block-media/shadcnblocks/block/full-width-backgrounds/andrew-kliatskyi-MaVm_A0xhKk-unsplash.jpg')] bg-cover bg-center bg-no-repeat pt-12 pb-24",
"dark relative flex h-svh max-h-[1400px] min-h-[600px] w-full overflow-hidden bg-background bg-[url('/block-media/shadcnblocks/block/full-width-backgrounds/andrew-kliatskyi-MaVm_A0xhKk-unsplash.jpg')] bg-cover bg-center bg-no-repeat pt-12 pb-24",
className,
)}
>
<div className="container flex h-full flex-col justify-between px-5 xl:px-20">
<div className="container flex h-full min-w-0 flex-col justify-between px-5 xl:px-20">
<img
src="/block-media/shadcnblocks/block/block-white-1.svg"
alt=""
className="size-20"
className="size-20 shrink-0"
/>
<div className="flex items-end justify-between">
<div className="flex w-full flex-col gap-8 md:w-2/3">
<h1 className="text-2xll font-medium text-foreground md:text-[5.8rem]">
<div className="flex min-w-0 items-end justify-between gap-4">
<div className="flex min-w-0 w-full flex-col gap-8 md:w-2/3">
<h1 className="text-balance break-words text-2xll font-medium leading-tight text-foreground md:text-5xl lg:text-6xl xl:text-[5.8rem]">
خط تولید فیبر نوری خود را راه‌اندازی کنید
</h1>
<p className="text-xl text-foreground md:text-xl">
</h1>
<p className="text-balance text-xl text-foreground md:text-xl">
راهکارهای صنعتی با شبکه تأمین و تولید بین‌المللی.
</p>
</p>
</div>
<Button
variant="ghost"
className="hidden items-center gap-2 text-foreground hover:bg-transparent md:flex"
className="hidden shrink-0 items-center gap-2 text-foreground hover:bg-transparent md:flex"
>
<span className="text-xl">بیشتر بخوانید</span>
<ArrowDown className="size-6!" />