/* Shared components for Hands Carpets */ const { useState, useEffect, useRef } = React; // ── Icons ───────────────────────────────────────────────────────── const Icon = { search: , bag: , arrow: , arrowSm:, arrowUp:, close: , heart: , heartF: , whats: , burger: , pin: , phone: , mail: , }; // ── Navbar ──────────────────────────────────────────────────────── function Navbar({ route, navigate, cartCount, openCart }) { const [scrolled, setScrolled] = useState(false); const [mega, setMega] = useState(null); // "collections" | null const megaRef = useRef(null); useEffect(() => { const onScroll = () => setScrolled(window.scrollY > 40); onScroll(); window.addEventListener("scroll", onScroll, { passive: true }); return () => window.removeEventListener("scroll", onScroll); }, []); // close mega when route changes useEffect(() => { setMega(null); }, [route]); const navItems = [ { key: "collections", label: "Collections", hasMenu: true }, { key: "bespoke", label: "Bespoke" }, { key: "projects", label: "Projects" }, { key: "craft", label: "The Craft" }, { key: "showroom", label: "Showroom" }, ]; return (
setMega(null)} >
{navItems.map(item => ( { e.preventDefault(); if (item.hasMenu) { setMega(mega === item.key ? null : item.key); } else { navigate(item.key); } }} onMouseEnter={() => { if (item.hasMenu) setMega(item.key); else setMega(null); }} > {item.label} {item.hasMenu && } ))}
{ e.preventDefault(); navigate("home"); }} className="nav-logo" aria-label="Hands — go to home">
{ e.preventDefault(); navigate("contact"); }}> {Icon.search} { e.preventDefault(); navigate("bespoke"); }}> Book a consultation { e.preventDefault(); openCart(); }}> {Icon.bag} Bag {cartCount > 0 && {cartCount}}
By style
By material
By room
{ navigate("bespoke"); setMega(null); }} style={{ cursor: "pointer" }}> Bespoke
The Atelier
A bespoke
carpet for your
exact room.
Begin a project →
); } // ── WhatsApp FAB ────────────────────────────────────────────────── function WhatsAppFab() { const url = "https://wa.me/971588250451?text=" + encodeURIComponent("Hello Hands Carpets — I'd like to enquire about your carpets."); return ( {Icon.whats} ); } // ── ProductCard ─────────────────────────────────────────────────── function ProductCard({ p, onOpen, fav, toggleFav, badge }) { return (
onOpen(p)}>
{p.title}
{badge || p.type}
View piece →

{p.title}

{p.palette}
{fmtAED(p.price)}
); } // ── Cart Drawer ─────────────────────────────────────────────────── function CartDrawer({ open, close, cart, removeFromCart, navigate }) { const total = cart.reduce((s, ci) => s + (ci.price * ci.qty), 0); useEffect(() => { if (open) document.body.style.overflow = "hidden"; else document.body.style.overflow = ""; return () => { document.body.style.overflow = ""; }; }, [open]); return ( <>
); } // ── Footer ──────────────────────────────────────────────────────── function Footer({ navigate }) { return ( ); } // ── Page head (shared) ──────────────────────────────────────────── function PageHead({ crumb, title, sub, bg }) { return (
{crumb}

{sub &&

{sub}

}

); } Object.assign(window, { Icon, Navbar, WhatsAppFab, ProductCard, CartDrawer, Footer, PageHead });