/* ============================================================
   APP — wires page + Tweaks + Router
   ============================================================ */

function useRouter() {
  const [path, setPath] = React.useState(window.location.pathname);
  React.useEffect(() => {
    const handler = () => setPath(window.location.pathname);
    window.addEventListener("popstate", handler);
    return () => window.removeEventListener("popstate", handler);
  }, []);
  return path;
}

function navigate(to) {
  history.pushState({}, "", to);
  if (window.__scrollReset) window.__scrollReset();
  window.dispatchEvent(new PopStateEvent("popstate"));
  window.scrollTo(0, 0);
}

window.__navigate = navigate;
window.__openContact = () => window.dispatchEvent(new CustomEvent("digro:openContact"));

function DotGrid() {
  const canvasRef = React.useRef(null);
  React.useEffect(() => {
    const canvas = canvasRef.current;
    const ctx = canvas.getContext("2d");
    const GAP = 28, R = 1.8, REACH = 55, FADE = 1400;
    const active = new Map();
    let raf;
    let marqueeBottom = 0;

    const resize = () => {
      canvas.width = window.innerWidth;
      canvas.height = window.innerHeight;
    };

    const updateMarqueeBottom = () => {
      const el = document.querySelector(".marquee");
      marqueeBottom = el ? el.getBoundingClientRect().top : 0;
    };

    const onMove = e => {
      updateMarqueeBottom();
      if (e.clientY < marqueeBottom) return;
      const now = Date.now();
      const ci = Math.round(e.clientX / GAP);
      const cj = Math.round(e.clientY / GAP);
      const steps = Math.ceil(REACH / GAP);
      for (let di = -steps; di <= steps; di++) {
        for (let dj = -steps; dj <= steps; dj++) {
          const x = (ci + di) * GAP, y = (cj + dj) * GAP;
          if (y < marqueeBottom) continue;
          const d = Math.sqrt((x - e.clientX) ** 2 + (y - e.clientY) ** 2);
          if (d < REACH) {
            const key = `${ci+di},${cj+dj}`;
            active.set(key, { x, y, t: now, peak: 1 - d / REACH });
          }
        }
      }
    };

    const draw = () => {
      ctx.clearRect(0, 0, canvas.width, canvas.height);
      const now = Date.now();
      for (const [key, dot] of active) {
        const age = (now - dot.t) / FADE;
        if (age >= 1) { active.delete(key); continue; }
        const a = dot.peak * Math.pow(1 - age, 1.4) * 0.85;
        ctx.beginPath();
        ctx.arc(dot.x, dot.y, R, 0, Math.PI * 2);
        ctx.fillStyle = `rgba(255,92,0,${a.toFixed(3)})`;
        ctx.fill();
      }
      raf = requestAnimationFrame(draw);
    };

    resize();
    window.addEventListener("resize", resize);
    window.addEventListener("mousemove", onMove, { passive: true });
    draw();
    return () => {
      cancelAnimationFrame(raf);
      window.removeEventListener("resize", resize);
      window.removeEventListener("mousemove", onMove);
    };
  }, []);
  return <canvas ref={canvasRef} style={{ position: "fixed", inset: 0, pointerEvents: "none", zIndex: 0 }}/>;
}


const TWEAK_DEFAULTS = /*EDITMODE-BEGIN*/{
  "heroVariant": "type",
  "accent": "#FF5C00",
  "displayFont": "Archivo",
  "subCopy": "Vi hjælper din virksomhed med at blive set online — og gør synlighed til kunder, der ringer.",
  "stripes": true,
  "scrollSpeed": 0.7
}/*EDITMODE-END*/;

const DISPLAY_FONTS = {
  "Archivo": "\"Archivo\", system-ui, sans-serif",
  "Anton": "\"Anton\", \"Archivo\", sans-serif",
  "Syne": "\"Syne\", \"Archivo\", sans-serif",
};

function useSharedEffects(t) {
  React.useEffect(() => {
    const r = document.documentElement;
    r.style.setProperty("--orange", t.accent);
    r.style.setProperty("--ff-display", DISPLAY_FONTS[t.displayFont] || DISPLAY_FONTS.Archivo);
  }, [t.accent, t.displayFont]);

  React.useEffect(() => {
    document.body.classList.toggle("no-stripes", !t.stripes);
  }, [t.stripes]);

  React.useEffect(() => {
    if (window.__lenis) window.__lenis.options.wheelMultiplier = t.scrollSpeed;
  }, [t.scrollSpeed]);

  /* Scroll progress bar */
  React.useEffect(() => {
    const bar = document.querySelector(".scroll-bar");
    if (!bar) return;
    const update = () => {
      const h = document.documentElement.scrollHeight - window.innerHeight;
      bar.style.width = (h > 0 ? (window.scrollY / h) * 100 : 0) + "%";
    };
    window.addEventListener("scroll", update, { passive: true });
    return () => window.removeEventListener("scroll", update);
  }, []);


  /* Intercept internal link clicks for client-side routing */
  React.useEffect(() => {
    function onClick(e) {
      const a = e.target.closest("a");
      if (!a) return;
      const href = a.getAttribute("href");
      if (!href || href.startsWith("http") || href.startsWith("mailto:") || href.startsWith("tel:") || href.startsWith("#")) return;
      e.preventDefault();
      if (href === "/kontakt") { window.__openContact(); return; }
      navigate(href);
    }
    document.addEventListener("click", onClick);
    return () => document.removeEventListener("click", onClick);
  }, []);
}

function PageHome({ t }) {
  useReveal();
  const copy = { sub: t.subCopy };
  return (
    <React.Fragment>
      <Hero variant={t.heroVariant} copy={copy} key={t.heroVariant} />
      <Marquee />
      <HomeContent />
      <CTA />
    </React.Fragment>
  );
}

function PageYdelser() {
  const plans = [
    {
      name: "Simpel",
      price: "500",
      sub: "kr / md",
      tag: "Mest populær",
      includes: [
        "Professionel hjemmeside (op til 5 sider)",
        "Mobilvenligt design",
        "Grundlæggende SEO-opsætning",
        "Domæne inkluderet",
        "Professionel mailadresse",
        "SSL-certifikat & hosting",
        "Månedlig vedligeholdelse",
        "Du ejer alt fra dag ét",
      ],
    },
    {
      name: "Avanceret",
      price: "1.000",
      sub: "kr / md",
      tag: null,
      includes: [
        "Alt fra Simpel",
        "Op til 10 sider",
        "Dybdegående SEO & Google My Business",
        "Google Ads opsætning",
        "Webshop (op til 20 produkter)",
        "Månedlig trafikrapport",
        "Prioriteret support",
        "Løbende indholdsoptimering",
      ],
    },
  ];

  const addons = [
    { name: "Logo", price: "Inkluderet" },
    { name: "Google My Business", price: "Tilkøb" },
    { name: "Sociale medier", price: "Tilkøb" },
    { name: "Google Ads", price: "Tilkøb" },
    { name: "Digital rådgivning", price: "Tilkøb" },
    { name: "Ekstra sider", price: "Tilkøb" },
  ];

  return (
    <div style={{ background: "#F5ECD7", minHeight: "100vh", paddingTop: 120, paddingBottom: 100 }}>
      <div className="wrap">

        {/* Headline */}
        <div style={{ marginBottom: 72 }}>
          <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.78rem", letterSpacing: "0.2em",
            color: "#FF5C00", display: "block", marginBottom: 20 }}>YDELSER & PRISER</span>
          <h1 style={{ fontFamily: "var(--ff-display)", fontVariationSettings: '"wdth" 125',
            fontWeight: 900, fontSize: "clamp(3rem, 7vw, 6.5rem)", color: "#3d3d3d",
            lineHeight: 0.95, margin: "0 0 24px", letterSpacing: "-0.02em" }}>
            Vælg din pakke:<br/>
            <span style={{ color: "rgba(61,61,61,0.22)" }}>fast pris, ingen overraskelser.</span>
          </h1>
          <p style={{ color: "rgba(61,61,61,0.55)", fontSize: "clamp(1rem,1.8vw,1.15rem)",
            maxWidth: "52ch", lineHeight: 1.6, margin: 0 }}>
            Ingen binding ud over dit abonnement. Du ejer domæne, indhold og kode — fra dag ét.
          </p>
        </div>

        {/* Pricing cards */}
        <div style={{ display: "grid", gridTemplateColumns: "1fr 1fr", gap: 16, marginBottom: 64 }}>
          {plans.map((plan, i) => (
            <div key={plan.name} style={{
              background: i === 0 ? "#fff" : "#3d3d3d",
              borderRadius: 24, padding: "clamp(32px,4vw,52px)",
              display: "flex", flexDirection: "column", gap: 0,
              boxShadow: i === 0 ? "0 2px 24px rgba(0,0,0,0.07)" : "0 2px 24px rgba(0,0,0,0.18)",
              position: "relative", overflow: "hidden",
            }}>
              {plan.tag && (
                <span style={{ position: "absolute", top: 24, right: 24,
                  background: "#FF5C00", color: "#fff", fontFamily: "var(--ff-mono)",
                  fontSize: "0.68rem", fontWeight: 700, letterSpacing: "0.1em",
                  padding: "5px 12px", borderRadius: 100 }}>{plan.tag}</span>
              )}

              <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.78rem", letterSpacing: "0.14em",
                color: i === 0 ? "rgba(61,61,61,0.45)" : "rgba(245,236,215,0.45)",
                marginBottom: 40, display: "block" }}>{plan.name.toUpperCase()}</span>

              <div style={{ marginBottom: 40 }}>
                <span style={{ fontFamily: "var(--ff-display)", fontVariationSettings: '"wdth" 125',
                  fontWeight: 900, fontSize: "clamp(3.5rem,6vw,5.5rem)",
                  color: i === 0 ? "#3d3d3d" : "#F5ECD7", lineHeight: 1, letterSpacing: "-0.02em" }}>
                  {plan.price}
                </span>
                <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.85rem",
                  color: i === 0 ? "rgba(61,61,61,0.45)" : "rgba(245,236,215,0.45)",
                  marginLeft: 8 }}>{plan.sub}</span>
              </div>

              <div style={{ borderTop: `1px solid ${i === 0 ? "rgba(61,61,61,0.1)" : "rgba(245,236,215,0.1)"}`,
                paddingTop: 32, marginBottom: 40 }}>
                <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.72rem", letterSpacing: "0.1em",
                  color: i === 0 ? "rgba(61,61,61,0.4)" : "rgba(245,236,215,0.4)",
                  display: "block", marginBottom: 20 }}>{plan.name} inkluderer:</span>
                <ul style={{ listStyle: "none", margin: 0, padding: 0, display: "flex", flexDirection: "column", gap: 13 }}>
                  {plan.includes.map((item, j) => (
                    <li key={j} style={{ display: "flex", alignItems: "flex-start", gap: 12,
                      color: i === 0 ? "rgba(61,61,61,0.8)" : "rgba(245,236,215,0.85)",
                      fontSize: "0.92rem", lineHeight: 1.4 }}>
                      <svg width="16" height="16" viewBox="0 0 16 16" fill="none" style={{ flexShrink: 0, marginTop: 1 }}>
                        <circle cx="8" cy="8" r="7.5" stroke={i === 0 ? "#FF5C00" : "#FF5C00"} strokeOpacity="0.4"/>
                        <path d="M4.5 8l2.5 2.5 4-5" stroke="#FF5C00" strokeWidth="1.5" strokeLinecap="round" strokeLinejoin="round"/>
                      </svg>
                      {item}
                    </li>
                  ))}
                </ul>
              </div>

              <button onClick={() => window.__openContact()}
                style={{ marginTop: "auto", background: i === 0 ? "#FF5C00" : "#F5ECD7",
                  color: i === 0 ? "#fff" : "#1a1a1a", border: "none", borderRadius: 100,
                  padding: "16px 28px", fontFamily: "var(--ff-mono)", fontWeight: 700,
                  fontSize: "0.85rem", cursor: "none", width: "100%",
                  boxShadow: i === 0 ? "0 8px 32px -8px rgba(255,92,0,0.45)" : "none" }}>
                Kom i gang →
              </button>
            </div>
          ))}
        </div>

        {/* Add-ons strip */}
        <div style={{ borderTop: "1px solid rgba(61,61,61,0.1)", paddingTop: 48 }}>
          <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.75rem", letterSpacing: "0.16em",
            color: "rgba(61,61,61,0.4)", display: "block", marginBottom: 28 }}>TILKØB</span>
          <div style={{ display: "flex", flexWrap: "wrap", gap: 12 }}>
            {addons.map(a => (
              <div key={a.name} style={{ background: "#fff", borderRadius: 100,
                padding: "12px 22px", display: "flex", alignItems: "center", gap: 12,
                boxShadow: "0 1px 8px rgba(0,0,0,0.06)" }}>
                <span style={{ fontSize: "0.88rem", color: "#3d3d3d", fontWeight: 500 }}>{a.name}</span>
                <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.7rem",
                  color: a.price === "Inkluderet" ? "#FF5C00" : "rgba(61,61,61,0.4)",
                  fontWeight: a.price === "Inkluderet" ? 700 : 400 }}>{a.price}</span>
              </div>
            ))}
          </div>
        </div>

      </div>
    </div>
  );
}

function PageProces() {
  useReveal();
  return <React.Fragment><div style={{ paddingTop: 100 }} /><Process /></React.Fragment>;
}

function PageOmOs() {
  return (
    <section style={{ minHeight: "100vh", display: "flex", alignItems: "center",
      background: "#F5ECD7", paddingTop: 100, paddingBottom: 80 }}>
      <div className="wrap" style={{ display: "flex", gap: "clamp(40px,6vw,96px)", alignItems: "flex-start", flexWrap: "wrap" }}>

        {/* Left */}
        <div style={{ flex: "1 1 45%", minWidth: 280 }}>
          <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.78rem", letterSpacing: "0.2em",
            color: "#FF5C00", display: "block", marginBottom: 24 }}>OM OS</span>
          <h1 style={{ fontFamily: "var(--ff-display)", fontVariationSettings: '"wdth" 125',
            fontWeight: 900, fontSize: "clamp(2.8rem,6vw,5.5rem)", color: "#3d3d3d",
            lineHeight: 1.0, margin: "0 0 32px", letterSpacing: "-0.02em" }}>
            Digital Growth<br/>for små<br/>virksomheder.
          </h1>
          <p style={{ fontSize: "1.05rem", lineHeight: 1.7, color: "rgba(61,61,61,0.7)",
            maxWidth: "44ch", margin: "0 0 20px" }}>
            Digro blev startet i 2026 med én mission: at give danske småvirksomheder adgang til den samme digitale synlighed som de store — til en pris der giver mening.
          </p>
          <p style={{ fontSize: "1.05rem", lineHeight: 1.7, color: "rgba(61,61,61,0.7)",
            maxWidth: "44ch", margin: "0 0 40px" }}>
            Vi er to iværksættere fra Nordsjælland der brænder for design, teknologi og at se lokale virksomheder vokse online.
          </p>
          <button onClick={() => window.__openContact()}
            style={{ background: "#FF5C00", color: "#1a1a1a", border: "none", borderRadius: 100,
              padding: "16px 32px", fontFamily: "var(--ff-mono)", fontWeight: 700, fontSize: "0.92rem",
              cursor: "none", boxShadow: "0 8px 32px -8px rgba(255,92,0,0.5)" }}>
            Start dit projekt →
          </button>
        </div>

        {/* Right — stats */}
        <div style={{ flex: "1 1 40%", minWidth: 260, display: "flex", flexDirection: "column", gap: 2, paddingTop: 16 }}>
          {[
            { n: "2026", l: "Grundlagt" },
            { n: "2", l: "Medarbejdere" },
            { n: "1 uge", l: "Gennemsnitlig leveringstid" },
            { n: "500 kr", l: "Fra pr. måned" },
            { n: "100%", l: "Ejerskab til kunden" },
          ].map(({ n, l }) => (
            <div key={l} style={{ borderTop: "1px solid rgba(61,61,61,0.12)", padding: "28px 0",
              display: "flex", justifyContent: "space-between", alignItems: "baseline", gap: 16 }}>
              <span style={{ fontFamily: "var(--ff-display)", fontVariationSettings: '"wdth" 125',
                fontWeight: 900, fontSize: "clamp(1.8rem,4vw,3rem)", color: "#FF5C00" }}>{n}</span>
              <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.82rem", color: "rgba(61,61,61,0.55)",
                textAlign: "right", maxWidth: "20ch" }}>{l}</span>
            </div>
          ))}
          <div style={{ borderTop: "1px solid rgba(61,61,61,0.12)" }}/>
        </div>
      </div>
    </section>
  );
}

function PageCases() {
  return (
    <section style={{ minHeight: "100vh", display: "flex", alignItems: "center", justifyContent: "center",
      background: "#F5ECD7", position: "relative", overflow: "hidden" }}>
      {/* Orange glow */}
      <div style={{ position: "absolute", width: 600, height: 600, borderRadius: "50%",
        background: "radial-gradient(circle, rgba(255,92,0,0.12) 0%, transparent 70%)",
        top: "50%", left: "50%", transform: "translate(-50%,-50%)", pointerEvents: "none" }}/>
      <div style={{ textAlign: "center", position: "relative", zIndex: 2, padding: "0 24px" }}>
        <span style={{ fontFamily: "var(--ff-mono)", fontSize: "0.78rem", letterSpacing: "0.2em",
          color: "#FF5C00", display: "block", marginBottom: 32 }}>CASES</span>
        <h1 style={{ fontFamily: "var(--ff-display)", fontVariationSettings: '"wdth" 125',
          fontWeight: 900, fontSize: "clamp(3.5rem, 10vw, 9rem)", color: "#3d3d3d",
          lineHeight: 0.92, margin: "0 0 32px", letterSpacing: "-0.02em" }}>
          Kommer<br/><span style={{ color: "#FF5C00" }}>snart.</span>
        </h1>
        <p style={{ color: "rgba(61,61,61,0.55)", fontFamily: "var(--ff-body)",
          fontSize: "clamp(1rem, 2vw, 1.2rem)", maxWidth: "38ch", margin: "0 auto 48px", lineHeight: 1.6 }}>
          Vi er i gang med at samle vores første cases. Vend tilbage snart — eller skriv til os allerede nu.
        </p>
        <button onClick={() => window.__openContact()}
          style={{ background: "#FF5C00", color: "#1a1a1a", border: "none", borderRadius: 100,
            padding: "18px 36px", fontFamily: "var(--ff-mono)", fontWeight: 700, fontSize: "0.92rem",
            cursor: "none", boxShadow: "0 8px 40px -8px rgba(255,92,0,0.6)" }}>
          Kontakt os →
        </button>
      </div>
    </section>
  );
}

function PageKontakt() {
  return <ContactForm />;
}

function App() {
  const [t, setTweak] = useTweaks(TWEAK_DEFAULTS);
  const [contactOpen, setContactOpen] = React.useState(false);
  const path = useRouter();
  useSharedEffects(t);

  React.useEffect(() => {
    const open = () => setContactOpen(true);
    window.addEventListener("digro:openContact", open);
    return () => window.removeEventListener("digro:openContact", open);
  }, []);

  React.useEffect(() => {
    document.body.classList.toggle('no-scroll', contactOpen);
    window.__scrollLocked = contactOpen;
  }, [contactOpen]);

  function renderPage() {
    if (path === "/ydelser") return <PageYdelser />;
    if (path === "/proces")  return <PageProces />;
    if (path === "/cases")   return <PageCases />;
    if (path === "/om-os")   return <PageOmOs />;
    return <PageHome t={t} />;
  }

  /* Custom SVG cursor */
  React.useEffect(() => {
    const el = document.getElementById("custom-cursor");
    const path = document.getElementById("custom-cursor-path");
    if (!el || !path) return;

    function getBg(x, y) {
      const node = document.elementFromPoint(x, y);
      let cur = node;
      while (cur && cur !== document.body) {
        const bg = window.getComputedStyle(cur).backgroundColor;
        if (bg === "rgb(255, 92, 0)" || bg === "rgb(238, 106, 43)") return "orange";
        if (bg === "rgb(26, 26, 26)" || bg === "rgb(17, 17, 17)") return "dark";
        cur = cur.parentElement;
      }
      return "light";
    }

    function isClickable(x, y) {
      const node = document.elementFromPoint(x, y);
      if (!node) return false;
      return !!node.closest("a, button, [role=button], input, select, textarea, label");
    }

    const move = (e) => {
      el.style.transform = `translate(${e.clientX}px, ${e.clientY}px)`;
      const bg = getBg(e.clientX, e.clientY);
      const color = bg === "orange" ? "#F5ECD7" : bg === "dark" ? "#F5ECD7" : "#FF5C00";
      path.setAttribute("fill", color);
      const svg = document.getElementById("cursor-svg");
      if (svg) svg.style.transform = isClickable(e.clientX, e.clientY) ? "scale(0.7)" : "scale(1)";
    };
    const hide = () => el.style.opacity = "0";
    const show = () => el.style.opacity = "1";
    window.addEventListener("mousemove", move, { passive: true });
    document.addEventListener("mouseleave", hide);
    document.addEventListener("mouseenter", show);
    return () => {
      window.removeEventListener("mousemove", move);
      document.removeEventListener("mouseleave", hide);
      document.removeEventListener("mouseenter", show);
    };
  }, []);

  return (
    <React.Fragment>
      <DotGrid />
      {contactOpen && <ContactForm onClose={() => setContactOpen(false)} />}
      <div id="custom-cursor">
        <svg id="cursor-svg" width="22" height="30" viewBox="0 0 128.04 170.8" fill="none" xmlns="http://www.w3.org/2000/svg">
          <path id="custom-cursor-path" d="M0,152.12V18.68C0,2.07,20.09-6.25,31.83,5.5l90.71,90.71c11.75,11.75,3.43,31.83-13.19,31.83h-40.33c-5.92,0-11.48,2.81-15,7.57l-20.38,27.59c-10.69,14.47-33.65,6.91-33.65-11.08Z" fill="#FF5C00"/>
        </svg>
      </div>
      <div className="scroll-bar" />
      <Nav />
      {renderPage()}
      <Footer />

      <TweaksPanel>
        <TweakSection label="Hero" />
        <TweakRadio
          label="Variant"
          value={t.heroVariant}
          options={[
            { value: "radar", label: "Radar" },
            { value: "type", label: "Typo" },
            { value: "search", label: "Søgning" },
          ]}
          onChange={(v) => setTweak("heroVariant", v)}
        />
        <TweakText label="Undertekst" value={t.subCopy} onChange={(v) => setTweak("subCopy", v)} />

        <TweakSection label="Udseende" />
        <TweakColor
          label="Accentfarve"
          value={t.accent}
          options={["#ee6a2b", "#f24d2e", "#e8a33d", "#2fb872", "#3d6bff"]}
          onChange={(v) => setTweak("accent", v)}
        />
        <TweakSelect
          label="Overskrift-skrift"
          value={t.displayFont}
          options={["Archivo", "Anton", "Syne"]}
          onChange={(v) => setTweak("displayFont", v)}
        />
        <TweakToggle label="Striber i baggrund" value={t.stripes} onChange={(v) => setTweak("stripes", v)} />

        <TweakSection label="Scroll" />
        <TweakSlider label="Scroll-hastighed" value={t.scrollSpeed} min={0.2} max={2.5} step={0.05} onChange={(v) => setTweak("scrollSpeed", v)} />
      </TweaksPanel>
    </React.Fragment>
  );
}

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