/* global React */

// ============================================================================
// Pixel UI primitives — shared across the portfolio
// ============================================================================

const { useState, useEffect, useRef } = React;

// ---------- Heart Row (HP-style) ----------
function HeartRow({ filled = 5, total = 5, half = false }) {
  const hearts = [];
  for (let i = 0; i < total; i++) {
    if (i < filled) hearts.push("full");
    else if (half && i === filled) hearts.push("half");
    else hearts.push("empty");
  }
  return (
    <div className="heart-row" role="img" aria-label={`${filled} of ${total}`}>
      {hearts.map((k, i) => (
        <span key={i} className={`heart ${k === "empty" ? "heart--empty" : ""} ${k === "half" ? "heart--half" : ""}`}></span>
      ))}
    </div>
  );
}

// ---------- Pixel Panel wrapper ----------
function Panel({ variant = "", tight = false, children, style, ...rest }) {
  const cls = [
    "pixel-panel",
    variant === "simple" && "pixel-panel--simple",
    variant === "dark" && "pixel-panel--dark",
    tight && "pixel-panel--tight",
  ].filter(Boolean).join(" ");
  return <div className={cls} style={style} {...rest}>{children}</div>;
}

// ---------- Status Badge ----------
function Badge({ kind = "shipped", children }) {
  return <span className={`badge badge--${kind}`}>{children}</span>;
}

// ---------- Chapter / Section header ----------
function Chapter({ tag, title, sub, id }) {
  return (
    <header id={id} style={{ marginBottom: 40 }}>
      <span className="chapter-tag">{tag}</span>
      <h2 className="chapter-title">{title}</h2>
      {sub && <p className="chapter-sub">{sub}</p>}
    </header>
  );
}

// ---------- Stat row (label : value) ----------
function StatLine({ label, value, max }) {
  const pct = max ? Math.min(100, (value / max) * 100) : null;
  return (
    <div style={{ marginBottom: 14 }}>
      <div style={{ display: "flex", justifyContent: "space-between", fontFamily: "var(--font-pixel)", fontSize: 10, marginBottom: 6, letterSpacing: "0.05em" }}>
        <span>{label}</span>
        <span>{max ? `${value}/${max}` : value}</span>
      </div>
      {max && (
        <div style={{
          height: 14,
          background: "var(--parchment-3)",
          boxShadow: "inset 0 0 0 2px var(--ink)",
          position: "relative"
        }}>
          <div style={{
            width: `${pct}%`,
            height: "100%",
            background: "var(--heart)",
            transition: "width 0.6s steps(20)"
          }}></div>
        </div>
      )}
    </div>
  );
}

// ---------- Currency / Counter HUD (like the $0.00 box in the reference) ----------
function CounterHUD({ icon, label, value }) {
  return (
    <div style={{
      background: "var(--parchment)",
      padding: "8px 12px",
      boxShadow: "0 0 0 3px var(--ink), 3px 3px 0 3px var(--shadow)",
      display: "flex",
      alignItems: "center",
      gap: 10,
      minWidth: 110,
    }}>
      <span style={{ fontFamily: "var(--font-pixel)", fontSize: 12, color: "var(--ink)" }}>{icon}</span>
      <div style={{ fontFamily: "var(--font-pixel)", fontSize: 9, lineHeight: 1.4 }}>
        <div style={{ opacity: 0.6, color: "var(--ink)" }}>{label}</div>
        <div style={{ fontSize: 12, marginTop: 2, color: "var(--ink)" }}>{value}</div>
      </div>
    </div>
  );
}

// ---------- Pixel link/button ----------
function PixelBtn({ href, kind, children, onClick, target, ...rest }) {
  const cls = `pixel-btn ${kind ? `pixel-btn--${kind}` : ""}`;
  if (href) {
    return <a className={cls} href={href} target={target} rel={target === "_blank" ? "noopener noreferrer" : undefined} {...rest}>{children}</a>;
  }
  return <button type="button" className={cls} onClick={onClick} {...rest}>{children}</button>;
}

// ---------- Quest Log entry — multi-line ticked list ----------
function QuestLog({ entries }) {
  return (
    <ul style={{ listStyle: "none", fontFamily: "var(--font-crt)", fontSize: 22, lineHeight: 1.45 }}>
      {entries.map((e, i) => (
        <li key={i} style={{ display: "flex", gap: 10, alignItems: "flex-start", padding: "6px 0", borderBottom: i < entries.length - 1 ? "2px dashed var(--ink-soft)" : "none" }}>
          <span style={{
            display: "inline-block",
            width: 14, height: 14,
            marginTop: 6,
            background: e.done ? "var(--grass)" : "transparent",
            boxShadow: "0 0 0 2px var(--ink)",
            flexShrink: 0,
          }}>
            {e.done && <span style={{ display: "block", color: "var(--parchment)", fontFamily: "var(--font-pixel)", fontSize: 10, lineHeight: "14px", textAlign: "center" }}>✓</span>}
          </span>
          <span style={{ textDecoration: e.done ? "none" : "none", color: e.done ? "var(--ink)" : "var(--ink-soft)" }}>{e.text}</span>
        </li>
      ))}
    </ul>
  );
}

// ---------- Pixel image placeholder — striped, with monospace caption ----------
function PixelImagePlaceholder({ label, h = 240, color = "river", note }) {
  const colors = {
    river: ["var(--river)", "var(--river-deep)"],
    grass: ["var(--grass)", "var(--grass-deep)"],
    stone: ["#3a3a40", "#1a1a1e"],
    dirt: ["var(--path)", "var(--path-deep)"],
    gold: ["var(--gold)", "var(--gold-deep)"],
  }[color] || ["var(--river)", "var(--river-deep)"];

  return (
    <div style={{
      height: h,
      background: `repeating-linear-gradient(135deg, ${colors[0]} 0 12px, ${colors[1]} 12px 24px)`,
      boxShadow: "inset 0 0 0 4px var(--ink)",
      position: "relative",
      display: "flex",
      flexDirection: "column",
      justifyContent: "center",
      alignItems: "center",
      gap: 8,
      color: "var(--parchment)",
      fontFamily: "var(--font-pixel)",
    }}>
      <div style={{
        background: "var(--ink)",
        padding: "8px 14px",
        fontSize: 11,
        letterSpacing: "0.1em",
        boxShadow: "0 0 0 2px var(--parchment)",
      }}>{label}</div>
      {note && <div style={{ fontFamily: "var(--font-crt)", fontSize: 18, color: "var(--parchment)", textShadow: "2px 2px 0 var(--ink)" }}>{note}</div>}
    </div>
  );
}

// ---------- Pixel sprite (CSS art) — small character/items ----------
function PixelSprite({ kind = "pickaxe", size = 64 }) {
  // Simple CSS-grid pixel sprites — kept small and blocky on purpose
  const sprites = {
    pickaxe: {
      // 8x8 grid, simple pickaxe
      grid: [
        "........",
        "..####..",
        ".#WWWW#.",
        "#WWWW#..",
        "..#W#...",
        "...#W#..",
        "....#W#.",
        ".....##.",
      ],
      colors: { "#": "var(--ink)", "W": "#cfcfcf" }
    },
    coin: {
      grid: [
        "..####..",
        ".#GGGG#.",
        "#GGYYGG#",
        "#GYYYYG#",
        "#GGYYGG#",
        ".#GGGG#.",
        "..####..",
        "........",
      ],
      colors: { "#": "var(--ink)", "G": "var(--gold)", "Y": "var(--gold-deep)" }
    },
    gem: {
      grid: [
        "..####..",
        ".#BBBB#.",
        "#BBBBBB#",
        "#BCCCCB#",
        "#BCCCCB#",
        ".#BBBB#.",
        "..####..",
        "........",
      ],
      colors: { "#": "var(--ink)", "B": "var(--river-deep)", "C": "var(--river)" }
    },
    heart: {
      grid: [
        ".##..##.",
        "#RR##RR#",
        "#RRRRRR#",
        "#RRRRRR#",
        ".#RRRR#.",
        "..#RR#..",
        "...##...",
        "........",
      ],
      colors: { "#": "var(--ink)", "R": "var(--heart)" }
    },
    sword: {
      grid: [
        ".....##.",
        "....#WW#",
        "...#WW#.",
        "..#WW#..",
        ".#WW#...",
        "#WW#....",
        "##......",
        "#.......",
      ],
      colors: { "#": "var(--ink)", "W": "#cfcfcf" }
    },
    chest: {
      grid: [
        "########",
        "#YYYYYY#",
        "#Y####Y#",
        "########",
        "#WWWWWW#",
        "#W#YY#W#",
        "#WWWWWW#",
        "########",
      ],
      colors: { "#": "var(--ink)", "Y": "var(--gold)", "W": "var(--wood)" }
    },
    pc: {
      grid: [
        "########",
        "#GGGGGG#",
        "#G####G#",
        "#G####G#",
        "#GGGGGG#",
        "########",
        "..####..",
        ".######.",
      ],
      colors: { "#": "var(--ink)", "G": "#7dff8a" }
    },
  };

  const s = sprites[kind] || sprites.pickaxe;
  const cell = size / 8;
  return (
    <div style={{
      display: "grid",
      gridTemplateColumns: `repeat(8, ${cell}px)`,
      gridTemplateRows: `repeat(8, ${cell}px)`,
      width: size, height: size,
    }}>
      {s.grid.flatMap((row, r) =>
        row.split("").map((ch, c) => (
          <div key={`${r}-${c}`} style={{
            background: ch === "." ? "transparent" : (s.colors[ch] || "var(--ink)")
          }}></div>
        ))
      )}
    </div>
  );
}

// ---------- Animated 8x8 character (idle bob) ----------
function PixelCharacter({ size = 96 }) {
  // simple character: head, body (red), legs — like the reference player
  const grid = [
    "...####.",
    "..#SSSS#",
    "..#SHHS#",   // hat band
    "..#FFFF#",   // face
    "..#RRRR#",   // body red
    ".#RRRRR#",
    ".#PP##PP",   // pants
    ".##....##",
  ];
  const colors = {
    "#": "var(--ink)",
    "S": "var(--wood)",
    "H": "var(--gold)",
    "F": "#f4c8a8",
    "R": "var(--heart)",
    "P": "var(--river-deep)",
  };
  const cell = size / 8;
  return (
    <div className="pixel-char-bob" style={{
      display: "grid",
      gridTemplateColumns: `repeat(8, ${cell}px)`,
      gridTemplateRows: `repeat(8, ${cell}px)`,
      width: size, height: size,
    }}>
      {grid.flatMap((row, r) =>
        row.split("").map((ch, c) => (
          <div key={`${r}-${c}`} style={{
            background: ch === "." ? "transparent" : (colors[ch] || "var(--ink)")
          }}></div>
        ))
      )}
    </div>
  );
}

// ---------- Typing effect (CRT) ----------
function Typewriter({ lines = [], speed = 30, startDelay = 0 }) {
  const [output, setOutput] = useState([]);
  const [done, setDone] = useState(false);

  useEffect(() => {
    let cancelled = false;
    let timers = [];

    const start = setTimeout(() => {
      let i = 0, j = 0;
      const acc = lines.map(() => "");

      const tick = () => {
        if (cancelled) return;
        if (i >= lines.length) { setDone(true); return; }
        if (j >= lines[i].length) { i++; j = 0; timers.push(setTimeout(tick, 200)); return; }
        acc[i] = lines[i].slice(0, j + 1);
        setOutput([...acc]);
        j++;
        timers.push(setTimeout(tick, speed));
      };
      tick();
    }, startDelay);

    return () => {
      cancelled = true;
      clearTimeout(start);
      timers.forEach(clearTimeout);
    };
  }, []);

  return (
    <div>
      {output.map((line, i) => <div key={i}>{line}{i === output.length - 1 && !done && <span className="cursor-blink">▌</span>}</div>)}
    </div>
  );
}

// ---------- Section divider — pixel border with title ----------
function PixelDivider({ children }) {
  return (
    <div style={{
      display: "flex",
      alignItems: "center",
      gap: 16,
      margin: "20px 0",
    }}>
      <div style={{ flex: 1, height: 4, background: "var(--ink)" }}></div>
      {children && <span className="px-xs" style={{ background: "var(--parchment)", padding: "6px 10px", boxShadow: "0 0 0 3px var(--ink)" }}>{children}</span>}
      <div style={{ flex: 1, height: 4, background: "var(--ink)" }}></div>
    </div>
  );
}

// Export to window so other Babel scripts can use them
Object.assign(window, {
  HeartRow, Panel, Badge, Chapter, StatLine, CounterHUD, PixelBtn,
  QuestLog, PixelImagePlaceholder, PixelSprite, PixelCharacter,
  Typewriter, PixelDivider,
});
