/* ============================================================
   Poket Library - Shared components (React, via Babel)
   Exported to window for use across Home & Products pages.
   ============================================================ */
const { useState, useEffect, useRef, useCallback, createContext, useContext } = React;

/* ---------- Context ---------- */
const PoketCtx = createContext(null);
const usePoket = () => useContext(PoketCtx);

function PoketProvider({ children }) {
  const [lang, setLangState] = useState(() => window.PL_I18N.detectLang());
  useEffect(() => { window.PL_I18N.setLang(lang); }, [lang]);
  const setLang = useCallback((code) => setLangState(window.PL_I18N.setLang(code)), []);
  const t = window.PL_I18N.makeT(lang);
  return React.createElement(PoketCtx.Provider, { value: { lang, setLang, t } }, children);
}

/* ============================================================
   Icons — line, 2px, rounded
   ============================================================ */
const Ico = {
  arrow: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M5 12h14M13 6l6 6-6 6"/></svg>),
  download: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M12 3v12M7 11l5 5 5-5M5 21h14"/></svg>),
  chevron: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M6 9l6 6 6-6"/></svg>),
  globe: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><circle cx="12" cy="12" r="9"/><path d="M3 12h18M12 3c2.5 2.6 2.5 15.4 0 18M12 3c-2.5 2.6-2.5 15.4 0 18"/></svg>),
  menu: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M4 7h16M4 12h16M4 17h16"/></svg>),
  close: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M6 6l12 12M18 6L6 18"/></svg>),
  check: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M20 6L9 17l-5-5"/></svg>),
  // categories
  relationships: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M4 5h10a2 2 0 0 1 2 2v4a2 2 0 0 1-2 2H9l-4 3v-3a2 2 0 0 1-2-2V7a2 2 0 0 1 1-2Z"/><path d="M16 9h3a2 2 0 0 1 2 2v3a2 2 0 0 1-2 2v3l-3-2"/></svg>),
  money: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><rect x="3" y="6" width="18" height="13" rx="3"/><path d="M3 10h18"/><circle cx="16.5" cy="14.5" r="1.4"/></svg>),
  switzerland: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><rect x="4" y="4" width="16" height="16" rx="5"/><path d="M12 8.5v7M8.5 12h7"/></svg>),
  mind: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><circle cx="12" cy="6.5" r="2.2"/><path d="M5 19c0-3 3.1-5 7-5s7 2 7 5"/><path d="M8 13.5c1-1.2 1.6-2 4-2s3 .8 4 2"/></svg>),
  templates: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M9 5l1.5 1.5L13 4M9 12l1.5 1.5L13 11M9 19l1.5 1.5L13 18"/><path d="M16 5.5h4M16 12.5h4M16 19.5h4"/></svg>),
  work: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><rect x="3" y="7" width="18" height="13" rx="2.5"/><path d="M8 7V5.5A1.5 1.5 0 0 1 9.5 4h5A1.5 1.5 0 0 1 16 5.5V7M3 12h18"/></svg>),
  // steps
  compass: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><circle cx="12" cy="12" r="9"/><path d="M15.5 8.5l-2 5-5 2 2-5 5-2Z"/></svg>),
  cloud: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M7 18a4 4 0 0 1 0-8 5 5 0 0 1 9.6-1.5A3.5 3.5 0 0 1 17 18H7Z"/><path d="M12 12v3.5M10.3 14l1.7 1.7 1.7-1.7"/></svg>),
  checkCircle: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><circle cx="12" cy="12" r="9"/><path d="M8.5 12l2.5 2.5 4.5-5"/></svg>),
  // values
  speech: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M4 6a2 2 0 0 1 2-2h12a2 2 0 0 1 2 2v8a2 2 0 0 1-2 2H9l-5 4V6Z"/><path d="M8 9h8M8 12h5"/></svg>),
  file: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M7 3h7l5 5v12a1 1 0 0 1-1 1H7a1 1 0 0 1-1-1V4a1 1 0 0 1 1-1Z"/><path d="M14 3v5h5M9 13h6M9 16h6"/></svg>),
  sparkle: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M12 3l1.8 5.2L19 10l-5.2 1.8L12 17l-1.8-5.2L5 10l5.2-1.8L12 3Z"/><path d="M18.5 16.5l.7 2 .7-2 .7-.7-.7-.7-.7-2-.7 2-.7.7.7.7Z"/></svg>),
  bolt: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M13 3L5 13h6l-1 8 8-10h-6l1-8Z"/></svg>),
  heart: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M12 20s-7-4.5-9.2-9C1.4 8 3 5 6 5c2 0 3.2 1.3 4 2.6C10.8 6.3 12 5 14 5c3 0 4.6 3 3.2 6C19 15.5 12 20 12 20Z"/></svg>),
  layers: (p) => (<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.85" strokeLinecap="round" strokeLinejoin="round" {...p}><path d="M12 3l9 5-9 5-9-5 9-5Z"/><path d="M3 13l9 5 9-5M3 17l9 5 9-5" opacity="0.55"/></svg>)
};

/* ============================================================
   Reveal-on-scroll
   ============================================================ */
function Reveal({ as = "div", delay = 0, className = "", children, ...rest }) {
  const ref = useRef(null);
  const [seen, setSeen] = useState(false);
  useEffect(() => {
    const el = ref.current;
    if (!el) return;
    if (window.matchMedia && window.matchMedia("(prefers-reduced-motion: reduce)").matches) { setSeen(true); return; }
    const io = new IntersectionObserver((entries) => {
      entries.forEach((e) => { if (e.isIntersecting) { setSeen(true); io.disconnect(); } });
    }, { threshold: 0.14, rootMargin: "0px 0px -8% 0px" });
    io.observe(el);
    return () => io.disconnect();
  }, []);
  return React.createElement(as, {
    ref,
    className: `reveal ${seen ? "in" : ""} ${className}`.trim(),
    "data-delay": delay || undefined,
    ...rest
  }, children);
}

/* ============================================================
   Logo
   ============================================================ */
function Logo({ footer = false }) {
  return (
    <a href="index.html" className={`logo ${footer ? "logo-footer" : ""}`} aria-label="Poket Library">
      <img src="assets/poket-logo.png" alt="Poket Library" />
    </a>
  );
}

/* ============================================================
   Language selector
   ============================================================ */
function LangSelector() {
  const { lang, setLang } = usePoket();
  const [open, setOpen] = useState(false);
  const wrap = useRef(null);
  useEffect(() => {
    const onDoc = (e) => { if (wrap.current && !wrap.current.contains(e.target)) setOpen(false); };
    document.addEventListener("click", onDoc);
    return () => document.removeEventListener("click", onDoc);
  }, []);
  const langs = window.PL_I18N.SUPPORTED;
  return (
    <div className="lang-select" ref={wrap}>
      <button className="lang-btn" onClick={() => setOpen((o) => !o)} aria-haspopup="listbox" aria-expanded={open}>
        <Ico.globe />
        {lang.toUpperCase()}
        <Ico.chevron style={{ width: 12, height: 12 }} />
      </button>
      {open && (
        <div className="lang-menu" role="listbox">
          {langs.map((code) => (
            <button key={code} className={code === lang ? "active" : ""} onClick={() => { setLang(code); setOpen(false); }}>
              {window.PL_I18N.STR[code].langName}
              <span className="flag">{code.toUpperCase()}</span>
            </button>
          ))}
        </div>
      )}
    </div>
  );
}

/* ============================================================
   Header
   ============================================================ */
function Header() {
  const { t } = usePoket();
  const [scrolled, setScrolled] = useState(false);
  const [mobileOpen, setMobileOpen] = useState(false);
  useEffect(() => {
    const onScroll = () => setScrolled(window.scrollY > 8);
    onScroll();
    window.addEventListener("scroll", onScroll, { passive: true });
    return () => window.removeEventListener("scroll", onScroll);
  }, []);
  const nav = [
    { href: "index.html#categories", label: t("nav.categories") },
    { href: "index.html#how", label: t("nav.how") },
    { href: "index.html#about", label: t("nav.about") }
  ];
  return (
    <header className={`site-header ${scrolled ? "scrolled" : ""}`}>
      <div className="container header-inner">
        <Logo />
        <nav className={`header-nav ${mobileOpen ? "open" : ""}`}>
          {nav.map((n) => (<a key={n.label} href={n.href} onClick={() => setMobileOpen(false)}>{n.label}</a>))}
        </nav>
        <div className="header-actions">
          <LangSelector />
          <a className="btn btn-primary" href="products.html" style={{ padding: "11px 18px" }}>{t("cta.explore")}</a>
        </div>
        <button className="menu-toggle" onClick={() => setMobileOpen((o) => !o)} aria-label={t("cta.menu")}>
          {mobileOpen ? <Ico.close /> : <Ico.menu />}
        </button>
      </div>
    </header>
  );
}

/* ============================================================
   CSS Product Cover (collection look)
   ============================================================ */
function Cover({ product, style }) {
  const { lang } = usePoket();
  const cat = window.PL_DATA.categories.find((c) => c.key === product.category);
  return (
    <div className={`cover ${cat.cls}`} style={style}>
      <div className="cover-shape" style={{ width: "58%", aspectRatio: "1", right: "-16%", top: "46%" }}></div>
      <div className="cover-brand"><span className="pmark">p</span> poket library</div>
      <div className="cover-cat">{cat.name[lang]}</div>
      <div className="cover-title">{product.title[lang]}</div>
      <div className="cover-sub">{product.promise[lang].split(/[.—]/)[0]}.</div>
      <div className="cover-band">
        <span className="cover-num">{product.num}</span>
      </div>
    </div>
  );
}

/* ============================================================
   Product card
   ============================================================ */
function ProductCard({ product }) {
  const { lang, t } = usePoket();
  const cat = window.PL_DATA.categories.find((c) => c.key === product.category);
  const comingSoon = !product.available;
  const external = !comingSoon && product.url && /^https?:/.test(product.url);

  const inner = (
    <React.Fragment>
      <div className="product-cover-wrap">
        <Cover product={product} />
        {comingSoon && <span className="coming-badge">{t("cta.soon")}</span>}
      </div>
      <div className="product-body">
        <span className="product-cat">{cat.name[lang]}</span>
        <h3>{product.title[lang]}</h3>
        <p className="product-promise">{product.promise[lang]}</p>
        <div className="product-formats">
          {product.formats.map((f) => (<span className="format-pill" key={f}>{t("formats." + f)}</span>))}
        </div>
        {!comingSoon && (
          <div className="product-foot">
            {product.price ? <span className="price">{product.price}</span> : <span className="price-empty" />}
            <span className="view-link">{t("cta.discover")} <Ico.arrow /></span>
          </div>
        )}
      </div>
    </React.Fragment>
  );

  if (comingSoon) {
    return <div className={`product-card ${cat.cls} is-coming`} aria-disabled="true">{inner}</div>;
  }
  if (external) {
    return <a className={`product-card ${cat.cls}`} href={product.url} target="_blank" rel="noopener noreferrer">{inner}</a>;
  }
  return <a className={`product-card ${cat.cls}`} href={"product.html?id=" + product.id}>{inner}</a>;
}

/* ============================================================
   Category card
   ============================================================ */
function CategoryCard({ category }) {
  const { lang, t } = usePoket();
  const Icon = Ico[category.icon];
  return (
    <a className={`cat-card ${category.cls}`} href={"products.html?cat=" + category.key}>
      <div className="cat-corner"></div>
      <div className="cat-icon">{Icon ? <Icon /> : null}</div>
      <h3>{category.name[lang]}</h3>
      <p>{category.copy[lang]}</p>
      <span className="cat-arrow">{t("cats.explore")} <Ico.arrow style={{ width: 15, height: 15 }} /></span>
    </a>
  );
}

/* ============================================================
   Footer
   ============================================================ */
function Footer() {
  const { lang, setLang, t } = usePoket();
  const cats = window.PL_DATA.categories;
  return (
    <footer className="site-footer">
      <div className="container footer-inner">
        <div className="footer-brand">
          <Logo footer />
          <p>{t("footer.tagline")}</p>
        </div>
        <div className="footer-col">
          <h4>{t("footer.categories")}</h4>
          <ul>{cats.map((c) => (<li key={c.key}><a href="products.html">{c.name[lang]}</a></li>))}</ul>
        </div>
        <div className="footer-col">
          <h4>{t("footer.company")}</h4>
          <ul>
            <li><a href="index.html#about">{t("footer.about")}</a></li>
            <li><a href="index.html">{t("footer.blog")}</a></li>
            <li><a href="index.html">{t("footer.contact")}</a></li>
            <li><a href="index.html">{t("footer.affiliates")}</a></li>
          </ul>
        </div>
        <div className="footer-col">
          <h4>{t("footer.support")}</h4>
          <ul>
            <li><a href="help.html">{t("footer.help")}</a></li>
            <li><a href="terms.html">{t("footer.terms")}</a></li>
            <li><a href="privacy.html">{t("footer.privacy")}</a></li>
            <li><a href="refund.html">{t("footer.refund")}</a></li>
          </ul>
        </div>
      </div>
      <div className="container">
        <div className="footer-bottom">
          <p>{t("footer.rights")}</p>
          <div className="footer-langs">
            {window.PL_I18N.SUPPORTED.map((code) => (
              <button key={code} className={code === lang ? "active" : ""} onClick={() => setLang(code)}>{code.toUpperCase()}</button>
            ))}
          </div>
        </div>
      </div>
    </footer>
  );
}

/* ============================================================
   Legal / support page (multilingual, driven by PL_LEGAL)
   ============================================================ */
function autoLink(text) {
  // turn email addresses into mailto links
  const re = /([A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,})/g;
  const parts = String(text).split(re);
  return parts.map((part, i) =>
    re.test(part)
      ? React.createElement("a", { key: i, href: "mailto:" + part }, part)
      : part
  );
}

function LegalPage({ page }) {
  const { lang } = usePoket();
  const data = (window.PL_LEGAL[page] && (window.PL_LEGAL[page][lang] || window.PL_LEGAL[page].en)) || {};
  const ui = window.PL_LEGAL.ui[lang] || window.PL_LEGAL.ui.en;
  useEffect(() => { document.title = (data.title || "Poket Library") + " — Poket Library"; }, [lang, page]);
  return (
    <main className="container">
      <article className="legal">
        <span className="eyebrow">{data.eyebrow}</span>
        <h1>{data.title}</h1>
        <p className="updated">{data.updated}</p>
        {data.intro && <p>{autoLink(data.intro)}</p>}
        {(data.sections || []).map((s, i) => (
          <React.Fragment key={i}>
            <h2>{s.h}</h2>
            {(s.p || []).map((para, j) => (<p key={j}>{autoLink(para)}</p>))}
            {s.list && (<ul>{s.list.map((li, k) => (<li key={k}>{autoLink(li)}</li>))}</ul>)}
          </React.Fragment>
        ))}
        <p style={{ marginTop: 40 }}><a href="index.html">{ui.back}</a></p>
      </article>
    </main>
  );
}

/* ---------- export ---------- */
Object.assign(window, {
  PoketCtx, usePoket, PoketProvider,
  Ico, Reveal, Logo, LangSelector, Header, Footer,
  Cover, ProductCard, CategoryCard, LegalPage
});
