const BusinessStats = ({ stats, biz, onClose, onBizUpdate, onPinVerified }) => {
  const t = useT();
  const plt = usePLT();
  const [pinVerified, setPinVerified] = useState(false);
  const [pinInput, setPinInput] = useState('');
  const [pinLoading, setPinLoading] = useState(false);
  const [pinError, setPinError] = useState('');
  const [clientsOpen, setClientsOpen] = useState(false);
  const [filter, setFilter] = useState('all');
  const [analyticsOpen, setAnalyticsOpen] = useState(false);

  // ── Config: VIP Perk ────────────────────────────────────────────────
  const [editingPromo, setEditingPromo] = useState(false);
  const [promoPin, setPromoPin] = useState('');
  const [promoRewardEs, setPromoRewardEs] = useState('');
  const [promoRewardEn, setPromoRewardEn] = useState('');
  const [promoGoal, setPromoGoal] = useState('');
  const [promoLoading, setPromoLoading] = useState(false);
  const [promoError, setPromoError] = useState('');
  const [promoSuccess, setPromoSuccess] = useState(false);

  // ── Config: Birthday Gift ────────────────────────────────────────────
  const [bdayOpen, setBdayOpen] = useState(false);
  const [bdayActive, setBdayActive] = useState(false);
  const [bdayGift, setBdayGift] = useState('');
  const [bdayTerms, setBdayTerms] = useState('');
  const [bdayRedeemPin, setBdayRedeemPin] = useState('');
  const [bdayHasPin, setBdayHasPin] = useState(false);
  const [bdaySaving, setBdaySaving] = useState(false);
  const [bdaySaveError, setBdaySaveError] = useState('');
  const [bdaySaved, setBdaySaved] = useState(false);

  // ── Config: Promos por Día ────────────────────────────────────────────
  const [dailyPromosOpen, setDailyPromosOpen] = useState(false);
  const [dailyPromos, setDailyPromos] = useState(Array.from({ length:7 }, (_, i) => ({ day_of_week:i, name_es:'', name_en:'', active:false })));
  const [dailyPromosSaving, setDailyPromosSaving] = useState({});
  const [dailyPromosSaved, setDailyPromosSaved] = useState({});
  const [dailyPromosError, setDailyPromosError] = useState({});

  // ── Config: Catálogo ─────────────────────────────────────────────
  const [menuOpen, setMenuOpen] = useState(false);
  const [menuItems, setMenuItems] = useState([]);
  const [menuLoading, setMenuLoading] = useState(false);
  const [menuAddOpen, setMenuAddOpen] = useState(false);
  const [menuForm, setMenuForm] = useState({ name_es:'', description_es:'', item_type:'food', category:'otros', price:'', image_url:'', external_booking_url:'' });
  const [menuFormSaving, setMenuFormSaving] = useState(false);
  const [menuFormError, setMenuFormError] = useState('');
  const [menuImageUploading, setMenuImageUploading] = useState(false);
  const menuFileRef = useRef(null);
  const [menuEditItem, setMenuEditItem] = useState(null);
  const [menuEditForm, setMenuEditForm] = useState({ name_es:'', description_es:'', item_type:'food', category:'otros', price:'', image_url:'', external_booking_url:'' });
  const [menuEditSaving, setMenuEditSaving] = useState(false);
  const [menuEditError, setMenuEditError] = useState('');
  const [menuEditImageUploading, setMenuEditImageUploading] = useState(false);
  const menuEditFileRef = useRef(null);

  const MENU_CATEGORIES = [
    { key:'alimentos',    label:'Alimentos',    emoji:'🍽' },
    { key:'bebidas',      label:'Bebidas',      emoji:'🥤' },
    { key:'postres',      label:'Postres',      emoji:'🍰' },
    { key:'tours',        label:'Tours',        emoji:'🗺️' },
    { key:'servicios',    label:'Servicios',    emoji:'✂️' },
    { key:'experiencias', label:'Experiencias', emoji:'🤿' },
    { key:'hospedaje',    label:'Hospedaje',    emoji:'🏡' },
    { key:'otros',        label:'Otros',        emoji:'📦' },
  ];

  const loadMenu = async () => {
    setMenuLoading(true);
    try {
      const res = await fetch(`${API}/business/${biz.id}/menu`);
      const data = await res.json();
      const flat = (data.categories || []).flatMap(cat =>
        cat.items.map(item => ({ ...item, _catKey: cat.key, _catLabel: cat.label?.es || cat.key }))
      );
      setMenuItems(flat);
    } catch(_) {}
    setMenuLoading(false);
  };

  const toggleAvailable = async (item) => {
    const newVal = !item.available;
    setMenuItems(prev => prev.map(i => i.id === item.id ? { ...i, available: newVal } : i));
    fetch(`${API}/menu/${item.id}`, {
      method: 'PATCH',
      headers: { 'Content-Type':'application/json', 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput },
      body: JSON.stringify({ available: newVal ? 1 : 0 }),
    }).catch(() => {});
  };

  const deleteMenuItem = async (itemId) => {
    setMenuItems(prev => prev.filter(i => i.id !== itemId));
    fetch(`${API}/menu/${itemId}`, {
      method: 'DELETE',
      headers: { 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput },
    }).catch(() => {});
  };

  const handleMenuImagePick = async (e) => {
    const file = e.target.files?.[0];
    if (!file) return;
    setMenuImageUploading(true);
    try {
      const res = await fetch(`${API}/business/menu/image?id=${biz.id}`, {
        method: 'PUT',
        headers: { 'Content-Type': file.type, 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput },
        body: file,
      });
      const data = await res.json();
      if (data.publicUrl) setMenuForm(prev => ({ ...prev, image_url: data.publicUrl }));
    } catch(_) {}
    setMenuImageUploading(false);
    e.target.value = '';
  };

  const handleAddMenuItem = async () => {
    if (!menuForm.name_es.trim()) { setMenuFormError('El nombre es obligatorio'); return; }
    if (menuForm.price === '') { setMenuFormError('El precio es obligatorio'); return; }
    if (menuForm.item_type === 'accommodation' && !menuForm.external_booking_url.trim()) {
      setMenuFormError('La URL de reserva es obligatoria para hospedaje');
      return;
    }
    setMenuFormSaving(true); setMenuFormError('');
    try {
      const res = await fetch(`${API}/business/menu`, {
        method: 'POST',
        headers: { 'Content-Type':'application/json', 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput },
        body: JSON.stringify({
          id: biz.id,
          name_es: menuForm.name_es.trim(),
          description_es: menuForm.description_es.trim(),
          item_type: menuForm.item_type,
          category: menuForm.category,
          price: parseFloat(menuForm.price) || 0,
          image_url: menuForm.image_url || null,
          external_booking_url: menuForm.external_booking_url.trim() || null,
        }),
      });
      const data = await res.json();
      if (!res.ok) { setMenuFormError(data.error || 'Error'); setMenuFormSaving(false); return; }
      setMenuAddOpen(false);
      setMenuForm({ name_es:'', description_es:'', item_type:'food', category:'otros', price:'', image_url:'', external_booking_url:'' });
      loadMenu();
    } catch(_) { setMenuFormError('Error de conexión'); }
    setMenuFormSaving(false);
  };

  const openEditItem = (item) => {
    setMenuEditForm({
      name_es: item.translations?.es?.name || '',
      description_es: item.translations?.es?.description || '',
      item_type: item.item_type || 'food',
      category: item.category || 'otros',
      price: String(item.price ?? ''),
      image_url: item.image_url || '',
      external_booking_url: item.external_booking_url || '',
    });
    setMenuEditError('');
    setMenuEditItem(item);
  };

  const handleMenuEditImagePick = async (e) => {
    const file = e.target.files?.[0];
    if (!file) return;
    setMenuEditImageUploading(true);
    try {
      const res = await fetch(`${API}/business/menu/image?id=${biz.id}`, {
        method: 'PUT',
        headers: { 'Content-Type': file.type, 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput },
        body: file,
      });
      if (!res.ok) throw new Error();
      const { url } = await res.json();
      setMenuEditForm(prev => ({ ...prev, image_url: url }));
    } catch(_) { alert('Error subiendo imagen'); }
    finally { setMenuEditImageUploading(false); e.target.value = ''; }
  };

  const handleEditMenuItem = async () => {
    if (!menuEditForm.name_es.trim()) { setMenuEditError('El nombre es obligatorio'); return; }
    if (menuEditForm.price === '') { setMenuEditError('El precio es obligatorio'); return; }
    if (menuEditForm.item_type === 'accommodation' && !menuEditForm.external_booking_url.trim()) {
      setMenuEditError('La URL de reserva es obligatoria para hospedaje'); return;
    }
    setMenuEditSaving(true); setMenuEditError('');
    try {
      const body = {
        name_es: menuEditForm.name_es.trim(),
        description_es: menuEditForm.description_es.trim(),
        item_type: menuEditForm.item_type,
        category: menuEditForm.category,
        price: parseFloat(menuEditForm.price) || 0,
        image_url: menuEditForm.image_url || null,
        external_booking_url: menuEditForm.item_type === 'accommodation' ? menuEditForm.external_booking_url.trim() || null : null,
      };
      const res = await fetch(`${API}/menu/${menuEditItem.id}`, {
        method: 'PATCH',
        headers: { 'Content-Type':'application/json', 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput },
        body: JSON.stringify(body),
      });
      if (!res.ok) throw new Error();
      const data = await res.json();
      setMenuItems(prev => prev.map(it => it.id === menuEditItem.id ? {
        ...it,
        item_type: body.item_type,
        category: body.category,
        price: body.price,
        image_url: body.image_url,
        external_booking_url: body.external_booking_url,
        translations: { ...it.translations, es: { name: body.name_es, description: body.description_es } },
        translations_ready: data.retranslated ? 0 : it.translations_ready,
        _catLabel: MENU_CATEGORIES.find(c => c.key === body.category)?.label || body.category,
      } : it));
      setMenuEditItem(null);
    } catch(_) { setMenuEditError('Error guardando, intenta de nuevo'); }
    finally { setMenuEditSaving(false); }
  };

  const handleOpenBday = async () => {
    setBdaySaveError('');
    try {
      const res = await fetch(`${API}/business/promo/load`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ id: biz.id, code: biz.code, pin: pinInput }),
      });
      const data = await res.json();
      if (!res.ok) { setBdaySaveError(data.error || 'Error'); return; }
      setBdayActive(!!data.birthday_active);
      setBdayGift(data.birthday_gift || '');
      setBdayTerms(data.birthday_terms || '');
      setBdayRedeemPin('');
      setBdayHasPin(!!data.has_redeem_pin);
      if (data.birthday_gift) setBdaySaved(true);
      setBdayOpen(true);
    } catch(_) { setBdaySaveError(t('biz_conn_error')); }
  };

  // Auto-load daily promos once Command Center PIN is verified
  useEffect(() => {
    if (!pinVerified || !pinInput || !biz?.id) return;
    fetch(`${API}/business/daily-promos?id=${biz.id}`, {
      headers: { 'X-Biz-Code': biz.code, 'X-Biz-Pin': pinInput }
    })
      .then(r => r.ok ? r.json() : null)
      .then(rows => {
        if (!Array.isArray(rows)) return;
        setDailyPromos(prev => {
          const updated = [...prev];
          rows.forEach(r => {
            const idx = r.day_of_week;
            if (idx >= 0 && idx < 7) {
              updated[idx] = { day_of_week: idx, name_es: r.name_es || '', name_en: r.name_en || '', active: !!r.active };
            }
          });
          return updated;
        });
      })
      .catch(() => {});
  }, [pinVerified]);

  // Auto-load menu once Command Center PIN is verified
  useEffect(() => {
    if (!pinVerified || !biz?.id) return;
    loadMenu();
  }, [pinVerified]);

  // Auto-load birthday status once Command Center PIN is verified
  useEffect(() => {
    if (!pinVerified || !pinInput || !biz?.id) return;
    fetch(`${API}/business/promo/load`, {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({ id: biz.id, code: biz.code, pin: pinInput }),
    })
      .then(r => r.ok ? r.json() : null)
      .then(data => {
        if (!data) return;
        setBdayActive(!!data.birthday_active);
        setBdayGift(data.birthday_gift || '');
        setBdayTerms(data.birthday_terms || '');
        setBdayRedeemPin('');
        setBdayHasPin(!!data.has_redeem_pin);
        if (data.birthday_gift) setBdaySaved(true);
      })
      .catch(() => {});
  }, [pinVerified]);

  const handleSaveDayPromo = async (dayIdx) => {
    const entry = dailyPromos[dayIdx];
    if (entry.active && !entry.name_es.trim()) {
      setDailyPromosError(prev => ({ ...prev, [dayIdx]: 'La descripción no puede estar vacía' }));
      return;
    }
    setDailyPromosSaving(prev => ({ ...prev, [dayIdx]: true }));
    setDailyPromosError(prev => ({ ...prev, [dayIdx]: '' }));
    setDailyPromosSaved(prev => ({ ...prev, [dayIdx]: false }));
    try {
      const res = await fetch(`${API}/business/daily-promos`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ id: biz.id, code: biz.code, pin: pinInput, day_of_week: dayIdx, name_es: entry.name_es, name_en: entry.name_en || '', active: entry.active }),
      });
      if (!res.ok) { const d = await res.json(); setDailyPromosError(prev => ({ ...prev, [dayIdx]: d.error || 'Error' })); }
      else setDailyPromosSaved(prev => ({ ...prev, [dayIdx]: true }));
    } catch(_) { setDailyPromosError(prev => ({ ...prev, [dayIdx]: t('biz_conn_error') })); }
    setDailyPromosSaving(prev => ({ ...prev, [dayIdx]: false }));
  };

  const handleSaveBdayPromo = async () => {
    setBdaySaving(true); setBdaySaveError(''); setBdaySaved(false);
    if (bdayActive && bdayRedeemPin.length < 4 && !bdayHasPin) {
      setBdaySaveError(t('biz_birthday_pin_required'));
      setBdaySaving(false);
      return;
    }
    try {
      const res = await fetch(`${API}/business/promo`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ id: biz.id, code: biz.code, pin: pinInput, birthday_active: bdayActive, birthday_gift: bdayGift, birthday_terms: bdayTerms, birthday_redeem_pin: bdayRedeemPin }),
      });
      const data = await res.json();
      if (!res.ok) { setBdaySaveError(data.error); setBdaySaving(false); return; }
      setBdaySaved(true);
      setBdayOpen(false);
    } catch(_) { setBdaySaveError(t('biz_conn_error')); }
    setBdaySaving(false);
  };

  const handleSavePromo = async () => {
    setPromoLoading(true); setPromoError(''); setPromoSuccess(false);
    try {
      const res = await fetch(`${API}/business/update-promo`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ id: biz.id, code: biz.code, pin: promoPin, reward: JSON.stringify({ es: promoRewardEs.trim(), en: promoRewardEn.trim() }), reward_goal: promoGoal }),
      });
      const data = await res.json();
      if (!res.ok) { setPromoError(data.error); setPromoLoading(false); return; }
      const updatedBiz = { ...biz, reward: data.reward, reward_goal: data.reward_goal };
      try { localStorage.setItem('helixBiz', JSON.stringify(updatedBiz)); } catch(_){}
      if (onBizUpdate) onBizUpdate(updatedBiz);
      setPromoSuccess(true);
      setEditingPromo(false);
    } catch(e) { setPromoError(t('biz_conn_error')); }
    setPromoLoading(false);
  };

  const clients = stats?.clients || [];
  // SQLite returns "YYYY-MM-DD HH:MM:SS" (space). new Date() with a space is Invalid
  // in Safari — replace space with T to force unambiguous local-time ISO parse.
  const pd = s => new Date((s || '').replace(' ', 'T'));

  const DAY_SHORT = t('biz_days_short').split(',');
  const days = Array.from({ length: 7 }, (_, i) => {
    const d = new Date(); d.setDate(d.getDate() - (6 - i)); return d;
  });
  const toISO = d => {
    const y = d.getFullYear();
    const m = String(d.getMonth() + 1).padStart(2, '0');
    const dd = String(d.getDate()).padStart(2, '0');
    return `${y}-${m}-${dd}`;
  };
  const curMap = {};
  (stats?.current_week || []).forEach(r => { curMap[r.day] = r.n; });
  const prevMap = {};
  (stats?.prev_week || []).forEach(r => { prevMap[r.day] = r.n; });
  const dailyData = days.map(d => {
    const prevDay = new Date(d); prevDay.setDate(prevDay.getDate() - 7);
    return {
      name: `${DAY_SHORT[d.getDay()]} ${d.getDate()}/${d.getMonth() + 1}`,
      visitas:  curMap[toISO(d)]       || 0,
      anterior: prevMap[toISO(prevDay)] || 0,
    };
  });
  const HOUR_SLOTS = [[8,10],[10,12],[12,14],[14,16],[16,18],[18,20],[20,22]];
  const hourlyData = HOUR_SLOTS.map(([s, e]) => ({
    name: `${s}–${e}`,
    visitas: clients.filter(c => { const h = pd(c.last_visit).getHours(); return h >= s && h < e; }).length,
  }));
  const peakIdx = hourlyData.reduce((mi, b, i, a) => b.visitas > a[mi].visitas ? i : mi, 0);
  const quietSlot = hourlyData.reduce((mn, b) => b.visitas < mn.visitas ? b : mn, hourlyData[0]);
  const opportunityMsg = (() => {
    if (hourlyData[peakIdx].visitas === 0) return null;
    const [pStart, pEnd] = HOUR_SLOTS[peakIdx];
    const twoDaysAgo = Date.now() - 2 * 86400000;
    const peakHasRecent = clients.some(c => {
      const d = pd(c.last_visit);
      return d.getTime() > twoDaysAgo && d.getHours() >= pStart && d.getHours() < pEnd;
    });
    if (peakHasRecent && hourlyData[peakIdx].visitas >= 2)
      return t('biz_opportunity_growth', { slot: hourlyData[peakIdx].name });
    if (quietSlot.visitas < hourlyData[peakIdx].visitas * 0.4)
      return t('biz_opportunity_low', { slot: quietSlot.name });
    return null;
  })();

  const insight = (() => {
    const thisWeekN    = dailyData.reduce((s, d) => s + d.visitas,  0);
    const prevWeekTot  = dailyData.reduce((s, d) => s + d.anterior, 0);
    if (thisWeekN === 0) return { fact: t('biz_si_empty_f'), action: t('biz_si_empty_a') };

    const frequentN  = clients.filter(c => c.visits >= 5).length;
    const newN       = clients.filter(c => c.visits === 1).length;
    const peak       = hourlyData[peakIdx];
    const hourlyTot  = hourlyData.reduce((s, h) => s + h.visitas, 0);
    const peakPct    = hourlyTot > 0 ? Math.round(peak.visitas / hourlyTot * 100) : 0;
    const freqVisits = clients.filter(c => c.visits >= 5).reduce((s, c) => s + c.visits, 0);
    const loyalPct   = (stats?.total_visits || 0) > 0
      ? Math.round(freqVisits / stats.total_visits * 100) : 0;

    // Week-over-week (real DB data, highest confidence)
    const wowPct = prevWeekTot > 0
      ? Math.round(((thisWeekN - prevWeekTot) / prevWeekTot) * 100) : null;

    // Intra-week fallback (when no prev week data yet)
    const early = dailyData.slice(0, 3).reduce((s, d) => s + d.visitas, 0);
    const late  = dailyData.slice(4).reduce((s, d) => s + d.visitas, 0);
    const pct   = early > 0 ? Math.round(((late - early) / early) * 100) : null;

    // P1: loyalty base strong, acquisition stalled
    if (frequentN >= 2 && newN < frequentN) return {
      fact:   t('biz_si_loyal_f', { freq: frequentN, loyalPct }),
      action: t('biz_si_loyal_a', { new: newN }),
    };
    // P2: week-over-week growth (real comparison)
    if (wowPct !== null && wowPct >= 10) return {
      fact:   t('biz_si_wow_up_f', { pct: wowPct }),
      action: t('biz_si_wow_up_a', { slot: peak.name }),
    };
    // P3: week-over-week decline (real comparison)
    if (wowPct !== null && wowPct <= -10) return {
      fact:   t('biz_si_wow_dn_f', { pct: Math.abs(wowPct) }),
      action: t('biz_si_wow_dn_a'),
    };
    // P4: intra-week growth (fallback, no prev week data)
    if (pct !== null && pct >= 20) return {
      fact:   t('biz_si_growth_f', { pct }),
      action: t('biz_si_growth_a', { slot: peak.name }),
    };
    // P5: intra-week decline
    if (pct !== null && pct <= -20) return {
      fact:   t('biz_si_decline_f', { pct: Math.abs(pct) }),
      action: frequentN > 0
        ? t('biz_si_decline_a_freq', { freq: frequentN })
        : t('biz_si_decline_a_nofq', { slot: peak.name }),
    };
    // Default: peak concentration
    return {
      fact:   t('biz_si_peak_f', { n: thisWeekN, peakPct, slot: peak.name }),
      action: t('biz_si_peak_a', { slot: peak.name }),
    };
  })();

  const maxVReal = Math.max(...clients.map(c => c.visits), 0);
  const getTag = (c) => {
    if (c.visits === maxVReal && maxVReal >= 3) return { label: t('biz_tag_topfan'),    color: '#b45309',    bg: 'rgba(180,83,9,0.1)'   };
    if (c.visits >= 5)                          return { label: t('biz_tag_frequent'),  color:'var(--teal)', bg: 'rgba(13,148,136,0.1)' };
    if ((Date.now() - pd(c.last_visit).getTime()) < 259200000)
                                                return { label: t('biz_tag_recent'),    color: '#7c3aed',    bg: 'rgba(124,58,237,0.1)' };
    return null;
  };
  const weekAgo = new Date(Date.now() - 604800000);
  const filteredClients = (() => {
    if (filter === 'recent') {
      return [...clients]
        .filter(c => pd(c.last_visit) >= weekAgo)
        .sort((a, b) => pd(b.last_visit) - pd(a.last_visit));
    }
    const sorted = [...clients].sort((a, b) => b.visits - a.visits);
    if (filter === 'top') return sorted.filter(c => c.visits >= 3);
    return sorted;
  })();

  const handlePinSubmit = async () => {
    if (pinInput.length < 6 || pinLoading) return;
    setPinLoading(true); setPinError('');
    try {
      const res = await fetch(`${API}/business/login`, {
        method: 'POST', headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ code: biz.code, pin: pinInput }),
      });
      if (res.ok) { setPinVerified(true); onPinVerified?.(pinInput); }
      else { const d = await res.json(); setPinError(d.error || 'PIN incorrecto'); }
    } catch(_) { setPinError(t('biz_conn_error')); }
    setPinLoading(false);
  };

  const { AreaChart, Area, XAxis, YAxis, Tooltip, ResponsiveContainer,
          BarChart: RechartBar, Bar, CartesianGrid, Cell, LabelList } = window.Recharts || {};

  // ── PIN Gate ──────────────────────────────────────────────────────────────
  if (!pinVerified) return ReactDOM.createPortal(
    <div style={{ position:'fixed', inset:0, zIndex:300, background:'var(--ink)', display:'flex', flexDirection:'column', animation:'fadeIn .2s ease both' }}>
      <div style={{ padding:'18px 24px', display:'flex', alignItems:'center', gap:12 }}>
        <button onClick={onClose} style={{ background:'rgba(255,255,255,0.1)', border:0, borderRadius:99, padding:8, cursor:'pointer', display:'flex' }}>
          <IconArrowLeft size={18} color="white"/>
        </button>
        <div style={{ color:'rgba(255,255,255,0.45)', fontSize:12, fontWeight:700, letterSpacing:'.1em', textTransform:'uppercase' }}>
          {t('biz_stats_title')}
        </div>
      </div>
      <div style={{ flex:1, display:'flex', flexDirection:'column', alignItems:'center', justifyContent:'center', padding:'32px 24px' }}>
        <div style={{ marginBottom:16, opacity:.35 }}><IconLock size={40} color="white"/></div>
        <h2 style={{ color:'white', fontWeight:800, fontSize:22, margin:'0 0 10px', letterSpacing:'-0.02em', textAlign:'center' }}>
          {t('biz_pin_gate_title')}
        </h2>
        <p style={{ color:'rgba(255,255,255,0.4)', fontSize:14, margin:'0 0 36px', textAlign:'center', lineHeight:1.6, maxWidth:280 }}>
          {t('biz_pin_gate_sub')}
        </p>
        <div style={{ width:'100%', maxWidth:320 }}>
          <input
            value={pinInput}
            onChange={e => { setPinInput(e.target.value.replace(/\D/g,'').slice(0,6)); setPinError(''); }}
            onKeyDown={e => e.key === 'Enter' && handlePinSubmit()}
            placeholder="● ● ● ● ● ●"
            type="password"
            inputMode="numeric"
            autoComplete="new-password"
            autoFocus
            style={{ width:'100%', boxSizing:'border-box', background:'rgba(255,255,255,0.07)', border:'1px solid rgba(255,255,255,0.1)', borderRadius:14, padding:'16px', fontSize:22, letterSpacing:'.4em', color:'white', outline:'none', textAlign:'center', marginBottom:8 }}
          />
          {pinError && <div style={{ color:'#fca5a5', fontSize:12, fontWeight:600, marginBottom:8, textAlign:'center' }}>{pinError}</div>}
          <button
            onClick={handlePinSubmit}
            disabled={pinLoading || pinInput.length < 6}
            style={{ width:'100%', background:'var(--teal)', border:0, borderRadius:14, padding:'16px', color:'white', fontWeight:700, fontSize:15, cursor:'pointer', opacity: pinLoading || pinInput.length < 6 ? 0.5 : 1 }}
          >
            {pinLoading ? t('biz_verifying') : t('biz_pin_enter')}
          </button>
        </div>
      </div>
    </div>,
    document.body
  );

  // ── Command Center ────────────────────────────────────────────────────────
  return (<>
  {ReactDOM.createPortal(
    <div style={{ position:'fixed', inset:0, zIndex:300, background:'rgba(15,23,42,0.72)', backdropFilter:'blur(6px)', WebkitBackdropFilter:'blur(6px)', display:'flex', flexDirection:'column', animation:'fadeIn .2s ease both' }}>
      <div className="scroll-panel" style={{ flex:1, background:'rgba(251,249,243,0.97)', backdropFilter:'blur(24px)', WebkitBackdropFilter:'blur(24px)', overflowY:'auto' }}>

        <div style={{ position:'sticky', top:0, zIndex:10, background:'rgba(251,249,243,0.95)', backdropFilter:'blur(12px)', WebkitBackdropFilter:'blur(12px)' }}>
          <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center', padding:'18px 24px 12px' }}>
            <div>
              <div className="label-eyebrow" style={{ color:'var(--teal)', marginBottom:2 }}>{t('biz_cmd_center')}</div>
              <div style={{ fontWeight:800, fontSize:17, letterSpacing:'-0.02em' }}>{biz.name}</div>
            </div>
            <button onClick={onClose} style={{ background:'var(--fog)', border:0, borderRadius:99, padding:8, cursor:'pointer', display:'flex' }}>
              <IconX size={18}/>
            </button>
          </div>
          <div style={{ background:'linear-gradient(135deg,#0D9488,#06B6D4)', padding:'14px 24px' }}>
            <div style={{ fontSize:9, fontWeight:700, letterSpacing:'.12em', textTransform:'uppercase', color:'rgba(255,255,255,0.65)', marginBottom:5 }}>
              {t('biz_insight_moment')}
            </div>
            <div style={{ fontSize:13, color:'rgba(255,255,255,0.88)', lineHeight:1.55, marginBottom:3 }}>{insight.fact}</div>
            <div style={{ fontSize:13, fontWeight:700, color:'white', lineHeight:1.5 }}>→ {insight.action}</div>
          </div>
        </div>

        <div style={{ padding:'24px', display:'flex', flexDirection:'column', gap:24 }}>

          <div>
            <div className="label-eyebrow" style={{ marginBottom:12 }}>{t('biz_stats_week')}</div>
            <div style={{ background:'var(--fog)', borderRadius:14, padding:'16px 10px 8px', border:'1px solid rgba(15,23,42,0.06)' }}>
              {ResponsiveContainer ? (
                <ResponsiveContainer width="100%" height={150}>
                  <AreaChart data={dailyData} margin={{ top:5, right:8, left:-28, bottom:0 }}>
                    <defs>
                      <linearGradient id="tealArea" x1="0" y1="0" x2="0" y2="1">
                        <stop offset="5%" stopColor="#0D9488" stopOpacity={0.25}/>
                        <stop offset="95%" stopColor="#0D9488" stopOpacity={0}/>
                      </linearGradient>
                    </defs>
                    <CartesianGrid strokeDasharray="3 3" stroke="rgba(15,23,42,0.05)" vertical={false}/>
                    <XAxis dataKey="name" tick={{ fontSize:10, fill:'#6B7280' }} axisLine={false} tickLine={false}/>
                    <YAxis tick={{ fontSize:10, fill:'#6B7280' }} axisLine={false} tickLine={false} allowDecimals={false}/>
                    <Tooltip contentStyle={{ background:'#FBF9F3', border:'1px solid rgba(15,23,42,0.1)', borderRadius:10, fontSize:12, boxShadow:'0 4px 12px rgba(0,0,0,0.08)' }} cursor={{ stroke:'rgba(13,148,136,0.15)', strokeWidth:1 }}/>
                    <Area type="monotone" dataKey="anterior" name={t('biz_legend_prev')} stroke="rgba(156,163,175,0.65)" strokeWidth={1.5} strokeDasharray="4 3" fill="none" dot={false} activeDot={{ r:4, fill:'rgba(156,163,175,0.8)', strokeWidth:0 }}/>
                    <Area type="monotone" dataKey="visitas" name={t('biz_legend_current')} stroke="#0D9488" strokeWidth={2.5} fill="url(#tealArea)" dot={false} activeDot={{ r:5, fill:'#0D9488', strokeWidth:0 }}/>
                  </AreaChart>
                </ResponsiveContainer>
              ) : (
                <div style={{ height:150, display:'flex', alignItems:'center', justifyContent:'center', color:'var(--muted)', fontSize:12, textAlign:'center', padding:'0 20px', lineHeight:1.6 }}>
                  {t('biz_si_empty_f')}
                </div>
              )}
              <div style={{ display:'flex', gap:16, justifyContent:'center', paddingTop:6, paddingBottom:4 }}>
                <div style={{ display:'flex', alignItems:'center', gap:5 }}>
                  <div style={{ width:16, height:2.5, background:'#0D9488', borderRadius:2 }}/>
                  <span style={{ fontSize:10, color:'#6B7280' }}>{t('biz_legend_current')}</span>
                </div>
                <div style={{ display:'flex', alignItems:'center', gap:5 }}>
                  <svg width="16" height="3"><line x1="0" y1="1.5" x2="16" y2="1.5" stroke="rgba(156,163,175,0.75)" strokeWidth="1.5" strokeDasharray="4 3"/></svg>
                  <span style={{ fontSize:10, color:'#6B7280' }}>{t('biz_legend_prev')}</span>
                </div>
              </div>
            </div>
          </div>

          <div>
            <div className="label-eyebrow" style={{ marginBottom:12 }}>{t('biz_stats_hours')}</div>
            <div style={{ background:'var(--fog)', borderRadius:14, padding:'16px 10px 8px', border:'1px solid rgba(15,23,42,0.06)' }}>
              {RechartBar && Bar && ResponsiveContainer ? (
                <ResponsiveContainer width="100%" height={140}>
                  <RechartBar data={hourlyData} margin={{ top:22, right:8, left:-28, bottom:0 }} barSize={20}>
                    <CartesianGrid strokeDasharray="3 3" stroke="rgba(15,23,42,0.05)" vertical={false}/>
                    <XAxis dataKey="name" tick={{ fontSize:9, fill:'#6B7280' }} axisLine={false} tickLine={false}/>
                    <YAxis tick={{ fontSize:10, fill:'#6B7280' }} axisLine={false} tickLine={false} allowDecimals={false}/>
                    <Tooltip contentStyle={{ background:'#FBF9F3', border:'1px solid rgba(15,23,42,0.1)', borderRadius:10, fontSize:12, boxShadow:'0 4px 12px rgba(0,0,0,0.08)' }} cursor={{ fill:'rgba(6,182,212,0.06)' }}/>
                    <Bar dataKey="visitas" name={t('biz_vip_visits')} radius={[5,5,0,0]}>
                      {hourlyData.map((_, i) => (
                        <Cell key={i}
                          fill={i === peakIdx && hourlyData[peakIdx].visitas > 0 ? '#0D9488' : '#06B6D4'}
                          fillOpacity={i === peakIdx && hourlyData[peakIdx].visitas > 0 ? 1 : 0.6}
                        />
                      ))}
                      <LabelList content={(props) => {
                        const { x, y, width, index } = props;
                        if (index !== peakIdx || !hourlyData[peakIdx] || hourlyData[peakIdx].visitas === 0) return null;
                        return (
                          <text x={(x||0)+(width||0)/2} y={(y||0)-6} textAnchor="middle" fill="#0D9488" fontSize={8} fontWeight="700">
                            {t('biz_peak_label')}
                          </text>
                        );
                      }}/>
                    </Bar>
                  </RechartBar>
                </ResponsiveContainer>
              ) : null}
              {opportunityMsg && (
                <div style={{ margin:'8px 6px 4px', padding:'10px 12px', background:'rgba(13,148,136,0.06)', borderRadius:10, border:'1px solid rgba(13,148,136,0.12)' }}>
                  <div style={{ fontSize:10, fontWeight:700, color:'var(--teal)', marginBottom:2, textTransform:'uppercase', letterSpacing:'.06em' }}>{t('biz_opportunity_title')}</div>
                  <div style={{ fontSize:12, color:'#374151', lineHeight:1.55 }}>{opportunityMsg}</div>
                </div>
              )}
            </div>
          </div>

          <div>
            <button
              onPointerDown={(e) => { e.preventDefault(); setClientsOpen(v => !v); }}
              style={{ width:'100%', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.06)', borderRadius: clientsOpen ? '14px 14px 0 0' : 14, padding:'14px 16px', display:'flex', justifyContent:'space-between', alignItems:'center', cursor:'pointer', userSelect:'none' }}
            >
              <div style={{ fontWeight:700, fontSize:14 }}>{t('biz_clients')} · {clients.length}</div>
              <div style={{ color:'var(--muted)', transition:'transform .2s', transform: clientsOpen ? 'rotate(-90deg)' : 'rotate(90deg)' }}>
                <IconChevronRight size={16}/>
              </div>
            </button>
            {clientsOpen && (
              <div style={{ background:'var(--fog)', border:'1px solid rgba(15,23,42,0.06)', borderTop:0, borderRadius:'0 0 14px 14px', padding:'12px 14px' }}>
                <div style={{ display:'flex', gap:6, marginBottom:14 }}>
                  {[['all', t('biz_filter_all')],['top', t('biz_filter_top')],['recent', t('biz_filter_recent')]].map(([v,l]) => (
                    <button key={v} onClick={() => setFilter(v)} style={{ background: filter === v ? 'var(--ink)' : 'transparent', color: filter === v ? 'white' : 'var(--muted)', border: filter === v ? 0 : '1px solid rgba(15,23,42,0.15)', borderRadius:99, padding:'9px 14px', minHeight:38, fontSize:12, fontWeight:700, cursor:'pointer', whiteSpace:'nowrap' }}>{l}</button>
                  ))}
                </div>
                <div style={{ display:'flex', flexDirection:'column', gap:8 }}>
                  {filteredClients.length === 0 && (
                    <div style={{ textAlign:'center', color:'var(--muted)', fontSize:13, padding:'16px 0' }}>{t('biz_no_visits')}</div>
                  )}
                  {filteredClients.map((c, i) => {
                    const tag = getTag(c);
                    return (
                      <div key={i} style={{ background:'white', borderRadius:12, padding:'12px 14px', border:'1px solid rgba(15,23,42,0.06)', display:'flex', justifyContent:'space-between', alignItems:'center' }}>
                        <div>
                          <div style={{ fontWeight:700, fontSize:14 }}>{c.name}</div>
                          {tag && <div style={{ fontSize:10, fontWeight:700, color:tag.color, background:tag.bg, display:'inline-block', padding:'2px 7px', borderRadius:99, marginTop:3 }}>{tag.label}</div>}
                        </div>
                        <div style={{ textAlign:'right' }}>
                          <div style={{ fontWeight:700, fontSize:14, color:'var(--teal)' }}>{c.visits} {c.visits === 1 ? t('passport_visit_s') : t('passport_visit_p')}</div>
                          <div style={{ fontSize:10, color:'var(--muted)', marginTop:2 }}>{new Date(c.last_visit).toLocaleDateString()}</div>
                        </div>
                      </div>
                    );
                  })}
                </div>
              </div>
            )}
          </div>

          {/* ── Catálogo ── */}
          <div>
            <button
              onPointerDown={(e) => { e.preventDefault(); setMenuOpen(v => !v); if (!menuOpen) loadMenu(); }}
              style={{ width:'100%', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.06)', borderRadius: menuOpen ? '14px 14px 0 0' : 14, padding:'14px 16px', display:'flex', justifyContent:'space-between', alignItems:'center', cursor:'pointer', userSelect:'none' }}
            >
              <div style={{ fontWeight:700, fontSize:14 }}>📦 Catálogo · {menuItems.length}</div>
              <div style={{ color:'var(--muted)', transition:'transform .2s', transform: menuOpen ? 'rotate(-90deg)' : 'rotate(90deg)' }}>
                <IconChevronRight size={16}/>
              </div>
            </button>
            {menuOpen && (
              <div style={{ background:'var(--fog)', border:'1px solid rgba(15,23,42,0.06)', borderTop:0, borderRadius:'0 0 14px 14px', padding:'14px' }}>
                {menuLoading && <div style={{ textAlign:'center', color:'var(--muted)', fontSize:13, padding:'16px 0' }}>Cargando...</div>}
                {!menuLoading && menuItems.length === 0 && (
                  <div style={{ textAlign:'center', color:'var(--muted)', fontSize:13, padding:'16px 0', lineHeight:1.7 }}>
                    Aún no tienes ítems.<br/>Agrega el primero.
                  </div>
                )}
                <div style={{ display:'flex', flexDirection:'column', gap:8, marginBottom: menuItems.length > 0 ? 12 : 0 }}>
                  {menuItems.map(item => {
                    const name = item.translations?.es?.name || '';
                    const desc = item.translations?.es?.description || '';
                    return (
                      <div key={item.id} style={{ background:'white', borderRadius:12, padding:'12px 14px', border:`1px solid ${item.available ? 'rgba(15,23,42,0.06)' : 'rgba(185,28,28,0.15)'}`, display:'flex', gap:12, alignItems:'center' }}>
                        {item.image_url && (
                          <img src={item.image_url} alt="" style={{ width:52, height:52, objectFit:'cover', borderRadius:10, flexShrink:0 }}/>
                        )}
                        <div style={{ flex:1, minWidth:0 }}>
                          <div style={{ fontWeight:700, fontSize:14, display:'flex', alignItems:'center', gap:6, flexWrap:'wrap' }}>
                            {name}
                            {!item.translations_ready && (
                              <span style={{ fontSize:9, fontWeight:700, color:'#7c3aed', background:'rgba(124,58,237,0.08)', borderRadius:99, padding:'2px 6px', letterSpacing:'.04em', flexShrink:0 }}>🌐 TRAD</span>
                            )}
                          </div>
                          {desc && <div style={{ fontSize:11, color:'var(--muted)', marginTop:2, overflow:'hidden', textOverflow:'ellipsis', whiteSpace:'nowrap' }}>{desc}</div>}
                          <div style={{ display:'flex', alignItems:'center', gap:8, marginTop:4, flexWrap:'wrap' }}>
                            <span style={{ fontSize:12, fontWeight:700, color:'var(--teal)' }}>${item.price?.toLocaleString('es-MX')} MXN</span>
                            <span style={{ fontSize:10, color:'var(--muted)', background:'rgba(15,23,42,0.05)', borderRadius:99, padding:'2px 7px' }}>{item._catLabel}</span>
                          </div>
                        </div>
                        <div style={{ display:'flex', flexDirection:'column', alignItems:'center', gap:8, flexShrink:0 }}>
                          <button
                            onPointerDown={(e) => { e.preventDefault(); toggleAvailable(item); }}
                            style={{ width:38, height:22, borderRadius:11, position:'relative', border:0, cursor:'pointer', padding:0, background: item.available ? 'var(--teal)' : 'rgba(15,23,42,0.15)', transition:'background .2s', flexShrink:0 }}
                          >
                            <div style={{ position:'absolute', top:2, left: item.available ? 18 : 2, width:18, height:18, borderRadius:'50%', background:'white', transition:'left .2s', boxShadow:'0 1px 3px rgba(0,0,0,0.2)' }}/>
                          </button>
                          <button
                            onPointerDown={(e) => { e.preventDefault(); openEditItem(item); }}
                            style={{ background:'transparent', border:0, cursor:'pointer', padding:4, color:'var(--muted)', display:'flex' }}
                          >
                            <IconPencil size={14}/>
                          </button>
                          <button
                            onPointerDown={(e) => { e.preventDefault(); deleteMenuItem(item.id); }}
                            style={{ background:'transparent', border:0, cursor:'pointer', padding:4, color:'rgba(185,28,28,0.45)', display:'flex' }}
                          >
                            <IconX size={14}/>
                          </button>
                        </div>
                      </div>
                    );
                  })}
                </div>
                <button
                  onPointerDown={(e) => { e.preventDefault(); setMenuFormError(''); setMenuForm({ name_es:'', description_es:'', item_type:'food', category:'otros', price:'', image_url:'', external_booking_url:'' }); setMenuAddOpen(true); }}
                  style={{ width:'100%', background:'var(--teal)', color:'white', border:0, borderRadius:10, padding:'12px', fontWeight:700, fontSize:14, cursor:'pointer', display:'flex', alignItems:'center', justifyContent:'center', gap:8 }}
                >
                  + Agregar ítem
                </button>
              </div>
            )}
          </div>

          {/* ── Configuración colapsable (VIP Perk + Birthday Gift) ── */}
          <div>
            <button
              onPointerDown={(e) => { e.preventDefault(); setAnalyticsOpen(v => !v); }}
              style={{ width:'100%', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.06)', borderRadius: analyticsOpen ? '14px 14px 0 0' : 14, padding:'14px 16px', display:'flex', justifyContent:'space-between', alignItems:'center', cursor:'pointer', userSelect:'none' }}
            >
              <div style={{ fontWeight:700, fontSize:14 }}>⚙ {t('biz_promo_section')}</div>
              <div style={{ color:'var(--muted)', transition:'transform .2s', transform: analyticsOpen ? 'rotate(-90deg)' : 'rotate(90deg)' }}>
                <IconChevronRight size={16}/>
              </div>
            </button>
            {analyticsOpen && (
              <div style={{ background:'var(--fog)', border:'1px solid rgba(15,23,42,0.06)', borderTop:0, borderRadius:'0 0 14px 14px', padding:'16px 14px', display:'flex', flexDirection:'column', gap:20 }}>

                {/* VIP Perk */}
                <div>
                  <div className="label-eyebrow" style={{ marginBottom:10, padding:0 }}>{t('biz_vip_eyebrow')}</div>
                  <div style={{ background:'white', borderRadius:12, padding:'14px', border:'1px solid rgba(15,23,42,0.06)' }}>
                    {!editingPromo ? (
                      <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center' }}>
                        <div>
                          <div style={{ fontSize:13, color:'var(--muted)', marginBottom:4 }}>
                            {t('biz_reward_every')} <strong>{biz.reward_goal || '?'} {t('passport_visit_p')}</strong>
                          </div>
                          <div style={{ fontWeight:700, fontSize:15 }}>
                            🎁 {biz.reward ? plt(biz.reward) : <span style={{ color:'var(--muted)', fontWeight:400 }}>{t('biz_no_reward')}</span>}
                          </div>
                          {promoSuccess && <div style={{ color:'var(--teal)', fontSize:12, fontWeight:600, marginTop:6 }}>{t('biz_promo_updated')}</div>}
                        </div>
                        <button onClick={() => { let rwEs = '', rwEn = ''; try { const o = JSON.parse(biz.reward); rwEs = o?.es||''; rwEn = o?.en||''; } catch(_) { rwEs = biz.reward||''; } setPromoRewardEs(rwEs); setPromoRewardEn(rwEn); setPromoGoal(String(biz.reward_goal || 5)); setPromoError(''); setPromoSuccess(false); setEditingPromo(true); }} style={{ background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'8px 14px', fontSize:13, fontWeight:600, cursor:'pointer' }}>
                          {t('biz_edit')}
                        </button>
                      </div>
                    ) : (
                      <div style={{ display:'flex', flexDirection:'column', gap:10 }}>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_reward_label')} · ES *</div><input value={promoRewardEs} onChange={e => setPromoRewardEs(e.target.value)} placeholder={t('biz_reward_placeholder')} maxLength={80} style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/></div>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_reward_label')} · EN</div><input value={promoRewardEn} onChange={e => setPromoRewardEn(e.target.value)} placeholder={t('biz_reward_placeholder_en')} maxLength={80} style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/></div>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_goal_label')}</div><input value={promoGoal} onChange={e => setPromoGoal(e.target.value.replace(/\D/g,'').slice(0,2))} placeholder={t('biz_goal_placeholder')} inputMode="numeric" style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/></div>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_pin_label')}</div><input value={promoPin} onChange={e => setPromoPin(e.target.value.replace(/\D/g,'').slice(0,6))} placeholder={t('biz_pin6_placeholder')} type="password" inputMode="numeric" autoComplete="new-password" style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/></div>
                        {promoError && <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600 }}>{promoError}</div>}
                        <div style={{ display:'flex', gap:8, marginTop:2 }}>
                          <button onClick={() => { setEditingPromo(false); setPromoError(''); }} style={{ flex:1, background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'11px', fontSize:13, fontWeight:600, cursor:'pointer' }}>{t('scan_cancel')}</button>
                          <button onClick={handleSavePromo} disabled={promoLoading || !promoRewardEs.trim() || !promoGoal || promoPin.length < 6} style={{ flex:2, background:'var(--teal)', color:'white', border:0, borderRadius:10, padding:'11px', fontSize:13, fontWeight:700, cursor:'pointer', opacity: promoLoading || !promoRewardEs.trim() || !promoGoal || promoPin.length < 6 ? 0.5 : 1 }}>
                            {promoLoading ? t('biz_saving') : t('biz_save_promo')}
                          </button>
                        </div>
                      </div>
                    )}
                  </div>
                </div>

                {/* Birthday Gift */}
                <div>
                  <div className="label-eyebrow" style={{ marginBottom:10, padding:0 }}>{t('biz_birthday_title')}</div>
                  <div style={{ background:'white', borderRadius:12, padding:'14px', border:'1px solid rgba(15,23,42,0.06)' }}>
                    {!bdayOpen ? (
                      <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center' }}>
                        <div>
                          <div style={{ display:'flex', alignItems:'center', gap:6 }}>
                            <div style={{ width:7, height:7, borderRadius:'50%', background: bdaySaved ? (bdayActive ? '#16a34a' : '#9ca3af') : '#d1d5db' }}/>
                            <span style={{ fontSize:12, color:'var(--muted)' }}>
                              {bdaySaved ? (bdayActive ? t('biz_birthday_on') : t('biz_birthday_off')) : t('biz_birthday_not_set')}
                            </span>
                          </div>
                        </div>
                        <button onClick={handleOpenBday} style={{ background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'8px 14px', fontSize:13, fontWeight:600, cursor:'pointer' }}>
                          {t('biz_birthday_edit')}
                        </button>
                      </div>
                    ) : (
                      <div style={{ display:'flex', flexDirection:'column', gap:12 }}>
                        <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center' }}>
                          <span style={{ fontWeight:700, fontSize:14 }}>{t('biz_birthday_title')}</span>
                          <button onClick={() => setBdayActive(v => !v)} style={{ display:'flex', alignItems:'center', gap:8, background:'transparent', border:0, cursor:'pointer', padding:0 }}>
                            <div style={{ width:42, height:24, borderRadius:12, position:'relative', transition:'background .2s', background: bdayActive ? 'var(--teal)' : 'rgba(15,23,42,0.15)' }}>
                              <div style={{ position:'absolute', top:3, left: bdayActive ? 21 : 3, width:18, height:18, borderRadius:'50%', background:'white', transition:'left .2s', boxShadow:'0 1px 4px rgba(0,0,0,0.2)' }}/>
                            </div>
                            <span style={{ fontSize:13, fontWeight:700, color: bdayActive ? 'var(--teal)' : 'var(--muted)' }}>{bdayActive ? t('biz_birthday_on') : t('biz_birthday_off')}</span>
                          </button>
                        </div>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_birthday_gift_label')}</div><input value={bdayGift} onChange={e => setBdayGift(e.target.value)} placeholder={t('biz_birthday_gift_ph')} maxLength={100} style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/></div>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_birthday_terms_label')}</div><textarea value={bdayTerms} onChange={e => setBdayTerms(e.target.value)} placeholder={t('biz_birthday_terms_ph')} maxLength={300} rows={3} style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:13, outline:'none', resize:'vertical', fontFamily:'inherit', lineHeight:1.5 }}/></div>
                        <div><div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:5, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_birthday_redeem_pin_label')}</div><input value={bdayRedeemPin} onChange={e => setBdayRedeemPin(e.target.value.replace(/\D/g,'').slice(0,4))} placeholder={t('biz_birthday_redeem_pin_ph')} inputMode="numeric" maxLength={4} style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:20, letterSpacing:'.2em', outline:'none', fontWeight:700 }}/>{bdayHasPin && <div style={{ fontSize:11, color:'var(--muted)', marginTop:4 }}>{t('biz_birthday_pin_hint')}</div>}</div>
                        {bdaySaveError && <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600 }}>{bdaySaveError}</div>}
                        <div style={{ display:'flex', gap:8, marginTop:2 }}>
                          <button onClick={() => { setBdayOpen(false); setBdaySaveError(''); }} style={{ flex:1, background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'11px', fontSize:13, fontWeight:600, cursor:'pointer' }}>{t('scan_cancel')}</button>
                          <button onClick={handleSaveBdayPromo} disabled={bdaySaving || !bdayGift.trim() || (bdayActive && bdayRedeemPin.length < 4 && !bdayHasPin)} style={{ flex:2, background:'var(--teal)', color:'white', border:0, borderRadius:10, padding:'11px', fontSize:13, fontWeight:700, cursor:'pointer', opacity: bdaySaving || !bdayGift.trim() || (bdayActive && bdayRedeemPin.length < 4 && !bdayHasPin) ? 0.5 : 1 }}>{bdaySaving ? t('biz_saving') : t('biz_save_promo')}</button>
                        </div>
                      </div>
                    )}
                  </div>
                </div>

                {/* Promos por Día */}
                <div>
                  <div className="label-eyebrow" style={{ marginBottom:6, padding:0 }}>{t('biz_daily_promos_title')}</div>
                  <div style={{ fontSize:11, color:'var(--muted)', marginBottom:12, lineHeight:1.5 }}>{t('biz_daily_promos_sub')}</div>
                  <div style={{ display:'flex', flexDirection:'column', gap:10 }}>
                    {dailyPromos.map((entry, idx) => {
                      const DAY_NAMES_ES = ['Dom','Lun','Mar','Mié','Jue','Vie','Sáb'];
                      const DAY_NAMES_EN = ['Sun','Mon','Tue','Wed','Thu','Fri','Sat'];
                      const dayLabel = `${DAY_NAMES_ES[idx]} · ${DAY_NAMES_EN[idx]}`;
                      return (
                        <div key={idx} style={{ background:'white', borderRadius:12, padding:'12px 14px', border:'1px solid rgba(15,23,42,0.06)' }}>
                          <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center', marginBottom: entry.active ? 10 : 0 }}>
                            <span style={{ fontSize:13, fontWeight:700, color:'var(--ink)' }}>{dayLabel}</span>
                            <button
                              onClick={() => setDailyPromos(prev => {
                                const next = [...prev];
                                next[idx] = { ...next[idx], active: !next[idx].active };
                                return next;
                              })}
                              style={{ display:'flex', alignItems:'center', gap:8, background:'transparent', border:0, cursor:'pointer', padding:0 }}
                            >
                              <div style={{ width:38, height:22, borderRadius:11, position:'relative', transition:'background .2s', background: entry.active ? '#D97706' : 'rgba(15,23,42,0.15)' }}>
                                <div style={{ position:'absolute', top:2, left: entry.active ? 18 : 2, width:18, height:18, borderRadius:'50%', background:'white', transition:'left .2s', boxShadow:'0 1px 3px rgba(0,0,0,0.2)' }}/>
                              </div>
                            </button>
                          </div>
                          {entry.active && (
                            <>
                              {[{ key:'name_es', flag:'🇲🇽', lang:'ES', ph: t('biz_daily_promo_ph_es') }, { key:'name_en', flag:'🇺🇸', lang:'EN', ph: t('biz_daily_promo_ph_en') }].map(({ key, flag, lang, ph }) => (
                                <div key={key}>
                                  <div style={{ fontSize:10, fontWeight:700, color:'var(--muted)', letterSpacing:'.06em', textTransform:'uppercase', marginBottom:4 }}>{flag} {lang}</div>
                                  <input
                                    value={entry[key] || ''}
                                    onChange={e => setDailyPromos(prev => { const n=[...prev]; n[idx]={...n[idx],[key]:e.target.value}; return n; })}
                                    placeholder={ph}
                                    maxLength={80}
                                    style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:8, padding:'10px 12px', fontSize:13, outline:'none', marginBottom:8 }}
                                  />
                                </div>
                              ))}
                              {dailyPromosError[idx] && <div style={{ color:'#b91c1c', fontSize:11, fontWeight:600, marginBottom:4 }}>{dailyPromosError[idx]}</div>}
                              <div style={{ display:'flex', alignItems:'center', justifyContent:'space-between' }}>
                                {dailyPromosSaved[idx] && <span style={{ fontSize:11, color:'var(--teal)', fontWeight:700 }}>{t('biz_daily_promo_saved')}</span>}
                                <button
                                  onClick={() => handleSaveDayPromo(idx)}
                                  disabled={!!dailyPromosSaving[idx]}
                                  style={{ marginLeft:'auto', background:'var(--teal)', color:'white', border:0, borderRadius:8, padding:'8px 16px', fontSize:12, fontWeight:700, cursor:'pointer', opacity: dailyPromosSaving[idx] ? 0.5 : 1 }}
                                >
                                  {dailyPromosSaving[idx] ? t('biz_saving') : t('biz_save_promo')}
                                </button>
                              </div>
                            </>
                          )}
                          {!entry.active && dailyPromosSaved[idx] && (
                            <div style={{ fontSize:10, color:'#9CA3AF', marginTop:4 }}>{t('biz_daily_promo_saved')}</div>
                          )}
                        </div>
                      );
                    })}
                  </div>
                </div>

              </div>
            )}
          </div>

        </div>
      </div>

    </div>,
    document.body
  )}
  {menuAddOpen && ReactDOM.createPortal(
    <div style={{ position:'fixed', inset:0, zIndex:310, background:'rgba(15,23,42,0.6)', backdropFilter:'blur(4px)', WebkitBackdropFilter:'blur(4px)', display:'flex', alignItems:'flex-end', justifyContent:'center', animation:'fadeIn .15s ease both' }}
      onClick={e => { if (e.target === e.currentTarget) setMenuAddOpen(false); }}>
      <div style={{ background:'var(--canvas)', borderRadius:'20px 20px 0 0', padding:'24px 24px 44px', width:'100%', maxWidth:480, maxHeight:'90vh', overflowY:'auto', boxShadow:'0 -8px 40px rgba(15,23,42,0.25)', animation:'slideUp .25s cubic-bezier(.2,.8,.2,1) both' }}
        onClick={e => e.stopPropagation()}>
        <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center', marginBottom:20 }}>
          <div style={{ fontWeight:800, fontSize:16 }}>Nuevo ítem del catálogo</div>
          <button onClick={() => setMenuAddOpen(false)} style={{ background:'var(--fog)', border:0, borderRadius:99, padding:7, cursor:'pointer', display:'flex' }}><IconX size={16}/></button>
        </div>

        {/* Tipo */}
        <div style={{ marginBottom:16 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:8, textTransform:'uppercase', letterSpacing:'0.05em' }}>Tipo</div>
          <div style={{ display:'grid', gridTemplateColumns:'1fr 1fr 1fr', gap:8 }}>
            {[['food','🍽 Producto'],['service','✂️ Servicio'],['accommodation','🏡 Hospedaje']].map(([k,l]) => (
              <button key={k} onClick={() => setMenuForm(prev => ({ ...prev, item_type: k }))}
                style={{ background: menuForm.item_type === k ? 'var(--ink)' : 'var(--fog)', color: menuForm.item_type === k ? 'white' : 'var(--ink)', border:0, borderRadius:10, padding:'10px 6px', fontSize:12, fontWeight:700, cursor:'pointer', lineHeight:1.4 }}>
                {l}
              </button>
            ))}
          </div>
        </div>

        {/* Categoría */}
        <div style={{ marginBottom:16 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:8, textTransform:'uppercase', letterSpacing:'0.05em' }}>Categoría</div>
          <div style={{ display:'flex', gap:6, overflowX:'auto', paddingBottom:4 }}>
            {MENU_CATEGORIES.map(c => (
              <button key={c.key} onClick={() => setMenuForm(prev => ({ ...prev, category: c.key }))}
                style={{ background: menuForm.category === c.key ? 'var(--ink)' : 'var(--fog)', color: menuForm.category === c.key ? 'white' : 'var(--ink)', border:0, borderRadius:99, padding:'7px 12px', fontSize:12, fontWeight:700, cursor:'pointer', whiteSpace:'nowrap', flexShrink:0 }}>
                {c.emoji} {c.label}
              </button>
            ))}
          </div>
        </div>

        {/* Nombre ES */}
        <div style={{ marginBottom:12 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>🇲🇽 Nombre *</div>
          <input value={menuForm.name_es} onChange={e => setMenuForm(prev => ({ ...prev, name_es: e.target.value }))}
            placeholder="Ej: Ceviche de camarón" maxLength={80}
            style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/>
        </div>

        {/* Descripción */}
        <div style={{ marginBottom:12 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>Descripción (opcional)</div>
          <textarea value={menuForm.description_es} onChange={e => setMenuForm(prev => ({ ...prev, description_es: e.target.value }))}
            placeholder="Ingredientes, detalles, variaciones..." maxLength={200} rows={2}
            style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:13, outline:'none', resize:'none', fontFamily:'inherit', lineHeight:1.5 }}/>
        </div>

        {/* Precio */}
        <div style={{ marginBottom:12 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>Precio MXN *</div>
          <input value={menuForm.price} onChange={e => setMenuForm(prev => ({ ...prev, price: e.target.value.replace(/[^0-9.]/g,'') }))}
            placeholder="0.00" inputMode="decimal"
            style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:18, outline:'none', fontWeight:700 }}/>
        </div>

        {/* URL reserva — solo hospedaje */}
        {menuForm.item_type === 'accommodation' && (
          <div style={{ marginBottom:12 }}>
            <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>URL de reserva *</div>
            <input value={menuForm.external_booking_url} onChange={e => setMenuForm(prev => ({ ...prev, external_booking_url: e.target.value }))}
              placeholder="https://..." type="url"
              style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:13, outline:'none' }}/>
          </div>
        )}

        {/* Foto */}
        <div style={{ marginBottom:20 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:8, textTransform:'uppercase', letterSpacing:'0.05em' }}>Foto (opcional)</div>
          {menuForm.image_url ? (
            <div style={{ position:'relative', display:'inline-block' }}>
              <img src={menuForm.image_url} alt="" style={{ width:90, height:90, objectFit:'cover', borderRadius:12, border:'2px solid rgba(13,148,136,0.35)', display:'block' }}/>
              <button onClick={() => setMenuForm(prev => ({ ...prev, image_url:'' }))}
                style={{ position:'absolute', top:-6, right:-6, background:'var(--ink)', border:0, borderRadius:99, width:20, height:20, display:'flex', alignItems:'center', justifyContent:'center', cursor:'pointer' }}>
                <IconX size={11} color="white"/>
              </button>
            </div>
          ) : (
            <button onClick={() => menuFileRef.current?.click()} disabled={menuImageUploading}
              style={{ background:'var(--fog)', border:'1.5px dashed rgba(15,23,42,0.2)', borderRadius:12, padding:'14px 22px', fontSize:13, fontWeight:600, cursor:'pointer', color:'var(--muted)', display:'flex', alignItems:'center', gap:8, opacity: menuImageUploading ? 0.6 : 1 }}>
              {menuImageUploading ? '⏳ Subiendo...' : '📷 Subir foto'}
            </button>
          )}
          <input ref={menuFileRef} type="file" accept="image/*" style={{ display:'none' }} onChange={handleMenuImagePick}/>
          <div style={{ fontSize:10, color:'var(--muted)', marginTop:6 }}>Se traduce a EN, FR y DE con IA automáticamente ✨</div>
        </div>

        {menuFormError && (
          <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600, marginBottom:12, background:'rgba(185,28,28,0.07)', borderRadius:8, padding:'8px 12px' }}>{menuFormError}</div>
        )}

        <div style={{ display:'flex', gap:8 }}>
          <button onClick={() => { setMenuAddOpen(false); setMenuFormError(''); }}
            style={{ flex:1, background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'13px', fontSize:13, fontWeight:600, cursor:'pointer' }}>
            Cancelar
          </button>
          <button onClick={handleAddMenuItem} disabled={menuFormSaving || !menuForm.name_es.trim() || menuForm.price === ''}
            style={{ flex:2, background:'var(--teal)', color:'white', border:0, borderRadius:10, padding:'13px', fontSize:14, fontWeight:700, cursor:'pointer', opacity: menuFormSaving || !menuForm.name_es.trim() || menuForm.price === '' ? 0.5 : 1 }}>
            {menuFormSaving ? 'Guardando...' : 'Guardar ítem'}
          </button>
        </div>
      </div>
    </div>,
    document.body
  )}
  {menuEditItem && ReactDOM.createPortal(
    <div style={{ position:'fixed', inset:0, zIndex:310, background:'rgba(15,23,42,0.6)', backdropFilter:'blur(4px)', WebkitBackdropFilter:'blur(4px)', display:'flex', alignItems:'flex-end', justifyContent:'center', animation:'fadeIn .15s ease both' }}
      onClick={e => { if (e.target === e.currentTarget) setMenuEditItem(null); }}>
      <div style={{ background:'var(--canvas)', borderRadius:'20px 20px 0 0', padding:'24px 24px 44px', width:'100%', maxWidth:480, maxHeight:'90vh', overflowY:'auto', boxShadow:'0 -8px 40px rgba(15,23,42,0.25)', animation:'slideUp .25s cubic-bezier(.2,.8,.2,1) both' }}
        onClick={e => e.stopPropagation()}>
        <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center', marginBottom:20 }}>
          <div style={{ fontWeight:800, fontSize:16 }}>Editar ítem</div>
          <button onClick={() => setMenuEditItem(null)} style={{ background:'var(--fog)', border:0, borderRadius:99, padding:7, cursor:'pointer', display:'flex' }}><IconX size={16}/></button>
        </div>

        <div style={{ marginBottom:16 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:8, textTransform:'uppercase', letterSpacing:'0.05em' }}>Tipo</div>
          <div style={{ display:'grid', gridTemplateColumns:'1fr 1fr 1fr', gap:8 }}>
            {[['food','🍽 Producto'],['service','✂️ Servicio'],['accommodation','🏡 Hospedaje']].map(([k,l]) => (
              <button key={k} onClick={() => setMenuEditForm(prev => ({ ...prev, item_type: k }))}
                style={{ background: menuEditForm.item_type === k ? 'var(--ink)' : 'var(--fog)', color: menuEditForm.item_type === k ? 'white' : 'var(--ink)', border:0, borderRadius:10, padding:'10px 6px', fontSize:12, fontWeight:700, cursor:'pointer', lineHeight:1.4 }}>
                {l}
              </button>
            ))}
          </div>
        </div>

        <div style={{ marginBottom:16 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:8, textTransform:'uppercase', letterSpacing:'0.05em' }}>Categoría</div>
          <div style={{ display:'flex', gap:6, overflowX:'auto', paddingBottom:4 }}>
            {MENU_CATEGORIES.map(c => (
              <button key={c.key} onClick={() => setMenuEditForm(prev => ({ ...prev, category: c.key }))}
                style={{ background: menuEditForm.category === c.key ? 'var(--ink)' : 'var(--fog)', color: menuEditForm.category === c.key ? 'white' : 'var(--ink)', border:0, borderRadius:99, padding:'7px 12px', fontSize:12, fontWeight:700, cursor:'pointer', whiteSpace:'nowrap', flexShrink:0 }}>
                {c.emoji} {c.label}
              </button>
            ))}
          </div>
        </div>

        <div style={{ marginBottom:12 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>🇲🇽 Nombre *</div>
          <input value={menuEditForm.name_es} onChange={e => setMenuEditForm(prev => ({ ...prev, name_es: e.target.value }))}
            maxLength={80}
            style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/>
        </div>

        <div style={{ marginBottom:12 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>Descripción (opcional)</div>
          <textarea value={menuEditForm.description_es} onChange={e => setMenuEditForm(prev => ({ ...prev, description_es: e.target.value }))}
            maxLength={200} rows={2}
            style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:13, outline:'none', resize:'none', fontFamily:'inherit', lineHeight:1.5 }}/>
        </div>

        <div style={{ marginBottom:12 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>Precio MXN *</div>
          <input value={menuEditForm.price} onChange={e => setMenuEditForm(prev => ({ ...prev, price: e.target.value.replace(/[^0-9.]/g,'') }))}
            placeholder="0.00" inputMode="decimal"
            style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:18, outline:'none', fontWeight:700 }}/>
        </div>

        {menuEditForm.item_type === 'accommodation' && (
          <div style={{ marginBottom:12 }}>
            <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>URL de reserva *</div>
            <input value={menuEditForm.external_booking_url} onChange={e => setMenuEditForm(prev => ({ ...prev, external_booking_url: e.target.value }))}
              placeholder="https://..." type="url"
              style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:13, outline:'none' }}/>
          </div>
        )}

        <div style={{ marginBottom:20 }}>
          <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:8, textTransform:'uppercase', letterSpacing:'0.05em' }}>Foto (opcional)</div>
          {menuEditForm.image_url ? (
            <div style={{ position:'relative', display:'inline-block' }}>
              <img src={menuEditForm.image_url} alt="" style={{ width:90, height:90, objectFit:'cover', borderRadius:12, border:'2px solid rgba(13,148,136,0.35)', display:'block' }}/>
              <button onClick={() => setMenuEditForm(prev => ({ ...prev, image_url:'' }))}
                style={{ position:'absolute', top:-6, right:-6, background:'var(--ink)', border:0, borderRadius:99, width:20, height:20, display:'flex', alignItems:'center', justifyContent:'center', cursor:'pointer' }}>
                <IconX size={11} color="white"/>
              </button>
            </div>
          ) : (
            <button onClick={() => menuEditFileRef.current?.click()} disabled={menuEditImageUploading}
              style={{ background:'var(--fog)', border:'1.5px dashed rgba(15,23,42,0.2)', borderRadius:12, padding:'14px 22px', fontSize:13, fontWeight:600, cursor:'pointer', color:'var(--muted)', display:'flex', alignItems:'center', gap:8, opacity: menuEditImageUploading ? 0.6 : 1 }}>
              {menuEditImageUploading ? '⏳ Subiendo...' : '📷 Subir foto'}
            </button>
          )}
          <input ref={menuEditFileRef} type="file" accept="image/*" style={{ display:'none' }} onChange={handleMenuEditImagePick}/>
          <div style={{ fontSize:10, color:'var(--muted)', marginTop:6 }}>Si cambias nombre o descripción, se re-traduce con IA ✨</div>
        </div>

        {menuEditError && (
          <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600, marginBottom:12, background:'rgba(185,28,28,0.07)', borderRadius:8, padding:'8px 12px' }}>{menuEditError}</div>
        )}

        <div style={{ display:'flex', gap:8 }}>
          <button onClick={() => { setMenuEditItem(null); setMenuEditError(''); }}
            style={{ flex:1, background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'13px', fontSize:13, fontWeight:600, cursor:'pointer' }}>
            Cancelar
          </button>
          <button onClick={handleEditMenuItem} disabled={menuEditSaving || !menuEditForm.name_es.trim() || menuEditForm.price === ''}
            style={{ flex:2, background:'var(--teal)', color:'white', border:0, borderRadius:10, padding:'13px', fontSize:14, fontWeight:700, cursor:'pointer', opacity: menuEditSaving || !menuEditForm.name_es.trim() || menuEditForm.price === '' ? 0.5 : 1 }}>
            {menuEditSaving ? 'Guardando...' : 'Guardar cambios'}
          </button>
        </div>
      </div>
    </div>,
    document.body
  )}
  </>);
};

const BusinessPanel = ({ onClose }) => {
  const t = useT();
  const plt = usePLT();
  const [step, setStep] = useState(() => {
    try {
      const saved = localStorage.getItem('helixBiz');
      if (saved) return 'dashboard';
    } catch(_){}
    return 'login';
  });
  const [bizSaved] = useState(() => {
    try { return JSON.parse(localStorage.getItem('helixBiz') || 'null'); } catch(_){ return null; }
  }); // login | dashboard
  const [code, setCode] = useState('');
  const [pin, setPin] = useState('');
  const [error, setError] = useState('');
  const [biz, setBiz] = useState(bizSaved);
  const [stats, setStats] = useState(null);
  const [showStats, setShowStats] = useState(false);
  const [loading, setLoading] = useState(false);
  const [scanning, setScanning] = useState(false);
  const [scanResult, setScanResult] = useState(null);
  const [drawerClient, setDrawerClient] = useState(null);

  const [bizPin, setBizPin] = useState(() => {
    try { return JSON.parse(localStorage.getItem('helixBiz') || 'null')?._pin || ''; } catch(_) { return ''; }
  });
  const [showLogoutPin, setShowLogoutPin] = useState(false);
  const [logoutPin, setLogoutPin] = useState('');
  const [logoutError, setLogoutError] = useState('');

  const loadStats = (bCode, bPinVal, bizId) => {
    const id = bizId || biz?.id || bizSaved?.id;
    if (!id || !bCode || !bPinVal) return;
    fetch(`${API}/business/stats?id=${id}`, {
      headers: { 'X-Biz-Code': bCode, 'X-Biz-Pin': bPinVal }
    }).then(r => r.json()).then(s => setStats(s)).catch(() => {});
  };

  useEffect(() => {
    const saved = bizSaved || biz;
    if (bizPin && saved?.code && saved?.id) loadStats(saved.code, bizPin, saved.id);
  }, []);
  const [logoutLoading, setLogoutLoading] = useState(false);

  // ── Birthday redemption (acción operativa — sin PIN) ──────────────────
  const [redeemStep, setRedeemStep] = useState(0);
  const [redeemAuth, setRedeemAuth] = useState('');
  const [redeemIneOk, setRedeemIneOk] = useState(false);
  const [redeemPin, setRedeemPin] = useState('');
  const [redeemPassport, setRedeemPassport] = useState('');
  const [redeemLoading, setRedeemLoading] = useState(false);
  const [redeemError, setRedeemError] = useState('');
  const [redeemLookup, setRedeemLookup] = useState(null);
  const [redeemRequestId, setRedeemRequestId] = useState(null);

  const resetRedeem = () => {
    setRedeemStep(0); setRedeemAuth(''); setRedeemIneOk(false);
    setRedeemPin(''); setRedeemPassport(''); setRedeemError('');
    setRedeemLoading(false); setRedeemLookup(null); setRedeemRequestId(null);
  };

  const handleFinalizeRedeem = async (reqId) => {
    setRedeemLoading(true); setRedeemError('');
    try {
      const res = await fetch(`${API}/birthday/redeem`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ requestId: reqId, authorizer: redeemAuth.trim(), pin: redeemPin }),
      });
      const data = await res.json();
      if (!res.ok) {
        const msg = data.error === 'window'       ? t('biz_redeem_err_window', { n: data.birth_month })
                  : data.error === 'cooldown_24h' ? t('biz_redeem_err_24h')
                  : data.error === 'annual_limit' ? t('biz_redeem_err_annual')
                  : data.error || 'Error';
        setRedeemError(msg); setRedeemStep(1);
      } else {
        setRedeemLookup(v => ({ ...v, user_name: data.user_name || v?.user_name, gift: data.gift || v?.gift }));
        setRedeemStep(4);
      }
    } catch(_) { setRedeemError(t('biz_conn_error')); setRedeemStep(1); }
    setRedeemLoading(false);
  };

  // Poll for user authorization when in waiting step (step 3)
  useEffect(() => {
    if (redeemStep !== 3 || !redeemRequestId) return;
    const poll = setInterval(async () => {
      try {
        const res = await fetch(`${API}/birthday/auth-status?requestId=${redeemRequestId}`);
        const data = await res.json();
        if (data.status === 'approved') {
          clearInterval(poll);
          handleFinalizeRedeem(redeemRequestId);
        } else if (data.status === 'rejected') {
          clearInterval(poll);
          setRedeemError(t('biz_redeem_err_rejected'));
          setRedeemStep(1);
        } else if (data.status === 'expired') {
          clearInterval(poll);
          setRedeemError(t('biz_redeem_err_expired'));
          setRedeemStep(1);
        }
      } catch(_) {}
    }, 3000);
    return () => clearInterval(poll);
  }, [redeemStep, redeemRequestId]);

  const handleRedeemVerify = async () => {
    if (!redeemPassport.trim()) return;
    setRedeemLoading(true); setRedeemError('');
    try {
      const res = await fetch(`${API}/birthday/request-auth`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ bizId: biz.id, code: biz.code, passport: redeemPassport.trim() }),
      });
      const data = await res.json();
      if (!res.ok) {
        const msg = data.error === 'window'       ? t('biz_redeem_err_window', { n: data.birth_month })
                  : data.error === 'cooldown_24h' ? t('biz_redeem_err_24h')
                  : data.error === 'annual_limit' ? t('biz_redeem_err_annual')
                  : data.error || 'Error';
        setRedeemError(msg); setRedeemLoading(false); return;
      }
      setRedeemLookup({ user_name: data.user_name, gift: data.gift });
      setRedeemRequestId(data.requestId);
      setRedeemStep(3);
      if (data.auto_approved) handleFinalizeRedeem(data.requestId);
    } catch(_) { setRedeemError(t('biz_conn_error')); }
    setRedeemLoading(false);
  };

  const panelRef = useRef(null);
  const videoRef = useRef(null);
  const canvasRef = useRef(null);
  const scanInterval = useRef(null);

  useEffect(() => {
    return () => {
      clearInterval(scanInterval.current);
      if (videoRef.current?.srcObject) {
        videoRef.current.srcObject.getTracks().forEach(t => t.stop());
      }
    };
  }, []);

  const startScan = async () => {
    setScanResult(null);
    setScanning(true);
    try {
      const stream = await navigator.mediaDevices.getUserMedia({ video: { facingMode: 'environment' } });
      videoRef.current.srcObject = stream;
      videoRef.current.play();
      scanInterval.current = setInterval(() => {
        const video = videoRef.current;
        const canvas = canvasRef.current;
        if (!video || !canvas || video.readyState !== 4) return;
        canvas.width = video.videoWidth;
        canvas.height = video.videoHeight;
        const ctx = canvas.getContext('2d');
        ctx.drawImage(video, 0, 0);
        const img = ctx.getImageData(0, 0, canvas.width, canvas.height);
        const code = jsQR(img.data, img.width, img.height);
        if (code) {
          clearInterval(scanInterval.current);
          stream.getTracks().forEach(t => t.stop());
          setScanning(false);
          verifyQR(code.data);
        }
      }, 300);
    } catch(e) {
      setScanning(false);
      setScanResult({ error: t('biz_cam_error') });
    }
  };

  const stopScan = () => {
    clearInterval(scanInterval.current);
    if (videoRef.current?.srcObject) {
      videoRef.current.srcObject.getTracks().forEach(t => t.stop());
    }
    setScanning(false);
  };

  const verifyQR = async (token) => {

    try {
      const res = await fetch(`${API}/qr/verify`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ token, bizId: biz.id })
      });
      const data = await res.json();
      if (res.ok) {
        setScanResult({ ok: true, message: t('biz_visit_ok') });
        if (bizPin) loadStats(biz.code, bizPin, biz.id);
        return;
      }
      // Intentar como QR de canje de recompensa
      const res2 = await fetch(`${API}/rewards/redeem`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ token, bizId: biz.id })
      });
      const data2 = await res2.json();
      if (res2.ok) {
       setScanResult({ ok: true, message: t('biz_reward_ok') + ' ' + plt(data2.reward) });
        if (bizPin) loadStats(biz.code, bizPin, biz.id);
      } else {
        setScanResult({ error: data2.error || data.error });
      }
    } catch(e) {
      setScanResult({ error: t('biz_conn_error') });
    }
  };

  const handleLogoutConfirm = async () => {
    setLogoutLoading(true);
    setLogoutError('');
    try {
      const res = await fetch(`${API}/business/login`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ code: biz.code, pin: logoutPin })
      });
      const data = await res.json();
      if (!res.ok) {
        setLogoutError(data.error || 'PIN incorrecto');
        setLogoutLoading(false);
        return;
      }
      localStorage.removeItem('helixBiz');
      setShowLogoutPin(false);
      setLogoutPin('');
      setStep('login');
      setBiz(null);
    } catch(e) {
      setLogoutError(t('biz_conn_error'));
    }
    setLogoutLoading(false);
  };

  const handleLogin = async () => {
    setLoading(true);
    setError('');
    try {
      const res = await fetch(`${API}/business/login`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ code, pin })
      });
      const data = await res.json();
      if (!res.ok) { setError(data.error); setLoading(false); return; }
      const bizData = { ...data, code: data.code || code };
      setBiz(bizData);
      try { localStorage.setItem('helixBiz', JSON.stringify({ ...bizData, _pin: pin })); } catch(_){}
      setBizPin(pin);
      setStep('dashboard');
      loadStats(code, pin, data.id);
    } catch(e) {
      setError(t('biz_conn_error'));
    }
    setLoading(false);
  };

  if (step === 'login') return (
    <div style={{
      position:'fixed', inset:0, zIndex:200,
      background:'var(--canvas)',
      display:'flex', flexDirection:'column',
      animation:'fadeIn .15s ease both'
    }}>
      <div style={{
        padding:'18px 24px',
        borderBottom:'1px solid rgba(15,23,42,0.08)',
        display:'flex', alignItems:'center', justifyContent:'space-between'
      }}>
        <div style={{ fontWeight:800, fontSize:16 }}>{t('biz_panel_title')}</div>
        <button onClick={onClose} style={{ background:'transparent', border:0, cursor:'pointer' }}>
          <IconX size={22}/>
        </button>
      </div>
      <div style={{ padding:'40px 24px', flex:1 }}>
        <div className="label-eyebrow" style={{ color:'var(--teal)', marginBottom:8 }}>{t('biz_access_eyebrow')}</div>
        <h2 className="h-section" style={{ fontSize:26, margin:'0 0 24px' }}>{t('biz_access_h')}</h2>
        <div style={{ display:'flex', flexDirection:'column', gap:12 }}>
          <input
            value={code}
            onChange={e => setCode(e.target.value.toUpperCase())}
            placeholder={t('biz_code_placeholder')}
            autoComplete="off"
            style={{ background:'var(--fog)', border:0, borderRadius:12, padding:'16px', fontSize:16, outline:'none' }}
          />
          <input
            value={pin}
            onChange={e => setPin(e.target.value.replace(/\D/g,'').slice(0,6))}
            placeholder={t('biz_pin6_placeholder')}
            type="password"
            inputMode="numeric"
            autoComplete="new-password"
            style={{ background:'var(--fog)', border:0, borderRadius:12, padding:'16px', fontSize:16, outline:'none' }}
          />
          {error && <div style={{ color:'#b91c1c', fontSize:13, fontWeight:600 }}>{error}</div>}
          <button
            onClick={handleLogin}
            disabled={loading || code.length < 10 || pin.length < 6}
            style={{
              marginTop:8, background:'var(--teal)', color:'white',
              border:0, borderRadius:14, padding:'16px',
              fontWeight:700, fontSize:15, cursor:'pointer',
              opacity: loading || code.length < 10 || pin.length < 6 ? 0.5 : 1
            }}>
            {loading ? t('biz_verifying') : t('biz_enter')}
          </button>
        </div>
      </div>
    </div>

  );

  return (
    <div ref={panelRef} style={{
      position:'fixed', inset:0, zIndex:200,
      background:'var(--canvas)',
      overflowY: drawerClient ? 'hidden' : 'auto',
      animation:'fadeIn .15s ease both'
    }}>
      <div style={{
        padding:'18px 24px',
        borderBottom:'1px solid rgba(15,23,42,0.08)',
        display:'flex', alignItems:'center', justifyContent:'space-between',
        position:'sticky', top:0, background:'rgba(251,249,243,0.92)',
        backdropFilter:'blur(10px)', zIndex:10
      }}>
        <div>
          <div className="label-eyebrow">Panel</div>
          <div style={{ fontWeight:800, fontSize:16 }}>{biz.name}</div>
        </div>
        <button onClick={onClose} style={{ background:'transparent', border:0, cursor:'pointer' }}>
          <IconX size={22}/>
        </button>
      </div>

      <div style={{ padding:'24px' }}>

        {/* Stats */}
        <div style={{ display:'grid', gridTemplateColumns:'1fr 1fr', gap:12, marginBottom:24 }}>
          <div style={{ background:'var(--fog)', borderRadius:14, padding:'16px', border:'1px solid rgba(15,23,42,0.06)' }}>
            <div className="label-eyebrow" style={{ marginBottom:4 }}>{t('biz_total_visits')}</div>
            <div style={{ fontSize:32, fontWeight:800, color:'var(--teal)' }}>{stats?.total_visits || 0}</div>
          </div>
          <div style={{ background:'var(--fog)', borderRadius:14, padding:'16px', border:'1px solid rgba(15,23,42,0.06)' }}>
            <div className="label-eyebrow" style={{ marginBottom:4 }}>{t('biz_unique_clients')}</div>
            <div style={{ fontSize:32, fontWeight:800, color:'var(--teal)' }}>{stats?.unique_clients || 0}</div>
          </div>
        </div>

        {/* Ver Estadísticas */}
        {stats && (
          <button onClick={() => setShowStats(true)} style={{
            width:'100%', background:'transparent',
            border:'1px solid rgba(13,148,136,0.3)', borderRadius:12,
            padding:'12px', fontSize:14, fontWeight:700,
            color:'var(--teal)', cursor:'pointer',
            display:'flex', alignItems:'center', justifyContent:'center', gap:8,
            marginBottom:24,
          }}>
            <IconBarChart size={16}/> {t('biz_stats_cta')}
          </button>
        )}

        {/* Escáner */}
        <div style={{ marginBottom:24 }}>
          <SectionLabel style={{ padding:0 }}>{t('biz_verify_section')}</SectionLabel>
          <div style={{ background:'var(--fog)', borderRadius:14, padding:'16px', border:'1px solid rgba(15,23,42,0.06)' }}>
            {!scanning && !scanResult && (
              <button onClick={startScan} style={{
                width:'100%', background:'var(--teal)', color:'white',
                border:0, borderRadius:12, padding:'14px',
                fontWeight:700, fontSize:14, cursor:'pointer',
                display:'flex', alignItems:'center', justifyContent:'center', gap:8
              }}>
                <IconQrCode size={18}/> {t('biz_scan_cta')}
              </button>
            )}
            {scanning && (
              <div style={{ textAlign:'center' }}>
                <video ref={videoRef} className="scanner-video" style={{ width:'100%', borderRadius:10, maxHeight:260, aspectRatio:'4/3', objectFit:'cover' }} playsInline muted/>
                <canvas ref={canvasRef} style={{ display:'none' }}/>
                <button onClick={stopScan} style={{
                  marginTop:12, background:'transparent', border:'1px solid rgba(15,23,42,0.15)',
                  borderRadius:10, padding:'14px 24px', minHeight:48, cursor:'pointer', fontSize:14, fontWeight:500
                }}>{t('scan_cancel')}</button>
              </div>
            )}
            {scanResult && (
              <div style={{ textAlign:'center', padding:'10px 0' }}>
                {scanResult.ok ? (
                  <div style={{ color:'var(--teal)', fontWeight:700, fontSize:16 }}>{scanResult.message || t('biz_visit_ok')}</div>
                ) : (
                  <div style={{ color:'#b91c1c', fontWeight:600, fontSize:14 }}>{scanResult.error}</div>
                )}
                <button onClick={() => setScanResult(null)} style={{
                  marginTop:12, background:'transparent', border:'1px solid rgba(15,23,42,0.15)',
                  borderRadius:10, padding:'8px 18px', cursor:'pointer', fontSize:13
                }}>{t('biz_scan_another')}</button>
              </div>
            )}
          </div>
        </div>

        {/* QR del negocio */}
        <div style={{ background:'var(--fog)', borderRadius:14, padding:'16px', border:'1px solid rgba(15,23,42,0.06)', marginBottom:16, textAlign:'center' }}>
          <div className="label-eyebrow" style={{ marginBottom:12 }}>{t('biz_qr_label')}</div>
          <div style={{ display:'inline-block', background:'white', padding:12, borderRadius:12, maxWidth:'calc(100vw - 100px)' }}>
            <img src={`https://api.qrserver.com/v1/create-qr-code/?size=220x220&data=${encodeURIComponent('https://helixpassport.com/?b=' + biz.id + '&z=' + biz.zone)}`} style={{ display:'block', borderRadius:4, width:'min(200px, calc(100vw - 130px))', height:'auto' }} alt="QR"/>
          </div>
          <div style={{ marginTop:10, fontSize:11, color:'var(--muted)' }}>{biz.code}</div>
        </div>

        {/* Canjear Regalo de Cumpleaños — acción operativa, sin PIN */}
        <button
          onClick={() => { setRedeemStep(1); setRedeemError(''); }}
          style={{ width:'100%', background:'linear-gradient(135deg,#E91E8C,#C2185B)', color:'white', border:0, borderRadius:14, padding:'16px 20px', fontWeight:700, fontSize:15, cursor:'pointer', display:'flex', alignItems:'center', justifyContent:'center', gap:10, boxShadow:'0 4px 20px rgba(233,30,140,0.28)', marginBottom:24 }}
        >
          🎁 {t('biz_redeem_btn')}
        </button>

        {/* Cerrar sesión */}
        <button onClick={() => { setLogoutPin(''); setLogoutError(''); setShowLogoutPin(true); }} style={{
          marginTop:32, width:'100%', background:'transparent',
          border:'1px solid rgba(185,28,28,0.2)', borderRadius:12,
          padding:'12px', fontSize:13, fontWeight:600,
          color:'#b91c1c', cursor:'pointer'
        }}>{t('biz_logout')}</button>
      </div>

      {showStats && <BusinessStats stats={stats} biz={biz} onClose={() => setShowStats(false)} onBizUpdate={setBiz} onPinVerified={(p) => { setBizPin(p); if (!stats) loadStats(biz?.code, p, biz?.id); }}/>}

      {drawerClient && (
        <RewardsDrawer
          businessName={drawerClient.name}
          rewards={stats.pending_rewards.filter(r => r.phone === drawerClient.phone)}
          onClose={() => setDrawerClient(null)}
          readOnly
        />
      )}

      {/* ── Redemption modal ── */}
      {redeemStep > 0 && ReactDOM.createPortal(
        <div style={{ position:'fixed', inset:0, zIndex:300, background:'rgba(15,23,42,0.6)', backdropFilter:'blur(4px)', display:'flex', alignItems:'flex-end', justifyContent:'center', animation:'fadeIn .15s ease both' }}
          onClick={e => { if (e.target === e.currentTarget) resetRedeem(); }}>
          <div style={{ background:'var(--canvas)', borderRadius:'20px 20px 0 0', padding:'24px 24px 36px', width:'100%', maxWidth:430, boxShadow:'0 -8px 40px rgba(15,23,42,0.25)', animation:'slideUp .25s cubic-bezier(.2,.8,.2,1) both' }}
            onClick={e => e.stopPropagation()}>
            <div style={{ display:'flex', justifyContent:'space-between', alignItems:'center', marginBottom:20 }}>
              <div style={{ fontWeight:800, fontSize:16, display:'flex', alignItems:'center', gap:8 }}>🎁 {t('biz_redeem_title')}</div>
              <button onClick={resetRedeem} style={{ background:'var(--fog)', border:0, borderRadius:99, padding:7, cursor:'pointer', display:'flex' }}><IconX size={16}/></button>
            </div>
            {redeemStep === 1 && (
              <div style={{ display:'flex', flexDirection:'column', gap:14 }}>
                <div style={{ background:'rgba(234,179,8,0.1)', border:'1px solid rgba(234,179,8,0.3)', borderRadius:12, padding:'12px 14px' }}>
                  <div style={{ fontWeight:800, fontSize:13, color:'#92400e', marginBottom:4 }}>{t('biz_redeem_ine_title')}</div>
                  <div style={{ fontSize:12, color:'#78350f', lineHeight:1.55 }}>{t('biz_redeem_ine_body')}</div>
                </div>
                <label style={{ display:'flex', alignItems:'center', gap:10, cursor:'pointer' }}>
                  <input type="checkbox" checked={redeemIneOk} onChange={e => setRedeemIneOk(e.target.checked)} style={{ width:18, height:18, accentColor:'var(--teal)', cursor:'pointer' }}/>
                  <span style={{ fontSize:13, fontWeight:600 }}>{t('biz_redeem_ine_check')}</span>
                </label>
                <div>
                  <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_redeem_auth_label')}</div>
                  <input value={redeemAuth} onChange={e => setRedeemAuth(e.target.value)} placeholder="Ej: Carlos M." maxLength={60} style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:14, outline:'none' }}/>
                </div>
                <div>
                  <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_redeem_pin_label')}</div>
                  <input value={redeemPin} onChange={e => setRedeemPin(e.target.value.replace(/\D/g,'').slice(0,4))} placeholder={t('biz_redeem_pin_ph')} type="password" inputMode="numeric" autoComplete="new-password" style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:20, letterSpacing:'.25em', outline:'none', fontWeight:700 }}/>
                </div>
                {redeemError && <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600, background:'rgba(185,28,28,0.07)', borderRadius:8, padding:'8px 12px' }}>{redeemError}</div>}
                <button onClick={() => { setRedeemError(''); setRedeemStep(2); }} disabled={!redeemIneOk || !redeemAuth.trim() || redeemPin.length !== 4} style={{ background:'var(--teal)', color:'white', border:0, borderRadius:12, padding:'14px', fontWeight:700, fontSize:14, cursor:'pointer', opacity: !redeemIneOk || !redeemAuth.trim() || redeemPin.length !== 4 ? 0.45 : 1 }}>
                  {t('biz_redeem_continue')}
                </button>
              </div>
            )}
            {redeemStep === 2 && (
              <div style={{ display:'flex', flexDirection:'column', gap:14 }}>
                <div>
                  <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, marginBottom:6, textTransform:'uppercase', letterSpacing:'0.05em' }}>{t('biz_redeem_passport_label')}</div>
                  <input value={redeemPassport} onChange={e => setRedeemPassport(e.target.value.replace(/\D/g,''))} placeholder={t('biz_redeem_passport_ph')} inputMode="numeric" style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:10, padding:'12px', fontSize:22, letterSpacing:'.15em', outline:'none', fontWeight:700 }}/>
                </div>
                {redeemError && <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600, background:'rgba(185,28,28,0.07)', borderRadius:8, padding:'8px 12px' }}>{redeemError}</div>}
                <div style={{ display:'flex', gap:8 }}>
                  <button onClick={() => { setRedeemStep(1); setRedeemError(''); }} style={{ flex:1, background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'12px', fontSize:13, fontWeight:600, cursor:'pointer' }}>{t('scan_cancel')}</button>
                  <button onClick={handleRedeemVerify} disabled={redeemLoading || !redeemPassport.trim()} style={{ flex:2, background:'var(--teal)', color:'white', border:0, borderRadius:10, padding:'12px', fontSize:13, fontWeight:700, cursor:'pointer', opacity: redeemLoading || !redeemPassport.trim() ? 0.5 : 1 }}>
                    {redeemLoading ? t('biz_verifying') : t('biz_redeem_verify_btn')}
                  </button>
                </div>
              </div>
            )}
            {redeemStep === 3 && (
              <div style={{ display:'flex', flexDirection:'column', gap:16, alignItems:'center', padding:'8px 0' }}>
                <div style={{ fontSize:42 }}>⏳</div>
                <div style={{ fontWeight:800, fontSize:16, textAlign:'center' }}>
                  {redeemLoading ? t('biz_saving') : t('biz_redeem_waiting_title')}
                </div>
                {redeemLookup && (
                  <div style={{ background:'var(--fog)', borderRadius:14, padding:'14px 16px', width:'100%' }}>
                    <div style={{ fontSize:11, color:'var(--muted)', fontWeight:600, textTransform:'uppercase', letterSpacing:'0.05em', marginBottom:4 }}>Cliente</div>
                    <div style={{ fontWeight:800, fontSize:17 }}>{redeemLookup.user_name}</div>
                    {redeemLookup.gift && <div style={{ fontSize:13, color:'var(--muted)', marginTop:4 }}>🎁 {redeemLookup.gift}</div>}
                  </div>
                )}
                <div style={{ fontSize:13, color:'var(--muted)', textAlign:'center', lineHeight:1.6 }}>{t('biz_redeem_waiting_body')}</div>
                {redeemError && <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600, textAlign:'center', background:'rgba(185,28,28,0.07)', borderRadius:8, padding:'8px 12px', width:'100%' }}>{redeemError}</div>}
                {!redeemLoading && (
                  <button onClick={resetRedeem} style={{ background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'12px 24px', fontSize:13, fontWeight:600, cursor:'pointer', marginTop:4 }}>
                    {t('scan_cancel')}
                  </button>
                )}
              </div>
            )}
            {redeemStep === 4 && (
              <div style={{ textAlign:'center', padding:'8px 0 16px' }}>
                <div style={{ fontSize:48, marginBottom:12 }}>🎉</div>
                <div style={{ fontWeight:800, fontSize:20, color:'var(--teal)', marginBottom:6 }}>{t('biz_redeem_success_title')}</div>
                <div style={{ fontSize:14, color:'var(--muted)', marginBottom:4 }}>{t('biz_redeem_success_sub')}</div>
                <div style={{ fontWeight:700, fontSize:16, marginBottom:20 }}>{redeemLookup?.user_name}</div>
                {redeemLookup?.gift && <div style={{ fontSize:13, color:'#E91E8C', fontWeight:600, marginBottom:24 }}>🎁 {redeemLookup.gift}</div>}
                <button onClick={resetRedeem} style={{ background:'var(--teal)', color:'white', border:0, borderRadius:12, padding:'14px 32px', fontWeight:700, fontSize:14, cursor:'pointer' }}>
                  {t('biz_scan_another')}
                </button>
              </div>
            )}
          </div>
        </div>,
        document.body
      )}

      {showLogoutPin && (
        <div style={{
          position:'fixed', inset:0, zIndex:300,
          background:'rgba(15,23,42,0.72)', backdropFilter:'blur(4px)',
          display:'flex', alignItems:'center', justifyContent:'center',
          padding:'24px', animation:'fadeIn .15s ease both'
        }} onClick={() => { setShowLogoutPin(false); setLogoutPin(''); }}>
          <div style={{
            background:'var(--canvas)', borderRadius:20,
            padding:'28px 24px', width:'100%', maxWidth:360,
            boxShadow:'0 20px 60px rgba(15,23,42,0.3)'
          }} onClick={e => e.stopPropagation()}>
            <div style={{ fontWeight:800, fontSize:17, marginBottom:6 }}>{t('biz_logout')}</div>
            <div style={{ fontSize:13, color:'var(--muted)', marginBottom:20, lineHeight:1.5 }}>
              {t('biz_logout_pin_sub')}
            </div>
            <input
              value={logoutPin}
              onChange={e => { setLogoutPin(e.target.value.replace(/\D/g,'').slice(0,6)); setLogoutError(''); }}
              placeholder={t('biz_pin6_placeholder')}
              type="password"
              inputMode="numeric"
              autoComplete="new-password"
              style={{ width:'100%', boxSizing:'border-box', background:'var(--fog)', border:'1px solid rgba(15,23,42,0.12)', borderRadius:12, padding:'14px', fontSize:16, outline:'none', marginBottom:8 }}
            />
            {logoutError && <div style={{ color:'#b91c1c', fontSize:12, fontWeight:600, marginBottom:8 }}>{logoutError}</div>}
            <div style={{ display:'flex', gap:8, marginTop:4 }}>
              <button onClick={() => { setShowLogoutPin(false); setLogoutPin(''); setLogoutError(''); }} style={{ flex:1, background:'transparent', border:'1px solid rgba(15,23,42,0.15)', borderRadius:10, padding:'11px', fontSize:13, fontWeight:600, cursor:'pointer' }}>
                {t('scan_cancel')}
              </button>
              <button
                onClick={handleLogoutConfirm}
                disabled={logoutLoading || logoutPin.length < 6}
                style={{ flex:2, background:'#b91c1c', color:'white', border:0, borderRadius:10, padding:'11px', fontSize:13, fontWeight:700, cursor:'pointer', opacity: logoutLoading || logoutPin.length < 6 ? 0.5 : 1 }}
              >
                {logoutLoading ? t('biz_verifying') : t('biz_logout')}
              </button>
            </div>
          </div>
        </div>
      )}
    </div>
  );
};

Object.assign(window, { BusinessPanel });