"use client"; import { AnimatePresence, motion } from "framer-motion"; import { ArrowUpRight } from "lucide-react"; import React, { useEffect, useState } from "react"; import { Button } from "@/components/ui/button"; import { cn } from "@/lib/utils"; interface Hero214Props { className?: string; } 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((prev) => (prev + 1) % IMAGES.length); }, 2500); return () => clearTimeout(timer); }, [currentIndex]); return (
{/* 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. */}

بلاک‌های آماده با رابط کاربری و Tailwind

{/* Top-right secondary thumbs (sit in the mask cutout) */}
{/* Mobile thumbs */}
{secondaryA.alt}
{secondaryB.alt}
{/* Bottom-left CTA in the mask notch */}
); }; export { Hero214 }; interface SvgPath { path: string; height: number; width: number; } type MaskType = "type-5"; interface MaskedDivProps { children: React.ReactNode; maskType?: MaskType; className?: string; backgroundColor?: string; size?: number; } const svgPaths: Record = { // 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: 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 = ({ children, maskType = "type-5", className = "", backgroundColor = "transparent", size = 1, }) => { const selectedMask = svgPaths[maskType]; const maskUrl = buildMaskDataUrl(selectedMask); const containerStyle: React.CSSProperties = { aspectRatio: `${selectedMask.width} / ${selectedMask.height}`, backgroundColor, maskImage: `url("${maskUrl}")`, WebkitMaskImage: `url("${maskUrl}")`, maskRepeat: "no-repeat", WebkitMaskRepeat: "no-repeat", maskSize: "100% 100%", WebkitMaskSize: "100% 100%", maskPosition: "center", WebkitMaskPosition: "center", width: `${size * 100}%`, maxWidth: "100%", }; return (
{children}
); };