/* schematic-actualize.jsx — Level 2 · The Language.
   The heart of the chapter: a circuit shown two ways at once — as a schematic
   AND as the real breadboard build — with every part cross-highlighted, plus
   ReadTheLoop (trace the current round a diagram). Depends on schematic-kit.jsx
   (SlgSym, SLG_HOT/INK, slgGlow). All names sla-/Sla- prefixed. */

const { useState: _slaState, useEffect: _slaEffect, useRef: _slaRef } = React;

/* hover/tap wrapper — children is a render fn (on) => svg */
function SlaHot({ id, active, setActive, hit, children }) {
  const on = active === id;
  return (
    <g style={{ cursor: "pointer" }}
       onMouseEnter={() => setActive(id)}
       onMouseLeave={() => setActive(a => (a === id ? null : a))}
       onClick={() => setActive(a => (a === id ? null : id))}>
      {hit}
      <g style={{ filter: slgGlow(on), transition: "filter 120ms ease" }}>{children(on)}</g>
    </g>
  );
}
const slaCol = (on) => (on ? SLG_HOT : SLG_INK);

/* ── physical breadboard part glyphs ───────────────────────────────────── */
function slaBoardFrame() {
  const holes = [];
  for (let r = 0; r < 5; r++) for (let c = 0; c < 11; c++)
    holes.push(<circle key={r + "-" + c} cx={56 + c * 19} cy={70 + r * 16} r="1.7" fill="var(--rule-strong)" />);
  return (
    <g>
      <rect x="10" y="20" width="280" height="172" rx="10" fill="var(--bg-card)" stroke="var(--rule-strong)" strokeWidth="1.4" />
      {/* + rail */}
      <line x1="26" y1="40" x2="274" y2="40" stroke="#c0392b" strokeWidth="2.6" />
      <text x="16" y="44" fontFamily="IBM Plex Mono, monospace" fontSize="11" fill="#c0392b">+</text>
      {/* − rail */}
      <line x1="26" y1="172" x2="274" y2="172" stroke="#2a6fb0" strokeWidth="2.6" />
      <text x="16" y="176" fontFamily="IBM Plex Mono, monospace" fontSize="11" fill="#2a6fb0">−</text>
      <g opacity="0.6">{holes}</g>
    </g>
  );
}
const slaLead = (x1, y1, x2, y2, col) => <line x1={x1} y1={y1} x2={x2} y2={y2} stroke={col} strokeWidth="2" strokeLinecap="round" />;

function slaBatt9V(col, on) {
  // a 9V block at far left with + (red) and − (blue) leads to the rails
  return (
    <g>
      <rect x="20" y="86" width="34" height="44" rx="4" fill={on ? "#33312b" : "#2b2924"} stroke={col} strokeWidth="1.8" />
      <text x="37" y="105" textAnchor="middle" fontFamily="IBM Plex Mono, monospace" fontSize="10" fill="#e8e2d2">9V</text>
      <text x="37" y="118" textAnchor="middle" fontFamily="IBM Plex Mono, monospace" fontSize="9" fill="#b9b3a4">▇</text>
      {/* terminals up to rails */}
      <path d="M30 86 L30 40" fill="none" stroke="#c0392b" strokeWidth="2.2" />
      <path d="M44 86 L44 172" fill="none" stroke="#2a6fb0" strokeWidth="2.2" />
    </g>
  );
}
function slaResV(x, y1, y2, col) {
  const cy = (y1 + y2) / 2;
  return (
    <g>
      {slaLead(x, y1, x, cy - 15, col)}{slaLead(x, cy + 15, x, y2, col)}
      <rect x={x - 11} y={cy - 15} width="22" height="30" rx="6" fill="#d9c089" stroke="var(--ink)" strokeWidth="1.3" />
      <rect x={x - 11} y={cy - 8} width="22" height="3" fill="#7a4a2a" /><rect x={x - 11} y={cy - 1} width="22" height="3" fill="#b03030" />
      <rect x={x - 11} y={cy + 6} width="22" height="3" fill="#caa23a" />
    </g>
  );
}
function slaLedV(x, y1, y2, col, lit) {
  const cy = (y1 + y2) / 2;
  return (
    <g>
      {slaLead(x - 4, cy + 6, x - 4, y2, col)}{slaLead(x + 4, cy + 6, x + 4, y1, col)}
      <circle cx={x} cy={cy} r="11" fill={lit ? "var(--current)" : "var(--bg-deeper)"} stroke="var(--ink)" strokeWidth="1.5"
              style={{ transition: "fill 90ms linear", filter: lit ? "drop-shadow(0 0 8px var(--current))" : "none" }} />
      <path d={`M${x - 7} ${cy - 6} a7 7 0 0 1 14 0`} fill="none" stroke="var(--bg-card)" strokeWidth="1.1" opacity="0.7" />
    </g>
  );
}
function slaCapV(x, y1, y2, col) {
  const cy = (y1 + y2) / 2;
  return (
    <g>
      {slaLead(x, y1, x, cy - 16, col)}{slaLead(x, cy + 16, x, y2, col)}
      <rect x={x - 10} y={cy - 16} width="20" height="32" rx="4" fill="#2b3a55" stroke="var(--ink)" strokeWidth="1.4" />
      <rect x={x - 10} y={cy - 16} width="6" height="32" rx="2" fill="#54657f" />
      <text x={x + 2} y={cy + 3} textAnchor="middle" fontFamily="IBM Plex Mono, monospace" fontSize="10" fill="#cdd6e2">+</text>
    </g>
  );
}
const slaWireSeg = (pts, col) => <polyline points={pts} fill="none" stroke={col} strokeWidth="2.4" strokeLinecap="round" strokeLinejoin="round" />;

/* ════════ CIRCUIT A — the simple loop: battery → resistor → LED ════════ */
function SlaLoopSchematic({ active, setActive, lit }) {
  const T = 46, B = 178, L = 46, R = 250;
  return (
    <svg viewBox="0 0 300 210" className="sla-svg">
      {/* wires (frame) */}
      <polyline points={`${L},${T} ${R},${T} ${R},${B} ${L},${B} ${L},${T}`} fill="none" stroke={SLG_INK} strokeWidth="2" />
      {/* battery on left edge */}
      <SlaHot id="batt" active={active} setActive={setActive}
        hit={<rect x={L - 22} y="90" width="44" height="44" fill="transparent" />}>
        {on => <g>{SlgSym.battery(L, 112, slaCol(on))}</g>}
      </SlaHot>
      {/* resistor on top edge */}
      <SlaHot id="res" active={active} setActive={setActive}
        hit={<rect x="120" y="30" width="56" height="32" fill="transparent" />}>
        {on => <><rect x="131" y="40" width="34" height="12" fill="var(--bg-card)" />{SlgSym.resistor(148, 46, slaCol(on))}</>}
      </SlaHot>
      {/* LED on right edge */}
      <SlaHot id="led" active={active} setActive={setActive}
        hit={<rect x={R - 18} y="90" width="40" height="44" fill="transparent" />}>
        {on => <><rect x={R - 10} y="98" width="20" height="28" fill="var(--bg-card)" />{SlgSym.led(R, 112, slaCol(on), { dir: "down" })}</>}
      </SlaHot>
      <text x="148" y="28" textAnchor="middle" className="sla-lbl">R</text>
    </svg>
  );
}
function SlaLoopBoard({ active, setActive, lit }) {
  return (
    <svg viewBox="0 0 300 210" className="sla-svg">
      {slaBoardFrame()}
      <SlaHot id="batt" active={active} setActive={setActive}
        hit={<rect x="16" y="34" width="44" height="142" fill="transparent" />}>
        {on => slaBatt9V(slaCol(on), on)}
      </SlaHot>
      {/* node column x=170 */}
      <SlaHot id="res" active={active} setActive={setActive}
        hit={<rect x="150" y="40" width="40" height="68" fill="transparent" />}>
        {on => slaResV(170, 40, 108, slaCol(on))}
      </SlaHot>
      <SlaHot id="led" active={active} setActive={setActive}
        hit={<rect x="150" y="108" width="40" height="66" fill="transparent" />}>
        {on => slaLedV(170, 108, 172, slaCol(on), lit)}
      </SlaHot>
      <circle cx="170" cy="108" r="2.4" fill={SLG_INK} />
    </svg>
  );
}

/* ════════ CIRCUIT B — the blinker (RC): battery → R → (cap ∥ LED) ════════ */
function SlaBlinkSchematic({ active, setActive, lit }) {
  const T = 46, B = 178, L = 46, R = 250, NODE = 178;
  return (
    <svg viewBox="0 0 300 210" className="sla-svg">
      <polyline points={`${L},${T} ${R},${T} ${R},${B} ${L},${B} ${L},${T}`} fill="none" stroke={SLG_INK} strokeWidth="2" />
      {/* node drop for the cap at x=178 */}
      <line x1={NODE} y1={T} x2={NODE} y2={B} stroke={SLG_INK} strokeWidth="2" />
      <SlaHot id="batt" active={active} setActive={setActive}
        hit={<rect x={L - 22} y="90" width="44" height="44" fill="transparent" />}>
        {on => SlgSym.battery(L, 112, slaCol(on))}
      </SlaHot>
      <SlaHot id="res" active={active} setActive={setActive}
        hit={<rect x="96" y="30" width="56" height="32" fill="transparent" />}>
        {on => <><rect x="107" y="40" width="34" height="12" fill="var(--bg-card)" />{SlgSym.resistor(124, 46, slaCol(on))}</>}
      </SlaHot>
      <SlaHot id="cap" active={active} setActive={setActive}
        hit={<rect x={NODE - 18} y="92" width="40" height="40" fill="transparent" />}>
        {on => <><rect x={NODE - 12} y="104" width="24" height="16" fill="var(--bg-card)" />{SlgSym.capacitor(NODE, 112, slaCol(on))}</>}
      </SlaHot>
      <SlaHot id="led" active={active} setActive={setActive}
        hit={<rect x={R - 18} y="90" width="40" height="44" fill="transparent" />}>
        {on => <><rect x={R - 10} y="98" width="20" height="28" fill="var(--bg-card)" />{SlgSym.led(R, 112, slaCol(on), { dir: "down" })}</>}
      </SlaHot>
      <text x="124" y="28" textAnchor="middle" className="sla-lbl">R</text>
      <text x={NODE + 16} y="80" className="sla-lbl">C</text>
    </svg>
  );
}
function SlaBlinkBoard({ active, setActive, lit }) {
  return (
    <svg viewBox="0 0 300 210" className="sla-svg">
      {slaBoardFrame()}
      <SlaHot id="batt" active={active} setActive={setActive}
        hit={<rect x="16" y="34" width="44" height="142" fill="transparent" />}>
        {on => slaBatt9V(slaCol(on), on)}
      </SlaHot>
      {/* node row at y=108 joining columns 132 & 208 (jumper) */}
      {slaWireSeg("132,108 208,108", SLG_INK)}
      <circle cx="132" cy="108" r="2.4" fill={SLG_INK} /><circle cx="208" cy="108" r="2.4" fill={SLG_INK} />
      <SlaHot id="res" active={active} setActive={setActive}
        hit={<rect x="112" y="40" width="40" height="68" fill="transparent" />}>
        {on => slaResV(132, 40, 108, slaCol(on))}
      </SlaHot>
      <SlaHot id="led" active={active} setActive={setActive}
        hit={<rect x="112" y="108" width="40" height="66" fill="transparent" />}>
        {on => slaLedV(132, 108, 172, slaCol(on), lit)}
      </SlaHot>
      <SlaHot id="cap" active={active} setActive={setActive}
        hit={<rect x="188" y="108" width="40" height="66" fill="transparent" />}>
        {on => slaCapV(208, 108, 172, slaCol(on))}
      </SlaHot>
    </svg>
  );
}

/* the two circuits, registry */
const SLA_CIRCUITS = {
  loop: {
    title: { adult: "The simplest loop", kids: "One light, one loop" },
    blurb: { adult: "A battery, one resistor, one LED — a single series loop. Hover any part to see it in both views.",
             kids: "A battery pushes flow through a pinch (resistor) and a light (LED), then home. Tap a part to find it on the board!" },
    Schem: SlaLoopSchematic, Board: SlaLoopBoard,
    parts: [
      { id: "batt", n: { adult: "Battery (9 V)", kids: "Battery" },
        s: { adult: "Two stacked lines = the source. On the board it's the 9 V block, + lead to the red rail, − to the blue.",
             kids: "The pusher. On the board it's the 9V block — red wire to the + line, black to the − line." } },
      { id: "res", n: { adult: "Resistor", kids: "Resistor (pinch)" },
        s: { adult: "The rectangle on the top wire = the beige banded resistor bridging the + rail down to the LED's column.",
             kids: "The little box = the striped resistor. It pinches the flow so the LED is safe." } },
      { id: "led", n: { adult: "LED", kids: "LED (light)" },
        s: { adult: "Triangle + bar on the right wire = the domed LED, long leg (+) up toward the resistor, short leg to the − rail.",
             kids: "The triangle = the round light. It only glows one way round — long leg toward the push." } },
    ],
  },
  blink: {
    title: { adult: "The blinker (RC)", kids: "The blinker" },
    blurb: { adult: "Add a capacitor across the LED and the current ramps instead of snapping on — the bones of Level 2's RC timer.",
             kids: "Add a bucket (capacitor) and the light fades in instead of popping on. Tap a part to match it up." },
    Schem: SlaBlinkSchematic, Board: SlaBlinkBoard,
    parts: [
      { id: "batt", n: { adult: "Battery (9 V)", kids: "Battery" },
        s: { adult: "Same source: 9 V block feeding the + and − rails.",
             kids: "The same 9V pusher, feeding the two rails." } },
      { id: "res", n: { adult: "Resistor", kids: "Resistor (pinch)" },
        s: { adult: "Sets how fast the cap fills. On the board it runs from the + rail to the shared node row.",
             kids: "Decides how fast the bucket fills. It runs from + down to the middle row." } },
      { id: "cap", n: { adult: "Capacitor", kids: "Bucket (capacitor)" },
        s: { adult: "Two plates on the middle branch = the electrolytic can from the node to the − rail. Mind the + leg.",
             kids: "Two lines = the bucket. It sits from the middle row down to −, filling and emptying." } },
      { id: "led", n: { adult: "LED", kids: "LED (light)" },
        s: { adult: "Shares the node with the cap, then down to −. It brightens as the cap charges.",
             kids: "Sits next to the bucket. It glows brighter as the bucket fills up." } },
    ],
  },
};

function SlaSchematicVsBoard({ kids }) {
  const [which, setWhich] = _slaState("loop");
  const [active, setActive] = _slaState(null);
  const C = SLA_CIRCUITS[which];
  const activePart = C.parts.find(p => p.id === active);
  return (
    <div className="sla-wrap">
      <div className="sla-tabs">
        {Object.entries(SLA_CIRCUITS).map(([k, c]) => (
          <button key={k} className={`sla-tab ${which === k ? "on" : ""}`}
                  onClick={() => { setWhich(k); setActive(null); }}>
            {kids ? c.title.kids : c.title.adult}
          </button>
        ))}
      </div>
      <p className="sla-blurb">{kids ? C.blurb.kids : C.blurb.adult}</p>
      <div className="sla-panels">
        <figure className="sla-panel">
          <figcaption><span className="sla-cap-tag">schematic</span>{kids ? "the drawing" : "how it's drawn"}</figcaption>
          <C.Schem active={active} setActive={setActive} lit={true} />
        </figure>
        <div className="sla-arrow" aria-hidden="true">
          <span>becomes</span><div className="sla-arrow-line">→</div>
        </div>
        <figure className="sla-panel">
          <figcaption><span className="sla-cap-tag board">breadboard</span>{kids ? "the real build" : "how it's built"}</figcaption>
          <C.Board active={active} setActive={setActive} lit={true} />
        </figure>
      </div>
      {/* part chips + explanation */}
      <div className="sla-parts">
        {C.parts.map(p => (
          <button key={p.id} className={`sla-chip ${active === p.id ? "on" : ""}`}
                  onMouseEnter={() => setActive(p.id)} onMouseLeave={() => setActive(a => (a === p.id ? null : a))}
                  onClick={() => setActive(a => (a === p.id ? null : p.id))}>
            {kids ? p.n.kids : p.n.adult}
          </button>
        ))}
      </div>
      <div className={`sla-explain ${activePart ? "on" : ""}`}>
        {activePart
          ? <><b>{kids ? activePart.n.kids : activePart.n.adult}.</b> {kids ? activePart.s.kids : activePart.s.adult}</>
          : (kids ? "Hover or tap a part above to light it up in both pictures." : "Hover or tap any part — symbol or chip — to see the same component highlighted in the diagram and on the board.")}
      </div>
    </div>
  );
}

/* ════════ ReadTheLoop — trace the current around a diagram ════════ */
const SLA_LOOP_PTS = [[46, 46], [250, 46], [250, 178], [46, 178]]; // closed rect, clockwise
function slaLoopGeom() {
  const pts = SLA_LOOP_PTS;
  const segs = [];
  let total = 0;
  for (let i = 0; i < pts.length; i++) {
    const a = pts[i], b = pts[(i + 1) % pts.length];
    const len = Math.hypot(b[0] - a[0], b[1] - a[1]);
    segs.push({ a, b, len, start: total }); total += len;
  }
  return { segs, total };
}
function slaPosAt(u, geom) {
  let d = u * geom.total;
  for (const s of geom.segs) {
    if (d <= s.len || s === geom.segs[geom.segs.length - 1]) {
      const f = Math.max(0, Math.min(1, d / s.len));
      return [s.a[0] + (s.b[0] - s.a[0]) * f, s.a[1] + (s.b[1] - s.a[1]) * f];
    }
    d -= s.len;
  }
  return geom.segs[0].a;
}
/* which story beat is the dot in, by position */
function slaBeat(pos, kids) {
  const [x, y] = pos;
  if (x <= 70 && y > 70) return kids ? { t: "The battery pushes", d: "The + side shoves the flow out the top." } : { t: "1 · The source", d: "Current leaves the battery's + terminal (top-left)." };
  if (y <= 70) return x < 180
    ? (kids ? { t: "Into the resistor", d: "The pinch slows the flow to a safe trickle." } : { t: "2 · Through the resistor", d: "The resistor limits the current before it reaches the LED." })
    : (kids ? { t: "Along the wire", d: "Plain wire — no slowing here." } : { t: "Wire — no drop", d: "A bare wire carries current with ~no resistance." });
  if (x >= 230) return kids ? { t: "The LED lights!", d: "Flow passes the right way through the light — it glows." } : { t: "3 · Through the LED", d: "Current passes the LED in its forward (arrow) direction — it emits light." };
  return kids ? { t: "Back home", d: "The flow returns to the battery's − side." } : { t: "4 · Return to −", d: "Current completes the loop back to the battery's − terminal." };
}
function SlaReadTheLoop({ kids }) {
  const dotRef = _slaRef(null);
  const [playing, setPlaying] = _slaState(true);
  const [beat, setBeat] = _slaState(() => slaBeat([46, 120], kids));
  const geom = _slaRef(slaLoopGeom()).current;
  _slaEffect(() => {
    let raf, t0 = performance.now(), last = -1;
    const speed = 0.16; // loops/sec
    const tick = (now) => {
      const u = ((now - t0) / 1000 * speed) % 1;
      const pos = slaPosAt(u, geom);
      if (dotRef.current) { dotRef.current.setAttribute("cx", pos[0].toFixed(1)); dotRef.current.setAttribute("cy", pos[1].toFixed(1)); }
      const zone = Math.floor(u * 8);
      if (zone !== last) { last = zone; setBeat(slaBeat(pos, kids)); }
      if (playing) raf = requestAnimationFrame(tick);
    };
    if (playing) raf = requestAnimationFrame(tick);
    return () => raf && cancelAnimationFrame(raf);
  }, [playing, kids]);
  const T = 46, B = 178, L = 46, R = 250;
  return (
    <div className="sla-loop">
      <svg viewBox="0 0 300 210" className="sla-svg">
        <polyline points={`${L},${T} ${R},${T} ${R},${B} ${L},${B} ${L},${T}`} fill="none" stroke={SLG_INK} strokeWidth="2" />
        {SlgSym.battery(L, 112, SLG_INK)}
        <rect x="131" y="40" width="34" height="12" fill="var(--bg-card)" />{SlgSym.resistor(148, 46, SLG_INK)}
        <rect x={R - 10} y="98" width="20" height="28" fill="var(--bg-card)" />{SlgSym.led(R, 112, SLG_INK, { dir: "down" })}
        {/* travelling charge */}
        <circle ref={dotRef} cx="46" cy="120" r="6" fill={SLG_HOT} style={{ filter: "drop-shadow(0 0 6px var(--current))" }} />
        <text x="148" y="28" textAnchor="middle" className="sla-lbl">R</text>
      </svg>
      <div className="sla-loop-side">
        <div className="sla-beat-t">{beat.t}</div>
        <div className="sla-beat-d">{beat.d}</div>
        <button className="sla-loop-btn" onClick={() => setPlaying(p => !p)}>{playing ? "❚❚ Pause" : "▶ Play"}</button>
        <p className="sla-loop-note">{kids ? "The orange dot is the flow. Watch it go round and round — that's a circuit!" : "The dot follows conventional current: + → around the loop → −. A circuit must be a closed loop or nothing flows."}</p>
      </div>
    </div>
  );
}

Object.assign(window, { SlaSchematicVsBoard, SlaReadTheLoop });
