/* Sidebar.jsx — Play + Make panels and small parts. Exports window.PlayPanel, window.MakePanel */
const { useRef: useRefSB } = React;

function Hearts({ lives, max }) {
  return (
    <div className="hearts" aria-label={lives + " lives left"}>
      {Array.from({ length: max }).map((_, i) => (
        <span key={i} className={"heart" + (i < lives ? "" : " gone")}>♥</span>
      ))}
    </div>
  );
}

function Thumb({ puzzle, solved, size }) {
  size = size || 44;
  const cell = size / Math.max(puzzle.rows, puzzle.cols);
  return (
    <div className={"thumb" + (solved ? " solved" : "")} style={{ width: size, height: size }}>
      {solved ? (
        <div className="thumb-grid" style={{ gridTemplateColumns: `repeat(${puzzle.cols}, 1fr)`, gridTemplateRows: `repeat(${puzzle.rows}, 1fr)` }}>
          {puzzle.colorSolution.map((row, r) =>
            row.map((col, c) => (
              <span key={r + "-" + c} style={{ background: col === "transparent" ? "transparent" : col }} />
            ))
          )}
        </div>
      ) : (
        <span className="thumb-q">?</span>
      )}
    </div>
  );
}

function PlayPanel({
  puzzles, currentId, solvedMap, onSelect,
  lives, zen, time, won, dead, onReset, onHint, hintsLeft, onImportJSON,
  dailyLabel, dailyDone, streak, onPlayDaily, onOpenStats, dailyActive, onOpenLibrary,
}) {
  const fileRef = useRefSB(null);
  const cur = puzzles.find((p) => p.id === currentId);
  const solvedTotal = puzzles.filter((p) => solvedMap[p.id] != null).length;
  const pctTotal = Math.round((solvedTotal / puzzles.length) * 100);
  const shuffleUnsolved = () => {
    const pool = puzzles.filter((p) => solvedMap[p.id] == null);
    const list = pool.length ? pool : puzzles;
    const pick = list[Math.floor(Math.random() * list.length)];
    if (pick) onSelect(pick.id);
  };
  return (
    <div className="panel-inner">
      <div className="top-actions">
        <button className={"daily-btn" + (dailyActive ? " active" : "")} onClick={onPlayDaily}>
          <div className="daily-l">
            <span className="daily-k">Daily Puzzle</span>
            <span className="daily-date">{dailyLabel}</span>
          </div>
          <div className="daily-r">
            {streak > 0 && <span className="streak">▲{streak}</span>}
            {dailyDone && <span className="daily-chk">✓ done</span>}
          </div>
        </button>
        <button className="stats-btn" onClick={onOpenStats} title="Player card" aria-label="Player card">▤</button>
      </div>

      <div className="now-playing">
        <div className="np-label">Now solving</div>
        <div className="np-name">{cur ? cur.name : "—"}</div>
        <div className="np-meta">
          <span>{cur ? cur.rows + "×" + cur.cols : ""}</span>
          <span className="dot-sep">·</span>
          <span>{cur ? cur.level : ""}</span>
        </div>
      </div>

      <div className="play-status">
        {zen ? (
          <div className="zen-tag">Zen — no mistakes counted</div>
        ) : (
          <div className="status-row">
            <span className="sr-label">Lives</span>
            <Hearts lives={dead ? 0 : lives} max={3} />
          </div>
        )}
        <div className="status-row">
          <span className="sr-label">Time</span>
          <span className="timer">{Engine.fmtTime(time)}</span>
        </div>
      </div>

      <div className="btn-row">
        <button className="btn" onClick={onReset}>Reset</button>
        <button className="btn" onClick={onHint} disabled={won || dead || hintsLeft <= 0}>
          Hint{hintsLeft > 0 ? " · " + hintsLeft : ""}
        </button>
      </div>

      <div className="sep" />

      <div className="lib-head">
        <span className="lib-title">Library</span>
        <span className="lib-count lib-count-total">{solvedTotal}/{puzzles.length} solved</span>
      </div>
      <div className="browse-bar"><span className="browse-bar-fill" style={{ width: pctTotal + "%" }} /></div>
      <div className="btn-row">
        <button className="btn primary" onClick={onOpenLibrary}>Browse →</button>
        <button className="btn" onClick={shuffleUnsolved} title="Jump to a random unsolved puzzle">Shuffle</button>
      </div>

      <div className="sep" />
      <button className="btn ghost wide" onClick={() => fileRef.current && fileRef.current.click()}>Load .json puzzle</button>
      <input ref={fileRef} type="file" accept="application/json,.json" hidden onChange={(e) => { const f = e.target.files && e.target.files[0]; if (f) onImportJSON(f); e.target.value = ""; }} />
    </div>
  );
}

function MakePanel({
  rows, cols, setRows, setCols, filled,
  onClear, onLoadInPlayer,
  onImportImage, importStatus, importSize, setImportSize, threshold, setThreshold, invert, setInvert,
  showColorPreview, toggleColorPreview, hasColor,
  onExportJSON, onExportPNG, makeColored, setMakeColored,
}) {
  const imgRef = useRefSB(null);
  const clampDim = (v) => Math.max(5, Math.min(30, Number(v) || 5));
  return (
    <div className="panel-inner">
      <div className="now-playing">
        <div className="np-label">Drafting table</div>
        <div className="np-name">Make a puzzle</div>
        <div className="np-meta"><span>{filled} cells inked</span></div>
      </div>

      <div className="field">
        <label className="field-label">Dimensions</label>
        <div className="dim-row">
          <input className="num" type="number" min={5} max={30} value={rows} onChange={(e) => setRows(clampDim(e.target.value))} />
          <span className="dim-x">×</span>
          <input className="num" type="number" min={5} max={30} value={cols} onChange={(e) => setCols(clampDim(e.target.value))} />
        </div>
      </div>

      <label className="check-row">
        <input type="checkbox" checked={makeColored} onChange={(e) => setMakeColored(e.target.checked)} />
        <span>Color mode — paint a palette</span>
      </label>

      <div className="btn-row">
        <button className="btn" onClick={onClear}>Clear</button>
        <button className="btn primary" onClick={onLoadInPlayer}>Play it →</button>
      </div>

      <div className="sep" />

      <div className="field">
        <label className="field-label">Trace an image</label>
        <button className="btn ghost wide" onClick={() => imgRef.current && imgRef.current.click()}>Choose image…</button>
        <input ref={imgRef} type="file" accept="image/*" hidden onChange={(e) => { const f = e.target.files && e.target.files[0]; if (f) onImportImage(f); e.target.value = ""; }} />
        <div className="mini-controls">
          <div className="mini-row">
            <span className="mini-label">Size {importSize}</span>
            <input type="range" min={8} max={30} value={importSize} onChange={(e) => setImportSize(Number(e.target.value))} />
          </div>
          <div className="mini-row">
            <span className="mini-label">Threshold {threshold}</span>
            <input type="range" min={20} max={235} value={threshold} onChange={(e) => setThreshold(Number(e.target.value))} />
          </div>
          <label className="check-row">
            <input type="checkbox" checked={invert} onChange={(e) => setInvert(e.target.checked)} />
            <span>Invert</span>
          </label>
        </div>
        {importStatus && <div className="import-status">{importStatus}</div>}
      </div>

      {hasColor && (
        <label className="check-row">
          <input type="checkbox" checked={showColorPreview} onChange={toggleColorPreview} />
          <span>Show color preview</span>
        </label>
      )}

      <div className="sep" />
      <div className="btn-row">
        <button className="btn ghost" onClick={onExportJSON}>Export JSON</button>
        <button className="btn ghost" onClick={onExportPNG}>Export PNG</button>
      </div>

      <div className="hint-card">
        <strong>Left-click</strong> ink a cell · <strong>drag</strong> to paint a run. Clues update live on the board.
      </div>
    </div>
  );
}

window.PlayPanel = PlayPanel;
window.MakePanel = MakePanel;
window.Thumb = Thumb;
