// React app for landing page. Uses window.PORTO_DATA from data.js.
const { useState, useEffect, useRef } = React;

const D = window.PORTO_DATA;

// ── Icons (inline SVG) ─────────────────────────────────────
const Icon = {
  github: (
    <svg viewBox="0 0 24 24" width="14" height="14" fill="currentColor" aria-hidden="true">
      <path d="M12 .5C5.65.5.5 5.65.5 12c0 5.08 3.29 9.39 7.86 10.91.58.1.79-.25.79-.56v-1.97c-3.2.7-3.87-1.54-3.87-1.54-.52-1.33-1.27-1.69-1.27-1.69-1.04-.71.08-.7.08-.7 1.15.08 1.76 1.18 1.76 1.18 1.02 1.75 2.68 1.24 3.34.95.1-.74.4-1.24.72-1.53-2.55-.29-5.24-1.28-5.24-5.69 0-1.26.45-2.28 1.18-3.08-.12-.29-.51-1.46.11-3.05 0 0 .96-.31 3.15 1.18.92-.26 1.9-.39 2.88-.39s1.96.13 2.88.39c2.19-1.49 3.15-1.18 3.15-1.18.62 1.59.23 2.76.11 3.05.74.8 1.18 1.82 1.18 3.08 0 4.42-2.69 5.39-5.25 5.68.41.36.78 1.05.78 2.13v3.16c0 .31.21.67.8.55C20.21 21.39 23.5 17.08 23.5 12 23.5 5.65 18.35.5 12 .5z"/>
    </svg>
  ),
  mail: (
    <svg viewBox="0 0 24 24" width="14" height="14" fill="none" stroke="currentColor" strokeWidth="1.6" aria-hidden="true">
      <rect x="3" y="5" width="18" height="14" rx="2"/>
      <path d="M3 7l9 6 9-6"/>
    </svg>
  ),
  wa: (
    <svg viewBox="0 0 24 24" width="14" height="14" fill="currentColor" aria-hidden="true">
      <path d="M17.5 14.4c-.3-.1-1.7-.8-2-.9-.3-.1-.5-.1-.7.1s-.8.9-.9 1.1c-.2.2-.3.2-.6.1-1.7-.8-2.8-1.5-4-3.4-.3-.5.3-.5.9-1.6.1-.2 0-.4 0-.5s-.7-1.7-1-2.3c-.3-.6-.5-.5-.7-.5h-.6c-.2 0-.5.1-.8.4-.3.3-1.1 1-1.1 2.5s1.1 2.9 1.3 3.1c.2.2 2.2 3.4 5.3 4.7 2 .8 2.8.9 3.8.7.6-.1 1.7-.7 2-1.4.2-.7.2-1.2.2-1.4-.1-.2-.3-.2-.6-.4zM12 2C6.5 2 2 6.5 2 12c0 1.8.5 3.5 1.3 5L2 22l5-1.3c1.4.8 3.1 1.3 5 1.3 5.5 0 10-4.5 10-10S17.5 2 12 2z"/>
    </svg>
  ),
  download: (
    <svg viewBox="0 0 24 24" width="14" height="14" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round" aria-hidden="true">
      <path d="M12 4v12"/><path d="M6 12l6 6 6-6"/><path d="M4 20h16"/>
    </svg>
  ),
  arrow: (
    <svg viewBox="0 0 24 24" width="12" height="12" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" aria-hidden="true">
      <path d="M7 17L17 7"/><path d="M8 7h9v9"/>
    </svg>
  ),
  back: (
    <svg viewBox="0 0 24 24" width="12" height="12" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" aria-hidden="true">
      <path d="M19 12H5"/><path d="M12 19l-7-7 7-7"/>
    </svg>
  ),
  linkedin: (
    <svg viewBox="0 0 24 24" width="14" height="14" fill="currentColor" aria-hidden="true">
      <path d="M20.45 20.45h-3.55v-5.57c0-1.33-.02-3.04-1.85-3.04-1.85 0-2.13 1.45-2.13 2.94v5.67H9.36V9h3.41v1.56h.05c.48-.9 1.65-1.85 3.4-1.85 3.63 0 4.3 2.39 4.3 5.5v6.24zM5.34 7.43c-1.14 0-2.06-.92-2.06-2.06 0-1.14.92-2.06 2.06-2.06 1.14 0 2.06.92 2.06 2.06 0 1.14-.92 2.06-2.06 2.06zm1.78 13.02H3.56V9h3.56v11.45zM22.22 0H1.77C.79 0 0 .77 0 1.72v20.56C0 23.23.79 24 1.77 24h20.45C23.21 24 24 23.23 24 22.28V1.72C24 .77 23.21 0 22.22 0z"/>
    </svg>
  ),
};

// ── Reveal-on-scroll ───────────────────────────────────────
function useReveal() {
  const ref = useRef(null);
  useEffect(() => {
    if (!ref.current) return;
    const obs = new IntersectionObserver(
      (entries) => entries.forEach((e) => { if (e.isIntersecting) e.target.classList.add('is-visible'); }),
      { threshold: 0.12, rootMargin: '0px 0px -40px 0px' }
    );
    obs.observe(ref.current);
    return () => obs.disconnect();
  }, []);
  return ref;
}

function Reveal({ children, delay = 0, as: Tag = 'div', className = '', ...rest }) {
  const ref = useReveal();
  return (
    <Tag ref={ref} className={`reveal ${className}`} style={{ transitionDelay: `${delay}ms` }} {...rest}>
      {children}
    </Tag>
  );
}

// ── Scrollspy: track section closest to a trigger line near top of viewport ─
function useScrollspy(ids) {
  const [active, setActive] = useState(ids[0]);
  useEffect(() => {
    function update() {
      const triggerLine = window.innerHeight * 0.35;
      let current = ids[0];
      for (const id of ids) {
        const el = document.getElementById(id);
        if (!el) continue;
        const top = el.getBoundingClientRect().top;
        if (top - triggerLine <= 0) current = id;
      }
      setActive(current);
    }
    update();
    window.addEventListener('scroll', update, { passive: true });
    window.addEventListener('resize', update);
    return () => {
      window.removeEventListener('scroll', update);
      window.removeEventListener('resize', update);
    };
  }, [ids.join(',')]);
  return active;
}

// ── Side / hero ────────────────────────────────────────────
function Side() {
  const navItems = [
    { id: 'about', label: 'About' },
    { id: 'work', label: 'Work' },
    { id: 'experience', label: 'Experience' },
    { id: 'skills', label: 'Skills' },
    { id: 'contact', label: 'Contact' },
  ];
  const active = useScrollspy(navItems.map((n) => n.id));

  return (
    <aside className="side">
      <div>
        {D.identity.available && (
          <div className="avail">
            <span style={{ width: 6, height: 6, borderRadius: '50%', background: 'var(--accent)', boxShadow: '0 0 8px var(--accent)' }}></span>
            {D.identity.availabilityNote}
          </div>
        )}
        <div className="hero-eyebrow">
          <span className="dot"></span>
          {D.identity.location}
        </div>
        <h1 className="hero-name">{D.identity.name}</h1>
        <p className="hero-tag">{D.identity.tagline}</p>
        <p className="hero-sub">{D.identity.subtagline}</p>

        <nav className="side-nav" aria-label="Section navigation">
          <ul>
            {navItems.map((n) => (
              <li key={n.id}>
                <a href={`#${n.id}`} className={active === n.id ? 'is-active' : ''}>
                  <span className="bar"></span>{n.label}
                </a>
              </li>
            ))}
          </ul>
        </nav>
      </div>

      <div className="socials">
        {D.socials.map((s) => {
          const lc = s.label.toLowerCase();
          const ic = lc.includes('github') ? Icon.github
            : lc.includes('email') ? Icon.mail
            : lc.includes('linkedin') ? Icon.linkedin
            : Icon.wa;
          return (
            <a key={s.label} href={s.href} target="_blank" rel="noreferrer noopener">
              <span className="icn">{ic}</span>{s.handle}
            </a>
          );
        })}
      </div>
    </aside>
  );
}

// ── About ─────────────────────────────────────────────────
function About() {
  return (
    <section id="about" className="section">
      <Reveal as="h2" className="section-head"><span className="num">01 ·</span> About</Reveal>
      <div className="prose">
        {D.intro.map((p, i) => (
          <Reveal key={`i${i}`} as="p" delay={i * 60}>{p}</Reveal>
        ))}
        {D.about.map((p, i) => (
          <Reveal key={`a${i}`} as="p" delay={(i + D.intro.length) * 60}>{p}</Reveal>
        ))}
      </div>
    </section>
  );
}

// ── Work / Projects ───────────────────────────────────────
function Work() {
  return (
    <section id="work" className="section">
      <Reveal as="h2" className="section-head"><span className="num">02 ·</span> Selected Work</Reveal>
      <div className="proj-list">
        {D.projects.map((p, i) => (
          <Reveal key={p.id} delay={i * 80}>
            <a className="proj" href={`/projects/${p.slug}`}>
              <div className="proj-year">{p.year}</div>
              <div className="proj-body">
                <div className="proj-title-row">
                  <span className="proj-title">{p.title}</span>
                  <span className="proj-arrow">↗</span>
                </div>
                <div className="proj-kicker">{p.kicker}</div>
                <p className="proj-summary">{p.summary}</p>
                <div className="stack">
                  {p.stack.map((s) => <span key={s} className="stack-chip">{s}</span>)}
                </div>
              </div>
            </a>
          </Reveal>
        ))}
      </div>
    </section>
  );
}

// ── Experience ────────────────────────────────────────────
function Experience() {
  return (
    <section id="experience" className="section">
      <Reveal as="h2" className="section-head"><span className="num">03 ·</span> Experience</Reveal>
      <div className="exp-list">
        {D.experience.map((e, i) => (
          <Reveal key={e.role + i} className="exp" delay={i * 80}>
            <div className="exp-period">{e.period}</div>
            <div>
              <h3 className="exp-role">{e.role}</h3>
              <div className="exp-company">{e.company}</div>
              <div className="exp-loc">{e.location}</div>
              <ul className="exp-bullets">
                {e.bullets.map((b, j) => <li key={j}>{b}</li>)}
              </ul>
            </div>
          </Reveal>
        ))}
        {D.education.map((ed, i) => (
          <Reveal key={ed.school} className="exp" delay={(D.experience.length + i) * 80}>
            <div className="exp-period">{ed.period}</div>
            <div>
              <h3 className="exp-role">{ed.school}</h3>
              <div className="exp-company">{ed.program}</div>
              <div className="exp-loc">Education</div>
            </div>
          </Reveal>
        ))}
      </div>
    </section>
  );
}

// ── Skills ────────────────────────────────────────────────
function Skills() {
  return (
    <section id="skills" className="section">
      <Reveal as="h2" className="section-head"><span className="num">04 ·</span> Skills & Stack</Reveal>
      <div className="skills-grid">
        {D.skills.map((g, i) => (
          <Reveal key={g.group} className="skill-group" delay={i * 40}>
            <h4>{g.group}</h4>
            <ul className="skill-list">
              {g.items.map((s) => <li key={s}>{s}</li>)}
            </ul>
          </Reveal>
        ))}
      </div>
    </section>
  );
}

// ── Contact ───────────────────────────────────────────────
function Contact() {
  return (
    <section id="contact" className="section">
      <Reveal as="h2" className="section-head"><span className="num">05 ·</span> Contact</Reveal>
      <Reveal className="cta-card">
        <h3 className="cta-title">Mau ngobrol soal proyek atau peluang kerja?</h3>
        <p className="cta-sub">
          Boleh diskusi soal proyek, kolaborasi teknis, atau sekadar obrolan seputar otomasi industri
          dan enterprise web. Biasanya saya respons dalam 1×24 jam.
        </p>
        <div className="cta-row">
          <a className="btn btn-primary" href="mailto:djalfin8@gmail.com">
            <span className="icn">{Icon.mail}</span>djalfin8@gmail.com
          </a>
          <a className="btn" href={D.linkedinUrl} target="_blank" rel="noreferrer noopener">
            <span className="icn">{Icon.linkedin}</span>LinkedIn
          </a>
          <a className="btn" href="https://github.com/Alfin712" target="_blank" rel="noreferrer noopener">
            <span className="icn">{Icon.github}</span>GitHub
          </a>
        </div>
      </Reveal>

      <div className="foot">
        <span>© {new Date().getFullYear()} Djonathan Alfin Ellsyan Mustofa</span>
      </div>
    </section>
  );
}

// ── App ───────────────────────────────────────────────────
function App() {
  return (
    <div className="shell">
      <Side />
      <main className="main">
        <About />
        <Work />
        <Experience />
        <Skills />
        <Contact />
      </main>
    </div>
  );
}

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

// Console easter egg for fellow devs
console.log(
  '%c>_ hi 👋',
  'font-family: monospace; font-size: 16px; color: #34d399; font-weight: 700;'
);
console.log(
  '%cLooking for the source? https://github.com/Alfin712/PersonalPorto',
  'font-family: monospace; font-size: 12px; color: #9a9aa3;'
);
