// =============================================================================
// PAGES — vues principales (un onglet = une vue)
// =============================================================================

// =============================================================================
// PAGES — vues principales (un onglet = une vue)
// =============================================================================

// === TabsScreen (gestion des ardoises) ===
function TabsScreen({ tabs, activeTabId, setActiveTabId, createTab, addToTab, removeFromTab, closeTab, cancelTab, setTabsScreenOpen, isOnline, drinks }) {
  // 'list' (toutes les ardoises ouvertes) | 'tab' (une ardoise détaillée) | 'pay' (étape de paiement)
  const [view, setLocalView] = useState('list');
  const [openedTabId, setOpenedTabId] = useState(null);
  const [newTabName, setNewTabName] = useState('');
  const [showNewTab, setShowNewTab] = useState(false);
  const [confirmCancel, setConfirmCancel] = useState(false);
  const [pendingPayment, setPendingPayment] = useState(null);
  const [tabDiscount, setTabDiscount] = useState(0);

  const openTabs = (tabs || []).filter(t => t.status === 'open');
  const openedTab = openedTabId ? openTabs.find(t => t._key === openedTabId) : null;

  // Quand l'ardoise consultée se referme (par clôture par ex.) → retour à la liste
  useEffect(() => {
    if (view !== 'list' && !openedTab) {
      setLocalView('list');
      setOpenedTabId(null);
      setPendingPayment(null);
      setTabDiscount(0);
    }
  }, [openedTab, view]);

  const handleCreate = async () => {
    if (!newTabName.trim()) return;
    const tabId = await createTab(newTabName.trim());
    if (tabId) {
      setNewTabName(''); setShowNewTab(false);
      setActiveTabId(tabId); // active immédiatement la nouvelle ardoise
      setTabsScreenOpen(false); // retour à la vue Ventes pour ajouter des items
    }
  };

  const handleSetActive = (tabId) => {
    setActiveTabId(tabId);
    setTabsScreenOpen(false); // retour à la carte pour ajouter
  };

  const handleOpenTab = (tabId) => {
    setOpenedTabId(tabId);
    setLocalView('tab');
  };

  const itemsArr = openedTab ? Object.values(openedTab.items || {}).filter(i => (i.quantity || 0) > 0) : [];
  const subtotal = itemsArr.reduce((s, it) => s + (it.price || 0) * (it.quantity || 0), 0);
  const total = subtotal * (1 - (tabDiscount || 0));

  // === Vue paiement d'une ardoise ===
  if (view === 'pay' && openedTab) {
    const isOfferedPending = pendingPayment === 'offert';
    const displayedTotal = isOfferedPending ? 0 : total;
    return (
      <div className="px-4 pt-4 pb-4 space-y-3">
        <div className="flex items-center gap-2">
          <button onClick={() => { setLocalView('tab'); setPendingPayment(null); }} className="text-stone-500 hover:text-stone-900 p-1">
            <Icon name="ChevronUp" className="w-5 h-5 rotate-[-90deg]" strokeWidth={2.5} />
          </button>
          <h2 className="font-display font-bold text-xl text-stone-900 tracking-tight flex-1 truncate">Encaisser : {openedTab.name}</h2>
        </div>
        <div className="bg-stone-50 border border-stone-200 rounded-xl p-3 space-y-1">
          {itemsArr.map(it => (
            <div key={it.drinkId} className="flex justify-between text-sm">
              <span className="text-stone-700 truncate">{it.quantity} × {it.name}</span>
              <span className="font-mono tabular-nums text-stone-900 font-semibold">{formatPrice((it.price || 0) * (it.quantity || 0))}</span>
            </div>
          ))}
          <div className="border-t border-stone-200 pt-2 mt-2 flex justify-between text-base">
            <span className="font-bold text-stone-900">Sous-total</span>
            <span className="font-mono tabular-nums font-bold text-stone-900">{formatPrice(subtotal)}</span>
          </div>
        </div>

        {!pendingPayment && (
          <button
            onClick={() => setTabDiscount(tabDiscount > 0 ? 0 : DISCOUNT_RATE)}
            className={`w-full flex items-center justify-center gap-2 rounded-xl py-3 text-sm font-bold transition-all ${
              tabDiscount > 0 ? 'bg-emerald-500 hover:bg-emerald-600 text-white' : 'bg-stone-100 hover:bg-stone-200 text-stone-700'
            }`}>
            <Icon name="Percent" className="w-4 h-4" strokeWidth={2.5} />
            Réduction -{Math.round(DISCOUNT_RATE * 100)}%
            {tabDiscount > 0 && <Icon name="Check" className="w-4 h-4" strokeWidth={2.5} />}
          </button>
        )}

        {pendingPayment ? (
          <div className="space-y-3 slide-up">
            <div className={`text-center py-3 rounded-xl ${isOfferedPending ? 'bg-violet-50' : 'bg-stone-50'}`}>
              <div className="text-xs uppercase tracking-widest text-stone-500 font-semibold mb-1">Confirmer l'encaissement</div>
              <div className={`flex items-center justify-center gap-2 mb-1 ${isOfferedPending ? 'text-violet-700' : 'text-stone-700'}`}>
                <Icon name={PAYMENT_BY_ID[pendingPayment].icon} className="w-5 h-5" />
                <span className="font-bold text-base">{PAYMENT_BY_ID[pendingPayment].label}</span>
                {tabDiscount > 0 && !isOfferedPending && (
                  <span className="bg-emerald-100 text-emerald-700 text-[10px] font-bold px-1.5 py-0.5 rounded-full">-{Math.round(tabDiscount * 100)}%</span>
                )}
              </div>
              {isOfferedPending ? (
                <>
                  <div className="font-mono text-base text-stone-400 line-through tabular-nums">{formatPrice(subtotal)}</div>
                  <div className="font-mono text-4xl font-bold text-violet-700 tabular-nums leading-none mt-1">OFFERT</div>
                </>
              ) : (
                <>
                  {tabDiscount > 0 && <div className="font-mono text-sm text-stone-400 line-through tabular-nums">{formatPrice(subtotal)}</div>}
                  <div className="font-mono text-4xl font-bold text-stone-900 tabular-nums leading-none">{formatPrice(displayedTotal)}</div>
                </>
              )}
            </div>
            <div className="grid grid-cols-[1fr_2fr] gap-2">
              <button onClick={() => setPendingPayment(null)} className="bg-stone-100 hover:bg-stone-200 text-stone-700 rounded-xl py-4 font-bold text-base">Retour</button>
              <button onClick={async () => {
                const ok = await closeTab(openedTab._key, pendingPayment, tabDiscount);
                if (ok) { setLocalView('list'); setOpenedTabId(null); setPendingPayment(null); setTabDiscount(0); }
              }} className={`rounded-xl py-4 font-bold text-lg flex items-center justify-center gap-2 text-white ${
                isOfferedPending ? 'bg-violet-600 hover:bg-violet-700' : 'bg-emerald-500 hover:bg-emerald-600'
              }`}>
                <Icon name="Check" className="w-6 h-6" strokeWidth={2.5} /> Confirmer
              </button>
            </div>
          </div>
        ) : (
          <div className="grid grid-cols-4 gap-1.5">
            {PAYMENT_METHODS.map(pm => {
              const isOffert = pm.id === 'offert';
              return (
                <button key={pm.id} onClick={() => setPendingPayment(pm.id)} className={`active:scale-95 rounded-xl py-4 px-1 flex flex-col items-center gap-1 font-bold text-sm text-white ${
                  isOffert ? 'bg-violet-600 hover:bg-violet-700' : 'bg-stone-900 hover:bg-stone-700'
                }`}>
                  <Icon name={pm.icon} className="w-6 h-6" /> {pm.label}
                </button>
              );
            })}
          </div>
        )}
      </div>
    );
  }

  // === Vue détail d'une ardoise ===
  if (view === 'tab' && openedTab) {
    return (
      <div className="px-4 pt-4 pb-4 space-y-3">
        <div className="flex items-center gap-2">
          <button onClick={() => { setLocalView('list'); setOpenedTabId(null); setConfirmCancel(false); }} className="text-stone-500 hover:text-stone-900 p-1">
            <Icon name="ChevronUp" className="w-5 h-5 rotate-[-90deg]" strokeWidth={2.5} />
          </button>
          <h2 className="font-display font-bold text-xl text-stone-900 tracking-tight flex-1 truncate">{openedTab.name}</h2>
        </div>
        <div className="text-[10px] text-stone-500 font-mono">
          Créée par {openedTab.createdBy || '?'} · {new Date(openedTab.createdAt || 0).toLocaleTimeString('fr-BE', { hour: '2-digit', minute: '2-digit' })}
        </div>

        <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
          {itemsArr.length === 0 ? (
            <div className="px-4 py-8 text-center text-sm text-stone-500">Aucun item — retourne à la carte pour en ajouter</div>
          ) : itemsArr.map(it => (
            <div key={it.drinkId} className="px-3 py-2.5 flex items-center justify-between gap-2">
              <div className="min-w-0 flex-1">
                <div className="text-sm font-semibold text-stone-900 truncate">{it.name}</div>
                <div className="text-[11px] text-stone-500 font-mono tabular-nums">{formatPrice(it.price)} × {it.quantity}</div>
              </div>
              <div className="flex items-center gap-2 shrink-0">
                <div className="font-mono text-sm font-bold tabular-nums text-stone-900">{formatPrice((it.price || 0) * (it.quantity || 0))}</div>
                <button onClick={() => removeFromTab(openedTab._key, it.drinkId)} disabled={!isOnline} className="w-8 h-8 rounded-md bg-stone-100 hover:bg-stone-200 disabled:opacity-30 flex items-center justify-center text-stone-700" title="Retirer 1 unité">
                  <Icon name="Minus" className="w-3.5 h-3.5" strokeWidth={2.5} />
                </button>
              </div>
            </div>
          ))}
          {itemsArr.length > 0 && (
            <div className="px-3 py-2.5 flex justify-between items-baseline bg-stone-50">
              <span className="text-xs uppercase tracking-widest text-stone-500 font-bold">Total</span>
              <span className="font-mono text-xl font-bold text-stone-900 tabular-nums">{formatPrice(subtotal)}</span>
            </div>
          )}
        </div>

        <div className="grid grid-cols-2 gap-2">
          <button onClick={() => { setActiveTabId(openedTab._key); setTabsScreenOpen(false); }} disabled={!isOnline}
            className="flex items-center justify-center gap-1.5 bg-violet-600 hover:bg-violet-700 disabled:opacity-40 text-white rounded-xl py-3 text-sm font-bold">
            <Icon name="Plus" className="w-4 h-4" strokeWidth={2.5} /> Ajouter des items
          </button>
          <button onClick={() => setLocalView('pay')} disabled={!isOnline || itemsArr.length === 0}
            className="flex items-center justify-center gap-1.5 bg-emerald-500 hover:bg-emerald-600 disabled:opacity-40 text-white rounded-xl py-3 text-sm font-bold">
            <Icon name="Check" className="w-4 h-4" strokeWidth={2.5} /> Encaisser
          </button>
        </div>

        {!confirmCancel ? (
          <button onClick={() => setConfirmCancel(true)} disabled={!isOnline} className="w-full flex items-center justify-center gap-1 text-xs text-stone-500 hover:text-rose-600 py-2 disabled:opacity-30">
            <Icon name="Trash2" className="w-3 h-3" /> Supprimer cette ardoise (restaurer le stock)
          </button>
        ) : (
          <div className="bg-rose-50 border border-rose-200 rounded-xl p-3 space-y-2 slide-up">
            <div className="text-xs text-rose-800">Supprimer l'ardoise et restaurer le stock de tous ses items ?</div>
            <div className="grid grid-cols-2 gap-2">
              <button onClick={() => setConfirmCancel(false)} className="bg-stone-100 text-stone-700 text-xs py-2 rounded-lg font-semibold">Annuler</button>
              <button onClick={async () => {
                const ok = await cancelTab(openedTab._key);
                if (ok) { setLocalView('list'); setOpenedTabId(null); setConfirmCancel(false); }
              }} className="bg-rose-500 text-white text-xs py-2 rounded-lg font-bold">Supprimer</button>
            </div>
          </div>
        )}
      </div>
    );
  }

  // === Vue liste des ardoises ouvertes ===
  return (
    <div className="px-4 pt-4 pb-4 space-y-3">
      <div className="flex items-center justify-between gap-2">
        <div className="flex items-center gap-2">
          <button onClick={() => setTabsScreenOpen(false)} className="text-stone-500 hover:text-stone-900 p-1">
            <Icon name="ChevronUp" className="w-5 h-5 rotate-[-90deg]" strokeWidth={2.5} />
          </button>
          <h2 className="font-display font-bold text-2xl text-stone-900 tracking-tight">Ardoises</h2>
        </div>
        <button onClick={() => setShowNewTab(s => !s)} disabled={!isOnline} className="flex items-center gap-1 text-xs text-white bg-orange-500 hover:bg-orange-600 disabled:opacity-40 px-3 py-2 rounded-full font-bold uppercase tracking-wider">
          <Icon name="Plus" className="w-3 h-3" strokeWidth={2.5} /> Nouvelle
        </button>
      </div>

      {!isOnline && (
        <div className="bg-rose-50 border border-rose-200 rounded-xl px-3 py-2 flex items-center gap-2">
          <Icon name="CloudOff" className="w-4 h-4 text-rose-700 shrink-0" strokeWidth={2.5} />
          <div className="text-xs text-rose-900 leading-tight">
            <span className="font-bold">Hors ligne.</span> Tu peux consulter les ardoises mais pas les modifier tant que le wifi n'est pas revenu.
          </div>
        </div>
      )}

      {showNewTab && isOnline && (
        <div className="bg-white border border-stone-300 rounded-xl p-3 space-y-2 slide-up">
          <input type="text" autoFocus value={newTabName} onChange={e => setNewTabName(e.target.value)}
            placeholder="Nom (ex: Marie, Table 5, Famille)"
            onKeyDown={e => { if (e.key === 'Enter') handleCreate(); if (e.key === 'Escape') { setShowNewTab(false); setNewTabName(''); } }}
            className="w-full bg-stone-50 border border-stone-200 rounded-lg px-3 py-2 text-sm focus:border-orange-500 focus:outline-none" />
          <div className="grid grid-cols-2 gap-2">
            <button onClick={() => { setShowNewTab(false); setNewTabName(''); }} className="bg-stone-100 hover:bg-stone-200 text-stone-700 rounded-lg py-2 text-sm font-semibold">Annuler</button>
            <button onClick={handleCreate} disabled={!newTabName.trim()} className="bg-orange-500 hover:bg-orange-600 disabled:opacity-40 text-white rounded-lg py-2 text-sm font-bold">Créer</button>
          </div>
        </div>
      )}

      {openTabs.length === 0 ? (
        <div className="bg-white border border-stone-200 rounded-xl px-4 py-12 text-center text-sm text-stone-500">
          <Icon name="Receipt" className="w-10 h-10 text-stone-300 mx-auto mb-2" strokeWidth={1.5} />
          Aucune ardoise ouverte
        </div>
      ) : (
        <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
          {openTabs.map(tab => {
            const items = Object.values(tab.items || {}).filter(i => (i.quantity || 0) > 0);
            const tabSubtotal = items.reduce((s, it) => s + (it.price || 0) * (it.quantity || 0), 0);
            const tabCount = items.reduce((s, it) => s + (it.quantity || 0), 0);
            const isActive = tab._key === activeTabId;
            return (
              <div key={tab._key} className={`px-3 py-3 flex items-center gap-3 ${isActive ? 'bg-violet-50' : ''}`}>
                <div className="w-10 h-10 rounded-full bg-violet-100 flex items-center justify-center shrink-0">
                  <Icon name="Receipt" className="w-5 h-5 text-violet-700" strokeWidth={2} />
                </div>
                <div className="min-w-0 flex-1">
                  <div className="flex items-center gap-2">
                    <div className="text-sm font-bold text-stone-900 truncate">{tab.name}</div>
                    {isActive && <span className="bg-violet-200 text-violet-800 text-[9px] font-bold uppercase tracking-wider px-1.5 py-0.5 rounded-full">Active</span>}
                  </div>
                  <div className="text-[11px] text-stone-500 font-mono">
                    {tabCount} item{tabCount > 1 ? 's' : ''} · {tab.createdBy || '?'}
                  </div>
                </div>
                <div className="font-mono text-base font-bold text-stone-900 tabular-nums shrink-0">{formatPrice(tabSubtotal)}</div>
                <div className="flex flex-col gap-1 shrink-0">
                  {!isActive ? (
                    <button onClick={() => handleSetActive(tab._key)} disabled={!isOnline} className="bg-violet-600 hover:bg-violet-700 disabled:opacity-40 text-white text-[10px] font-bold px-2.5 py-1.5 rounded">
                      Activer
                    </button>
                  ) : (
                    <button onClick={() => setActiveTabId(null)} className="bg-stone-200 text-stone-700 text-[10px] font-bold px-2.5 py-1.5 rounded">
                      Désactiver
                    </button>
                  )}
                  <button onClick={() => handleOpenTab(tab._key)} className="bg-white hover:bg-stone-50 border border-stone-200 text-stone-700 text-[10px] font-bold px-2.5 py-1.5 rounded">
                    Voir
                  </button>
                </div>
              </div>
            );
          })}
        </div>
      )}
    </div>
  );
}

// === SalesView (onglet Ventes) ===
function SalesView({ drinks, photos, cart, onDrinkTap, canUndo, undoLastSale, activeCategory, setActiveCategory, quickMode, toggleQuickMode, lowStockCount, setView, isAdmin, tabs, activeTabId, setActiveTabId, setTabsScreenOpen, isOnline }) {
  const sellable = drinks.filter(d => !d.stockOnly);
  const visible = activeCategory === 'all' ? sellable : sellable.filter(d => d.category === activeCategory);
  const openTabs = (tabs || []).filter(t => t.status === 'open');
  const activeTab = activeTabId ? openTabs.find(t => t._key === activeTabId) : null;
  // Total de l'ardoise active (calculé à la volée depuis les items)
  const activeTabTotal = activeTab
    ? Object.values(activeTab.items || {}).reduce((s, it) => s + (it.price || 0) * (it.quantity || 0), 0)
    : 0;
  const activeTabCount = activeTab
    ? Object.values(activeTab.items || {}).reduce((s, it) => s + (it.quantity || 0), 0)
    : 0;
  return (
    <div className="px-4 pt-4">
      <div className="flex items-center justify-between mb-3 gap-2">
        <h2 className="font-display font-bold text-2xl text-stone-900 tracking-tight">Carte</h2>
        <div className="flex items-center gap-2 flex-wrap justify-end">
          {isAdmin && lowStockCount > 0 && (
            <button onClick={() => setView('stock')} className="flex items-center gap-1.5 text-xs text-orange-700 bg-orange-50 border border-orange-200 px-2.5 py-1.5 rounded-full font-bold hover:bg-orange-100">
              <Icon name="AlertCircle" className="w-3.5 h-3.5" strokeWidth={2.5} />
              {lowStockCount} stock bas
            </button>
          )}
          <button onClick={() => setTabsScreenOpen(true)} disabled={!isOnline && openTabs.length === 0}
            className={`flex items-center gap-1.5 text-xs px-3 py-1.5 rounded-full font-semibold border transition-all ${
              openTabs.length > 0 ? 'bg-violet-100 text-violet-800 border-violet-300 hover:bg-violet-200' : 'bg-white text-stone-700 border-stone-200 hover:bg-stone-50 disabled:opacity-40'
            }`}>
            <Icon name="Receipt" className="w-3.5 h-3.5" strokeWidth={2.5} />
            Ardoises{openTabs.length > 0 ? ` (${openTabs.length})` : ''}
          </button>
          {isAdmin && !activeTabId && (
            <button onClick={toggleQuickMode} className={`flex items-center gap-1.5 text-xs px-3 py-1.5 rounded-full font-semibold border transition-all ${
              quickMode ? 'bg-amber-400 text-stone-900 border-amber-500 shadow-sm' : 'bg-white text-stone-700 border-stone-200 hover:bg-stone-50'
            }`}>
              <Icon name="Zap" className={`w-3 h-3 ${quickMode ? '' : 'text-stone-400'}`} strokeWidth={2.5} />
              Rapide
            </button>
          )}
          {canUndo && (
            <button onClick={undoLastSale} className="flex items-center gap-1.5 text-xs text-stone-700 hover:text-orange-600 px-3 py-1.5 rounded-full bg-white border border-stone-200 font-semibold">
              <Icon name="Undo2" className="w-3 h-3" /> Annuler
            </button>
          )}
        </div>
      </div>

      {/* Bandeau d'ardoise active (priorité visuelle sur le mode rapide) */}
      {activeTab && (
        <div className="bg-violet-100 border border-violet-300 rounded-xl px-3 py-2.5 mb-3 flex items-center gap-2 slide-up">
          <Icon name="Receipt" className="w-5 h-5 text-violet-700 shrink-0" strokeWidth={2.5} />
          <div className="flex-1 min-w-0">
            <div className="text-[10px] uppercase tracking-widest text-violet-700 font-bold leading-none">Ardoise active</div>
            <div className="text-sm font-bold text-violet-900 truncate mt-0.5">{activeTab.name}</div>
          </div>
          <div className="text-right">
            <div className="font-mono text-base font-bold text-violet-900 tabular-nums">{formatPrice(activeTabTotal)}</div>
            <div className="text-[10px] text-violet-700 font-mono tabular-nums">{activeTabCount} item{activeTabCount > 1 ? 's' : ''}</div>
          </div>
          <button onClick={() => setTabsScreenOpen(true)} className="bg-violet-600 hover:bg-violet-700 text-white text-xs font-bold px-3 py-1.5 rounded-lg shrink-0">
            Voir
          </button>
          <button onClick={() => setActiveTabId(null)} className="text-violet-700 hover:text-violet-900 p-1 shrink-0" title="Quitter l'ardoise (sans clôturer)">
            <Icon name="X" className="w-4 h-4" strokeWidth={2.5} />
          </button>
        </div>
      )}

      {!activeTab && quickMode && (
        <div className="bg-amber-50 border border-amber-300 rounded-xl px-3 py-2 mb-3 flex items-center gap-2 slide-up">
          <Icon name="Zap" className="w-4 h-4 text-amber-700 shrink-0" strokeWidth={2.5} />
          <div className="text-xs text-amber-900 font-semibold leading-tight">Mode rapide actif — un appui = vente cash immédiate</div>
        </div>
      )}

      {!isOnline && (
        <div className="bg-rose-50 border border-rose-200 rounded-xl px-3 py-2 mb-3 flex items-center gap-2 slide-up">
          <Icon name="CloudOff" className="w-4 h-4 text-rose-700 shrink-0" strokeWidth={2.5} />
          <div className="text-xs text-rose-900 leading-tight">
            <span className="font-bold">Hors ligne.</span> Les ventes du panier sont mises en file d'attente et synchronisées dès le retour du wifi. Les ardoises sont indisponibles.
          </div>
        </div>
      )}

      <CategoryFilter drinks={sellable} activeCategory={activeCategory} setActiveCategory={setActiveCategory} />
      <div className="grid grid-cols-2 gap-3 mt-3">
        {visible.map(d => <DrinkCard key={d.id} drink={d} drinks={drinks} photo={photos[d.id]} inCart={cart[d.id] || 0} onTap={() => onDrinkTap(d.id)} />)}
      </div>
      {visible.length === 0 && (
        <div className="text-center py-12 text-stone-500">
          <div className="mb-2">Aucune boisson dans cette catégorie</div>
        </div>
      )}
    </div>
  );
}

// === StockInput (saisie clavier de la quantité de stock) ===
// Accepte des décimales quand l'item a un stockUnit (ex: 0.7 pour 70cl en L).
// Sinon comportement entier (compte de bouteilles, canettes, etc.)
function StockInput({ drink, tracked, stock, isOut, isLow, setStock, updateDrink }) {
  const [editing, setEditing] = useState(false);
  const allowDecimals = !!drink.stockUnit;
  // Format propre pour l'affichage : 2 décimales max, sans zéros inutiles, et nettoyage des erreurs IEEE-754.
  const fmt = (n) => {
    if (!isFinite(n)) return '0';
    if (!allowDecimals) return String(Math.floor(n));
    return parseFloat(n.toFixed(2)).toString();
  };
  const [value, setValue] = useState(fmt(stock));
  // Resync depuis Firebase quand on n'est pas en train de saisir
  useEffect(() => {
    if (!editing) setValue(fmt(stock));
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [stock, editing]);

  const commit = async () => {
    setEditing(false);
    const parsed = parseFloat(value.replace(',', '.'));
    let v = isNaN(parsed) ? 0 : Math.max(0, parsed);
    if (!allowDecimals) v = Math.floor(v);
    else v = parseFloat(v.toFixed(2)); // évite les 0.6599999...
    if (!tracked) {
      await updateDrink(drink.id, { stockEnabled: true, stock: v });
    } else if (v !== stock) {
      await setStock(drink.id, v);
    }
    setValue(fmt(v));
  };

  const colorClass = !tracked && !editing
    ? 'text-stone-300'
    : isOut ? 'text-rose-600'
    : isLow ? 'text-orange-600'
    : 'text-stone-900';
  // Permet le séparateur décimal (point ou virgule) si décimales autorisées
  const sanitize = (raw) => allowDecimals
    ? raw.replace(/[^0-9.,]/g, '').replace(',', '.').replace(/(\..*)\./g, '$1')
    : raw.replace(/[^0-9]/g, '');

  return (
    <input
      type="text"
      inputMode={allowDecimals ? "decimal" : "numeric"}
      pattern={allowDecimals ? "[0-9.,]*" : "[0-9]*"}
      value={editing ? value : (tracked ? fmt(stock) : '—')}
      onFocus={(e) => { setEditing(true); setValue(tracked ? fmt(stock) : ''); e.target.select(); }}
      onChange={(e) => setValue(sanitize(e.target.value))}
      onBlur={commit}
      onKeyDown={(e) => { if (e.key === 'Enter') e.target.blur(); if (e.key === 'Escape') { setValue(fmt(stock)); setEditing(false); e.target.blur(); } }}
      className={`font-mono font-bold text-lg ${allowDecimals ? 'w-16' : 'w-12'} text-center tabular-nums bg-transparent border-0 rounded-md focus:bg-orange-50 focus:ring-2 focus:ring-orange-400 focus:outline-none px-0.5 ${colorClass}`}
      aria-label={`Stock ${drink.name}`}
    />
  );
}

// === StockView (onglet Stock) ===
function StockView({ drinks, photos, setDrinkPhoto, addDrink, updateDrink, adjustStock, setStock }) {
  const [showAdd, setShowAdd] = useState(false);
  const [newDrink, setNewDrink] = useState({ name: '', price: '', stock: '', icon: 'Wine', category: 'biere', photo: null });

  const handleAddDrink = async () => {
    if (!newDrink.name || !newDrink.price) return;
    const stockValue = parseFloat((newDrink.stock || '0').toString().replace(',', '.')) || 0;
    const newId = genId();
    await addDrink({
      id: newId,
      name: newDrink.name,
      price: parseFloat(newDrink.price.toString().replace(',', '.')) || 0,
      icon: newDrink.icon || 'Wine',
      category: newDrink.category || 'biere',
      stockEnabled: true,
      stock: stockValue,
    });
    if (newDrink.photo) await setDrinkPhoto(newId, newDrink.photo);
    setNewDrink({ name: '', price: '', stock: '', icon: 'Wine', category: 'biere', photo: null });
    setShowAdd(false);
  };

  const handleAdjust = async (drink, delta) => {
    if (drink.parentId) return;
    if (!drink.stockEnabled) {
      await updateDrink(drink.id, { stockEnabled: true, stock: Math.max(0, delta) });
    } else {
      await adjustStock(drink.id, delta);
    }
  };

  const standaloneAndParents = drinks.filter(d => !d.parentId && !(d.ingredients && d.ingredients.length > 0));

  return (
    <div className="px-4 pt-4 space-y-4 pb-4">
      <div className="flex items-center justify-between">
        <h2 className="font-display font-bold text-2xl text-stone-900 tracking-tight">Stock</h2>
        <button onClick={() => setShowAdd(!showAdd)} className="text-xs text-white bg-orange-500 hover:bg-orange-600 flex items-center gap-1 px-3 py-2 rounded-full font-bold uppercase tracking-wider">
          <Icon name="Plus" className="w-3 h-3" strokeWidth={2.5} /> Ajouter
        </button>
      </div>

      <div className="bg-white border border-stone-200 rounded-xl p-3 flex items-center justify-between">
        <div>
          <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">Valeur stock disponible</div>
          <div className="font-mono text-2xl text-stone-900 font-bold tabular-nums leading-tight">{formatPrice(stockTotalValue(drinks))}</div>
        </div>
        <div className="text-right">
          <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">Items suivis</div>
          <div className="font-mono text-2xl text-stone-900 font-bold tabular-nums leading-tight">{drinks.filter(d => d.stockEnabled && !d.parentId).length}</div>
        </div>
      </div>

      {showAdd && (
        <div className="bg-white border border-stone-300 rounded-xl p-3 slide-up space-y-2">
          <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">Nouvelle boisson</div>
          <input type="text" value={newDrink.name} onChange={e => setNewDrink({ ...newDrink, name: e.target.value })} placeholder="Nom (ex: Coca 33cl)" className="w-full bg-stone-50 border border-stone-200 rounded-lg px-3 py-2 text-sm focus:border-orange-500 focus:outline-none" />
          <div className="grid grid-cols-2 gap-2">
            <div>
              <div className="text-[10px] text-stone-500 mb-1">Prix de vente</div>
              <input type="text" inputMode="decimal" value={newDrink.price} onChange={e => setNewDrink({ ...newDrink, price: e.target.value })} placeholder="3,00" className="w-full bg-stone-50 border border-stone-200 rounded-lg px-2 py-2 text-sm font-mono text-right focus:border-orange-500 focus:outline-none" />
            </div>
            <div>
              <div className="text-[10px] text-stone-500 mb-1">Stock initial</div>
              <input type="text" inputMode="decimal" value={newDrink.stock} onChange={e => setNewDrink({ ...newDrink, stock: e.target.value })} placeholder="20" className="w-full bg-stone-50 border border-stone-200 rounded-lg px-2 py-2 text-sm font-mono text-right focus:border-orange-500 focus:outline-none" />
            </div>
          </div>
          <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold pt-1">Photo (optionnel)</div>
          <PhotoPicker value={newDrink.photo} onChange={(p) => setNewDrink({ ...newDrink, photo: p })} />
          <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold pt-1">Catégorie</div>
          <CategoryPicker value={newDrink.category} onChange={(v) => setNewDrink({ ...newDrink, category: v })} />
          <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold pt-1">Icône</div>
          <IconPicker value={newDrink.icon} onChange={(v) => setNewDrink({ ...newDrink, icon: v })} />
          <div className="flex gap-2 pt-2">
            <button onClick={handleAddDrink} disabled={!newDrink.name || !newDrink.price} className="flex-1 bg-orange-500 hover:bg-orange-600 disabled:opacity-40 text-white font-bold text-sm py-2.5 rounded-lg">Ajouter</button>
            <button onClick={() => setShowAdd(false)} className="flex-1 bg-stone-100 hover:bg-stone-200 text-stone-700 text-sm py-2.5 rounded-lg font-semibold">Annuler</button>
          </div>
        </div>
      )}

      <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
        {standaloneAndParents.length === 0 && (
          <div className="px-4 py-6 text-center text-stone-500 text-sm">Aucune boisson dans le menu</div>
        )}
        {standaloneAndParents.map(drink => {
          const cat = CATEGORIES[drink.category];
          const tracked = !!drink.stockEnabled;
          const stock = Math.floor(drink.stock || 0);
          const isOut = tracked && stock <= 0;
          const isLow = tracked && stock > 0 && stock <= 5;
          // Enfants par parentId classique OU par ingrédient
          const children = drinks.filter(d =>
            d.parentId === drink.id ||
            (d.ingredients && d.ingredients.some(i => i.parentId === drink.id))
          );
          const photo = photos[drink.id];
          const handleRowPhoto = async (e) => {
            const file = e.target.files && e.target.files[0];
            if (!file) return;
            try {
              const dataUrl = await processImage(file);
              await setDrinkPhoto(drink.id, dataUrl);
            } catch (err) { console.error('photo error', err); }
            e.target.value = '';
          };
          return (
            <div key={drink.id} className="px-3 py-3">
              <div className="flex items-center justify-between gap-3">
                <div className="flex items-center gap-2 min-w-0 flex-1">
                  <div className="relative shrink-0">
                    <input type="file" accept="image/*" id={`p-${drink.id}`} className="hidden" onChange={handleRowPhoto} />
                    <label htmlFor={`p-${drink.id}`} className="block w-12 h-12 rounded-lg overflow-hidden bg-stone-100 cursor-pointer border border-stone-200 hover:border-orange-300 transition-colors relative">
                      {photo ? (
                        <img src={photo} alt={drink.name} className="w-full h-full object-cover" loading="lazy" />
                      ) : (
                        <div className="w-full h-full flex items-center justify-center text-stone-400">
                          <Icon name={drink.icon} className="w-6 h-6" strokeWidth={1.5} />
                        </div>
                      )}
                      {!photo && (
                        <div className="absolute inset-x-0 bottom-0 bg-stone-900/60 text-white text-[8px] font-bold uppercase tracking-wider text-center py-0.5">+ Photo</div>
                      )}
                    </label>
                  </div>
                  <div className="min-w-0">
                    <div className="flex items-center gap-2">
                      <div className="text-sm font-semibold text-stone-900 truncate">{drink.name}</div>
                      {cat && <div className={`text-[9px] font-bold uppercase tracking-wider px-1.5 py-0.5 rounded-full shrink-0 ${cat.bg} ${cat.text}`}>{cat.label}</div>}
                    </div>
                    {drink.stockOnly ? (
                      <div className="text-[10px] text-stone-400 italic">Ingrédient (non vendu)</div>
                    ) : (
                      <div className="font-mono text-[10px] text-stone-500 tabular-nums">{formatPrice(drink.price)}</div>
                    )}
                  </div>
                </div>
                <div className="flex items-center gap-1 shrink-0">
                  {(() => {
                    // Pas d'incréments en unités si l'item est mesuré en L (incréments décimaux à la place)
                    const isLitres = drink.stockUnit === 'L';
                    const minusStep = isLitres ? -0.1 : -1;
                    const plusStep  = isLitres ?  0.1 :  1;
                    const bigStep   = isLitres ?  0.7 : 10;
                    const bigLabel  = isLitres ? '+0.7' : '+10';
                    return (
                      <>
                        <button onClick={() => handleAdjust(drink, minusStep)} disabled={!tracked || stock <= 0} className="w-7 h-7 rounded-md bg-stone-100 hover:bg-stone-200 disabled:opacity-30 flex items-center justify-center text-stone-700">
                          <Icon name="Minus" className="w-3 h-3" strokeWidth={2.5} />
                        </button>
                        <StockInput
                          drink={drink}
                          tracked={tracked}
                          stock={stock}
                          isOut={isOut}
                          isLow={isLow}
                          setStock={setStock}
                          updateDrink={updateDrink}
                        />
                        {drink.stockUnit && tracked && (
                          <span className="text-[10px] text-stone-500 font-semibold -ml-1 mr-0.5">{drink.stockUnit}</span>
                        )}
                        <button onClick={() => handleAdjust(drink, plusStep)} className="w-7 h-7 rounded-md bg-orange-500 hover:bg-orange-600 text-white flex items-center justify-center">
                          <Icon name="Plus" className="w-3 h-3" strokeWidth={2.5} />
                        </button>
                        <button onClick={() => handleAdjust(drink, bigStep)} className="ml-1 px-2 h-7 rounded-md bg-stone-900 hover:bg-stone-700 text-white text-[10px] font-bold">{bigLabel}</button>
                      </>
                    );
                  })()}
                </div>
              </div>
              {children.length > 0 && tracked && (
                <div className="mt-2 ml-7 pl-2 border-l-2 border-stone-100 space-y-1">
                  {children.map(c => {
                    // Trouver la relation : parentRatio ou ingrédient
                    const ing = c.ingredients && c.ingredients.find(i => i.parentId === drink.id);
                    let childStock, ratioLabel;
                    if (ing) {
                      childStock = ing.amount > 0 ? Math.floor((drink.stock || 0) / ing.amount) : 0;
                      // Affichage "humain" : 0.04L → "4cl" pour la lisibilité
                      const friendly = (drink.stockUnit === 'L' && ing.amount > 0 && ing.amount < 1)
                        ? `${parseFloat((ing.amount * 100).toFixed(2))}cl`
                        : `${ing.amount}${drink.stockUnit || ''}`;
                      ratioLabel = `(${friendly}/u)`;
                    } else {
                      childStock = Math.floor((drink.stock || 0) * (c.parentRatio || 1));
                      ratioLabel = `(1/${c.parentRatio})`;
                    }
                    return (
                      <div key={c.id} className="flex items-center justify-between gap-2 text-xs">
                        <div className="flex items-center gap-1.5 text-stone-600 min-w-0">
                          <Icon name={c.icon} className="w-3 h-3 shrink-0" />
                          <span className="truncate">{c.name}</span>
                          <span className="text-stone-400 text-[10px] shrink-0">{ratioLabel}</span>
                        </div>
                        <div className={`font-mono font-bold tabular-nums shrink-0 ${childStock <= 0 ? 'text-rose-600' : childStock <= 5 ? 'text-orange-600' : 'text-stone-700'}`}>
                          {childStock} restants
                        </div>
                      </div>
                    );
                  })}
                </div>
              )}
              {!tracked && (
                <div className="text-[10px] text-stone-400 mt-1.5 ml-7">
                  Stock désactivé · Tape sur <span className="font-bold">—</span> pour saisir une quantité, ou sur <span className="font-bold">+</span> pour activer
                </div>
              )}
            </div>
          );
        })}
      </div>

      <div className="text-[10px] text-stone-500 leading-relaxed">
        💡 Tape directement sur le chiffre du stock pour saisir une quantité au clavier, ou utilise <span className="font-bold">+</span> / <span className="font-bold">−</span> / <span className="font-bold">+10</span>. Le suivi s'active automatiquement à la première saisie. Les items dérivés (coupes, verres) sont calculés à partir de leurs bouteilles parents — configure les liens dans <span className="font-bold">Config</span>.
      </div>
    </div>
  );
}

// === StatsView (onglet Stats) ===
function StatsView({ allSales, mySalesCount, sessionId, drinks, cancelSale, tabs, pendingSales }) {
  const [showBarmen, setShowBarmen] = useState(false);
  const [showHistory, setShowHistory] = useState(false);
  const [confirmCancelKey, setConfirmCancelKey] = useState(null);
  const stats = useMemo(() => {
    const byDrink = {}, byPayment = {}, byHour = {}, byCategory = {}, byBarman = {};
    let total = 0, totalItems = 0, totalOffered = 0, totalDiscount = 0;
    PAYMENT_METHODS.forEach(pm => { byPayment[pm.id] = 0; });
    allSales.forEach(sale => {
      const isOffered = sale.paymentMethod === 'offert';
      const discount = sale.discount || 0;
      const subtotal = sale.subtotal !== undefined ? sale.subtotal : (sale.total || 0);
      total += sale.total || 0;
      byPayment[sale.paymentMethod] = (byPayment[sale.paymentMethod] || 0) + (sale.total || 0);
      const hour = new Date(sale.timestamp).getHours();
      byHour[hour] = (byHour[hour] || 0) + (sale.total || 0);
      if (isOffered) totalOffered += subtotal;
      else if (discount > 0) totalDiscount += subtotal * discount;
      // Agrégation par barman
      const barmanKey = sale.userName || '— inconnu';
      if (!byBarman[barmanKey]) {
        byBarman[barmanKey] = {
          name: barmanKey, salesCount: 0, items: 0, revenue: 0, offered: 0,
          firstSale: sale.timestamp, lastSale: sale.timestamp,
          byPayment: {}, byDrink: {},
        };
      }
      const bm = byBarman[barmanKey];
      bm.salesCount += 1;
      bm.revenue += sale.total || 0;
      if (isOffered) bm.offered += subtotal;
      bm.firstSale = Math.min(bm.firstSale, sale.timestamp);
      bm.lastSale = Math.max(bm.lastSale, sale.timestamp);
      bm.byPayment[sale.paymentMethod] = (bm.byPayment[sale.paymentMethod] || 0) + (sale.total || 0);
      (sale.items || []).forEach(item => {
        const lineFull = item.price * item.quantity;
        const lineRevenue = isOffered ? 0 : lineFull * (1 - discount);
        if (!byDrink[item.drinkId]) byDrink[item.drinkId] = { name: item.name, qty: 0, revenue: 0 };
        byDrink[item.drinkId].qty += item.quantity;
        byDrink[item.drinkId].revenue += lineRevenue;
        totalItems += item.quantity;
        bm.items += item.quantity;
        bm.byDrink[item.drinkId] = bm.byDrink[item.drinkId] || { name: item.name, qty: 0 };
        bm.byDrink[item.drinkId].qty += item.quantity;
        const d = drinks.find(d => d.id === item.drinkId);
        const cat = d?.category;
        if (cat) byCategory[cat] = (byCategory[cat] || 0) + lineRevenue;
      });
    });
    const drinkStats = Object.entries(byDrink).map(([id, s]) => ({ id, ...s })).sort((a, b) => b.qty - a.qty);
    const hourlyData = Object.entries(byHour).map(([h, v]) => ({ hour: parseInt(h), revenue: v })).sort((a, b) => a.hour - b.hour);
    const barmanStats = Object.values(byBarman).sort((a, b) => b.revenue - a.revenue);
    return { total, totalItems, totalOffered, totalDiscount, byPayment, byCategory, drinkStats, hourlyData, barmanStats, salesCount: allSales.length };
  }, [allSales, drinks]);

  return (
    <div className="px-4 pt-4 space-y-5">
      <h2 className="font-display font-bold text-2xl text-stone-900 tracking-tight">Tableau de bord</h2>
      <div className="grid grid-cols-2 gap-3">
        <StatCard label="Ventes" value={stats.salesCount} />
        <StatCard label="Items vendus" value={stats.totalItems} />
      </div>

      {/* Lot 3 : info ardoises ouvertes + ventes en attente de sync */}
      {(Array.isArray(tabs) && tabs.filter(t => t.status === 'open').length > 0) || (Array.isArray(pendingSales) && pendingSales.length > 0) ? (
        <div className="grid grid-cols-2 gap-3">
          {Array.isArray(tabs) && tabs.filter(t => t.status === 'open').length > 0 && (() => {
            const openTabs = tabs.filter(t => t.status === 'open');
            const openTotal = openTabs.reduce((s, t) => {
              return s + Object.values(t.items || {}).reduce((ss, it) => ss + (it.price || 0) * (it.quantity || 0), 0);
            }, 0);
            return (
              <div className="bg-violet-50 border border-violet-200 rounded-xl p-3">
                <div className="text-[10px] uppercase tracking-widest text-violet-700 font-bold flex items-center gap-1">
                  <Icon name="Receipt" className="w-3 h-3" /> Sur ardoises ouvertes
                </div>
                <div className="font-mono text-lg tabular-nums font-bold text-violet-800 mt-0.5">{formatPrice(openTotal)}</div>
                <div className="text-[10px] text-violet-700 mt-0.5">{openTabs.length} ardoise{openTabs.length > 1 ? 's' : ''}</div>
              </div>
            );
          })()}
          {Array.isArray(pendingSales) && pendingSales.length > 0 && (
            <div className="bg-amber-50 border border-amber-200 rounded-xl p-3">
              <div className="text-[10px] uppercase tracking-widest text-amber-800 font-bold flex items-center gap-1">
                <Icon name="CloudOff" className="w-3 h-3" /> En attente de sync
              </div>
              <div className="font-mono text-lg tabular-nums font-bold text-amber-900 mt-0.5">{pendingSales.length}</div>
              <div className="text-[10px] text-amber-800 mt-0.5">vente{pendingSales.length > 1 ? 's' : ''} hors-ligne</div>
            </div>
          )}
        </div>
      ) : null}

      {drinks.some(d => d.stockEnabled && !d.parentId) && (
        <section>
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Stock restant</h3>
          <div className="bg-white border border-stone-200 rounded-xl p-3 flex items-center justify-between">
            <div className="text-sm text-stone-700">Valeur stock disponible</div>
            <div className="font-mono text-base tabular-nums font-bold text-stone-900">{formatPrice(stockTotalValue(drinks))}</div>
          </div>
        </section>
      )}

      <section>
        <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Par mode de paiement</h3>
        <div className="space-y-2">
          {PAYMENT_METHODS.map(pm => {
            const amount = stats.byPayment[pm.id] || 0;
            const pct = stats.total > 0 ? (amount / stats.total) * 100 : 0;
            const isOffert = pm.id === 'offert';
            // Pour 'offert', amount = 0 par construction. On affiche plutôt la valeur offerte.
            const displayAmount = isOffert ? stats.totalOffered : amount;
            return (
              <div key={pm.id} className={`bg-white border rounded-xl p-3 ${isOffert ? 'border-violet-200' : 'border-stone-200'}`}>
                <div className="flex items-center justify-between mb-2">
                  <div className="flex items-center gap-2">
                    <Icon name={pm.icon} className={`w-4 h-4 ${isOffert ? 'text-violet-700' : 'text-stone-700'}`} />
                    <span className="text-sm font-semibold text-stone-900">{pm.label}</span>
                    {isOffert && <span className="text-[9px] uppercase tracking-wider text-violet-600 font-bold">valeur offerte</span>}
                  </div>
                  <div className={`font-mono text-sm tabular-nums font-bold ${isOffert ? 'text-violet-700' : 'text-stone-900'}`}>{formatPrice(displayAmount)}</div>
                </div>
                {!isOffert && (
                  <>
                    <div className="h-1.5 bg-stone-100 rounded-full overflow-hidden">
                      <div className="h-full bg-orange-500" style={{ width: `${pct}%` }} />
                    </div>
                    <div className="text-[10px] text-stone-500 mt-1 font-mono tabular-nums">{pct.toFixed(0)}%</div>
                  </>
                )}
              </div>
            );
          })}
        </div>
      </section>

      {(stats.totalOffered > 0 || stats.totalDiscount > 0) && (
        <section>
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Cadeaux & remises</h3>
          <div className="grid grid-cols-2 gap-2">
            <div className="bg-violet-50 border border-violet-200 rounded-xl p-3">
              <div className="text-[10px] uppercase tracking-widest text-violet-700 font-bold flex items-center gap-1">
                <Icon name="Gift" className="w-3 h-3" /> Offert
              </div>
              <div className="font-mono text-lg tabular-nums font-bold text-violet-800 mt-0.5">{formatPrice(stats.totalOffered)}</div>
            </div>
            <div className="bg-emerald-50 border border-emerald-200 rounded-xl p-3">
              <div className="text-[10px] uppercase tracking-widest text-emerald-700 font-bold flex items-center gap-1">
                <Icon name="Percent" className="w-3 h-3" /> Remises
              </div>
              <div className="font-mono text-lg tabular-nums font-bold text-emerald-800 mt-0.5">{formatPrice(stats.totalDiscount)}</div>
            </div>
          </div>
        </section>
      )}

      {Object.keys(stats.byCategory).length > 0 && (
        <section>
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Par catégorie</h3>
          <div className="space-y-2">
            {Object.entries(stats.byCategory).sort((a,b) => b[1]-a[1]).map(([key, amount]) => {
              const cat = CATEGORIES[key];
              if (!cat) return null;
              const pct = stats.total > 0 ? (amount / stats.total) * 100 : 0;
              return (
                <div key={key} className="bg-white border border-stone-200 rounded-xl p-3 flex items-center justify-between gap-3">
                  <div className={`text-[10px] font-bold uppercase tracking-wider px-2 py-0.5 rounded-full ${cat.bg} ${cat.text}`}>{cat.label}</div>
                  <div className="flex items-center gap-3">
                    <div className="text-xs text-stone-500 font-mono tabular-nums">{pct.toFixed(0)}%</div>
                    <div className="font-mono text-sm tabular-nums text-stone-900 font-bold">{formatPrice(amount)}</div>
                  </div>
                </div>
              );
            })}
          </div>
        </section>
      )}

      {stats.hourlyData.length > 0 && (
        <section>
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Ventes par heure</h3>
          <div className="bg-white border border-stone-200 rounded-xl p-3"><HourlyChart data={stats.hourlyData} /></div>
        </section>
      )}

      <section>
        <div className="flex items-center justify-between mb-2">
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">Top boissons</h3>
        </div>
        <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
          {stats.drinkStats.length === 0 && <div className="px-4 py-6 text-center text-stone-500 text-sm">Aucune vente pour le moment</div>}
          {stats.drinkStats.map((d, i) => (
            <div key={d.id} className="px-3 py-2.5 flex items-center justify-between gap-2">
              <div className="flex items-center gap-2 min-w-0">
                <div className="font-mono text-xs text-stone-400 w-5 tabular-nums font-bold">{i + 1}</div>
                <div className="text-sm text-stone-900 truncate font-semibold">{d.name}</div>
              </div>
              <div className="flex items-baseline gap-3 shrink-0">
                <div className="font-mono text-xs text-stone-500 tabular-nums">×{d.qty}</div>
                <div className="font-mono text-sm text-stone-900 tabular-nums font-bold">{formatPrice(d.revenue)}</div>
              </div>
            </div>
          ))}
        </div>
      </section>

      {stats.barmanStats.length > 0 && (
        <section>
          <button onClick={() => setShowBarmen(s => !s)} className="w-full flex items-center justify-between mb-2 text-left">
            <h3 className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">
              Par barman ({stats.barmanStats.length})
            </h3>
            <Icon name={showBarmen ? 'ChevronUp' : 'ChevronDown'} className="w-3.5 h-3.5 text-stone-400" />
          </button>
          {showBarmen && (
            <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100 slide-up">
              {stats.barmanStats.map((bm, i) => {
                const initial = (bm.name || '?')[0].toUpperCase();
                const fmt = (ts) => new Date(ts).toLocaleTimeString('fr-BE', { hour: '2-digit', minute: '2-digit' });
                const topItems = Object.values(bm.byDrink).sort((a,b) => b.qty - a.qty).slice(0, 3);
                return (
                  <div key={bm.name} className="px-3 py-3">
                    <div className="flex items-start gap-3">
                      <div className={`w-10 h-10 rounded-full flex items-center justify-center font-bold text-white shrink-0 ${
                        ['bg-orange-500','bg-emerald-500','bg-violet-500','bg-sky-500','bg-rose-500','bg-amber-500'][i % 6]
                      }`}>{initial}</div>
                      <div className="min-w-0 flex-1">
                        <div className="flex items-center justify-between gap-2">
                          <div className="text-sm font-bold text-stone-900 truncate">{bm.name}</div>
                          <div className="font-mono text-base font-bold text-stone-900 tabular-nums shrink-0">{formatPrice(bm.revenue)}</div>
                        </div>
                        <div className="flex items-center gap-3 text-[11px] text-stone-500 mt-0.5">
                          <span className="font-mono tabular-nums">{bm.salesCount} ventes</span>
                          <span className="font-mono tabular-nums">{bm.items} items</span>
                          {bm.offered > 0 && <span className="text-violet-600 font-mono tabular-nums">{formatPrice(bm.offered)} offert</span>}
                        </div>
                        <div className="text-[10px] text-stone-400 mt-0.5 font-mono">
                          {fmt(bm.firstSale)} → {fmt(bm.lastSale)}
                        </div>
                        {topItems.length > 0 && (
                          <div className="mt-1.5 flex flex-wrap gap-1.5">
                            {topItems.map(it => (
                              <span key={it.name} className="text-[10px] bg-stone-100 text-stone-700 px-2 py-0.5 rounded-full font-semibold">
                                {it.name} ×{it.qty}
                              </span>
                            ))}
                          </div>
                        )}
                      </div>
                    </div>
                  </div>
                );
              })}
            </div>
          )}
        </section>
      )}

      {allSales.length > 0 && (
        <section>
          <button onClick={() => setShowHistory(s => !s)} className="w-full flex items-center justify-between mb-2 text-left">
            <h3 className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">
              Historique des ventes ({allSales.length})
            </h3>
            <Icon name={showHistory ? 'ChevronUp' : 'ChevronDown'} className="w-3.5 h-3.5 text-stone-400" />
          </button>
          {showHistory && (
            <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100 slide-up max-h-[480px] overflow-y-auto scrollbar-thin">
              {[...allSales].reverse().slice(0, 200).map(sale => {
                const isOffered = sale.paymentMethod === 'offert';
                const discount = sale.discount || 0;
                const pm = PAYMENT_BY_ID[sale.paymentMethod];
                const itemsLabel = (sale.items || []).map(i => `${i.quantity}× ${i.name}`).join(', ');
                const time = new Date(sale.timestamp).toLocaleTimeString('fr-BE', { hour: '2-digit', minute: '2-digit' });
                const isConfirming = confirmCancelKey === sale._key;
                return (
                  <div key={sale._key} className="px-3 py-2.5">
                    <div className="flex items-start justify-between gap-2">
                      <div className="min-w-0 flex-1">
                        <div className="flex items-center gap-2 text-[10px] text-stone-500 font-mono">
                          <span className="font-bold text-stone-700">{time}</span>
                          {sale.userName && <span>· {sale.userName}</span>}
                          {pm && (
                            <span className={`flex items-center gap-1 ${isOffered ? 'text-violet-600 font-bold' : ''}`}>
                              · <Icon name={pm.icon} className="w-3 h-3" /> {pm.label}
                            </span>
                          )}
                          {!isOffered && discount > 0 && (
                            <span className="text-emerald-600 font-bold">-{Math.round(discount * 100)}%</span>
                          )}
                        </div>
                        <div className="text-xs text-stone-700 mt-0.5 truncate">{itemsLabel}</div>
                      </div>
                      <div className="flex items-center gap-2 shrink-0">
                        <div className={`font-mono text-sm font-bold tabular-nums ${isOffered ? 'text-violet-700' : 'text-stone-900'}`}>
                          {isOffered ? 'OFFERT' : formatPrice(sale.total || 0)}
                        </div>
                        {!isConfirming ? (
                          <button onClick={() => setConfirmCancelKey(sale._key)} className="text-stone-400 hover:text-rose-600 p-1" title="Annuler cette vente">
                            <Icon name="Trash2" className="w-3.5 h-3.5" />
                          </button>
                        ) : (
                          <div className="flex items-center gap-1">
                            <button onClick={async () => { await cancelSale(sale._key); setConfirmCancelKey(null); }} className="bg-rose-500 hover:bg-rose-600 text-white text-[10px] font-bold px-2 py-1 rounded">
                              Confirmer
                            </button>
                            <button onClick={() => setConfirmCancelKey(null)} className="bg-stone-200 text-stone-700 text-[10px] font-bold px-2 py-1 rounded">
                              ✕
                            </button>
                          </div>
                        )}
                      </div>
                    </div>
                  </div>
                );
              })}
              {allSales.length > 200 && (
                <div className="px-3 py-2 text-center text-[10px] text-stone-400 italic">
                  200 ventes les plus récentes affichées sur {allSales.length}
                </div>
              )}
            </div>
          )}
        </section>
      )}

      <section className="pb-4">
        <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Cette session</h3>
        <div className="bg-white border border-stone-200 rounded-xl p-3 flex items-center justify-between">
          <div>
            <div className="text-xs text-stone-500">Vos ventes ({mySalesCount})</div>
            <div className="font-mono text-[10px] text-stone-400 mt-1">id: {sessionId.slice(0, 6)}</div>
          </div>
        </div>
      </section>
    </div>
  );
}

// === EventManagementSection (gestion du nom, des membres, et accès au compte) ===
function EventManagementSection({ eventId, eventMeta, firebaseUser, updateEventMembers, updateEventName, deleteEvent, onSwitchEvent, onOwnerSignout }) {
  const [showName, setShowName] = useState(false);
  const [nameValue, setNameValue] = useState(eventMeta?.name || '');
  const [showMembers, setShowMembers] = useState(false);
  const [savingName, setSavingName] = useState(false);
  const [savingMembers, setSavingMembers] = useState(false);
  const [memberDraft, setMemberDraft] = useState([]);
  const [confirmDelete, setConfirmDelete] = useState(false);
  const [linkCopied, setLinkCopied] = useState(false);
  const [memberError, setMemberError] = useState('');

  const isOwner = firebaseUser?.uid && eventMeta?.ownerUid === firebaseUser.uid;
  const shareLink = buildEventShareLink(eventId);

  useEffect(() => { setNameValue(eventMeta?.name || ''); }, [eventMeta?.name]);

  // Initialise le brouillon de membres à partir de la meta
  useEffect(() => {
    if (showMembers && eventMeta?.members) {
      setMemberDraft(eventMeta.members.map(m => ({
        name: m.name, role: m.role, password: '',
      })));
      setMemberError('');
    }
  }, [showMembers, eventMeta?.members]);

  const handleSaveName = async () => {
    const v = nameValue.trim();
    if (!v) return;
    setSavingName(true);
    const ok = await updateEventName(v);
    setSavingName(false);
    if (ok) setShowName(false);
  };

  const handleAddDraftMember = () => setMemberDraft(d => [...d, { name: '', role: 'barman', password: '' }]);
  const handleUpdateDraftMember = (i, patch) => setMemberDraft(d => d.map((m, idx) => idx === i ? { ...m, ...patch } : m));
  const handleRemoveDraftMember = (i) => setMemberDraft(d => d.filter((_, idx) => idx !== i));
  const handleSaveMembers = async () => {
    setMemberError('');
    const cleaned = memberDraft.map(m => ({ name: m.name.trim(), role: m.role, password: m.password }));
    if (cleaned.some(m => !m.name)) { setMemberError('Tous les membres doivent avoir un nom.'); return; }
    const lower = cleaned.map(m => m.name.toLowerCase());
    if (new Set(lower).size !== lower.length) { setMemberError('Les noms doivent être uniques.'); return; }
    if (!cleaned.some(m => m.role === 'admin')) { setMemberError('Au moins un admin requis.'); return; }
    const existingNames = new Set((eventMeta?.members || []).map(m => m.name));
    for (const m of cleaned) {
      if (!m.password && !existingNames.has(m.name)) {
        setMemberError(`Renseigne un mot de passe pour « ${m.name} ».`);
        return;
      }
    }
    setSavingMembers(true);
    try {
      await updateEventMembers(cleaned);
      setShowMembers(false);
    } catch (e) {
      setMemberError('Échec de l\'enregistrement : ' + (e?.message || e));
    } finally {
      setSavingMembers(false);
    }
  };

  const handleCopyLink = async () => {
    try {
      if (navigator.clipboard) await navigator.clipboard.writeText(shareLink);
      else { const ta = document.createElement('textarea'); ta.value = shareLink; document.body.appendChild(ta); ta.select(); document.execCommand('copy'); ta.remove(); }
      setLinkCopied(true);
      setTimeout(() => setLinkCopied(false), 2000);
    } catch (e) { alert('Impossible de copier — ' + (e?.message || '')); }
  };

  return (
    <section>
      <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold flex items-center gap-1.5">
        <Icon name="Receipt" className="w-3 h-3" /> Comptoir
      </h3>
      <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
        {/* Nom de l'événement */}
        <div className="px-3 py-3">
          {!showName ? (
            <div className="flex items-center justify-between gap-2">
              <div className="min-w-0">
                <div className="text-[10px] uppercase tracking-widest text-stone-400 font-bold">Nom de l'événement</div>
                <div className="text-sm font-bold text-stone-900 truncate">{eventMeta?.name || '—'}</div>
              </div>
              {isOwner && (
                <button onClick={() => setShowName(true)} className="text-xs font-bold text-orange-600 hover:text-orange-700 px-2 py-1">Modifier</button>
              )}
            </div>
          ) : (
            <div className="space-y-2">
              <input type="text" value={nameValue} onChange={e => setNameValue(e.target.value)} autoFocus
                className="w-full bg-stone-50 border border-stone-200 rounded-lg px-3 py-2 text-sm focus:border-orange-500 focus:outline-none" />
              <div className="grid grid-cols-2 gap-2">
                <button onClick={() => { setNameValue(eventMeta?.name || ''); setShowName(false); }} disabled={savingName} className="bg-stone-100 text-stone-700 text-sm py-2 rounded-lg font-semibold">Annuler</button>
                <button onClick={handleSaveName} disabled={savingName || !nameValue.trim()} className="bg-stone-900 text-white text-sm py-2 rounded-lg font-bold disabled:opacity-50">{savingName ? '…' : 'Enregistrer'}</button>
              </div>
            </div>
          )}
        </div>

        {/* Lien de partage */}
        <div className="px-3 py-3">
          <div className="text-[10px] uppercase tracking-widest text-stone-400 font-bold mb-1">Lien pour les barmen</div>
          <div className="text-[11px] text-stone-600 mb-2 leading-relaxed">
            Envoie ce lien à ton équipe. Ils choisiront leur nom et taperont leur mot de passe pour rejoindre.
          </div>
          <div className="flex items-center gap-2">
            <input type="text" value={shareLink} readOnly onFocus={e => e.target.select()}
              className="flex-1 bg-stone-50 border border-stone-200 rounded-md px-2 py-1.5 text-[11px] font-mono text-stone-700 focus:outline-none" />
            <button onClick={handleCopyLink} className={`text-xs font-bold px-3 py-1.5 rounded-md ${linkCopied ? 'bg-emerald-500 text-white' : 'bg-stone-900 text-white hover:bg-stone-700'}`}>
              {linkCopied ? <><Icon name="Check" className="w-3 h-3 inline" /> OK</> : 'Copier'}
            </button>
          </div>
        </div>

        {/* Membres */}
        <div className="px-3 py-3">
          {!showMembers ? (
            <div className="flex items-center justify-between gap-2">
              <div className="min-w-0">
                <div className="text-[10px] uppercase tracking-widest text-stone-400 font-bold">Équipe</div>
                <div className="text-sm text-stone-900 mt-0.5">
                  {(eventMeta?.members || []).map(m => m.name).join(', ') || '—'}
                </div>
              </div>
              {isOwner && (
                <button onClick={() => setShowMembers(true)} className="text-xs font-bold text-orange-600 hover:text-orange-700 px-2 py-1 shrink-0">Gérer</button>
              )}
            </div>
          ) : (
            <div className="space-y-2 slide-up">
              <div className="text-[10px] text-stone-500 leading-relaxed mb-1">
                Mot de passe vide = on garde l'ancien. Saisis-en un pour le changer.
              </div>
              {memberDraft.map((m, i) => (
                <div key={i} className="bg-stone-50 border border-stone-200 rounded-lg p-2 space-y-1.5">
                  <div className="grid grid-cols-[1fr_auto_auto] gap-1.5">
                    <input type="text" value={m.name} onChange={e => handleUpdateDraftMember(i, { name: e.target.value })} placeholder="Prénom"
                      className="bg-white border border-stone-200 rounded px-2 py-1.5 text-sm focus:border-orange-500 focus:outline-none" />
                    <select value={m.role} onChange={e => handleUpdateDraftMember(i, { role: e.target.value })}
                      className="bg-white border border-stone-200 rounded px-1 py-1.5 text-xs focus:border-orange-500 focus:outline-none">
                      <option value="admin">Admin</option>
                      <option value="barman">Barman</option>
                    </select>
                    {memberDraft.length > 1 && (
                      <button type="button" onClick={() => handleRemoveDraftMember(i)} className="bg-white border border-stone-200 text-rose-600 px-2 rounded">
                        <Icon name="Trash2" className="w-3 h-3" />
                      </button>
                    )}
                  </div>
                  <input type="text" value={m.password} onChange={e => handleUpdateDraftMember(i, { password: e.target.value })} placeholder="Nouveau mot de passe (vide = inchangé)"
                    className="w-full bg-white border border-stone-200 rounded px-2 py-1.5 text-xs font-mono focus:border-orange-500 focus:outline-none" />
                </div>
              ))}
              <button onClick={handleAddDraftMember} className="w-full text-xs font-bold text-orange-600 border border-dashed border-stone-300 rounded-lg py-1.5">
                + Ajouter un membre
              </button>
              {memberError && (
                <div className="bg-rose-50 border border-rose-200 rounded-lg px-3 py-2 text-xs text-rose-700 flex items-start gap-1.5">
                  <Icon name="AlertTriangle" className="w-3.5 h-3.5 mt-0.5 shrink-0" /> {memberError}
                </div>
              )}
              <div className="grid grid-cols-2 gap-2 pt-1">
                <button onClick={() => setShowMembers(false)} disabled={savingMembers} className="bg-stone-100 text-stone-700 text-sm py-2 rounded-lg font-semibold">Annuler</button>
                <button onClick={handleSaveMembers} disabled={savingMembers} className="bg-stone-900 text-white text-sm py-2 rounded-lg font-bold disabled:opacity-50">{savingMembers ? '…' : 'Enregistrer'}</button>
              </div>
            </div>
          )}
        </div>

        {/* Actions de session */}
        <div className="px-3 py-3 space-y-1.5">
          <button onClick={onSwitchEvent} className="w-full text-left text-xs text-stone-700 hover:text-stone-900 py-1.5">
            ↻ Changer de comptoir
          </button>
          {firebaseUser && !firebaseUser.isAnonymous && (
            <button onClick={onOwnerSignout} className="w-full text-left text-xs text-stone-700 hover:text-stone-900 py-1.5">
              ⏻ Déconnexion du compte ({firebaseUser.email || 'compte propriétaire'})
            </button>
          )}
          {isOwner && (
            !confirmDelete ? (
              <button onClick={() => setConfirmDelete(true)} className="w-full text-left text-xs text-rose-600 hover:text-rose-700 py-1.5">
                🗑 Supprimer ce comptoir définitivement
              </button>
            ) : (
              <div className="bg-rose-50 border border-rose-200 rounded-lg p-2.5 space-y-2 mt-1">
                <div className="text-xs text-rose-800 leading-relaxed">
                  Supprimer définitivement <span className="font-bold">{eventMeta?.name}</span> ?<br/>
                  Toutes les ventes, archives, ardoises et photos seront perdues.
                </div>
                <div className="grid grid-cols-2 gap-2">
                  <button onClick={() => setConfirmDelete(false)} className="bg-stone-100 text-stone-700 text-xs py-1.5 rounded font-semibold">Annuler</button>
                  <button onClick={async () => { await deleteEvent(); }} className="bg-rose-500 text-white text-xs py-1.5 rounded font-bold">Supprimer</button>
                </div>
              </div>
            )
          )}
        </div>
      </div>
    </section>
  );
}

// === ClosureSection (clôture d'événement avec recompte) ===
function ClosureSection({ drinks, salesCount, closeEvent }) {
  // États : 'idle' → 'recompte' → 'confirm' → (clôture en cours pendant l'await)
  const [phase, setPhase] = useState('idle');
  const [eventName, setEventName] = useState('');
  const [resetStock, setResetStock] = useState(false);
  const [recompteEntries, setRecompteEntries] = useState({});  // drinkId → counted (string)
  const [busy, setBusy] = useState(false);

  // Items de stock à recompter : ceux avec un stock suivi indépendant (pas dérivés)
  const trackedItems = useMemo(() => drinks.filter(d => d.stockEnabled && !d.parentId), [drinks]);

  const startRecompte = () => {
    // Pré-remplir avec les valeurs théoriques (= ce que la caisse pense avoir en stock)
    const init = {};
    trackedItems.forEach(d => { init[d.id] = String(Math.floor(d.stock || 0)); });
    setRecompteEntries(init);
    setPhase('recompte');
  };

  const recompteData = useMemo(() => {
    return trackedItems.map(d => {
      const expected = Math.floor(d.stock || 0);
      const counted = parseFloat((recompteEntries[d.id] || '0').replace(',', '.')) || 0;
      const variance = counted - expected;
      const varianceValue = variance * (d.price || 0);
      return {
        drinkId: d.id, drinkName: d.name,
        unit: d.stockUnit || '',
        expected, counted, variance, varianceValue,
      };
    });
  }, [trackedItems, recompteEntries]);

  const totalVarianceValue = recompteData.reduce((s, r) => s + r.varianceValue, 0);
  const hasVariance = recompteData.some(r => r.variance !== 0);

  const skipRecompte = () => { setPhase('confirm'); };

  const handleClose = async () => {
    setBusy(true);
    const recompte = phase === 'confirm' && Object.keys(recompteEntries).length > 0 ? recompteData : null;
    const ok = await closeEvent({ eventName: eventName.trim(), recompte, resetStock });
    setBusy(false);
    if (ok) {
      setPhase('idle');
      setEventName('');
      setResetStock(false);
      setRecompteEntries({});
    }
  };

  if (phase === 'idle') {
    return (
      <section>
        <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold flex items-center gap-1.5">
          <Icon name="Check" className="w-3 h-3" /> Clôture d'événement
        </h3>
        <div className="bg-white border border-stone-200 rounded-xl p-3 space-y-2">
          <p className="text-xs text-stone-600 leading-relaxed">
            Archive les ventes courantes ({salesCount}), télécharge un CSV récapitulatif et remet le compteur à zéro pour le prochain événement. Optionnel : faire d'abord un recompte de stock pour mesurer les écarts.
          </p>
          <div className="grid grid-cols-2 gap-2 pt-1">
            <button onClick={startRecompte} disabled={trackedItems.length === 0} className="flex items-center justify-center gap-1.5 bg-white hover:bg-stone-50 disabled:opacity-40 border border-stone-300 text-stone-700 rounded-lg py-2.5 text-xs font-bold">
              <Icon name="Package" className="w-3.5 h-3.5" /> Recompte d'abord
            </button>
            <button onClick={skipRecompte} disabled={salesCount === 0} className="flex items-center justify-center gap-1.5 bg-stone-900 hover:bg-stone-700 disabled:opacity-40 text-white rounded-lg py-2.5 text-xs font-bold">
              <Icon name="Check" className="w-3.5 h-3.5" /> Clôturer direct
            </button>
          </div>
        </div>
      </section>
    );
  }

  if (phase === 'recompte') {
    return (
      <section>
        <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Recompte du stock</h3>
        <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
          <div className="px-3 py-2 bg-stone-50 grid grid-cols-[1fr_70px_70px_70px] gap-2 text-[9px] uppercase tracking-widest text-stone-500 font-bold">
            <div>Boisson</div>
            <div className="text-right">Théorique</div>
            <div className="text-right">Compté</div>
            <div className="text-right">Écart</div>
          </div>
          {trackedItems.map(d => {
            const entry = recompteData.find(r => r.drinkId === d.id);
            const variance = entry?.variance || 0;
            const varianceClass = variance === 0 ? 'text-stone-400' : variance < 0 ? 'text-rose-600' : 'text-emerald-600';
            const unit = d.stockUnit ? ` ${d.stockUnit}` : '';
            return (
              <div key={d.id} className="px-3 py-2 grid grid-cols-[1fr_70px_70px_70px] gap-2 items-center">
                <div className="text-xs font-semibold text-stone-900 truncate">{d.name}</div>
                <div className="font-mono text-xs text-stone-700 tabular-nums text-right">{Math.floor(d.stock || 0)}{unit}</div>
                <input type="text" inputMode="numeric" value={recompteEntries[d.id] ?? ''}
                  onChange={e => setRecompteEntries(prev => ({ ...prev, [d.id]: e.target.value.replace(/[^0-9]/g, '') }))}
                  className="bg-stone-50 border border-stone-200 rounded px-1.5 py-1 text-xs font-mono text-right tabular-nums focus:border-orange-500 focus:outline-none w-full" />
                <div className={`font-mono text-xs font-bold tabular-nums text-right ${varianceClass}`}>
                  {variance > 0 ? '+' : ''}{variance}
                </div>
              </div>
            );
          })}
        </div>
        {hasVariance && (
          <div className="bg-stone-50 border border-stone-200 rounded-xl p-3 mt-2">
            <div className="text-[10px] uppercase tracking-widest text-stone-500 font-bold mb-1">Valeur de l'écart total</div>
            <div className={`font-mono text-base font-bold tabular-nums ${totalVarianceValue < 0 ? 'text-rose-700' : totalVarianceValue > 0 ? 'text-emerald-700' : 'text-stone-700'}`}>
              {totalVarianceValue > 0 ? '+' : ''}{formatPrice(totalVarianceValue)}
            </div>
            <div className="text-[10px] text-stone-500 mt-1 leading-relaxed">
              Écart négatif = manquant (vol, casse, ventes non enregistrées). Écart positif = surplus (erreur de saisie initiale).
            </div>
          </div>
        )}
        <div className="grid grid-cols-2 gap-2 mt-3">
          <button onClick={() => setPhase('idle')} className="bg-stone-100 hover:bg-stone-200 text-stone-700 rounded-lg py-2.5 text-xs font-bold">
            Annuler
          </button>
          <button onClick={() => setPhase('confirm')} className="bg-stone-900 hover:bg-stone-700 text-white rounded-lg py-2.5 text-xs font-bold">
            Continuer →
          </button>
        </div>
      </section>
    );
  }

  // phase === 'confirm'
  return (
    <section>
      <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Confirmation de clôture</h3>
      <div className="bg-white border border-stone-300 rounded-xl p-3 space-y-3">
        <div>
          <label className="text-[10px] uppercase tracking-widest text-stone-500 font-bold block mb-1">Nom de l'événement (optionnel)</label>
          <input type="text" value={eventName} onChange={e => setEventName(e.target.value)} placeholder="Ex: Anniversaire Marie"
            className="w-full bg-stone-50 border border-stone-200 rounded-lg px-3 py-2 text-sm focus:border-orange-500 focus:outline-none" />
        </div>
        <label className="flex items-start gap-2 cursor-pointer">
          <input type="checkbox" checked={resetStock} onChange={e => setResetStock(e.target.checked)} className="w-4 h-4 mt-0.5 accent-orange-500" />
          <div className="text-xs text-stone-700 leading-relaxed">
            <span className="font-semibold">Remettre le stock à zéro</span>
            <div className="text-stone-500 mt-0.5">Sinon les niveaux actuels (bouteilles entamées, etc.) sont conservés pour l'événement suivant.</div>
          </div>
        </label>
        <div className="bg-orange-50 border border-orange-200 rounded-lg p-2.5 text-[11px] text-stone-700 leading-relaxed">
          <div className="flex items-start gap-2">
            <Icon name="AlertTriangle" className="w-3.5 h-3.5 text-orange-600 mt-0.5 shrink-0" />
            <div>
              <span className="font-bold">Cette action :</span>
              <ul className="list-disc ml-4 mt-1 space-y-0.5">
                <li>Archive {salesCount} vente{salesCount > 1 ? 's' : ''} dans Firebase (téléchargement CSV automatique)</li>
                <li>Vide la liste des ventes (compteurs Stats remis à zéro)</li>
                <li>{resetStock ? 'Remet tous les stocks à 0' : 'Conserve les niveaux de stock actuels'}</li>
              </ul>
            </div>
          </div>
        </div>
        <div className="grid grid-cols-2 gap-2">
          <button onClick={() => setPhase('idle')} disabled={busy} className="bg-stone-100 hover:bg-stone-200 text-stone-700 rounded-lg py-2.5 text-xs font-bold disabled:opacity-40">
            Annuler
          </button>
          <button onClick={handleClose} disabled={busy} className="bg-rose-600 hover:bg-rose-700 text-white rounded-lg py-2.5 text-xs font-bold disabled:opacity-50">
            {busy ? 'Clôture en cours…' : 'Clôturer maintenant'}
          </button>
        </div>
      </div>
    </section>
  );
}

// === ConfigView (onglet Config) ===
function ConfigView({ drinks, photos, setDrinkPhoto, updateDrink, addDrink, removeDrink, editingDrink, setEditingDrink, exportCSV, confirmReset, setConfirmReset, resetAll, sessionId, allSalesCount, myKeysCount, resetDrinksToDefault, confirmDrinksReset, setConfirmDrinksReset, adjustStock, setStock, lastBackup, downloadBackup, restoreFromBackup, archives, closeEvent, exportArchiveCSV, deleteArchive, pendingSales, setPendingSales, syncPendingSales, isOnline, eventId, eventMeta, firebaseUser, updateEventMembers, updateEventName, deleteEvent, onSwitchEvent, onOwnerSignout }) {
  const [newDrink, setNewDrink] = useState({ name: '', price: '', icon: 'Wine', category: 'biere', photo: null });
  const [showAdd, setShowAdd] = useState(false);
  const [confirmRestore, setConfirmRestore] = useState(false);
  const [showArchives, setShowArchives] = useState(false);
  const [confirmDeleteArchive, setConfirmDeleteArchive] = useState(null);
  // Re-render léger toutes les 30s pour rafraîchir le "il y a X min"
  const [, setNowTick] = useState(0);
  useEffect(() => {
    const id = setInterval(() => setNowTick(t => t + 1), 30000);
    return () => clearInterval(id);
  }, []);
  const backupAgeMin = lastBackup ? Math.floor((Date.now() - lastBackup) / 60000) : null;

  const handleAddDrink = async () => {
    if (!newDrink.name || !newDrink.price) return;
    const newId = genId();
    await addDrink({
      id: newId,
      name: newDrink.name,
      price: parseFloat(newDrink.price.toString().replace(',', '.')) || 0,
      icon: newDrink.icon || 'Wine',
      category: newDrink.category || 'biere',
    });
    if (newDrink.photo) await setDrinkPhoto(newId, newDrink.photo);
    setNewDrink({ name: '', price: '', icon: 'Wine', category: 'biere', photo: null });
    setShowAdd(false);
  };

  return (
    <div className="px-4 pt-4 space-y-5 pb-4">
      <h2 className="font-display font-bold text-2xl text-stone-900 tracking-tight">Configuration</h2>

      <EventManagementSection
        eventId={eventId} eventMeta={eventMeta} firebaseUser={firebaseUser}
        updateEventMembers={updateEventMembers} updateEventName={updateEventName}
        deleteEvent={deleteEvent} onSwitchEvent={onSwitchEvent} onOwnerSignout={onOwnerSignout}
      />

      <section>
        <div className="flex items-center justify-between mb-2">
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">Catalogue ({drinks.length})</h3>
          <button onClick={() => setShowAdd(!showAdd)} className="text-xs text-white bg-stone-900 hover:bg-stone-700 flex items-center gap-1 px-3 py-1.5 rounded-full font-bold uppercase tracking-wider">
            <Icon name="Plus" className="w-3 h-3" /> Ajouter
          </button>
        </div>

        {showAdd && (
          <div className="bg-white border border-stone-300 rounded-xl p-3 mb-3 slide-up">
            <div className="grid grid-cols-[1fr_80px] gap-2 mb-2">
              <input type="text" value={newDrink.name} onChange={e => setNewDrink({ ...newDrink, name: e.target.value })} placeholder="Nom" className="bg-stone-50 border border-stone-200 rounded-lg px-3 py-2 text-sm text-stone-900 focus:border-orange-500 focus:outline-none" />
              <input type="text" inputMode="decimal" value={newDrink.price} onChange={e => setNewDrink({ ...newDrink, price: e.target.value })} placeholder="Prix €" className="bg-stone-50 border border-stone-200 rounded-lg px-2 py-2 text-sm font-mono text-right focus:border-orange-500 focus:outline-none" />
            </div>
            <div className="text-[10px] uppercase tracking-widest text-stone-500 mb-1.5 font-bold">Catégorie</div>
            <CategoryPicker value={newDrink.category} onChange={(v) => setNewDrink({ ...newDrink, category: v })} />
            <div className="text-[10px] uppercase tracking-widest text-stone-500 mb-1.5 font-bold mt-3">Icône</div>
            <IconPicker value={newDrink.icon} onChange={(v) => setNewDrink({ ...newDrink, icon: v })} />
            <div className="text-[10px] uppercase tracking-widest text-stone-500 mb-1.5 font-bold mt-3">Photo (optionnel)</div>
            <PhotoPicker value={newDrink.photo} onChange={(v) => setNewDrink({ ...newDrink, photo: v })} />
            <div className="flex gap-2 mt-3">
              <button onClick={handleAddDrink} className="flex-1 bg-orange-500 text-white font-bold text-sm py-2 rounded-lg hover:bg-orange-600">Ajouter</button>
              <button onClick={() => { setShowAdd(false); setNewDrink({ name: '', price: '', icon: 'Wine', category: 'biere', photo: null }); }} className="flex-1 bg-stone-100 text-stone-700 text-sm py-2 rounded-lg font-semibold">Annuler</button>
            </div>
          </div>
        )}

        {/* Trois sous-sections : Boissons / Nourriture / Ingrédients (filtrage dérivé) */}
        {(() => {
          const beverages = drinks.filter(d => !d.stockOnly && d.category !== 'snack');
          const food      = drinks.filter(d => !d.stockOnly && d.category === 'snack');
          const ingredients = drinks.filter(d => d.stockOnly);

          const renderGroup = (label, list, emptyText) => (
            <div className="mb-4 last:mb-0">
              <div className="text-[10px] uppercase tracking-widest text-stone-400 font-bold mb-1.5 px-1">{label} · {list.length}</div>
              {list.length > 0 ? (
                <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100">
                  {list.map(drink => (
                    <DrinkRow key={drink.id} drink={drink} drinks={drinks} photo={photos[drink.id]} setDrinkPhoto={setDrinkPhoto}
                      isEditing={editingDrink === drink.id}
                      onEdit={() => setEditingDrink(drink.id)}
                      onCancel={() => setEditingDrink(null)}
                      onSave={async (u) => { await updateDrink(drink.id, u); setEditingDrink(null); }}
                      onDelete={() => { removeDrink(drink.id); setEditingDrink(null); }} />
                  ))}
                </div>
              ) : (
                <div className="bg-white border border-stone-200 border-dashed rounded-xl px-3 py-4 text-center text-xs text-stone-400 italic">{emptyText}</div>
              )}
            </div>
          );

          return (
            <>
              {renderGroup('Boissons', beverages, 'Aucune boisson')}
              {renderGroup('Nourriture', food, 'Aucun item de nourriture')}
              {renderGroup('Ingrédients', ingredients, 'Aucun ingrédient — un ingrédient est un item suivi en stock mais non vendu directement (ex: liqueur pour cocktail)')}
            </>
          );
        })()}
      </section>

      {drinks.some(d => d.stockEnabled && !d.parentId) && (
        <div className="bg-orange-50 border border-orange-200 rounded-xl p-3 text-xs text-stone-700">
          <Icon name="Package" className="w-4 h-4 text-orange-600 inline mr-1" /> Pour gérer les stocks, va dans l'onglet <span className="font-bold">Stock</span> (en bas).
        </div>
      )}

      <section className="bg-orange-50 border border-orange-200 rounded-xl p-3">
        <div className="flex items-start gap-2">
          <div className="text-orange-600 mt-0.5"><Icon name="Wifi" className="w-4 h-4" /></div>
          <div className="text-xs text-stone-700 leading-relaxed">
            <div className="font-bold text-orange-700 mb-1">Sync Firebase active</div>
            Toutes les ventes sont synchronisées en temps réel entre les téléphones connectés à cette caisse.
          </div>
        </div>
      </section>

      <section>
        <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold flex items-center gap-1.5">
          <Icon name="Save" className="w-3 h-3" /> Sauvegarde locale
        </h3>
        <div className="bg-white border border-stone-200 rounded-xl p-3 space-y-2">
          <div className="flex items-center justify-between">
            <div className="text-xs text-stone-700">
              {lastBackup ? (
                <>
                  Dernière sauvegarde : <span className="font-bold text-stone-900">{
                    backupAgeMin === 0 ? 'à l\'instant' :
                    backupAgeMin === 1 ? 'il y a 1 min' :
                    `il y a ${backupAgeMin} min`
                  }</span>
                </>
              ) : (
                <span className="text-stone-500 italic">Pas encore de sauvegarde</span>
              )}
            </div>
            <div className="text-[10px] text-stone-400 font-mono">auto / 3 min</div>
          </div>
          <div className="grid grid-cols-2 gap-2 pt-1">
            <button onClick={downloadBackup} disabled={!lastBackup} className="flex items-center justify-center gap-1.5 bg-stone-900 hover:bg-stone-700 disabled:opacity-40 text-white rounded-lg py-2 text-xs font-bold">
              <Icon name="Download" className="w-3.5 h-3.5" /> Télécharger JSON
            </button>
            {!confirmRestore ? (
              <button onClick={() => setConfirmRestore(true)} disabled={!lastBackup} className="flex items-center justify-center gap-1.5 bg-white hover:bg-stone-50 disabled:opacity-40 border border-stone-200 text-stone-700 rounded-lg py-2 text-xs font-bold">
                <Icon name="History" className="w-3.5 h-3.5" /> Restaurer
              </button>
            ) : (
              <button onClick={async () => { await restoreFromBackup(); setConfirmRestore(false); }} className="flex items-center justify-center gap-1.5 bg-rose-500 hover:bg-rose-600 text-white rounded-lg py-2 text-xs font-bold">
                <Icon name="AlertTriangle" className="w-3.5 h-3.5" /> Confirmer
              </button>
            )}
          </div>
          {confirmRestore && (
            <div className="text-[10px] text-rose-700 bg-rose-50 border border-rose-200 rounded-lg p-2 leading-relaxed">
              ⚠️ Restaurer écrase les ventes et le stock actuels par la sauvegarde locale (de ce téléphone). Les ventes faites depuis la dernière sauvegarde seront perdues. <button onClick={() => setConfirmRestore(false)} className="underline font-bold ml-1">Annuler</button>
            </div>
          )}
        </div>
      </section>

      {Array.isArray(pendingSales) && pendingSales.length > 0 && (
        <section>
          <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold flex items-center gap-1.5">
            <Icon name="CloudOff" className="w-3 h-3" /> Ventes hors-ligne en attente ({pendingSales.length})
          </h3>
          <div className="bg-amber-50 border border-amber-200 rounded-xl p-3 space-y-2">
            <div className="text-xs text-amber-900 leading-relaxed">
              {isOnline
                ? <>Synchronisation automatique en cours. Si une vente est bloquée, tu peux relancer manuellement.</>
                : <>Pas de connexion à Firebase. Les ventes seront poussées dès que le wifi reviendra.</>}
            </div>
            <div className="bg-white border border-amber-200 rounded-lg divide-y divide-amber-100 max-h-40 overflow-y-auto scrollbar-thin">
              {pendingSales.map(p => {
                const items = (p.sale?.items || []).map(i => `${i.quantity}× ${i.name}`).join(', ');
                const time = new Date(p.sale?.timestamp || 0).toLocaleTimeString('fr-BE', { hour: '2-digit', minute: '2-digit' });
                const isOffered = p.sale?.paymentMethod === 'offert';
                return (
                  <div key={p.localId} className="px-2.5 py-1.5 flex items-start justify-between gap-2 text-[11px]">
                    <div className="min-w-0 flex-1">
                      <div className="font-semibold text-stone-800 truncate">{items}</div>
                      <div className="text-stone-500 font-mono">
                        {time} · {PAYMENT_BY_ID[p.sale?.paymentMethod]?.label || '?'}
                        {p.attempts > 0 && <span className="text-rose-600 ml-1">· {p.attempts} échec{p.attempts > 1 ? 's' : ''}</span>}
                      </div>
                    </div>
                    <div className={`font-mono font-bold tabular-nums shrink-0 ${isOffered ? 'text-violet-700' : 'text-stone-900'}`}>
                      {isOffered ? 'OFFERT' : formatPrice(p.sale?.total || 0)}
                    </div>
                  </div>
                );
              })}
            </div>
            <div className="grid grid-cols-2 gap-2">
              <button onClick={syncPendingSales} disabled={!isOnline} className="flex items-center justify-center gap-1.5 bg-stone-900 hover:bg-stone-700 disabled:opacity-40 text-white rounded-lg py-2 text-xs font-bold">
                <Icon name="History" className="w-3.5 h-3.5" /> Relancer la sync
              </button>
              <button onClick={() => {
                if (window.confirm(`Supprimer définitivement les ${pendingSales.length} ventes en attente ? Cette action est irréversible et ces ventes seront perdues.`)) {
                  setPendingSales([]);
                }
              }} className="flex items-center justify-center gap-1.5 bg-white hover:bg-rose-50 border border-stone-200 text-rose-600 rounded-lg py-2 text-xs font-bold">
                <Icon name="Trash2" className="w-3.5 h-3.5" /> Vider la file
              </button>
            </div>
          </div>
        </section>
      )}

      <ClosureSection drinks={drinks} salesCount={allSalesCount} closeEvent={closeEvent} />

      {Array.isArray(archives) && archives.length > 0 && (
        <section>
          <button onClick={() => setShowArchives(s => !s)} className="w-full flex items-center justify-between mb-2 text-left">
            <h3 className="text-[10px] uppercase tracking-widest text-stone-500 font-bold">
              Archives ({archives.length})
            </h3>
            <Icon name={showArchives ? 'ChevronUp' : 'ChevronDown'} className="w-3.5 h-3.5 text-stone-400" />
          </button>
          {showArchives && (
            <div className="bg-white border border-stone-200 rounded-xl divide-y divide-stone-100 slide-up">
              {archives.map(archive => {
                const closedDate = new Date(archive.closedAt || 0);
                const dateStr = closedDate.toLocaleDateString('fr-BE', { day: '2-digit', month: 'short', year: 'numeric' });
                const timeStr = closedDate.toLocaleTimeString('fr-BE', { hour: '2-digit', minute: '2-digit' });
                const totalCollected = archive.totalCollected || 0;
                const isConfirming = confirmDeleteArchive === archive._key;
                const hasRecompte = Array.isArray(archive.recompte) && archive.recompte.length > 0;
                return (
                  <div key={archive._key} className="px-3 py-2.5">
                    <div className="flex items-start justify-between gap-2">
                      <div className="min-w-0 flex-1">
                        <div className="flex items-baseline gap-2 flex-wrap">
                          <div className="text-sm font-bold text-stone-900 truncate">
                            {archive.eventName || dateStr}
                          </div>
                          {hasRecompte && (
                            <span className="text-[9px] font-bold uppercase tracking-wider px-1.5 py-0.5 rounded-full bg-emerald-100 text-emerald-800">
                              Recompté
                            </span>
                          )}
                        </div>
                        <div className="text-[10px] text-stone-500 font-mono mt-0.5">
                          {dateStr} · {timeStr} · {archive.salesCount || 0} ventes · clôturé par {archive.closedBy || '?'}
                        </div>
                      </div>
                      <div className="font-mono text-sm font-bold text-stone-900 tabular-nums shrink-0">
                        {formatPrice(totalCollected)}
                      </div>
                    </div>
                    <div className="flex items-center gap-1.5 mt-2">
                      <button onClick={() => exportArchiveCSV(archive)} className="flex items-center gap-1 bg-stone-900 hover:bg-stone-700 text-white text-[10px] font-bold px-2.5 py-1.5 rounded">
                        <Icon name="Download" className="w-3 h-3" /> CSV
                      </button>
                      {!isConfirming ? (
                        <button onClick={() => setConfirmDeleteArchive(archive._key)} className="flex items-center gap-1 bg-white hover:bg-rose-50 border border-stone-200 text-rose-600 text-[10px] font-bold px-2.5 py-1.5 rounded">
                          <Icon name="Trash2" className="w-3 h-3" /> Supprimer
                        </button>
                      ) : (
                        <>
                          <button onClick={async () => { await deleteArchive(archive._key); setConfirmDeleteArchive(null); }} className="bg-rose-500 hover:bg-rose-600 text-white text-[10px] font-bold px-2.5 py-1.5 rounded">
                            Confirmer
                          </button>
                          <button onClick={() => setConfirmDeleteArchive(null)} className="bg-stone-200 text-stone-700 text-[10px] font-bold px-2 py-1.5 rounded">
                            ✕
                          </button>
                        </>
                      )}
                    </div>
                  </div>
                );
              })}
            </div>
          )}
        </section>
      )}

      <section>
        <h3 className="text-[10px] uppercase tracking-widest text-stone-500 mb-2 font-bold">Export &amp; Reset</h3>
        <div className="space-y-2">
          <button onClick={exportCSV} disabled={allSalesCount === 0} className="w-full flex items-center justify-center gap-2 bg-white hover:bg-stone-50 disabled:opacity-40 border border-stone-200 rounded-xl py-3 text-sm font-semibold text-stone-900">
            <Icon name="Download" className="w-4 h-4" /> Exporter en CSV ({allSalesCount} ventes)
          </button>
          {!confirmReset ? (
            <button onClick={() => setConfirmReset(true)} className="w-full flex items-center justify-center gap-2 bg-white hover:bg-rose-50 border border-stone-200 hover:border-rose-200 rounded-xl py-3 text-sm font-semibold text-rose-600">
              <Icon name="Trash2" className="w-4 h-4" /> Tout réinitialiser
            </button>
          ) : (
            <div className="bg-rose-50 border border-rose-200 rounded-xl p-3 space-y-2 slide-up">
              <div className="flex items-start gap-2 text-sm">
                <Icon name="AlertTriangle" className="w-4 h-4 text-rose-600 mt-0.5 shrink-0" />
                <div className="text-rose-800 font-medium">Effacer toutes les ventes de tous les barmen ? Cette action est irréversible.</div>
              </div>
              <div className="grid grid-cols-2 gap-2">
                <button onClick={() => setConfirmReset(false)} className="bg-stone-100 text-stone-700 text-sm py-2 rounded-lg font-semibold">Annuler</button>
                <button onClick={resetAll} className="bg-rose-500 text-white text-sm py-2 rounded-lg font-bold">Confirmer</button>
              </div>
            </div>
          )}
        </div>
      </section>

      <div className="text-center text-[10px] text-stone-400 font-mono pt-2">
        session: {sessionId} · {myKeysCount}/{allSalesCount} ventes
      </div>
    </div>
  );
}
