/* global React, ReactDOM */
const { useState, useEffect, useRef, useCallback } = React;
const D = window.PORTFOLIO_DATA;
const C = D.copy; // Customizer copy — edit via Appearance → Customize → Kalligeris Copy

// Parse intrinsic dims from a URL: e.g. "-1024x683.jpg" or "-683x1024.jpg".
// Falls back to orientation flag when no dims present (e.g. "-scaled.jpg").
function aspectFor(item) {
  const m = item.src && item.src.match(/[-_](\d{2,4})x(\d{2,4})\.(jpe?g|png|webp)/i);
  if (m) return `${m[1]} / ${m[2]}`;
  if (item.o === 'p') return '2 / 3';
  if (item.o === 's') return '1 / 1';
  return '3 / 2';
}

// ---------- Tweaks (in-design) ----------
const TWEAK_DEFAULTS = /*EDITMODE-BEGIN*/{
  "theme": "cinema",
  "layout": "mosaic",
  "cursor": false,
  "marquee": true,
  "accent": "#C2884A"
} /*EDITMODE-END*/;

function postEdit(edits) {
  try {window.parent.postMessage({ type: '__edit_mode_set_keys', edits }, '*');} catch (e) {}
}
function useTweaks() {
  const [t, setT] = useState(TWEAK_DEFAULTS);
  const set = (k, v) => {setT((p) => ({ ...p, [k]: v }));postEdit({ [k]: v });};
  return [t, set];
}

// ---------- Custom cursor ----------
function Cursor({ enabled }) {
  const dot = useRef(null);
  const ring = useRef(null);
  const [label, setLabel] = useState('');
  useEffect(() => {
    if (!enabled) return;
    let mx = -100,my = -100,rx = -100,ry = -100,raf;
    const tick = () => {
      rx += (mx - rx) * 0.18;ry += (my - ry) * 0.18;
      if (dot.current) dot.current.style.transform = `translate(${mx}px,${my}px)`;
      if (ring.current) ring.current.style.transform = `translate(${rx}px,${ry}px)`;
      raf = requestAnimationFrame(tick);
    };
    const onMove = (e) => {mx = e.clientX;my = e.clientY;};
    const onOver = (e) => {
      const el = e.target.closest('[data-cursor]');
      const v = el ? el.getAttribute('data-cursor') : '';
      setLabel(v || '');
      document.documentElement.classList.toggle('cursor-hover', !!v);
    };
    window.addEventListener('mousemove', onMove);
    window.addEventListener('mouseover', onOver);
    raf = requestAnimationFrame(tick);
    return () => {
      cancelAnimationFrame(raf);
      window.removeEventListener('mousemove', onMove);
      window.removeEventListener('mouseover', onOver);
    };
  }, [enabled]);
  if (!enabled) return null;
  return (
    <>
      <div ref={dot} className="cursor-dot" />
      <div ref={ring} className="cursor-ring">
        <span className="cursor-label">{label}</span>
      </div>
    </>
  );
}

// ---------- Top nav ----------
function Nav({ now, onJump }) {
  const sections = [
    ...D.sections.map((s) => ({ id: s.slug, label: s.kicker || s.title })),
    { id: 'studio', label: 'Studio' },
    { id: 'contact', label: 'Contact' },
  ];
  return (
    <nav className="nav" data-cursor="">
      <div className="nav-l">
        <span className="brand">{C.brand}</span>
        <span className="dim mono">— {C.tagline}</span>
      </div>
      <div className="nav-c mono">
        <span className="dim">{now.toUpperCase()}</span>
      </div>
      <div className="nav-r mono">
        {sections.map((s) =>
          <a key={s.id} href={`#${s.id}`} onClick={(e) => {e.preventDefault();onJump(s.id);}} data-cursor="">{s.label}</a>
        )}
      </div>
    </nav>
  );
}

// ---------- Marquee ----------
function Marquee({ show }) {
  if (!show) return null;
  const items = C.marquee.split(',').map((s) => s.trim());
  const row = items.concat(items, items);
  return (
    <div className="marquee">
      <div className="marquee-track">
        {row.map((x, i) =>
          <span key={i} className="marquee-item"><span className="dot" />{x}</span>
        )}
      </div>
    </div>
  );
}

// ---------- Hero ----------
function Hero({ onJump }) {
  // heroR2 is rendered as plain text — the italic & is a design element kept in markup
  return (
    <section className="hero">
      <div className="hero-meta mono">
        <span>(01) — Index</span>
        <span>{C.heroVolume}</span>
      </div>
      <h1 className="hero-h">
        <span className="r1">{C.heroR1}</span>
        <span className="r2">{C.heroR2}</span>
        <span className="r3">{C.heroR3}</span>
        <span className="r4">{C.heroR4}</span>
      </h1>

      <div className="hero-foot">
        <div className="hero-block">
          <div className="kicker mono">{C.heroFeaturingLabel}</div>
          <div className="dim small">
            {D.sections.map((s, i) => {
              const count = s.kind === 'projects'
                ? (s.projects || []).reduce((a, p) => a + (p.images || []).length, 0)
                : (s.items || []).length;
              const label = s.kind === 'motion' ? 'motion' : s.kind === 'projects' ? 'spaces' : 'stills';
              return `${count} ${label}`;
            }).join(' · ')}
          </div>
        </div>
        <div className="hero-block">
          <div className="kicker mono">{C.heroRecentLabel}</div>
          <div className="dim small">{C.heroRecent}</div>
        </div>
        <div className="hero-block hero-cta">
          <button className="pill" onClick={() => onJump(D.sections[0]?.slug || 'motion')} data-cursor="ENTER">
            <span>{C.heroCta}</span>
            <svg viewBox="0 0 24 24" width="14" height="14"><path d="M5 12h14M13 6l6 6-6 6" fill="none" stroke="currentColor" strokeWidth="1.5" /></svg>
          </button>
        </div>
      </div>

      <div className="hero-collage">
        {D.heroPicks.map((src, i) =>
          <div key={i} className={`hc hc-${i}`} data-cursor="">
            <img src={src} alt="" loading="eager" />
          </div>
        )}
        <div className="hc-label mono">
          <span>STK / 25</span>
          <span>{C.tagline}</span>
        </div>
      </div>
    </section>
  );
}

// ---------- Section header ----------
function SectionHead({ idx, kicker, title, count, sub }) {
  return (
    <header className="sec-head">
      <div className="sh-l mono">
        <span>({idx})</span>
        <span className="dim">{kicker}</span>
      </div>
      <h2 className="sh-title">{title}</h2>
      <div className="sh-r mono">
        <span className="dim">{count} {count === 1 ? 'piece' : 'pieces'}</span>
        {sub ? <span className="dim">{sub}</span> : null}
      </div>
    </header>
  );
}

// ---------- Motion ----------
function MotionGrid({ items, onPlay, layout }) {
  const cls = layout === 'index' ? 'motion-grid index' : layout === 'stack' ? 'motion-grid stack' : 'motion-grid';
  return (
    <div className={cls}>
      {items.map((v, i) =>
        <article key={v.id} className={`vcard span-${v.span}`} onClick={() => onPlay(v)} data-cursor="PLAY">
          <div className="v-cover">
            <img src={`https://img.youtube.com/vi/${v.id}/maxresdefault.jpg`} alt={v.title} loading="lazy"
              onError={(e) => {e.currentTarget.src = `https://img.youtube.com/vi/${v.id}/hqdefault.jpg`;}} />
            <div className="v-shade" />
            <div className="v-play">
              <svg viewBox="0 0 24 24" width="18" height="18"><path d="M8 5v14l11-7z" fill="currentColor" /></svg>
              <span className="mono">Play</span>
            </div>
            <div className="v-num mono">№ {String(i + 1).padStart(2, '0')}</div>
          </div>
          <div className="v-meta">
            <div className="v-title"><span className="serif">{v.title}</span><span className="mono dim"> · {v.year}</span></div>
            <div className="v-sub mono dim">{v.tag} — {v.subtitle}</div>
          </div>
        </article>
      )}
    </div>
  );
}

// ---------- Food masonry ----------
function FoodGrid({ slug, items, onView, layout }) {
  return (
    <div className={`mason layout-${layout}`}>
      {items.map((it, i) =>
        <figure key={i} className={`mcell f-${it.o}`} style={{ aspectRatio: aspectFor(it) }}
          onClick={() => onView(slug, i)} data-cursor="VIEW">
          <img src={it.src} alt="" loading="lazy" decoding="async" />
          <figcaption className="mono dim">№ {String(i + 1).padStart(2, '0')}</figcaption>
        </figure>
      )}
    </div>
  );
}

// ---------- Interiors ----------
function InteriorsBlock({ projects, onView, layout }) {
  return (
    <div className="interiors">
      {projects.map((proj, p) =>
        <article key={proj.slug} className={`proj layout-${layout}`}>
          <header className="proj-head">
            <div className="ph-l mono">
              <span>Project {String(p + 1).padStart(2, '0')} / {String(projects.length).padStart(2, '0')}</span>
              <span className="dim">{proj.location} · {proj.year}</span>
            </div>
            <h3 className="ph-title serif">{proj.name}</h3>
            <p className="ph-blurb">{proj.blurb}</p>
          </header>
          <div className="mason mason-interior">
            {proj.images.map((im, i) =>
              <figure key={i} className={`mcell f-${im.o}`} style={{ aspectRatio: aspectFor(im) }}
                onClick={() => onView(proj.slug, i)} data-cursor="VIEW">
                <img src={im.src} alt="" loading="lazy" decoding="async" />
              </figure>
            )}
          </div>
        </article>
      )}
    </div>
  );
}

// ---------- Lightbox ----------
function Lightbox({ open, list, index, onClose, onPrev, onNext }) {
  useEffect(() => {
    if (!open) return;
    const k = (e) => {
      if (e.key === 'Escape') onClose();
      else if (e.key === 'ArrowLeft') onPrev();
      else if (e.key === 'ArrowRight') onNext();
    };
    window.addEventListener('keydown', k);
    document.body.style.overflow = 'hidden';
    return () => {window.removeEventListener('keydown', k);document.body.style.overflow = '';};
  }, [open, onClose, onPrev, onNext]);
  if (!open || !list) return null;
  const item = list[index];
  return (
    <div className="lb" onClick={onClose} data-cursor="CLOSE">
      <div className="lb-bar mono">
        <span>{String(index + 1).padStart(2, '0')} / {String(list.length).padStart(2, '0')}</span>
        <button className="lb-x" onClick={(e) => {e.stopPropagation();onClose();}} data-cursor="CLOSE">Close ×</button>
      </div>
      <button className="lb-nav lb-prev" onClick={(e) => {e.stopPropagation();onPrev();}} data-cursor="PREV">←</button>
      <img className="lb-img" src={item.src} alt="" onClick={(e) => e.stopPropagation()} data-cursor="" />
      <button className="lb-nav lb-next" onClick={(e) => {e.stopPropagation();onNext();}} data-cursor="NEXT">→</button>
    </div>
  );
}

// ---------- Video modal ----------
function VideoModal({ video, onClose }) {
  useEffect(() => {
    if (!video) return;
    const k = (e) => {if (e.key === 'Escape') onClose();};
    window.addEventListener('keydown', k);
    document.body.style.overflow = 'hidden';
    return () => {window.removeEventListener('keydown', k);document.body.style.overflow = '';};
  }, [video, onClose]);
  if (!video) return null;
  return (
    <div className="vm" onClick={onClose} data-cursor="CLOSE">
      <div className="vm-shell" onClick={(e) => e.stopPropagation()}>
        <div className="vm-bar mono">
          <span><em>{video.title}</em> — {video.subtitle}</span>
          <button className="lb-x" onClick={onClose} data-cursor="CLOSE">Close ×</button>
        </div>
        <div className="vm-frame">
          <iframe
            src={`https://www.youtube.com/embed/${video.id}?autoplay=1&rel=0&modestbranding=1`}
            title={video.title}
            allow="autoplay; encrypted-media; picture-in-picture"
            allowFullScreen />
        </div>
      </div>
    </div>
  );
}

// ---------- Studio ----------
function Studio({ onJump }) {
  return (
    <section id="studio" className="studio">
      <div className="st-l">
        <div className="kicker mono">(04) — Studio</div>
        <h2 className="st-title">{C.studioTitle}</h2>
        <ul className="st-list mono">
          <li><span className="dim">01</span> {C.studioItem1}</li>
          <li><span className="dim">02</span> {C.studioItem2}</li>
          <li><span className="dim">03</span> {C.studioItem3}</li>
          <li><span className="dim">04</span> {C.studioItem4}</li>
        </ul>
      </div>
<div className="st-r">
        <div className="st-img" data-cursor="">
          {C.studioImage
            ? <img src={C.studioImage} alt="Studio" />
            : <><div className="ph-stripes" /><div className="ph-meta mono"><span>Studio photo</span><span className="dim">drop a 4:5 image here · ~1600×2000px</span></div></>
          }
        </div>
        <div className="st-stats mono">
          <div><span className="big serif">{C.studioStat1}</span><span className="dim">{C.studioStat1Label}</span></div>
          <div><span className="big serif">{C.studioStat2}</span><span className="dim">{C.studioStat2Label}</span></div>
          <div><span className="big serif">{C.studioStat3}</span><span className="dim">{C.studioStat3Label}</span></div>
        </div>
      </div>
    </section>
  );
}

// ---------- Contact ----------
function Contact() {
  return (
    <section id="contact" className="contact">
      <div className="ct-top mono">
        <span>(05) — Contact</span>
        <span className="dim">{C.contactBooking}</span>
      </div>
      <h2 className="ct-h">
        {C.contactHeadline.split(' ').slice(0, 2).join(' ') === "Let's make"
          ? <><span>Let&rsquo;s make</span><span className="serif"><em>something</em></span><span>together.</span></>
          : <span>{C.contactHeadline}</span>
        }
      </h2>
      <div className="ct-grid">
        <a className="ct-card" href={`mailto:${C.contactEmail.replace('[at]','@').replace('[dot]','.')}`} data-cursor="MAIL">
  <div className="kicker mono">Email</div>
  <div className="ct-val serif">{C.contactEmail.replace('[at]','@').replace('[dot]','.')}</div>
</a>
        <a className="ct-card" href="tel:+30" data-cursor="CALL">
          <div className="kicker mono">Phone</div>
          <div className="ct-val serif">{C.contactPhone}</div>
        </a>
        <a className="ct-card" href={`https://instagram.com/${C.contactInstagram.replace('@','')}`} target="_blank" rel="noreferrer" data-cursor="OPEN">
          <div className="kicker mono">Instagram</div>
          <div className="ct-val serif">{C.contactInstagram}</div>
        </a>
        <div className="ct-card">
          <div className="kicker mono">Studio</div>
          <div className="ct-val serif">{C.contactStudio}</div>
        </div>
      </div>
      <footer className="foot mono">
        <span>{C.footerLeft}</span>
        <span className="dim">{C.footerRight}</span>
      </footer>
    </section>
  );
}

// ---------- Tweaks panel ----------
function TweaksUI({ t, setT, visible, onClose }) {
  if (!visible) return null;
  const themes = [
    { id: 'cinema',   label: 'Cinema' },
    { id: 'editorial',label: 'Editorial' },
    { id: 'daylight', label: 'Daylight' },
  ];
  const layouts = [
    { id: 'mosaic', label: 'Mosaic' },
    { id: 'index',  label: 'Index' },
    { id: 'stack',  label: 'Stack' },
  ];
  const accents = ['#C2884A', '#7C5C3E', '#D9C7A0', '#A33D2A', '#E8E2D2'];
  return (
    <div className="tw-panel">
      <div className="tw-head mono">
        <span>Tweaks</span>
        <button onClick={onClose} data-cursor="CLOSE">×</button>
      </div>
      <div className="tw-row">
        <div className="tw-lab mono">Theme</div>
        <div className="tw-seg">
          {themes.map((x) =>
            <button key={x.id} className={t.theme === x.id ? 'on' : ''} onClick={() => setT('theme', x.id)} data-cursor="">{x.label}</button>
          )}
        </div>
      </div>
      <div className="tw-row">
        <div className="tw-lab mono">Layout</div>
        <div className="tw-seg">
          {layouts.map((x) =>
            <button key={x.id} className={t.layout === x.id ? 'on' : ''} onClick={() => setT('layout', x.id)} data-cursor="">{x.label}</button>
          )}
        </div>
      </div>
      <div className="tw-row">
        <div className="tw-lab mono">Accent</div>
        <div className="tw-swatches">
          {accents.map((c) =>
            <button key={c} className={'sw' + (t.accent === c ? ' on' : '')} style={{ background: c }} onClick={() => setT('accent', c)} data-cursor="" />
          )}
        </div>
      </div>
      <div className="tw-row">
        <div className="tw-lab mono">Cursor</div>
        <button className={'tog ' + (t.cursor ? 'on' : '')} onClick={() => setT('cursor', !t.cursor)} data-cursor="">
          <span /> {t.cursor ? 'Custom' : 'Native'}
        </button>
      </div>
      <div className="tw-row">
        <div className="tw-lab mono">Marquee</div>
        <button className={'tog ' + (t.marquee ? 'on' : '')} onClick={() => setT('marquee', !t.marquee)} data-cursor="">
          <span /> {t.marquee ? 'On' : 'Off'}
        </button>
      </div>
    </div>
  );
}

// ---------- App ----------
function App() {
  const [t, setT] = useTweaks();
  const [video, setVideo] = useState(null);
  const [lb, setLb] = useState(null);
  const [now, setNow] = useState('');
  const [tweakOpen, setTweakOpen] = useState(false);

  useEffect(() => {
    const fmt = () => {
      const d = new Date();
      const time = d.toLocaleTimeString('en-GB', { hour: '2-digit', minute: '2-digit', hour12: false, timeZone: 'Europe/Athens' });
      setNow(`Athens ${time}`);
    };
    fmt();
    const i = setInterval(fmt, 30000);
    return () => clearInterval(i);
  }, []);

  useEffect(() => {
    const onMsg = (e) => {
      if (!e.data || typeof e.data !== 'object') return;
      if (e.data.type === '__activate_edit_mode') setTweakOpen(true);
      if (e.data.type === '__deactivate_edit_mode') setTweakOpen(false);
    };
    window.addEventListener('message', onMsg);
    try {window.parent.postMessage({ type: '__edit_mode_available' }, '*');} catch (e) {}
    return () => window.removeEventListener('message', onMsg);
  }, []);

  useEffect(() => {
    const root = document.documentElement;
    root.setAttribute('data-theme', t.theme);
    root.style.setProperty('--accent', t.accent);
  }, [t.theme, t.accent]);

  const jump = (id) => {
    const el = document.getElementById(id);
    if (el) el.scrollIntoView({ behavior: 'smooth', block: 'start' });
  };

  const openView = useCallback((key, idx) => {
    let list;
    for (const sec of D.sections) {
      if (sec.kind === 'stills' && sec.slug === key) list = sec.items;
      if (sec.kind === 'projects') {
        const p = (sec.projects || []).find((p) => p.slug === key);
        if (p) list = p.images;
      }
    }
    if (list) setLb({ key, list, index: idx });
  }, []);

  const closeLb = () => setLb(null);
  const prev = () => setLb((s) => s ? { ...s, index: (s.index - 1 + s.list.length) % s.list.length } : s);
  const next = () => setLb((s) => s ? { ...s, index: (s.index + 1) % s.list.length } : s);

  return (
    <>
      <Cursor enabled={t.cursor} />
      <Nav now={now} onJump={jump} />
      <Marquee show={t.marquee} />
      <main>
        <Hero onJump={jump} />

        {D.sections.map((sec, i) => {
          const idx = String(i + 1).padStart(2, '0');
          const count = sec.kind === 'projects'
            ? (sec.projects || []).reduce((a, p) => a + (p.images || []).length, 0)
            : (sec.items || []).length;
          const sub = sec.sub || (sec.kind === 'projects' ? `${(sec.projects || []).length} projects` : undefined);
          return (
            <section id={sec.slug} className="sec" key={sec.slug}>
              <SectionHead idx={idx} kicker={sec.kicker} title={sec.title} count={count} sub={sub} />
              {sec.kind === 'motion'   && <MotionGrid items={sec.items} onPlay={setVideo} layout={t.layout} />}
              {sec.kind === 'stills'   && <FoodGrid slug={sec.slug} items={sec.items} onView={openView} layout={t.layout} />}
              {sec.kind === 'projects' && <InteriorsBlock projects={sec.projects} onView={openView} layout={t.layout} />}
            </section>
          );
        })}

        <Studio onJump={jump} />
        <Contact />
      </main>

      <Lightbox
        open={!!lb}
        list={lb?.list}
        index={lb?.index || 0}
        onClose={closeLb}
        onPrev={prev}
        onNext={next} />

      <VideoModal video={video} onClose={() => setVideo(null)} />
      <TweaksUI t={t} setT={setT} visible={tweakOpen} onClose={() => {
        setTweakOpen(false);
        try {window.parent.postMessage({ type: '__edit_mode_dismissed' }, '*');} catch (e) {}
      }} />
    </>
  );
}

ReactDOM.createRoot(document.getElementById('root')).render(<App />);
