/* ───────────────────────────────────────────────────────────
   ArfDiagram.jsx — Schéma ARF dynamique (cadre séparé sous la scène)
   Rôles eIDAS2/ARF et flux en temps réel entre :
     • HOLDER             — ID Wallet (wallet du citoyen)
     • RELYING PARTY INTERMEDIARY — Doxallia (intermédiaire / vérificateur)
     • RELYING PARTY      — Banque Démo (service métier)
   Le schéma réagit à l'état du démonstrateur (mode, stage, wallet).
   Exporte aussi <DoxMark> : cadre coloré autour d'un composant fourni
   par Doxallia (ex. le QR code = Web Element marque blanche).
   ─────────────────────────────────────────────────────────── */

const { Ic: AIc, IIc: AIIc } = window;

const DOX  = '#e8513a';   // corail Doxallia (intermédiaire)
const BANK = '#1657c8';   // bleu Banque Démo (relying party)
const RF   = '#222834';   // Bleu France (holder / wallet)
const LINE = '#d8dee8';

// icône « relais / échange » pour le proxy
function RelayIcon({ s = 22, c = '#fff' }) {
  return (
    <svg viewBox="0 0 24 24" width={s} height={s} fill="none" stroke={c}
      strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round">
      <path d="M4 8.5h12l-3.2-3.2M16 8.5l-3.2 3.2" />
      <path d="M20 15.5H8l3.2-3.2M8 15.5l3.2 3.2" />
    </svg>
  );
}

/* ── résolution de l'étape ARF à partir de l'état du démo ──
   renvoie : on{holder,dox,bank}, L/R {dir,msg}, caption, tech       */
function resolveArf(mode, stage, wallet) {
  const same = mode === 'samedevice';
  const transport = same ? 'lien profond' : 'QR code';

  // priorité aux états « terminaux »
  if (stage === 'summary') return {
    on: { dox: 1, bank: 1 },
    L: { dir: 0 }, R: { dir: 1, msg: 'attributs vérifiés' },
    caption: "Banque Démo affiche les attributs vérifiés. La présentation n'a jamais transité en clair par la banque — Doxallia a assuré l'intermédiation et la vérification.",
    tech: 'claims (verified)', accent: BANK,
  };
  if (stage === 'verifying' || wallet === 'success') return {
    on: { dox: 1, bank: 1 },
    L: { dir: 1, msg: 'vp_token' }, R: { dir: 1, msg: 'données vérifiées' },
    caption: "Doxallia reçoit la présentation, contrôle signatures, émetteur et révocation, puis transmet à la banque uniquement les données vérifiées.",
    tech: 'verify → claims', accent: DOX,
  };

  switch (wallet) {
    case 'scan':
    case 'launch': return {
      on: { holder: 1, dox: 1 },
      L: { dir: 1, msg: 'request_uri' }, R: { dir: 0 },
      caption: same
        ? "Le lien profond ouvre ID Wallet, qui récupère la demande de présentation auprès de Doxallia."
        : "Le wallet scanne le QR et récupère la demande de présentation auprès du point d'entrée Doxallia.",
      tech: 'GET request_uri', accent: DOX,
    };
    case 'consent': return {
      on: { holder: 1, dox: 1 },
      L: { dir: -1, msg: 'presentation_definition' }, R: { dir: 0 },
      caption: "Doxallia a transmis la demande (presentation_definition) au wallet ; l'utilisateur choisit les attributs à partager.",
      tech: 'presentation_definition', accent: RF,
    };
    case 'auth': return {
      on: { holder: 1 },
      L: { dir: 0 }, R: { dir: 0 },
      caption: "Le wallet signe la présentation vérifiable avec le code personnel de l'utilisateur. Rien n'est encore transmis.",
      tech: 'sign vp_token', accent: RF,
    };
    case 'sharing': return {
      on: { holder: 1, dox: 1 },
      L: { dir: 1, msg: 'vp_token' }, R: { dir: 0 },
      caption: "Le wallet transmet la présentation vérifiable signée au vérificateur Doxallia.",
      tech: 'POST vp_token', accent: DOX,
    };
  }

  if (stage === 'qr') return {
    on: { dox: 1, bank: 1 },
    L: { dir: 0, msg: same ? 'en attente d\'ouverture' : 'en attente du scan' }, R: { dir: 0 },
    caption: `Doxallia génère la requête OpenID4VP et publie le ${transport} : c'est un Web Element marque blanche injecté dans la page de Banque Démo.`,
    tech: 'Authorization Request', accent: DOX,
  };
  if (stage === 'choose') return {
    on: { dox: 1, bank: 1 },
    L: { dir: 0 }, R: { dir: -1, msg: 'init session' },
    caption: "L'utilisateur choisit le portefeuille. La page banque demande à Doxallia d'initier une présentation d'identité.",
    tech: 'init presentation', accent: BANK,
  };
  // home / idle — l'utilisateur n'est encore que sur le site de la banque ;
  // Doxallia n'intervient qu'au lancement du parcours d'identification.
  return {
    on: { bank: 1 },
    L: { dir: 0 }, R: { dir: 0 },
    caption: same
      ? "L'utilisateur est sur le site mobile de Banque Démo. Aucune brique d'identité n'est encore sollicitée : Doxallia reste inactif tant que le parcours d'identification n'a pas démarré."
      : "L'utilisateur est sur le site de Banque Démo. Aucune brique d'identité n'est encore sollicitée : Doxallia reste inactif tant que le parcours d'identification n'a pas démarré.",
    tech: 'site banque', accent: BANK,
  };
}

/* ── carte d'un rôle ── */
function ArfNode({ role, name, sub, color, icon, active, focus, onInfo, info }) {
  return (
    <div style={{ position: 'relative', flex: '0 0 232px', maxWidth: 232,
      padding: '13px 15px', borderRadius: 14, background: active ? '#fff' : '#fbfcfe',
      border: `1.5px solid ${active ? color : LINE}`,
      boxShadow: focus ? `0 0 0 4px ${color}22, 0 14px 30px -18px ${color}66`
        : active ? `0 10px 26px -18px ${color}77` : 'none',
      transition: 'all .25s', animation: focus ? 'arf-focus 1.3s ease-out infinite' : 'none' }}>
      <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: 9 }}>
        <span style={{ fontSize: 9.5, fontWeight: 800, letterSpacing: '.07em', textTransform: 'uppercase',
          color: active ? color : '#9aa4b4' }}>{role}</span>
        <span style={{ width: 8, height: 8, borderRadius: '50%', flexShrink: 0,
          background: active ? color : '#cdd5e0',
          boxShadow: active ? `0 0 0 3px ${color}26` : 'none',
          animation: active ? 'pulse-soft 1.4s infinite' : 'none' }} />
      </div>
      <div style={{ display: 'flex', alignItems: 'center', gap: 11 }}>
        <div style={{ width: 40, height: 40, borderRadius: 11, flexShrink: 0,
          display: 'flex', alignItems: 'center', justifyContent: 'center',
          background: active ? color : '#e7ecf3', transition: 'background .25s' }}>
          {icon(active ? '#fff' : '#8a93a6')}
        </div>
        <div style={{ minWidth: 0 }}>
          <div style={{ fontSize: 15, fontWeight: 800, color: '#0e1726', letterSpacing: '-.01em',
            lineHeight: 1.15, whiteSpace: 'nowrap' }}>{name}</div>
          <div style={{ fontSize: 11, color: '#5b6678', marginTop: 1, lineHeight: 1.25 }}>{sub}</div>
        </div>
      </div>
      {onInfo && (
        <button onClick={onInfo} style={{ position: 'absolute', top: 10, right: 22, border: 'none',
          background: 'none', cursor: 'pointer', padding: 0, display: info ? 'none' : 'block' }} />
      )}
    </div>
  );
}

/* ── connecteur animé entre deux rôles ── */
function ArfLink({ protocol, color, dir = 0, msg, active }) {
  const live = dir !== 0;
  const railCol = live ? color : LINE;
  return (
    <div style={{ flex: '1 1 70px', minWidth: 64, maxWidth: 188, position: 'relative',
      display: 'flex', flexDirection: 'column', alignItems: 'center', justifyContent: 'center', gap: 7,
      padding: '0 4px', alignSelf: 'center' }}>
      {/* protocole */}
      <div style={{ display: 'inline-flex', alignItems: 'center', gap: 5, padding: '3px 9px', borderRadius: 999,
        background: active ? `${color}14` : '#eef1f6', transition: 'background .25s',
        fontSize: 9.5, fontWeight: 800, letterSpacing: '.02em', whiteSpace: 'nowrap',
        color: active ? color : '#8a93a6' }}>
        <AIc.lock s={11} c={active ? color : '#8a93a6'} /> {protocol}
      </div>
      {/* rail */}
      <div style={{ position: 'relative', width: '100%', height: 2,
        borderTop: `2px ${live ? 'solid' : 'dashed'} ${railCol}`, transition: 'border-color .25s' }}>
        {live && (
          <span style={{ position: 'absolute', top: -4, width: 8, height: 8, borderRadius: '50%',
            background: color, boxShadow: `0 0 10px ${color}`,
            animation: `${dir > 0 ? 'arf-r' : 'arf-l'} 1.35s linear infinite` }} />
        )}
        {/* pointe de flèche au point d'arrivée */}
        {live && (
          <span style={{ position: 'absolute', top: -4,
            [dir > 0 ? 'right' : 'left']: -1, width: 0, height: 0,
            borderTop: '5px solid transparent', borderBottom: '5px solid transparent',
            [dir > 0 ? 'borderLeft' : 'borderRight']: `7px solid ${color}` }} />
        )}
      </div>
      {/* message technique du flux */}
      <div style={{ fontSize: 9.5, fontFamily: 'ui-monospace, monospace', textAlign: 'center',
        color: live ? color : '#aab4c4', minHeight: 12, lineHeight: 1.2,
        fontWeight: live ? 700 : 500, whiteSpace: 'nowrap', maxWidth: '100%', overflow: 'hidden',
        textOverflow: 'ellipsis' }}>{msg || ''}</div>
    </div>
  );
}

/* ── popover « ce que fournit Doxallia » ── */
function DoxInfo({ onClose }) {
  const items = [
    ['Composants UI marque blanche', 'QR code, bouton « portefeuille », écrans d\'attente — intégrés dans la page banque (Web Elements).'],
    ['Vérificateur OpenID4VP', 'Doxallia dialogue avec le wallet à la place de la banque : génération de la requête, réception de la présentation.'],
    ['Contrôle de confiance', 'Vérifie signature, émetteur (eIDAS2) et révocation, puis ne transmet à la banque que des données vérifiées.'],
  ];
  return (
    <div style={{ position: 'absolute', bottom: 'calc(100% + 10px)', left: '50%', transform: 'translateX(-50%)',
      width: 340, background: '#fff', borderRadius: 14, padding: 16, zIndex: 30,
      border: `1.5px solid ${DOX}`, boxShadow: '0 26px 60px -26px rgba(14,23,38,.55)' }}>
      <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: 10 }}>
        <div style={{ display: 'inline-flex', alignItems: 'center', gap: 8, fontSize: 12.5, fontWeight: 800, color: DOX }}>
          <span style={{ width: 22, height: 22, borderRadius: 6, background: DOX, display: 'grid', placeItems: 'center' }}>
            <RelayIcon s={14} c="#fff" /></span>
          Ce que fournit Doxallia
        </div>
        <button onClick={onClose} style={{ border: 'none', background: 'none', cursor: 'pointer',
          fontSize: 15, color: '#8a93a6', lineHeight: 1 }}>✕</button>
      </div>
      <div style={{ display: 'flex', flexDirection: 'column', gap: 10 }}>
        {items.map(([t, d]) => (
          <div key={t} style={{ display: 'flex', gap: 9 }}>
            <span style={{ width: 6, height: 6, borderRadius: '50%', background: DOX, flexShrink: 0, marginTop: 6 }} />
            <div>
              <div style={{ fontSize: 12.5, fontWeight: 700, color: '#0e1726' }}>{t}</div>
              <div style={{ fontSize: 11.5, lineHeight: 1.45, color: '#56627a', marginTop: 1 }}>{d}</div>
            </div>
          </div>
        ))}
      </div>
      <span style={{ position: 'absolute', bottom: -8, left: '50%', transform: 'translateX(-50%) rotate(45deg)',
        width: 14, height: 14, background: '#fff', borderRight: `1.5px solid ${DOX}`, borderBottom: `1.5px solid ${DOX}` }} />
    </div>
  );
}

/* ── bande principale (cadre séparé) ── */
function ArfDiagram({ mode, stage, wallet, focusDox, open, onToggle }) {
  const [info, setInfo] = React.useState(false);
  const step = resolveArf(mode, stage, wallet);
  const on = step.on || {};
  const transport = mode === 'samedevice' ? 'OpenID4VP · lien' : 'OpenID4VP · QR';

  return (
    <div style={{ flexShrink: 0, padding: '0 clamp(12px,3vw,28px) 14px' }}>
      <div style={{ maxWidth: 1320, margin: '0 auto', background: '#fff', borderRadius: 16,
        border: '1px solid #e2e7ef', boxShadow: '0 18px 40px -28px rgba(14,23,38,.45)', overflow: 'visible' }}>
        {/* en-tête */}
        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between',
          padding: '11px 16px', borderBottom: open ? '1px solid #eef1f6' : 'none' }}>
          <div style={{ display: 'flex', alignItems: 'center', gap: 10 }}>
            <span style={{ width: 8, height: 8, borderRadius: '50%', background: step.accent,
              animation: 'pulse-soft 1.4s infinite' }} />
            <span style={{ fontSize: 13, fontWeight: 800, color: '#0e1726', letterSpacing: '-.01em' }}>
              Architecture ARF — flux en temps réel
            </span>
            <span style={{ fontSize: 11, color: '#8a93a6', fontWeight: 600 }}>eIDAS2 · rôles & protocoles</span>
          </div>
          <div style={{ display: 'flex', alignItems: 'center', gap: 14 }}>
            <div style={{ display: 'flex', alignItems: 'center', gap: 12 }}>
              {[['Holder', RF], ['Intermediary', DOX], ['Relying Party', BANK]].map(([l, c]) => (
                <span key={l} style={{ display: 'inline-flex', alignItems: 'center', gap: 5,
                  fontSize: 10.5, fontWeight: 700, color: '#56627a' }}>
                  <span style={{ width: 9, height: 9, borderRadius: 3, background: c }} /> {l}
                </span>
              ))}
            </div>
            <button onClick={onToggle} style={{ display: 'inline-flex', alignItems: 'center', gap: 6,
              border: '1px solid #e2e7ef', background: '#fff', borderRadius: 8, padding: '5px 9px',
              cursor: 'pointer', fontSize: 11.5, fontWeight: 700, color: '#56627a' }}>
              {open ? 'Réduire' : 'Afficher le schéma'}
              <span style={{ display: 'inline-block', transform: open ? 'rotate(180deg)' : 'none',
                transition: 'transform .2s' }}>⌄</span>
            </button>
          </div>
        </div>

        {open && (
          <div style={{ padding: '16px 18px 14px' }}>
            {/* rangée des rôles + flux */}
            <div style={{ display: 'flex', alignItems: 'stretch', justifyContent: 'center' }}>
              <ArfNode role="Holder" name="ID Wallet" sub="Wallet du citoyen · PID"
                color={RF} active={!!on.holder} focus={false}
                icon={(c) => <AIc.shield s={21} c={c} />} />

              <ArfLink protocol={transport} color={DOX} dir={step.L.dir} msg={step.L.msg} active={step.L.dir !== 0} />

              <div style={{ position: 'relative', flex: '0 0 232px', maxWidth: 232 }}>
                {info && <DoxInfo onClose={() => setInfo(false)} />}
                <div onClick={() => setInfo(v => !v)} style={{ cursor: 'pointer' }}>
                  <ArfNode role="Relying Party Intermediary" name="Doxallia" sub="Intermédiaire & vérificateur ⓘ"
                    color={DOX} active={!!on.dox} focus={focusDox}
                    icon={(c) => <RelayIcon s={21} c={c} />} />
                </div>
              </div>

              <ArfLink protocol="Marque blanche · API" color={BANK} dir={step.R.dir} msg={step.R.msg} active={step.R.dir !== 0} />

              <ArfNode role="Relying Party" name="Banque Démo" sub="Service métier (verifier)"
                color={BANK} active={!!on.bank} focus={false}
                icon={(c) => <AIc.bank s={21} c={c} />} />
            </div>

            {/* légende d'étape */}
            <div style={{ display: 'flex', alignItems: 'center', gap: 14, marginTop: 14, padding: '11px 14px',
              borderRadius: 12, background: `${step.accent}0c`, border: `1px solid ${step.accent}26` }}>
              <span style={{ flexShrink: 0, width: 26, height: 26, borderRadius: 8, background: step.accent,
                display: 'grid', placeItems: 'center', color: '#fff' }}>
                <AIc.arrow s={15} c="#fff" />
              </span>
              <div style={{ flex: 1, fontSize: 12.5, lineHeight: 1.45, color: '#26334a', fontWeight: 500 }}>
                {step.caption}
              </div>
              <span style={{ flexShrink: 0, fontSize: 10.5, fontFamily: 'ui-monospace, monospace', fontWeight: 700,
                color: step.accent, background: '#fff', border: `1px solid ${step.accent}33`,
                padding: '4px 9px', borderRadius: 7, whiteSpace: 'nowrap' }}>
                {step.tech}
              </span>
            </div>
          </div>
        )}
      </div>
    </div>
  );
}

/* ── DoxMark : cadre coloré autour d'un composant fourni par Doxallia ──
   Utilisé p.ex. autour du QR code (Web Element marque blanche).         */
function DoxMark({ children, label = 'Composant Doxallia', sub, onFocus }) {
  const [h, setH] = React.useState(false);
  return (
    <div style={{ position: 'relative', display: 'inline-block' }}
      onMouseEnter={() => { setH(true); onFocus && onFocus(true); }}
      onMouseLeave={() => { setH(false); onFocus && onFocus(false); }}>
      {children}
      {/* cadre */}
      <div style={{ position: 'absolute', inset: -11, borderRadius: 18, pointerEvents: 'none',
        border: `2px dashed ${DOX}`, transition: 'box-shadow .2s, background .2s',
        background: h ? `${DOX}0a` : 'transparent',
        boxShadow: h ? `0 0 0 5px ${DOX}1f` : 'none' }} />
      {/* étiquette */}
      <div style={{ position: 'absolute', top: -27, left: -11, display: 'inline-flex', alignItems: 'center', gap: 6,
        padding: '4px 9px', borderRadius: 999, background: DOX, color: '#fff', whiteSpace: 'nowrap',
        fontSize: 10.5, fontWeight: 800, boxShadow: `0 6px 16px -6px ${DOX}cc` }}>
        <RelayIcon s={12} c="#fff" /> {label}
      </div>
      {/* renvoi au schéma */}
      <div style={{ position: 'absolute', bottom: -25, right: -11, display: 'inline-flex', alignItems: 'center', gap: 5,
        padding: '3px 9px', borderRadius: 999, background: '#fff', border: `1px solid ${DOX}`, whiteSpace: 'nowrap',
        fontSize: 10, fontWeight: 700, color: DOX }}>
        {sub || 'voir le schéma ↓'}
      </div>
    </div>
  );
}

Object.assign(window, { ArfDiagram, DoxMark });
