// screens/Retoque.jsx — La mesa de revelado: retoca una pieza de la galería.
//
// Concepto (coherente con el museo nocturno de la galería): no es un panel de
// sliders genérico, es una MESA DE LUZ. La pieza descansa sobre el tablero; a un
// lado, una pila de AJUSTES en vivo (luz, contraste, color, desenfoque) y, abajo,
// CAPAS discretas que se apilan sobre el negativo (marco, texto, blanco y negro,
// giro). Cada cambio se revela contra el backend real (Pillow) con un respiro
// (debounce), como un positivo que aparece. Guardar = un nuevo positivo en la
// galería; el original (el negativo) nunca se toca.

// Ajustes continuos: factor 1 = sin cambio. Se compilan a pasos del pipeline.
const AJUSTES = [
  { clave: 'brightness', etiqueta: 'Luz',       min: 0.4, max: 1.8, paso: 0.02 },
  { clave: 'contrast',   etiqueta: 'Contraste', min: 0.4, max: 1.8, paso: 0.02 },
  { clave: 'saturation', etiqueta: 'Color',     min: 0.0, max: 2.0, paso: 0.02 },
  { clave: 'blur',       etiqueta: 'Niebla',    min: 0.0, max: 12,  paso: 0.5, esRadio: true },
];

// Capas discretas (se encienden/apagan o llevan su propio dato).
const NEGRO = '#0C0724';

function Deslizador({ etiqueta, valor, min, max, paso, defecto, onCambio }) {
  const pct = ((valor - min) / (max - min)) * 100;
  const tocado = Math.abs(valor - defecto) > 0.001;
  return (
    <div style={{ marginBottom: 18 }}>
      <div style={{
        display: 'flex', justifyContent: 'space-between', alignItems: 'baseline',
        marginBottom: 8,
      }}>
        <span style={{
          fontFamily: 'var(--hl-font-mono)', fontSize: 10, letterSpacing: 1.5,
          textTransform: 'uppercase',
          color: tocado ? 'var(--hl-accent-light)' : 'rgba(255,255,255,0.45)',
        }}>{etiqueta}</span>
        {tocado && (
          <button onClick={() => onCambio(defecto)} style={{
            background: 'none', border: 'none', cursor: 'pointer', padding: 0,
            fontFamily: 'var(--hl-font-mono)', fontSize: 9, letterSpacing: 1,
            color: 'rgba(255,255,255,0.35)',
          }}>↺</button>
        )}
      </div>
      <input type="range" min={min} max={max} step={paso} value={valor}
        onChange={e => onCambio(parseFloat(e.target.value))}
        style={{
          width: '100%', height: 3, appearance: 'none', WebkitAppearance: 'none',
          borderRadius: 2, outline: 'none', cursor: 'pointer',
          background: `linear-gradient(90deg, var(--hl-accent-1) ${pct}%, rgba(255,255,255,0.1) ${pct}%)`,
        }} />
    </div>
  );
}

function CapaToggle({ etiqueta, activa, onClick, hijo }) {
  return (
    <div style={{
      borderRadius: 12, overflow: 'hidden',
      border: `1px solid ${activa ? 'rgba(192,132,252,0.4)' : 'rgba(255,255,255,0.07)'}`,
      background: activa ? 'rgba(168,85,247,0.08)' : 'rgba(255,255,255,0.025)',
      transition: 'border-color 0.2s ease, background 0.2s ease',
    }}>
      <button onClick={onClick} style={{
        width: '100%', display: 'flex', alignItems: 'center', justifyContent: 'space-between',
        padding: '11px 13px', background: 'none', border: 'none', cursor: 'pointer',
      }}>
        <span style={{
          fontFamily: 'var(--hl-font-ui)', fontSize: 13.5, fontWeight: 500,
          color: activa ? '#fff' : 'rgba(255,255,255,0.65)', letterSpacing: -0.2,
        }}>{etiqueta}</span>
        <span style={{
          width: 34, height: 18, borderRadius: 9, position: 'relative', flexShrink: 0,
          background: activa ? 'var(--hl-accent-1)' : 'rgba(255,255,255,0.12)',
          transition: 'background 0.2s ease',
        }}>
          <span style={{
            position: 'absolute', top: 2, left: activa ? 18 : 2, width: 14, height: 14,
            borderRadius: '50%', background: '#fff',
            transition: 'left 0.22s cubic-bezier(0.22,1,0.36,1)',
          }} />
        </span>
      </button>
      {/* grid-template-rows para animar alto sin reflow brusco */}
      <div style={{
        display: 'grid', gridTemplateRows: activa && hijo ? '1fr' : '0fr',
        transition: 'grid-template-rows 0.28s cubic-bezier(0.22,1,0.36,1)',
      }}>
        <div style={{ overflow: 'hidden' }}>
          {activa && hijo && <div style={{ padding: '0 13px 13px' }}>{hijo}</div>}
        </div>
      </div>
    </div>
  );
}

function RetoqueScreen({ pieza, onCerrar, onGuardada }) {
  // pieza: {id, titulo, tipo, imagen(miniatura)} — la fuente real se lee por id.
  const [ajustes, setAjustes] = React.useState(
    () => Object.fromEntries(AJUSTES.map(a => [a.clave, a.esRadio ? 0 : 1])));
  const [marco, setMarco] = React.useState(false);
  const [marcoColor, setMarcoColor] = React.useState('#F5C56B');
  const [byn, setByn] = React.useState(false);
  const [rotar, setRotar] = React.useState(0);   // 0/90/180/270
  const [textoOn, setTextoOn] = React.useState(false);
  const [texto, setTexto] = React.useState('');

  const [preview, setPreview] = React.useState(pieza.imagen);   // arranca con la miniatura
  // Robustez: si la instancia se reutiliza para otra pieza (sin remount), el
  // preview vuelve a la miniatura de ESA pieza, no a la anterior.
  React.useEffect(() => { setPreview(pieza.imagen); }, [pieza.id, pieza.imagen]);
  const [revelando, setRevelando] = React.useState(false);
  // Presets ("looks de un clic"): el preset activo manda; sus pasos van ANTES
  // de los ajustes manuales, así un look se puede afinar con los sliders.
  const [presets, setPresets] = React.useState([]);
  const [presetActivo, setPresetActivo] = React.useState(null);
  React.useEffect(() => {
    window.estudioAPI.presetsImagen().then(d => setPresets(d.presets)).catch(() => {});
  }, []);
  const [guardando, setGuardando] = React.useState(false);
  const [error, setError] = React.useState(null);
  const tmr = React.useRef(null);

  // Compila el estado de la mesa a la lista de pasos del pipeline del backend.
  const construirPasos = React.useCallback(() => {
    const pasos = [];
    // El preset va primero (look base); los ajustes manuales lo afinan encima.
    if (presetActivo) {
      const pr = presets.find(p => p.clave === presetActivo);
      if (pr) pasos.push(...pr.pasos);
    }
    if (byn) pasos.push({ op: 'grayscale', params: {} });
    AJUSTES.forEach(a => {
      const v = ajustes[a.clave];
      if (a.esRadio) { if (v > 0) pasos.push({ op: 'blur', params: { radio: v } }); }
      else if (Math.abs(v - 1) > 0.001) pasos.push({ op: a.clave, params: { factor: v } });
    });
    if (rotar) pasos.push({ op: 'rotate', params: { grados: rotar, expandir: true } });
    if (textoOn && texto.trim()) pasos.push({
      op: 'text', params: { texto: texto.trim().toUpperCase(), x: 60, y: 60,
        tamano: 64, color: '#ffffff', sombra: true },
    });
    if (marco) pasos.push({ op: 'border', params: { ancho: 24, color: marcoColor } });
    return pasos;
  }, [presetActivo, presets, ajustes, byn, rotar, textoOn, texto, marco, marcoColor]);

  const pasos = construirPasos();
  const hayCambios = pasos.length > 0;
  // Firma estable de los pasos: el efecto solo se redispara cuando CAMBIAN de
  // verdad (no en cada render). Evita el bucle de tener construirPasos en deps.
  const firmaPasos = JSON.stringify(pasos);

  // Revela el positivo: aplica el pipeline en el backend (con respiro).
  React.useEffect(() => {
    const lista = JSON.parse(firmaPasos);
    if (lista.length === 0) { setPreview(pieza.imagen); return; }
    if (tmr.current) clearTimeout(tmr.current);
    tmr.current = setTimeout(async () => {
      setRevelando(true); setError(null);
      try {
        const d = await window.estudioAPI.editarImagen({
          fuente: { tipo: 'galeria', id: pieza.id },
          pasos: lista,
          salida: { formato: 'png' },
        });
        setPreview(d.imagen);
      } catch (e) { setError(e.message); }
      setRevelando(false);
    }, 450);
    return () => tmr.current && clearTimeout(tmr.current);
  }, [firmaPasos, pieza.id, pieza.imagen]);

  const guardar = async () => {
    const pasos = construirPasos();
    if (pasos.length === 0) return;
    setGuardando(true); setError(null);
    try {
      await window.estudioAPI.editarImagen({
        fuente: { tipo: 'galeria', id: pieza.id }, pasos,
        salida: { formato: 'png', guardar_en_galeria: true,
                  nombre: `${pieza.titulo} · retoque` },
      });
      onGuardada && onGuardada();
    } catch (e) { setError(e.message); setGuardando(false); }
  };

  const resetear = () => {
    setAjustes(Object.fromEntries(AJUSTES.map(a => [a.clave, a.esRadio ? 0 : 1])));
    setMarco(false); setByn(false); setRotar(0); setTextoOn(false); setTexto('');
    setPresetActivo(null);
  };

  return (
    <div style={{
      position: 'absolute', inset: 0, zIndex: 70,
      background: `radial-gradient(ellipse at 30% 0%, #14092E 0%, ${NEGRO} 55%, #04020E 100%)`,
      display: 'flex', flexDirection: 'column',
      animation: 'hlfade 0.3s ease both',
    }}>
      {/* Cabecera */}
      <div style={{ height: 'calc(var(--safe-top, 44px) + 8px)', flexShrink: 0 }} />
      <div style={{
        display: 'flex', alignItems: 'center', justifyContent: 'space-between',
        padding: '4px 18px 12px', flexShrink: 0,
      }}>
        <div>
          <div style={{
            fontFamily: 'var(--hl-font-mono)', fontSize: 9.5, letterSpacing: 2,
            color: 'var(--hl-accent-light)', textTransform: 'uppercase', marginBottom: 4,
          }}>Mesa de revelado</div>
          <div style={{
            fontFamily: 'var(--hl-font-display)', fontStyle: 'italic',
            fontSize: 22, color: '#fff', letterSpacing: -0.5, lineHeight: 1,
          }}>Retoque</div>
        </div>
        <button onClick={onCerrar} style={{
          width: 36, height: 36, borderRadius: 11, border: 'none',
          background: 'rgba(255,255,255,0.07)', color: 'rgba(255,255,255,0.75)',
          cursor: 'pointer', display: 'flex', alignItems: 'center', justifyContent: 'center',
        }}>
          <svg width="15" height="15" viewBox="0 0 14 14" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round">
            <path d="M2 2l10 10M12 2L2 12" />
          </svg>
        </button>
      </div>

      {/* Cuerpo: tablero (pieza) + panel de herramientas. Apila en móvil. */}
      <div style={{ flex: 1, overflowY: 'auto', overflowX: 'hidden', minHeight: 0 }}>
        <div style={{
          display: 'flex', flexDirection: 'column', gap: 0,
          padding: '0 18px 18px',
        }}>
          {/* Tablero */}
          <div style={{
            position: 'relative', display: 'flex', alignItems: 'center',
            justifyContent: 'center', padding: '6px 0 18px',
          }}>
            <img src={preview} alt={pieza.titulo} style={{
              maxWidth: '100%', maxHeight: '46vh', borderRadius: 12,
              boxShadow: '0 24px 70px rgba(0,0,0,0.65), 0 0 0 1px rgba(221,214,254,0.06)',
              filter: revelando ? 'brightness(0.82)' : 'none',
              transition: 'filter 0.3s ease',
            }} />
            {revelando && (
              <div style={{
                position: 'absolute', bottom: 30, left: '50%', transform: 'translateX(-50%)',
                display: 'flex', alignItems: 'center', gap: 8,
                padding: '6px 12px', borderRadius: 20,
                background: 'rgba(8,5,26,0.8)', backdropFilter: 'blur(8px)',
              }}>
                <div style={{
                  width: 11, height: 11, borderRadius: '50%',
                  border: '2px solid rgba(168,85,247,0.4)', borderTopColor: 'var(--hl-accent-1)',
                  animation: 'hlspin 0.7s linear infinite',
                }} />
                <span style={{
                  fontFamily: 'var(--hl-font-mono)', fontSize: 9, letterSpacing: 1.5,
                  color: 'rgba(255,255,255,0.6)', textTransform: 'uppercase',
                }}>Revelando</span>
              </div>
            )}
          </div>

          {/* Looks de un clic (presets) — tira horizontal con scroll */}
          {presets.length > 0 && (
            <div style={{ marginBottom: 18 }}>
              <div style={{
                fontFamily: 'var(--hl-font-mono)', fontSize: 9.5, letterSpacing: 1.5,
                textTransform: 'uppercase', color: 'rgba(255,255,255,0.4)',
                marginBottom: 10, padding: '0 2px',
              }}>Looks</div>
              <div style={{
                display: 'flex', gap: 8, overflowX: 'auto', paddingBottom: 4,
                WebkitOverflowScrolling: 'touch',
              }}>
                <button onClick={() => setPresetActivo(null)} style={{
                  flexShrink: 0, height: 38, padding: '0 16px', borderRadius: 19,
                  border: `1px solid ${!presetActivo ? 'rgba(192,132,252,0.5)' : 'rgba(255,255,255,0.1)'}`,
                  background: !presetActivo ? 'rgba(168,85,247,0.18)' : 'transparent',
                  color: !presetActivo ? 'var(--hl-accent-light)' : 'rgba(255,255,255,0.55)',
                  fontFamily: 'var(--hl-font-ui)', fontSize: 13, cursor: 'pointer',
                  whiteSpace: 'nowrap',
                }}>Original</button>
                {presets.map(pr => {
                  const on = presetActivo === pr.clave;
                  return (
                    <button key={pr.clave} onClick={() => setPresetActivo(on ? null : pr.clave)}
                      title={pr.descripcion} style={{
                        flexShrink: 0, height: 38, padding: '0 16px', borderRadius: 19,
                        border: `1px solid ${on ? 'rgba(192,132,252,0.5)' : 'rgba(255,255,255,0.1)'}`,
                        background: on
                          ? 'linear-gradient(135deg, rgba(180,94,255,0.25), rgba(79,31,203,0.2))'
                          : 'rgba(255,255,255,0.03)',
                        color: on ? '#fff' : 'rgba(255,255,255,0.7)',
                        fontFamily: 'var(--hl-font-ui)', fontSize: 13, fontWeight: on ? 600 : 400,
                        cursor: 'pointer', whiteSpace: 'nowrap', letterSpacing: -0.2,
                      }}>{pr.nombre}</button>
                  );
                })}
              </div>
            </div>
          )}

          {/* Ajustes de luz */}
          <div style={{ padding: '4px 2px' }}>
            {AJUSTES.map(a => (
              <Deslizador key={a.clave} etiqueta={a.etiqueta}
                valor={ajustes[a.clave]} min={a.min} max={a.max} paso={a.paso}
                defecto={a.esRadio ? 0 : 1}
                onCambio={v => setAjustes(p => ({ ...p, [a.clave]: v }))} />
            ))}
          </div>

          {/* Capas */}
          <div style={{ display: 'flex', flexDirection: 'column', gap: 9, marginTop: 6 }}>
            <CapaToggle etiqueta="Blanco y negro" activa={byn} onClick={() => setByn(b => !b)} />

            <CapaToggle etiqueta="Marco" activa={marco} onClick={() => setMarco(m => !m)}
              hijo={
                <div style={{ display: 'flex', gap: 8, paddingTop: 4 }}>
                  {['#F5C56B', '#A855F7', '#ffffff', '#0C0724'].map(c => (
                    <button key={c} onClick={() => setMarcoColor(c)} style={{
                      width: 26, height: 26, borderRadius: 8, cursor: 'pointer',
                      background: c, border: marcoColor === c
                        ? '2px solid #fff' : '1px solid rgba(255,255,255,0.2)',
                    }} />
                  ))}
                </div>
              } />

            <CapaToggle etiqueta="Texto" activa={textoOn} onClick={() => setTextoOn(t => !t)}
              hijo={
                <input type="text" value={texto} placeholder="Una frase corta…"
                  onChange={e => setTexto(e.target.value)} style={{
                    width: '100%', height: 40, marginTop: 4, padding: '0 12px',
                    background: 'rgba(255,255,255,0.05)',
                    border: '1px solid rgba(255,255,255,0.1)', borderRadius: 10,
                    color: '#fff', fontSize: 14, fontFamily: 'var(--hl-font-ui)',
                    outline: 'none', boxSizing: 'border-box',
                  }} />
              } />

            <CapaToggle etiqueta="Girar" activa={rotar !== 0} onClick={() => setRotar(r => (r + 90) % 360)}
              hijo={
                <div style={{
                  fontFamily: 'var(--hl-font-mono)', fontSize: 11, paddingTop: 4,
                  color: 'rgba(255,255,255,0.5)', letterSpacing: 1,
                }}>{rotar}° · toca para girar otros 90°</div>
              } />
          </div>

          {error && (
            <div style={{
              marginTop: 14, padding: '11px 13px', borderRadius: 11,
              background: 'rgba(177,74,96,0.12)', border: '1px solid rgba(177,74,96,0.3)',
              color: '#E8B4BE', fontSize: 12.5, lineHeight: 1.5,
            }}>{error}</div>
          )}
        </div>
      </div>

      {/* Acciones */}
      <div style={{
        flexShrink: 0, display: 'flex', gap: 10,
        padding: '12px 18px calc(12px + var(--safe-bottom, 16px))',
        background: 'rgba(8,5,26,0.72)', backdropFilter: 'blur(20px)',
        borderTop: '1px solid rgba(255,255,255,0.05)',
      }}>
        <button onClick={resetear} disabled={!hayCambios} style={{
          height: 50, padding: '0 18px', borderRadius: 14,
          border: '1px solid rgba(255,255,255,0.12)', background: 'transparent',
          color: hayCambios ? 'rgba(255,255,255,0.65)' : 'rgba(255,255,255,0.25)',
          fontSize: 13.5, fontFamily: 'var(--hl-font-ui)',
          cursor: hayCambios ? 'pointer' : 'not-allowed',
        }}>Limpiar</button>
        <button onClick={guardar} disabled={!hayCambios || guardando} style={{
          flex: 1, height: 50, borderRadius: 14, border: 'none',
          background: hayCambios
            ? 'linear-gradient(135deg, #B45EFF 0%, #7C3AED 50%, #4F1FCB 100%)'
            : 'rgba(255,255,255,0.06)',
          color: hayCambios ? '#fff' : 'rgba(255,255,255,0.3)',
          fontSize: 15, fontWeight: 600, fontFamily: 'var(--hl-font-ui)',
          cursor: hayCambios && !guardando ? 'pointer' : 'not-allowed', letterSpacing: -0.2,
          boxShadow: hayCambios ? '0 10px 30px rgba(168,85,247,0.32)' : 'none',
        }}>{guardando ? 'Revelando el positivo…' : 'Guardar como nueva pieza'}</button>
      </div>
    </div>
  );
}

Object.assign(window, { RetoqueScreen });
