/* ============================================================
   carousel.jsx — Hero carousel + Testimonial marquee
   ============================================================ */
const { useState, useEffect, useRef, useCallback } = React;

const PRM = () => typeof window.matchMedia === "function" &&
  window.matchMedia("(prefers-reduced-motion: reduce)").matches;

/* ---------- HERO CAROUSEL ---------- */
const HERO_SLIDES = [
  {
    n: "01", kicker: "TECHNICAL ANALYSIS",
    h1: "We map the markets, you make money.",
    h1Bold: "We map the markets,",
    h1Soft: " you make money.",
    body: "20 charts daily. Bullish setups, key levels and real-time buy alerts with our full reasoning behind every one. The market at your fingertips.",
    anchor: "#technical-analysis",
    pageHref: "/technical-analysis",
    ctaLabel: "Explore Technical Analysis",
    visual: "spot",
    aspect: "5 / 3",
  },
  {
    n: "02", kicker: "FUNDAMENTAL ANALYSIS",
    h1: "All You Need to Know About Your Stock.",
    h1Bold: "All You Need to Know",
    h1Soft: " About Your Stock.",
    body: "Deep Dives, Equity Briefs and Valuation Analysis; written, dated and stood by. Full theses with financials, recommended position sizing, risks, catalysts and explicit price targets.",
    anchor: "#fundamental-analysis",
    pageHref: "/fundamental-analysis",
    ctaLabel: "Explore Fundamental Analysis",
    visual: "fundamentals",
    aspect: "5 / 4",
  },
  {
    n: "03", kicker: "RESEARCH",
    h1: "We track the smart money.",
    h1Bold: "We track",
    h1Soft: " the smart money.",
    body: "Quarterly tracking of what the world’s super‑investors are buying, selling and holding. Druckenmiller, Buffett, Marks, Klarman and many more. Their positions, conviction trades and where capital is concentrating.",
    anchor: "#research",
    pageHref: "/research",
    ctaLabel: "Research",
    visual: "money-flow",
    aspect: "16 / 9",
  },
  {
    n: "04", kicker: "COMMUNITY",
    h1: "The 24/7 desk you can talk to.",
    h1Bold: "The 24/7 desk",
    h1Soft: " you can talk to.",
    body: "A live, always-on community of retail investors and a team of professionals who actually respond. The real value isn't only the research; it's a room of investors all pushing to improve and reach their goals together.",
    anchor: "#community",
    pageHref: "/community",
    ctaLabel: "Explore Community",
    visual: "chat",
  },
  {
    n: "05", kicker: "EDUCATION",
    h1: "Don't just follow signals. Learn the framework.",
    h1Bold: "Don't just follow signals.",
    h1Soft: " Learn the framework.",
    body: "The Elliott Wave course, the Learning Centre, video tutorials and our growing Lessons collection. Our goal isn't to hand you signals, it's to teach you to do what we do.",
    anchor: "#education",
    pageHref: "/education",
    ctaLabel: "Explore Education",
    visual: "course",
  },
];

/* ---------- Fanned stack of fundamental docs ---------- */
function FundamentalStack() {
  // Single composed image — Deep Dive ($NVO) and Equity Brief ($NFLX) on the
  // left, Valuation ($SOFI) and an explicit Buy ($SOFI summary) on the right,
  // fanned like a held hand of cards. The PNG has transparency between docs
  // so a drop-shadow filter applies to EACH document, not the whole frame.
  return (
    <div className="fund-stack" aria-label="A fanned stack of TLI research documents — Deep Dive, Equity Brief, Valuation Analysis">
      <img
        src="assets/fundamental-stack.png"
        alt="TLI Deep Dive ($NVO), Equity Brief ($NFLX), Valuation Analysis ($SOFI) and Buy rating — fanned like cards"
        draggable="false"
      />
    </div>
  );
}
window.FundamentalStack = FundamentalStack;

function HeroVisual({ kind }) {
  if (kind === "spot")   return (
    <img
      src="uploads/SPOT_2026-05-05_16-27-12_1a291.png"
      alt="$SPOT weekly chart with Elliott Wave count, Fibonacci levels and buy zone"
      style={{ display: "block", width: "100%", height: "100%", objectFit: "contain", borderRadius: 2 }}
    />
  );
  if (kind === "fundamentals") return <FundamentalStack />;
  if (kind === "money-flow") return (
    <img
      src="uploads/The Money Flow Research.png"
      alt="The Money Flow Research — quarterly report on what super‑investors are buying"
      style={{ display: "block", width: "100%", height: "100%", objectFit: "contain", borderRadius: 2 }}
    />
  );
  if (kind === "chat")   return (
    <div style={{
      width: "100%",
      display: "flex", alignItems: "center", justifyContent: "center",
    }}>
      <div style={{
        width: "100%",
        background: "rgba(255,250,238,0.025)",
        border: "1px solid rgba(255,250,238,0.10)",
        borderRadius: 14,
        padding: "clamp(20px, 2vw, 30px)",
      }}>
        <window.ChatPreview preview={true} />
      </div>
    </div>
  );
  if (kind === "course") return <div style={{ width: "100%", maxHeight: "100%" }}><window.CourseOutline /></div>;
  return null;
}

function HeroCarousel() {
  const [idx, setIdx] = useState(0);
  const [paused, setPaused] = useState(false);
  const [atTop, setAtTop] = useState(true);
  const lastActiveRef = useRef(Date.now());
  const bgVideoRef = useRef(null);
  const ADVANCE_MS = 6000;
  const reduced = PRM();

  useEffect(() => {
    const v = bgVideoRef.current;
    if (!v) return;
    v.playbackRate = 0.7;
    const onEnded = () => { v.currentTime = 0; v.play().catch(() => {}); };
    v.addEventListener("ended", onEnded);
    return () => v.removeEventListener("ended", onEnded);
  }, []);

  // Only auto-advance while the hero is actually framed at the top of the
  // page. The moment the user scrolls away, freeze the carousel — otherwise
  // swapping to a slide of a different height reflows the page and yanks the
  // viewport under the reader. (This was the "screen jumps on slide change".)
  useEffect(() => {
    const onScroll = () => setAtTop(window.scrollY < 80);
    onScroll();
    window.addEventListener("scroll", onScroll, { passive: true });
    return () => window.removeEventListener("scroll", onScroll);
  }, []);

  const frozen = paused || !atTop;

  // Auto-advance
  useEffect(() => {
    if (frozen || reduced) return;
    const id = setInterval(() => {
      setIdx(i => (i + 1) % HERO_SLIDES.length);
    }, ADVANCE_MS);
    return () => clearInterval(id);
  }, [frozen, reduced]);

  // Resume after 8s of inactivity
  const interact = (next) => {
    lastActiveRef.current = Date.now();
    setPaused(true);
    setIdx(next);
  };
  useEffect(() => {
    if (!paused) return;
    const id = setInterval(() => {
      if (Date.now() - lastActiveRef.current > 8000) setPaused(false);
    }, 500);
    return () => clearInterval(id);
  }, [paused]);

  const slide = HERO_SLIDES[idx];

  return (
    <section
      className="hero"
      onMouseEnter={() => setPaused(true)}
      onMouseLeave={() => { lastActiveRef.current = Date.now(); }}
      onFocus={() => setPaused(true)}
      style={{
        position: "relative",
        paddingTop: "calc(72px + 24px)",
        paddingBottom: 32,
        background:
          "radial-gradient(120% 80% at 15% 0%, rgba(235,207,0,0.04) 0%, transparent 55%), #000",
        minHeight: "calc(100vh - 90px)",
        display: "flex",
        alignItems: "center",
        overflow: "hidden",
      }}
    >
      <video
        ref={bgVideoRef}
        className="hero-bg-video"
        src="assets/hero-bg.mp4"
        autoPlay
        loop
        muted
        playsInline
        preload="auto"
        aria-hidden="true"
        style={{
          position: "absolute",
          inset: 0,
          width: "100%",
          height: "100%",
          objectFit: "cover",
          opacity: 0.22,
          pointerEvents: "none",
          zIndex: 0,
          mixBlendMode: "screen",
        }}
      />
      <div
        aria-hidden="true"
        style={{
          position: "absolute",
          inset: 0,
          pointerEvents: "none",
          zIndex: 0,
          background:
            "radial-gradient(ellipse 70% 75% at 50% 50%, rgba(0,0,0,0) 0%, rgba(0,0,0,0.55) 55%, rgba(0,0,0,0.95) 100%)",
        }}
      />
      <div className="container" style={{ width: "100%", position: "relative", zIndex: 1 }}>
        <div
          className="two-col"
          style={{
            alignItems: "center",
            gap: 80,
            gridTemplateColumns: (slide.visual === "spot" || slide.visual === "money-flow")
              ? "minmax(0, 38fr) minmax(0, 62fr)"
              : undefined,
          }}
        >
          {/* LEFT — text */}
          <div key={`l-${idx}`} className="hero-fade">
            <div className="eyebrow-tag" style={{ marginBottom: 28 }}>
              <span>{slide.n}</span><span>{slide.kicker}</span>
            </div>
            <h1 className="serif" style={{
              fontSize: "clamp(40px, 4.6vw, 60px)",
              lineHeight: 1.04,
              marginBottom: 22,
              maxWidth: "16ch",
            }}>
              {slide.h1Bold ? (
                <React.Fragment>
                  <span style={{ fontWeight: 700 }}>{slide.h1Bold}</span>
                  <span style={{ color: "var(--fg-dim)", fontWeight: 400 }}>{slide.h1Soft}</span>
                </React.Fragment>
              ) : slide.h1}
            </h1>
            <p className="lede" style={{ marginBottom: 36, maxWidth: "44ch" }}>
              {slide.body}
            </p>
            <div className="row-gap-16">
              <a className="btn btn-gold" href={slide.pageHref} aria-label={slide.ctaLabel}
                 style={{ height: 38, padding: "0 18px", fontSize: 11.5 }}>
                Read more →
              </a>
            </div>
          </div>

          {/* RIGHT — visual panel */}
          <div key={`r-${idx}`} className="hero-fade">
            <div className="hero-right-pane">
              {/* Slide selector — 5 clickable lines */}
              <div className="slide-lines" role="tablist" aria-label="Hero slides">
                {HERO_SLIDES.map((s, i) => {
                  const state = i === idx ? "active" : i < idx ? "done" : "todo";
                  return (
                    <button
                      key={i}
                      role="tab"
                      aria-selected={i === idx}
                      aria-label={`Slide ${i+1}: ${s.kicker}`}
                      onClick={() => interact(i)}
                      className={`slide-line ${state}`}
                    >
                      <span className="sl-track">
                        <span
                          className="sl-fill"
                          key={`f-${i}-${idx}-${frozen ? "p" : "r"}`}
                          style={{
                            animation: state === "active" && !frozen && !reduced
                              ? `progressFill ${ADVANCE_MS}ms linear forwards`
                              : "none",
                            transform: state === "done" ? "scaleX(1)" : (state === "active" && frozen ? "scaleX(0)" : undefined),
                          }}
                        />
                      </span>
                      <span className="sl-num">0{i+1}</span>
                      <span className="sl-label">{s.kicker}</span>
                    </button>
                  );
                })}
              </div>

              <a className="hero-visual-link" href={slide.pageHref} aria-label={`Open ${slide.kicker}`}>
                <div className="hero-visual-bare">
                  <div style={{
                    width: "100%",
                    aspectRatio: slide.visual === "chat" ? "auto" : (slide.aspect || "5 / 4"),
                    display: "flex", alignItems: "center", justifyContent: "center",
                    position: "relative",
                  }}>
                    <HeroVisual kind={slide.visual} />
                  </div>
                </div>
              </a>
            </div>
          </div>
        </div>
      </div>

      <style>{`
        @keyframes progressFill {
          from { transform: scaleX(0); }
          to   { transform: scaleX(1); }
        }
        @keyframes heroFade {
          from { opacity: 0; transform: translateY(6px); }
          to   { opacity: 1; transform: none; }
        }
        .hero-fade { animation: heroFade 360ms var(--ease-out) both; }
        .dot {
          width: 8px; height: 8px;
          border-radius: 50%;
          background: rgba(255,250,238,0.18);
          border: 0; padding: 0; cursor: pointer;
          transition: background 150ms var(--ease-out), transform 150ms var(--ease-out);
        }
        .dot:hover { background: rgba(255,250,238,0.32); }
        .dot.on { background: ${window.GOLD}; transform: scale(1.2); }
        .slide-lines {
          display: flex; align-items: stretch;
          gap: 12px;
          margin-bottom: 18px;
        }
        .slide-line {
          flex: 1; min-width: 0;
          background: transparent; border: 0; padding: 10px 0 0;
          cursor: pointer; text-align: left;
          display: flex; flex-direction: column; gap: 8px;
          color: rgba(255,250,238,0.45);
          transition: color 150ms var(--ease-out);
        }
        .slide-line .sl-track {
          display: block; position: relative;
          height: 2px; width: 100%;
          background: rgba(255,250,238,0.10);
          overflow: hidden;
        }
        .slide-line .sl-fill {
          position: absolute; inset: 0;
          background: ${window.GOLD};
          transform: scaleX(0); transform-origin: left center;
        }
        .slide-line.done .sl-fill { transform: scaleX(1); }
        .slide-line .sl-num {
          font-family: var(--font-mono);
          font-size: 10px; letter-spacing: 0.18em;
          color: rgba(255,250,238,0.45);
        }
        .slide-line .sl-label {
          font-family: var(--font-text);
          font-size: 11px; font-weight: 600;
          letter-spacing: 0.16em; text-transform: uppercase;
          color: rgba(255,250,238,0.55);
          white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
        }
        .slide-line:hover .sl-num,
        .slide-line:hover .sl-label { color: ${window.CREAM}; }
        .slide-line.active .sl-num { color: ${window.GOLD}; }
        .slide-line.active .sl-label { color: ${window.CREAM}; }
        .slide-line.done .sl-num { color: rgba(235,207,0,0.55); }
        @media (max-width: 720px) {
          .slide-line .sl-label { display: none; }
        }
        .carousel-arrow {
          width: 36px; height: 36px;
          background: transparent;
          border: 1px solid rgba(255,250,238,0.18);
          color: ${window.CREAM};
          border-radius: 50%;
          font-size: 18px; line-height: 1;
          cursor: pointer;
          font-family: var(--font-display);
          transition: border-color 150ms var(--ease-out), color 150ms var(--ease-out);
        }
        .carousel-arrow:hover { border-color: ${window.GOLD}; color: ${window.GOLD}; }
        @media (prefers-reduced-motion: reduce) {
          .hero-fade { animation: none; }
        }

        /* ---------- Hero right pane — glass + glow wraps tabs + image ---------- */
        .hero-right-pane {
          position: relative;
          isolation: isolate;
          padding: clamp(10px, 1.2vw, 18px);
          margin: clamp(-10px, -1.2vw, -18px);
          border: 1px solid transparent;
          transition: border-color 320ms var(--ease-out);
        }
        .hero-right-pane:hover {
          border-color: rgba(255,250,238,0.36);
        }
        /* Glass sheen — soft diffused white highlight that fades in on hover.
           Sits BEHIND the tabs and the visual so the content stays clean. */
        .hero-right-pane::before {
          content: "";
          position: absolute;
          inset: 0;
          z-index: -2;
          pointer-events: none;
          background:
            radial-gradient(70% 60% at 18% 0%,
              rgba(255,250,238,0.14) 0%,
              rgba(255,250,238,0.05) 35%,
              rgba(255,250,238,0) 65%),
            radial-gradient(65% 80% at 100% 100%,
              rgba(255,250,238,0.07) 0%,
              rgba(255,250,238,0) 60%);
          opacity: 0;
          transition: opacity 360ms var(--ease-out);
          filter: blur(0.4px);
        }
        /* Frosted backdrop */
        .hero-right-pane::after {
          content: "";
          position: absolute;
          inset: 0;
          z-index: -1;
          pointer-events: none;
          background: rgba(255,250,238,0.025);
          backdrop-filter: blur(10px);
          -webkit-backdrop-filter: blur(10px);
          opacity: 0;
          transition: opacity 380ms var(--ease-out);
        }
        .hero-right-pane:hover::before { opacity: 1; }
        .hero-right-pane:hover::after  { opacity: 1; }

        /* Visual link — just the clickable region; no chrome of its own */
        .hero-visual-link {
          display: block;
          color: inherit;
          text-decoration: none;
        }

        @media (prefers-reduced-motion: reduce) {
          .hero-right-pane::before,
          .hero-right-pane::after { transition: none; }
        }

        /* ---------- Fundamental Analysis stack ---------- */
        .fund-stack {
          position: relative;
          width: 100%;
          height: 100%;
          display: flex;
          align-items: center;
          justify-content: center;
          animation: fundStackIn 600ms var(--ease-out) both;
        }
        .fund-stack img {
          display: block;
          width: 100%;
          height: 100%;
          max-width: 100%;
          max-height: 100%;
          object-fit: contain;
          /* Per-document drop shadow — filter respects the PNG alpha so
             each card silhouette gets its own shadow. Two stacked passes
             give a softer, deeper fall-off without going muddy. */
          filter:
            drop-shadow(0 10px 14px rgba(0, 0, 0, 0.55))
            drop-shadow(0 2px 4px rgba(0, 0, 0, 0.45));
          pointer-events: none;
          user-select: none;
        }
        @keyframes fundStackIn {
          from { opacity: 0; transform: translateY(8px); }
          to   { opacity: 1; transform: none; }
        }
        @media (prefers-reduced-motion: reduce) {
          .fund-stack { animation: none; }
        }
      `}</style>
    </section>
  );
}

/* ---------- TESTIMONIAL MARQUEE ---------- */
const TESTIMONIALS = [
  { who: "FatherT",     since: 2023, tone: "cream",    quote: "Strategy removed emotion and replaced it with clarity. Volatility tested discipline, not conviction." },
  { who: "Federico S.", since: 2024, tone: "graphite", quote: "Fundamentals plus technical, with a clear strategy. Nobody does it the way you do." },
  { who: "JJ",          since: 2025, tone: "cream",    quote: "TLI till I die. Easiest $42 a month I'll ever spend." },
  { who: "Niall B.",    since: 2024, tone: "graphite", quote: "Seeing the resistance lines ahead of time is very empowering. The learning is huge." },
  { who: "Austin W.",   since: 2024, tone: "cream",    quote: "$100k invested at 22. Two days ago, $160k at 23. Never thought I'd have this kind of money." },
  { who: "Elad",        since: 2023, tone: "graphite", quote: "Every red cycle you deliver and keep improving the product. Nothing but mad respect." },
];

function TestimonialMarquee() {
  const [paused, setPaused] = useState(false);
  const reduced = PRM();
  // duplicate the list so the translate loop is seamless
  const loop = [...TESTIMONIALS, ...TESTIMONIALS];

  return (
    <section
      className="panel"
      onMouseEnter={() => setPaused(true)}
      onMouseLeave={() => setPaused(false)}
      style={{
        background: "#0c0c0c",
        borderTop: "1px solid rgba(255,250,238,0.06)",
        borderBottom: "1px solid rgba(255,250,238,0.06)",
        padding: "22px 0",
        overflow: "hidden",
        position: "relative",
      }}
    >
      {/* edge fades */}
      <div aria-hidden="true" style={{
        position: "absolute", inset: 0, pointerEvents: "none",
        background: "linear-gradient(to right, #0c0c0c 0%, rgba(12,12,12,0) 8%, rgba(12,12,12,0) 92%, #0c0c0c 100%)",
        zIndex: 2,
      }}/>
      <div
        className="tm-track"
        style={{
          display: "flex",
          gap: 80,
          width: "max-content",
          alignItems: "center",
          animation: reduced ? "none" : "tmScroll 90s linear infinite",
          animationPlayState: paused ? "paused" : "running",
        }}
      >
        {loop.map((t, i) => {
          const initials = t.who.split(" ").map(p => p[0]).join("").slice(0, 2);
          return (
            <div key={i} className="tm-card" style={{
              display: "flex", alignItems: "center", gap: 20,
              flex: "0 0 auto",
              width: 540,
              paddingRight: 32,
              borderRight: "1px solid rgba(255,250,238,0.06)",
            }}>
              <window.Avatar initials={initials} tone={t.tone} size={40} />
              <div style={{ minWidth: 0, flex: "0 0 auto", width: 92 }}>
                <div style={{
                  fontFamily: "var(--font-text)",
                  fontWeight: 600, fontSize: 13,
                  color: window.CREAM, letterSpacing: "0.02em",
                  whiteSpace: "nowrap",
                }}>{t.who}</div>
                <div style={{
                  fontSize: 9.5, color: window.CREAM_FAINT,
                  letterSpacing: "0.18em", textTransform: "uppercase",
                  marginTop: 2,
                  whiteSpace: "nowrap",
                }}>’{String(t.since).slice(2)}</div>
              </div>
              <div style={{
                fontFamily: "var(--font-display)",
                fontStyle: "italic",
                fontSize: 14.5, lineHeight: 1.4,
                color: "rgba(255,250,238,0.82)",
                flex: 1, minWidth: 0,
                whiteSpace: "normal",
              }}>
                <span style={{ color: window.GOLD, marginRight: 4 }}>“</span>
                {t.quote}
                <span style={{ color: window.GOLD, marginLeft: 3 }}>”</span>
              </div>
            </div>
          );
        })}
      </div>
      <style>{`
        @keyframes tmScroll {
          from { transform: translateX(0); }
          to   { transform: translateX(-50%); }
        }
        @media (max-width: 760px) {
          .tm-track { gap: 32px !important; animation-duration: 55s !important; }
        }
        @media (max-width: 480px) {
          .tm-track { gap: 24px !important; animation-duration: 42s !important; }
          .tm-card { width: 320px !important; gap: 14px !important; padding-right: 20px !important; }
          .tm-card > div:nth-child(2) { width: 74px !important; }
        }
      `}</style>
    </section>
  );
}

window.HeroCarousel = HeroCarousel;
window.TestimonialMarquee = TestimonialMarquee;
