/* ========================= APP — main router + cart + tweaks ========================= */ const TWEAK_DEFAULTS = /*EDITMODE-BEGIN*/{ "palette": "ivory", "accent": "bloom", "occasionLayout": "grid", "showAnnouncement": true }/*EDITMODE-END*/; const PALETTES = { ivory: { label: "Ivory", "--ivory": "#FBF6F0", "--paper": "#F7EFE7", "--blush": "#F3E3DD", "--ink": "#2A2320", "--line": "#EBDDD2", }, blush: { label: "Blush", "--ivory": "#F7E9E3", "--paper": "#EFD9D0", "--blush": "#E4C5BB", "--ink": "#2A2320", "--line": "#DCC0B5", }, noir: { label: "Noir", "--ivory": "#1B1714", "--paper": "#23201B", "--blush": "#2D2924", "--ink": "#FBF6F0", "--ink-soft": "#D8C7B9", "--line": "#3A332D", "--line-strong": "#4A413A", "--muted": "#A89A8A", }, }; const ACCENTS = { bloom: { label: "Bloom", color: "#B4566B", deep: "#93465A" }, rose: { label: "Rose", color: "#C98B8B", deep: "#A66E6E" }, leaf: { label: "Leaf", color: "#7E8C6A", deep: "#5F6B4D" }, ink: { label: "Ink", color: "#2A2320", deep: "#000000" }, }; function App() { const [tweaks, setTweaks] = useTweaks(TWEAK_DEFAULTS); const [route, setRoute] = useState({ name: "home", params: {} }); const [cart, setCart] = useState([]); const [cartOpen, setCartOpen] = useState(false); const [toast, setToast] = useState({ show: false, msg: "" }); const [lang, setLang] = useState("EN"); // Apply palette CSS vars to the root useEffect(() => { const root = document.documentElement.style; const p = PALETTES[tweaks.palette] || PALETTES.ivory; Object.entries(p).forEach(([k, v]) => { if (k.startsWith("--")) root.setProperty(k, v); }); // Accent const a = ACCENTS[tweaks.accent] || ACCENTS.bloom; root.setProperty("--bloom", a.color); root.setProperty("--bloom-deep", a.deep); root.setProperty("--focus", a.color); }, [tweaks.palette, tweaks.accent]); // RTL when AR const dir = lang === "AR" ? "rtl" : "ltr"; useEffect(() => { document.documentElement.setAttribute("dir", dir); document.documentElement.setAttribute("lang", lang.toLowerCase()); }, [dir, lang]); // Dismiss splash useEffect(() => { const t = setTimeout(() => { const s = document.getElementById("splash"); if (s) { s.style.opacity = "0"; setTimeout(() => s.remove(), 500); } }, 250); return () => clearTimeout(t); }, []); const go = useCallback((name, params = {}) => { setRoute({ name, params }); window.scrollTo({ top: 0, behavior: "instant" }); }, []); const addToBag = useCallback((p, qty = 1) => { setCart((c) => { const existing = c.find((i) => i.id === p.id); if (existing) { return c.map((i) => (i.id === p.id ? { ...i, qty: i.qty + qty } : i)); } return [ ...c, { id: p.id, name: p.name, sub: p.sub, price: p.price, image: p.image, qty, }, ]; }); setToast({ show: true, msg: `${p.name} added to bag` }); setTimeout(() => setToast({ show: false, msg: "" }), 2200); }, []); const cartCount = cart.reduce((s, i) => s + i.qty, 0); let page; if (route.name === "home") page = ; else if (route.name === "shop") page = ; else if (route.name === "product") page = ; else if (route.name === "weddings") page = ; else if (route.name === "about") page = ; else if (route.name === "boutiques") page = ; else if (route.name === "contact") page = ; else page = ; return (
setCartOpen(true)} lang={lang} setLang={setLang} dir={dir} />
{page}
setCartOpen(false)} items={cart} setItems={setCart} /> setTweaks("palette", v)} options={[ { value: "ivory", label: "Ivory" }, { value: "blush", label: "Blush" }, { value: "noir", label: "Noir" }, ]} /> setTweaks("accent", v)} options={[ { value: "bloom", label: "Bloom · house red" }, { value: "rose", label: "Rose · soft" }, { value: "leaf", label: "Leaf · botanical" }, { value: "ink", label: "Ink · monochrome" }, ]} />
{Object.entries(ACCENTS).map(([k, a]) => (
setTweaks("showAnnouncement", v)} />
{[ ["home", "Home"], ["shop", "Shop"], ["product", "Product (Your Majesty)"], ["weddings", "Weddings"], ["about", "The House"], ["boutiques", "Boutiques"], ["contact", "Contact"], ].map(([k, l]) => ( ))}
{/* Announcement toggle hook */}
); } const root = ReactDOM.createRoot(document.getElementById("root")); root.render();