// Main app — drives one question per page through QUESTIONS list.

const { useState, useEffect, useRef, useMemo } = React;

function App() {
  const [t, setTweak] = useTweaks(window.TWEAK_DEFAULTS);
  const [idx, setIdx] = useState(0);
  const [data, setData] = useState({});
  const [submitted, setSubmitted] = useState(false);
  const [transitioning, setTransitioning] = useState(false);
  const [direction, setDirection] = useState(1);

  // Refs so goNext (called from setTimeout in question components)
  // always reads the *current* data/idx, not a stale closure.
  const dataRef = useRef(data);
  const idxRef = useRef(idx);
  useEffect(() => { dataRef.current = data; idxRef.current = idx; });

  useEffect(() => { window.__autoAdvance = t.autoAdvance; }, [t.autoAdvance]);
  useEffect(() => { document.body.dataset.density = t.density; }, [t.density]);
  useEffect(() => { document.body.dataset.theme = t.theme || "institutional"; }, [t.theme]);

  const set = (k, v) => setData((d) => ({ ...d, [k]: v }));

  const q = QUESTIONS[idx];
  const QComponent = window[q.component];
  const canContinue = q.validate(data);
  const isLast = idx === QUESTIONS.length - 1;

  // Hide external-link distractions (testimonials carousel, social links)
  // until the user has captured their contact info — otherwise they may
  // click off to Google/Trustpilot/Instagram before completing the form.
  const contactCaptured = !!(data.firstName && data.email && data.phone);
  const showOffPage = contactCaptured || submitted;

  const animateTo = (i) => {
    setTransitioning(true);
    setTimeout(() => {
      setIdx(i);
      setTransitioning(false);
    }, 220);
  };

  // Stable goNext — reads live state via refs so deferred calls
  // (auto-advance setTimeouts) don't see a stale closure.
  const goNext = React.useCallback(() => {
    const i = idxRef.current;
    const d = dataRef.current;
    const qq = QUESTIONS[i];
    if (!qq.validate(d) && !qq.optional) return;
    if (i === QUESTIONS.length - 1) {
      setSubmitted(true);
      return;
    }
    setDirection(1);
    setTransitioning(true);
    setTimeout(() => {
      setIdx(i + 1);
      setTransitioning(false);
    }, 220);
  }, []);

  const goBack = () => {
    if (idx === 0) return;
    setDirection(-1);
    animateTo(idx - 1);
  };

  // Global Enter handler — supports keyboard-driven Typeform feel.
  useEffect(() => {
    const onKey = (e) => {
      if (e.key === "Enter" && e.target.tagName !== "TEXTAREA") {
        // Skip if focus is on an inline segmented or a button (they handle their own activation).
        if (e.target.tagName === "BUTTON") return;
        // Inputs that already wire onEnter via component prop will fire goNext via that path;
        // we still want fall-through for select / checkbox.
        if (e.target.tagName === "INPUT" || e.target.tagName === "SELECT") {
          // For text inputs, the component-level onEnter handles it. Avoid double-fire.
          if (e.target.type === "text" || e.target.type === "tel" ||
              e.target.type === "email" || e.target.type === "number") return;
        }
        goNext();
      }
    };
    window.addEventListener("keydown", onKey);
    return () => window.removeEventListener("keydown", onKey);
  }, [idx, data, canContinue]);

  // Brand-panel chips
  const brandAnswers = useMemo(() => {
    const out = {};
    const map = {
      paying: "Still paying", behind: "Behind",
      sued: "Sued / COJ", stacked: "Considering stack",
    };
    if (data.situation) out.situation = map[data.situation] || data.situation;
    if (data.advanceCount) out.advanceCount = data.advanceCount;
    if (data.balance) out.balance = data.balance;
    if (data.payment) out.payment = data.payment;
    if (data.frequency && data.frequency.length) out.frequency = data.frequency;
    if (data.firstName) out.firstName = `${data.firstName} ${data.lastName || ""}`.trim();
    if (data.businessName) out.businessName = data.businessName;
    if (data.state) out.state = data.state;
    return out;
  }, [data]);

  return (
    <>
      <DirectionStyles />
      <div className="shell">
        <BrandPanel answers={brandAnswers} showTestimonial={t.showTestimonial} showOffPage={showOffPage} stepIdx={idx} submitted={submitted} />

        <main className="form-panel">
          {!submitted ? (
            <>
              <ProgressBar questions={QUESTIONS} current={idx} />

              <div className="step-body">
                <div className="step-frame">
                  <div className="step"
                       key={q.id}
                       style={{
                         transform: transitioning
                           ? `translateX(${direction * -28}px)`
                           : "translateX(0)",
                         opacity: transitioning ? 0 : 1,
                       }}>
                    <QComponent data={data} set={set} onNext={goNext} />
                  </div>
                </div>

                <div className="controls">
                  <button
                    className={`ghost ${idx === 0 ? "disabled" : ""}`}
                    onClick={goBack}
                    aria-label="Previous question"
                  >
                    <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor"
                         strokeWidth="2" strokeLinecap="round" strokeLinejoin="round">
                      <path d="M19 12H5M12 19l-7-7 7-7" />
                    </svg>
                    Back
                  </button>

                  <div className="controls-right">
                    {q.optional && !canContinue ? (
                      <button className="ghost-link" onClick={goNext}>Skip →</button>
                    ) : null}
                    <button
                      className="primary"
                      onClick={goNext}
                      disabled={!canContinue && !q.optional}
                    >
                      {isLast ? "Submit case" : (q.optional && !canContinue ? "Continue" : "Continue")}
                      <svg className="arr" width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor"
                           strokeWidth="2" strokeLinecap="round" strokeLinejoin="round">
                        <path d="M5 12h14M12 5l7 7-7 7" />
                      </svg>
                    </button>
                  </div>
                </div>
              </div>
            </>
          ) : (
            <StepConfirm data={data} />
          )}
        </main>
      </div>

      <TrustpilotWidget />

      <TweaksPanel title="Tweaks">
        <TweakSection label="Direction">
          <TweakRadio
            label="Theme"
            value={t.theme || "institutional"}
            options={[
              { value: "institutional", label: "A · Bank" },
              { value: "fintech",       label: "B · Fintech" },
              { value: "concierge",     label: "C · Calm" },
            ]}
            onChange={(v) => setTweak("theme", v)}
          />
        </TweakSection>
        <TweakSection label="Layout">
          <TweakRadio
            label="Density"
            value={t.density}
            options={["compact", "regular", "comfy"]}
            onChange={(v) => setTweak("density", v)}
          />
          <TweakToggle
            label="Auto-advance"
            value={t.autoAdvance}
            onChange={(v) => setTweak("autoAdvance", v)}
          />
          <TweakToggle
            label="Show testimonial"
            value={t.showTestimonial}
            onChange={(v) => setTweak("showTestimonial", v)}
          />
        </TweakSection>
        <TweakSection label="Demo">
          <TweakButton
            label={submitted ? "Reset" : "Skip to confirmation"}
            onClick={() => {
              if (submitted) {
                setSubmitted(false);
                setIdx(0);
                setData({});
              } else {
                setSubmitted(true);
              }
            }}
            secondary
          />
        </TweakSection>
      </TweaksPanel>
    </>
  );
}

// ── Progress bar — section-grouped continuous bar ────────────────────────
function ProgressBar({ questions, current }) {
  const sections = [];
  questions.forEach((q, i) => {
    const last = sections[sections.length - 1];
    if (last && last.name === q.section) last.count += 1;
    else sections.push({ name: q.section, count: 1, start: i });
  });
  const cur = questions[current];
  const sectionIdx = sections.findIndex((s) => s.name === cur.section);
  const inSectionPos = current - sections[sectionIdx].start;
  const inSectionTotal = sections[sectionIdx].count;

  return (
    <div className="progress-wrap">
      <div className="progress-meta">
        <span className="step-num">
          {String(current + 1).padStart(2, "0")}<span className="dim"> / {String(questions.length).padStart(2, "0")}</span>
        </span>
        <span className="meta-spacer" />
        <span className="step-sub">
          {cur.section} · <span className="dim">{inSectionPos + 1} of {inSectionTotal}</span>
        </span>
      </div>
      <div className="progress-sections">
        {sections.map((s, si) => (
          <div key={s.name} className={`progress-section ${si === sectionIdx ? "on" : ""}`} style={{ flex: s.count }}>
            <div className="progress-section-bars">
              {Array.from({ length: s.count }).map((_, j) => {
                const qi = s.start + j;
                const state = qi < current ? "done" : qi === current ? "active" : "todo";
                return <div key={j} className={`progress-seg ${state}`}><div className="fill" /></div>;
              })}
            </div>
          </div>
        ))}
      </div>
    </div>
  );
}

// ── Direction (theme) styles ─────────────────────────────────────────────
function DirectionStyles() {
  return (
    <style dangerouslySetInnerHTML={{ __html: `
      /* A · Institutional uses :root defaults */

      body[data-theme="fintech"] {
        --navy: #15171C; --navy-2: #22262E; --navy-soft: #2B2F38;
        --cream: #F5F1EA; --cream-2: #FBF8F2; --paper: #FFFFFF; --card: #FFFFFF;
        --ink: #15171C; --ink-2: #3B3F47; --ink-3: #777C86;
        --rule: rgba(21,23,28,0.10);
        --accent: #E8703A; --accent-soft: #F0905E;
      }
      body[data-theme="fintech"] .question,
      body[data-theme="fintech"] .brand-headline,
      body[data-theme="fintech"] .confirm-title {
        font-family: var(--sans); font-weight: 600; letter-spacing: -0.025em;
      }
      body[data-theme="fintech"] .quote { font-family: var(--sans); font-style: normal; font-weight: 400; }
      body[data-theme="fintech"] .quote::before, body[data-theme="fintech"] .quote::after { content: ""; }
      body[data-theme="fintech"] .savings-cell .v,
      body[data-theme="fintech"] .advisor-avatar { font-family: var(--sans); font-weight: 600; }
      body[data-theme="fintech"] .primary { border-radius: 10px; }

      body[data-theme="concierge"] {
        --navy: #233A30; --navy-2: #2C4A3D; --navy-soft: #355A4A;
        --cream: #ECE3CC; --cream-2: #F1EAD6; --paper: #F7F1E1; --card: #FBF6EA;
        --ink: #1F2F27; --ink-2: #4D5D54; --ink-3: #7C887F;
        --rule: rgba(31,47,39,0.12);
        --accent: #C19A4E; --accent-soft: #D2AE63;
      }
      body[data-theme="concierge"] { background: var(--cream); }
      body[data-theme="concierge"] .question,
      body[data-theme="concierge"] .brand-headline,
      body[data-theme="concierge"] .confirm-title {
        font-family: var(--serif); font-style: normal; font-weight: 400;
      }
      body[data-theme="concierge"] .question { letter-spacing: -0.02em; }
      body[data-theme="concierge"] .opt, body[data-theme="concierge"] .seg,
      body[data-theme="concierge"] .input, body[data-theme="concierge"] .review-card,
      body[data-theme="concierge"] .savings-card, body[data-theme="concierge"] .advisor {
        border-radius: 4px;
      }
      body[data-theme="concierge"] .seg button { border-radius: 3px; }
      body[data-theme="concierge"] .primary { border-radius: 4px; }
      body[data-theme="concierge"] .form-panel { padding-top: 64px; padding-left: 80px; padding-right: 80px; }
      @media (max-width: 880px) {
        body[data-theme="concierge"] .form-panel { padding: 32px 24px; }
      }
    ` }} />
  );
}

// ── Trustpilot widget slot ───────────────────────────────────────────────
// Renders a placeholder rail along the bottom of the page. The real
// Trustpilot embed (TrustBox) goes inside `.trustpilot-slot` — drop the
// official Trustpilot <script> + <div class="trustpilot-widget" ...>
// snippet there and remove the placeholder content.
function TrustpilotWidget() {
  return (
    <div className="trustpilot-bar" data-noncommentable="">
      <div className="trustpilot-inner">
        <div className="trustpilot-slot" id="trustpilot-slot">
          {/* === TRUSTPILOT WIDGET PLACEHOLDER =================================
             Paste the Trustpilot embed snippet inside this div. Example:

             <div class="trustpilot-widget"
                  data-locale="en-US"
                  data-template-id="YOUR_TEMPLATE_ID"
                  data-businessunit-id="YOUR_BUSINESS_ID"
                  data-style-height="140px"
                  data-style-width="100%"
                  data-theme="light">
               <a href="https://www.trustpilot.com/review/yoursite.com"
                  target="_blank" rel="noopener">Trustpilot</a>
             </div>
             <script type="text/javascript"
                     src="//widget.trustpilot.com/bootstrap/v5/tp.widget.bootstrap.min.js"
                     async></script>
             =============================================================== */}
          <div className="tp-placeholder" aria-hidden="true">
            <div className="tp-placeholder-mark">
              <svg width="20" height="20" viewBox="0 0 24 24" fill="#00B67A" aria-hidden="true">
                <polygon points="12,2 14.9,8.6 22,9.3 16.7,14 18.3,21 12,17.3 5.7,21 7.3,14 2,9.3 9.1,8.6" />
              </svg>
              <span>Trustpilot</span>
            </div>
            <div className="tp-placeholder-text">
              <div className="tp-placeholder-title">Trustpilot widget loads here</div>
              <div className="tp-placeholder-sub">Drop the TrustBox embed snippet into <code>#trustpilot-slot</code> in production.</div>
            </div>
          </div>
        </div>
      </div>
    </div>
  );
}

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