// ArmoireB3.jsx — Full stock view: KPI row, floor plan, drawer.
// B3 drawer shows live sensor items; all others show static data.

const LINEN = ["Draps coton bio", "Taies d'oreiller", "Alèses", "Blouses patient", "Linges de toilette", "Couvertures"];

function mkArmoire(id, name, fill, levels) {
  const status = fill < 15 ? "out" : fill < 40 ? "low" : "ok";
  return { id, name, fill, status, items: LINEN.map((l, i) => ({ name: l, ...levels[i] })) };
}

const ARMOIRES_STATIC = [
  mkArmoire("A1", "Armoire A1", 82, [{pct:88,qty:44,par:50},{pct:80,qty:32,par:40},{pct:74,qty:22,par:30},{pct:90,qty:27,par:30},{pct:85,qty:51,par:60},{pct:70,qty:14,par:20}]),
  mkArmoire("A2", "Armoire A2", 76, [{pct:78,qty:39,par:50},{pct:72,qty:29,par:40},{pct:80,qty:24,par:30},{pct:70,qty:21,par:30},{pct:82,qty:49,par:60},{pct:65,qty:13,par:20}]),
  mkArmoire("A3", "Armoire A3", 38, [{pct:30,qty:15,par:50},{pct:45,qty:18,par:40},{pct:33,qty:10,par:30},{pct:40,qty:12,par:30},{pct:48,qty:29,par:60},{pct:25,qty:5,par:20}]),
  mkArmoire("A4", "Armoire A4", 41, [{pct:42,qty:21,par:50},{pct:38,qty:15,par:40},{pct:50,qty:15,par:30},{pct:35,qty:10,par:30},{pct:44,qty:26,par:60},{pct:36,qty:7,par:20}]),
  mkArmoire("A5", "Armoire A5", 91, [{pct:95,qty:48,par:50},{pct:90,qty:36,par:40},{pct:88,qty:26,par:30},{pct:93,qty:28,par:30},{pct:90,qty:54,par:60},{pct:85,qty:17,par:20}]),
  mkArmoire("A6", "Armoire A6", 84, [{pct:86,qty:43,par:50},{pct:82,qty:33,par:40},{pct:80,qty:24,par:30},{pct:88,qty:26,par:30},{pct:84,qty:50,par:60},{pct:78,qty:16,par:20}]),
  mkArmoire("B1", "Armoire B1", 44, [{pct:46,qty:23,par:50},{pct:40,qty:16,par:40},{pct:50,qty:15,par:30},{pct:42,qty:13,par:30},{pct:48,qty:29,par:60},{pct:38,qty:8,par:20}]),
  mkArmoire("B2", "Armoire B2", 9,  [{pct:6,qty:3,par:50},{pct:12,qty:5,par:40},{pct:10,qty:3,par:30},{pct:7,qty:2,par:30},{pct:14,qty:8,par:60},{pct:5,qty:1,par:20}]),
  mkArmoire("B3", "Armoire B3", 12, [{pct:10,qty:5,par:50},{pct:15,qty:6,par:40},{pct:13,qty:4,par:30},{pct:9,qty:3,par:30},{pct:16,qty:10,par:60},{pct:8,qty:2,par:20}]),
  mkArmoire("B4", "Armoire B4", 79, [{pct:80,qty:40,par:50},{pct:76,qty:30,par:40},{pct:82,qty:25,par:30},{pct:78,qty:23,par:30},{pct:80,qty:48,par:60},{pct:72,qty:14,par:20}]),
  mkArmoire("B5", "Armoire B5", 88, [{pct:90,qty:45,par:50},{pct:85,qty:34,par:40},{pct:86,qty:26,par:30},{pct:92,qty:28,par:30},{pct:88,qty:53,par:60},{pct:82,qty:16,par:20}]),
  mkArmoire("B6", "Armoire B6", 81, [{pct:84,qty:42,par:50},{pct:78,qty:31,par:40},{pct:80,qty:24,par:30},{pct:82,qty:25,par:30},{pct:84,qty:50,par:60},{pct:76,qty:15,par:20}]),
];

const DOT = { ok: "#A0A0BE", low: "#6B6D90", out: "#fff" };
const STLABEL = { ok: "Plein", low: "Sous seuil", out: "Rupture" };

const POS = {
  A1: { x: 9.29,  y: 34.35 }, A2: { x: 24.29, y: 34.35 }, A3: { x: 39.29, y: 34.35 },
  A4: { x: 9.29,  y: 65.65 }, A5: { x: 24.29, y: 65.65 }, A6: { x: 39.29, y: 65.65 },
  B1: { x: 60.71, y: 34.35 }, B2: { x: 75.71, y: 34.35 }, B3: { x: 90.71, y: 34.35 },
  B4: { x: 60.71, y: 65.65 }, B5: { x: 75.71, y: 65.65 }, B6: { x: 90.71, y: 65.65 },
};
const NAVY = "#2E3770", RULE_C = "#D0CFE0";

// --- helpers ---

function formatTime(isoStr) {
  if (!isoStr) return "—";
  try {
    return new Date(isoStr).toLocaleTimeString("fr-CH", { hour: "2-digit", minute: "2-digit", second: "2-digit" });
  } catch (e) { return isoStr; }
}

function timeSince(isoStr) {
  if (!isoStr) return "";
  try {
    var diff = Math.floor((Date.now() - new Date(isoStr).getTime()) / 1000);
    if (diff < 60) return "il y a " + diff + "s";
    if (diff < 3600) return "il y a " + Math.floor(diff / 60) + "min";
    return "il y a " + Math.floor(diff / 3600) + "h";
  } catch (e) { return ""; }
}

function getB3WithSensors(sensorData) {
  var base = ARMOIRES_STATIC.find(a => a.id === "B3");
  var laserLayers = sensorData.laser ? sensorData.laser.layers : null;
  var ultrasonLayers = sensorData.ultrason ? sensorData.ultrason.layers : null;

  var liveQty = 0, livePar = 0;
  if (laserLayers !== null) { liveQty += laserLayers; livePar += 9; }
  if (ultrasonLayers !== null) { liveQty += ultrasonLayers; livePar += 9; }
  var staticQty = base.items.reduce((a, it) => a + it.qty, 0);
  var staticPar = base.items.reduce((a, it) => a + it.par, 0);
  var totalPar = staticPar + livePar;
  var totalQty = staticQty + liveQty;
  var fill = totalPar > 0 ? Math.round((totalQty / totalPar) * 100) : base.fill;
  var status = fill < 15 ? "out" : fill < 40 ? "low" : "ok";

  return { ...base, fill, status };
}

function getArmoires(sensorData) {
  return ARMOIRES_STATIC.map(a => a.id === "B3" ? getB3WithSensors(sensorData) : a);
}

// --- KPI row ---

function KpiRow({ sensorData }) {
  var armoires = getArmoires(sensorData);
  var lowCount = armoires.filter(a => a.status === "low" || a.status === "out").length;

  return (
    <div className="kpis">
      <div className="kpi">
        <div className="lab">Consommation inhabituelle</div>
        <div className="val">{lowCount} <small>armoires</small></div>
      </div>
      <div className="kpi">
        <div className="lab">À charger</div>
        <div className="val">67 <small>pièces</small></div>
      </div>
      <div className="kpi">
        <div className="lab">Réserve de linge</div>
        <div className="val">28h</div>
      </div>
    </div>
  );
}

// --- floor plan SVG ---

function FloorPlanSVG() {
  const dividers = [188, 356, 764, 932];
  const topRoomNos = [["201", 104], ["202", 272], ["203", 440], ["211", 680], ["212", 848], ["213", 1016]];
  const botRoomNos = [["204", 104], ["205", 272], ["206", 440], ["214", 680], ["215", 848], ["216", 1016]];
  const doorsTop = [104, 272, 440, 680, 848, 1016];
  const doorsBot = [104, 272, 440, 680, 848, 1016];
  return (
    <svg viewBox="0 0 1120 460" xmlns="http://www.w3.org/2000/svg">
      <rect x="20" y="190" width="1080" height="80" fill="#F3F3F8" />
      <rect x="524" y="20" width="72" height="420" fill="#E7E6EE" />
      {dividers.map(x => (
        <g key={x} stroke={RULE_C} strokeWidth="1.5">
          <line x1={x} y1="20" x2={x} y2="190" />
          <line x1={x} y1="270" x2={x} y2="440" />
        </g>
      ))}
      <g stroke={NAVY} strokeWidth="1.5">
        <line x1="20" y1="190" x2="524" y2="190" />
        <line x1="596" y1="190" x2="1100" y2="190" />
        <line x1="20" y1="270" x2="524" y2="270" />
        <line x1="596" y1="270" x2="1100" y2="270" />
      </g>
      {doorsTop.map(cx => <rect key={"t"+cx} x={cx-18} y="187" width="36" height="6" fill="#F3F3F8" />)}
      {doorsBot.map(cx => <rect key={"b"+cx} x={cx-18} y="267" width="36" height="6" fill="#F3F3F8" />)}
      <rect x="524" y="20" width="72" height="420" fill="none" stroke={NAVY} strokeWidth="1.5" />
      <rect x="521" y="207" width="6" height="46" fill="#E7E6EE" />
      <rect x="593" y="207" width="6" height="46" fill="#E7E6EE" />
      <rect x="20" y="20" width="1080" height="420" fill="none" stroke={NAVY} strokeWidth="2" />
      <g fill={RULE_C} fontSize="13" fontWeight="600" fontFamily="inherit" textAnchor="middle">
        {topRoomNos.map(([n, x]) => <text key={"tn"+x} x={x} y="44">Ch. {n}</text>)}
        {botRoomNos.map(([n, x]) => <text key={"bn"+x} x={x} y="430">Ch. {n}</text>)}
      </g>
      <g fill="#A0A0BE" fontSize="11" fontWeight="600" fontFamily="inherit" letterSpacing="3" textAnchor="middle">
        <text x="272" y="234">COULOIR</text>
        <text x="848" y="234">COULOIR</text>
      </g>
    </svg>
  );
}

// --- floor plan marker ---

function Marker({ a, selected, onClick, isLive }) {
  const p = POS[a.id];
  return (
    <button className={"fp-marker" + (a.status === "out" ? " out" : "") + (selected ? " sel" : "")}
            style={{ left: p.x + "%", top: p.y + "%" }} onClick={onClick}>
      <div className="r1">
        <span className="nm">
          {a.name}
          {false && isLive && <span className="live-dot-sm" />}
        </span>
        <span className="dot" style={{ background: DOT[a.status] }} />
      </div>
      <div className="pct">{a.fill}%</div>
      <div className="mini"><i style={{ width: a.fill + "%" }} /></div>
    </button>
  );
}

// --- floor plan panel ---

function FloorPlan({ armoires, onSelect, selectedId }) {
  return (
    <div className="panel">
      <div className="panelhead">
        <h2>Plan d'étage — niveaux de stock</h2>
        <div className="legend">
          <span className="it"><span className="dot" style={{ background: "#A0A0BE" }} />Plein</span>
          <span className="it"><span className="dot" style={{ background: "#6B6D90" }} />Sous seuil</span>
          <span className="it inv"><span className="dot" />Rupture</span>
        </div>
      </div>
      <div className="map">
        <div className="fp-wings"><span>Aile A — Niveau 2</span><span>Aile B — Niveau 2</span></div>
        <div className="floorplan">
          <FloorPlanSVG />
          {armoires.map(a => (
            <Marker key={a.id} a={a} selected={selectedId === a.id}
                    onClick={() => onSelect(a)} isLive={a.id === "B3"} />
          ))}
          <div className="fp-reserve" style={{ left: "50%", top: "50%" }}>
            <span className="ic"><Icon name="warehouse" size={20} /></span>
            <span className="tg">Réserve</span>
          </div>
        </div>
      </div>
    </div>
  );
}

// --- drawer: B3 has live sensor items, others show static items ---

function ArmoireDrawer({ armoire, onClose, sensorData }) {
  const open = !!armoire;
  const isB3 = armoire && armoire.id === "B3";
  const out = armoire && armoire.status === "out";

  return (
    <React.Fragment>
      <div className={"scrim" + (open ? " open" : "")} onClick={onClose} />
      <aside className={"drawer" + (open ? " open" : "")}>
        {armoire && (
          <React.Fragment>
            <div className="dh">
              <div>
                <div className="zl">{armoire.id.startsWith("A") ? "Aile A — Niveau 2" : "Aile B — Niveau 2"} · STOCK</div>
                <h3>{armoire.name}</h3>
                <span className={"statuspill" + (out ? " out" : "")}>
                  <span className="d" />{STLABEL[armoire.status]} · {armoire.fill}%
                </span>
              </div>
              <button className="closebtn" onClick={onClose}><Icon name="x" size={20} /></button>
            </div>
            <div className="dbody">
              {isB3 && (
                <React.Fragment>
                  <LiveItem label="Couches" sensorName="laser" data={sensorData.laser} />
                  <LiveItem label="Alèses" sensorName="ultrason" data={sensorData.ultrason} />
                </React.Fragment>
              )}
              {armoire.items.map(it => (
                <div className="linerow" key={it.name}>
                  <div className="top">
                    <span className="nm">{it.name}</span>
                    <span className="q">{it.qty} / {it.par}</span>
                  </div>
                  <div className="track"><div className={"fill" + (it.pct < 40 ? " low" : "")} style={{ width: it.pct + "%" }} /></div>
                </div>
              ))}
            </div>
            {isB3 && <DiagnosticToggle sensorData={sensorData} />}
          </React.Fragment>
        )}
      </aside>
    </React.Fragment>
  );
}

// --- live sensor line item ---

function LiveItem({ label, sensorName, data }) {
  var layers = data ? data.layers : null;
  var par = 9;
  var pct = layers !== null ? Math.round((layers / par) * 100) : 0;
  var isLow = layers !== null && layers < 4;

  return (
    <div className="linerow">
      <div className="top">
        <span className="nm">{label}</span>
        <span className="q">
          {layers !== null ? (layers + " / " + par) : "— / " + par}
        </span>
      </div>
      <div className="track">
        <div className="fill" style={{ width: pct + "%" }} />
      </div>
    </div>
  );
}

// --- live "il y a Xs" counter ---

function TimeSince({ isoStr }) {
  var [now, setNow] = React.useState(Date.now());
  React.useEffect(function () {
    var id = setInterval(function () { setNow(Date.now()); }, 1000);
    return function () { clearInterval(id); };
  }, []);
  if (!isoStr) return <span>—</span>;
  var diff = Math.floor((now - new Date(isoStr).getTime()) / 1000);
  if (diff < 0) diff = 0;
  var text;
  if (diff < 60) text = "il y a " + diff + "s";
  else if (diff < 3600) text = "il y a " + Math.floor(diff / 60) + "min";
  else text = "il y a " + Math.floor(diff / 3600) + "h";
  return <span>{text}</span>;
}

// --- collapsible diagnostic panel ---

function DiagnosticToggle({ sensorData }) {
  const [open, setOpen] = React.useState(false);
  return (
    <div className="diag-toggle">
      <button className="diag-btn" onClick={() => setOpen(o => !o)}>
        <Icon name={open ? "chevron-down" : "chevron-right"} size={16} />
        Diagnostic capteurs
      </button>
      {open && (
        <div className="diag-body">
          <div className="debug-grid">
            <div>
              <div className="debug-section-title">Laser</div>
              {sensorData.laser ? (
                <React.Fragment>
                  <div className="debug-row"><span className="label">Distance</span><span className="value">{sensorData.laser.distance_mm} mm</span></div>
                  <div className="debug-row"><span className="label">Couches</span><span className="value">{sensorData.laser.layers} / 9</span></div>
                  <div className="debug-row"><span className="label">Confiance</span><span className="value">{Math.round(sensorData.laser.confidence * 100)}%</span></div>
                  <div className="debug-row"><span className="label">Flag</span><span className="value">{sensorData.laser.flag}</span></div>
                  <div className="debug-row"><span className="label">Dernière MAJ</span><span className="value"><TimeSince isoStr={sensorData.laser.received_at} /></span></div>
                </React.Fragment>
              ) : (
                <div className="debug-row"><span className="label">Status</span><span className="value">Aucune donnée</span></div>
              )}
            </div>
            <div>
              <div className="debug-section-title">Ultrason</div>
              {sensorData.ultrason ? (
                <React.Fragment>
                  <div className="debug-row"><span className="label">Distance</span><span className="value">{sensorData.ultrason.distance_mm} mm</span></div>
                  <div className="debug-row"><span className="label">Couches</span><span className="value">{sensorData.ultrason.layers} / 9</span></div>
                  <div className="debug-row"><span className="label">Confiance</span><span className="value">{Math.round(sensorData.ultrason.confidence * 100)}%</span></div>
                  <div className="debug-row"><span className="label">Flag</span><span className="value">{sensorData.ultrason.flag}</span></div>
                  <div className="debug-row"><span className="label">Dernière MAJ</span><span className="value"><TimeSince isoStr={sensorData.ultrason.received_at} /></span></div>
                </React.Fragment>
              ) : (
                <div className="debug-row"><span className="label">Status</span><span className="value">Aucune donnée</span></div>
              )}
            </div>
          </div>
        </div>
      )}
    </div>
  );
}

// --- stock view: alert + KPIs + floor plan ---

function StockView({ sensorData, pollStatus, corsMode, selected, onSelect }) {
  var armoires = getArmoires(sensorData);
  var ruptureCount = armoires.filter(a => a.status === "out").length;

  return (
    <React.Fragment>
      {ruptureCount > 0 && (
        <button className="alert" onClick={() => onSelect(armoires.find(a => a.id === "B3"))}>
          <span className="dot" />
          {ruptureCount} armoire{ruptureCount > 1 ? "s" : ""} en rupture — Aile B, niveau 2
          <span className="chev"><Icon name="chevron-right" size={20} /></span>
        </button>
      )}
      <KpiRow sensorData={sensorData} />
      <FloorPlan armoires={armoires} onSelect={onSelect} selectedId={selected && selected.id} />
    </React.Fragment>
  );
}

Object.assign(window, { StockView, ArmoireDrawer, getArmoires });
