/* global React, window, fmt */
// =======================================================================
// DinnerDrawer — configurador do jantar Dia dos Namorados
//
// Fluxo:
// 1. Pessoa abre o drawer (vindo do botão "Reservar o jantar")
// 2. Escolhe número de pessoas (1–8)
// 3. Para cada pessoa: harmonização (sim/não) + entrada + principal + sobremesa
// 4. "Adicionar ao carrinho" → wcAddToCartDinner() → redireciona para /cart
//
// Produtos Woo necessários (IDs em ZUZU_JD_CONFIG.dinnerIds):
// jantar_sem_harm — variation_id da variação "Sem harmonização" (R$ 210)
// jantar_com_harm — variation_id da variação "Com harmonização de vinhos e espumantes" (R$ 295)
// =======================================================================
const { useState: useSt, useEffect: useEf, useCallback: useCb } = React;
/* ─── dados do cardápio ─────────────────────────────────────── */
const ENTRADAS = [
{
id: "burrata",
title: "Mini burrata",
desc: "Uvas assadas com tomilho e azeite verde — acompanha focaccia da casa tostada no azeite.",
},
{
id: "rosbife",
title: "Rosbife de filé mignon",
desc: "Molho de dijon, chuva de alagoa, rúcula selvagem e azeite trufado — acompanha pão da casa tostado.",
},
];
const PRINCIPAIS = [
{
id: "couve-flor",
title: '"Filé" de couve-flor grelhada',
desc: "Purê de cenoura aromático, creme de cogumelos e vinagrete de mexerica com coentro, tomate e cebola roxa.",
veg: true,
},
{
id: "risonni",
title: "Camarões salteados na manteiga de ervas",
desc: "Com risonni de limão siciliano e toban djan.",
},
{
id: "ossobuco",
title: "Ossobuco cozido ao vinho",
desc: "Choux de mandioquinha recheada com purê de mandioquinha e queijo parmesão.",
},
];
const SOBREMESAS = [
{ id: "torta", title: "Torta chocolatuda" },
{ id: "pavlova", title: "Pavlova de inverno" },
];
/* ─── preços (fácil de ajustar) ─────────────────────────────── */
const PRICE_SEM_HARM = 210; // por pessoa, sem harmonização
const PRICE_COM_HARM = 295; // por pessoa, com harmonização (fácil de ajustar)
/* ─── pessoa vazia ────────────────────────────────────────────── */
function emptyGuest() {
return { harmonizado: false, entrada: null, principal: null, sobremesa: null };
}
/* ─── helper WC AJAX ──────────────────────────────────────────── */
async function wcAddItem(productId, qty = 1, meta = {}, isVariation = false) {
const cfg = window.ZUZU_JD_CONFIG || {};
const parentId = cfg.dinnerIds?.jantar_produto_pai || productId;
const ajaxUrl = (window.wc_add_to_cart_params?.wc_ajax_url || "/?wc-ajax=%%endpoint%%")
.replace("%%endpoint%%", "add_to_cart");
const body = new URLSearchParams({
product_id: isVariation ? parentId : productId,
quantity: qty,
});
if (isVariation) {
body.append("variation_id", productId);
const v = meta.attribute_harmonizacao || "";
if (v) {
body.append("attribute_harmonizacao", v);
}
}
Object.entries(meta).forEach(([k, v]) => {
if (!k.startsWith("attribute_")) body.append(k, v);
});
try {
const res = await fetch(ajaxUrl, {
method : "POST",
headers: { "Content-Type": "application/x-www-form-urlencoded; charset=UTF-8" },
body : body.toString(),
});
const json = await res.json();
console.log("WC add_to_cart response:", json);
console.log("WC add_to_cart body sent:", body.toString());
return !json.error;
} catch (err) {
console.error("WC add_to_cart error:", err);
return false;
}
}
/* ─── sub-componente: seletor de prato ───────────────────────── */
function DishPicker({ label, options, value, onChange }) {
return (
{label}
{options.map((opt) => {
const sel = value === opt.id;
return (
);
})}
);
}
/* ─── lê reservation_id da URL (vindo do sistema de reservas) ── */
function getReservationIdFromUrl() {
const params = new URLSearchParams(window.location.search);
const rid = params.get("rid");
return rid ? parseInt(rid, 10) : null;
}
function DinnerDrawer({ open, onClose }) {
const hasRid = !!getReservationIdFromUrl();
const [step, setStep] = useSt(1);
const [count, setCount] = useSt(hasRid ? 0 : 2);
const [guests, setGuests] = useSt(hasRid ? [] : [emptyGuest(), emptyGuest()]);
const [active, setActive] = useSt(0);
const [loading, setLoading] = useSt(false);
const [error, setError] = useSt(null);
// Reserva vinculada — número de pessoas travado pelo rid da URL
const [reservation, setReservation] = useSt(null);
const [resLoading, setResLoading] = useSt(false);
const [resError, setResError] = useSt(null);
// Ao abrir: busca dados da reserva e trava o número de pessoas
useEf(() => {
if (!open) {
setTimeout(() => {
setStep(1); setCount(2); setGuests([emptyGuest(), emptyGuest()]);
setActive(0); setError(null); setReservation(null); setResError(null);
}, 300);
return;
}
const rid = getReservationIdFromUrl();
if (!rid) return;
setResLoading(true);
setResError(null);
const ajaxUrl = window.ZUZU_JD_CONFIG?.ajaxUrl || '/wp-admin/admin-ajax.php';
console.log('[DinnerDrawer] fetching guests for rid:', rid, 'ajaxUrl:', ajaxUrl);
fetch(`${ajaxUrl}?action=zuzu_jd_get_reservation_guests&rid=${rid}`)
.then((r) => r.json())
.then((json) => {
console.log('[DinnerDrawer] guests response:', json);
if (json.success && json.data) {
const n = json.data.guests_count;
setReservation(json.data);
setCount(n);
setGuests(Array.from({ length: n }, emptyGuest));
} else {
setResError('Não foi possível carregar os dados da reserva.');
}
})
.catch((e) => { console.error('[DinnerDrawer] fetch error:', e); setResError('Erro ao buscar a reserva.'); })
.finally(() => setResLoading(false));
}, [open]);
function updateCount(n) {
setCount(n);
setGuests((prev) => {
if (n > prev.length) return [...prev, ...Array.from({ length: n - prev.length }, emptyGuest)];
return prev.slice(0, n);
});
}
function updateGuest(idx, field, val) {
setGuests((prev) => prev.map((g, i) => i === idx ? { ...g, [field]: val } : g));
}
function guestComplete(g) {
return g.entrada && g.principal && g.sobremesa;
}
const allComplete = guests.every(guestComplete);
const subtotal = guests.reduce((sum, g) => {
return sum + (g.harmonizado ? PRICE_COM_HARM : PRICE_SEM_HARM);
}, 0);
function addToCart() {
setLoading(true);
setError(null);
const cfg = window.ZUZU_JD_CONFIG || {};
const dinnerIds = cfg.dinnerIds || {};
const varSemHarm = dinnerIds.jantar_sem_harm;
const varComHarm = dinnerIds.jantar_com_harm;
const parentId = dinnerIds.jantar_produto_pai;
if (!varSemHarm || !varComHarm || !parentId) {
setError("Produto não configurado. Fale com a gente pelo WhatsApp.");
setLoading(false);
return;
}
const reservationId = getReservationIdFromUrl();
const semHarmCount = guests.filter((g) => !g.harmonizado).length;
const comHarmCount = guests.filter((g) => g.harmonizado).length;
// Salva dados do jantar no sessionStorage para o checkout usar
const allGuestData = guests.map((g, i) => ({
pessoa : i + 1,
harmonizado : g.harmonizado,
entrada : ENTRADAS.find((e) => e.id === g.entrada)?.title || "—",
principal : PRINCIPAIS.find((p) => p.id === g.principal)?.title || "—",
sobremesa : SOBREMESAS.find((s) => s.id === g.sobremesa)?.title || "—",
}));
sessionStorage.setItem("zuzu_jd_dinner_guests", JSON.stringify(allGuestData));
if (reservationId) sessionStorage.setItem("zuzu_jd_reservation_id", String(reservationId));
// Usa URL direta — mais confiável que AJAX para produtos variáveis
const base = window.location.origin;
const checkout = cfg.wcCheckoutUrl || (base + "/checkout/");
const semVal = encodeURIComponent("Sem harmonização");
const comVal = encodeURIComponent("Com harmonização de vinhos e espumantes");
const ridParam = reservationId ? "&rid=" + reservationId : "";
let addUrl;
if (comHarmCount > 0 && semHarmCount === 0) {
// Todos com harmonização
addUrl = base + "/?add-to-cart=" + parentId
+ "&variation_id=" + varComHarm
+ "&quantity=" + comHarmCount
+ "&attribute_harmonizacao=" + comVal
+ ridParam + "&checkout=1";
} else if (semHarmCount > 0 && comHarmCount === 0) {
// Todos sem harmonização
addUrl = base + "/?add-to-cart=" + parentId
+ "&variation_id=" + varSemHarm
+ "&quantity=" + semHarmCount
+ "&attribute_harmonizacao=" + semVal
+ ridParam + "&checkout=1";
} else {
// Mistos — passa os dois grupos via parâmetro extra que o PHP vai processar
// O hook zuzu_jd_handle_mixed_cart lê zuzu_jd_add2 e adiciona o segundo grupo
addUrl = base + "/?add-to-cart=" + parentId
+ "&variation_id=" + varSemHarm
+ "&quantity=" + semHarmCount
+ "&attribute_harmonizacao=" + semVal
+ "&zuzu_jd_add2=" + varComHarm
+ "&zuzu_jd_add2_qty=" + comHarmCount
+ "&zuzu_jd_add2_attr=" + comVal
+ ridParam + "&checkout=1";
}
window.location.href = addUrl;
}
/* ── render ── */
const drawerStyle = {
position : "fixed",
top : 0,
right : open ? 0 : "-100%",
width : "min(460px, 100vw)",
height : "100dvh",
background : "var(--paper)",
boxShadow : "-4px 0 40px rgba(0,0,0,0.12)",
display : "flex",
flexDirection : "column",
zIndex : 1100,
transition : "right .3s cubic-bezier(.4,0,.2,1)",
overflowY : "auto",
};
const scrimStyle = {
position : "fixed",
inset : 0,
background : "rgba(0,0,0,0.35)",
zIndex : 1099,
opacity : open ? 1 : 0,
pointerEvents : open ? "auto" : "none",
transition : "opacity .3s",
};
return (
<>
>
);
}
Object.assign(window, { DinnerDrawer, DINNER_MENU: { ENTRADAS, PRINCIPAIS, SOBREMESAS, PRICE_SEM_HARM, PRICE_COM_HARM } });