// VIEW 3 — Map. Dark field atlas, now backed by Mapbox GL JS v3.
//
// 3-column layout: property index rail / atlas / season feed.
//
// Mapbox integration:
//   - init once on mount, with dark-v11 style and the whole prairie in view
//   - one HTML marker per property, coloured by dominant-ownership rollup
//   - selecting a property (here, from the other views, or via "Zoom Mapbox →"
//     in the drawer) flies the camera to that block at zoom ~10
//   - satellite toggle swaps between dark-v11 and satellite-streets-v12
const MapView = ({ forcedSelect, onSwitchView }) => {
  const [sel, setSel] = useState(null);
  const [hover, setHover] = useState(null);
  const [satellite, setSatellite] = useState(false);
  const [mapReady, setMapReady] = useState(false);

  const mapContainerRef = useRef(null);
  const mapRef = useRef(null);
  const markersRef = useRef({}); // propId -> { marker, element }

  const rollups = useMemo(() => {
    const m = {};
    D.properties.forEach((p) => { m[p.id] = rollupProperty(p.id).rollup; });
    return m;
  }, []);

  // Pick the colour for a property's marker based on which ownership state
  // dominates its rollup. Falls back to "owned" when counts tie.
  const dominantColor = (id) => {
    const r = rollups[id];
    if (r.sold   > r.owned && r.sold   > r.rented) return OWN.sold.color;
    if (r.rented > r.owned)                        return OWN["rented-monette"].color;
    return OWN["owned-monette"].color;
  };

  // ── init map once ────────────────────────────────────────────────
  useEffect(() => {
    if (!mapContainerRef.current || mapRef.current) return;
    if (!window.mapboxgl) return; // mapbox-gl CDN not yet loaded

    window.mapboxgl.accessToken = window.MAPBOX_TOKEN;
    const map = new window.mapboxgl.Map({
      container: mapContainerRef.current,
      style: window.MAPBOX_STYLE_DARK,
      center: window.MAPBOX_HOME.center,
      zoom: window.MAPBOX_HOME.zoom,
      attributionControl: true,
      projection: "mercator",
    });
    map.addControl(new window.mapboxgl.NavigationControl({ visualizePitch: false }), "bottom-right");
    map.on("load", () => setMapReady(true));
    mapRef.current = map;

    return () => { map.remove(); mapRef.current = null; };
  }, []);

  // ── add markers once map is ready ───────────────────────────────
  useEffect(() => {
    const map = mapRef.current;
    if (!map || !mapReady) return;

    // Clear any prior markers (style changes keep them, but safe to re-sync).
    Object.values(markersRef.current).forEach(({ marker }) => marker.remove());
    markersRef.current = {};

    D.properties.forEach((p) => {
      const color = dominantColor(p.id);
      const size = Math.max(14, Math.round(Math.sqrt(p.titled) / 9));

      const el = document.createElement("div");
      el.className = "mb-pin";
      el.style.width  = size + "px";
      el.style.height = size + "px";
      el.style.background = color;
      el.style.color = color;
      el.style.border = `2px solid ${color}`;
      el.style.opacity = "0.82";

      const label = document.createElement("div");
      label.className = "mb-pin-label";
      label.textContent = p.name;
      el.appendChild(label);

      const ac = document.createElement("div");
      ac.className = "mb-pin-ac";
      ac.textContent = fmt(p.titled) + " ac";
      el.appendChild(ac);

      el.addEventListener("click", (e) => {
        e.stopPropagation();
        setSel(p);
      });
      el.addEventListener("mouseenter", () => setHover(p));
      el.addEventListener("mouseleave", () => setHover(null));

      const marker = new window.mapboxgl.Marker({ element: el, anchor: "center" })
        .setLngLat([p.lng, p.lat])
        .addTo(map);

      markersRef.current[p.id] = { marker, element: el };
    });
  }, [mapReady]);

  // ── highlight + flyTo on selection ──────────────────────────────
  useEffect(() => {
    Object.entries(markersRef.current).forEach(([id, { element }]) => {
      element.classList.toggle("is-active", sel?.id === id);
    });
    if (sel && mapRef.current) {
      mapRef.current.flyTo({ center: [sel.lng, sel.lat], zoom: 9.5, duration: 2000, essential: true });
    }
  }, [sel]);

  // ── forced select from a cross-view deep-link ───────────────────
  useEffect(() => {
    if (forcedSelect) {
      const p = D.properties.find((x) => x.id === forcedSelect);
      if (p) setSel(p);
    }
  }, [forcedSelect]);

  // ── satellite toggle ────────────────────────────────────────────
  useEffect(() => {
    const map = mapRef.current;
    if (!map || !mapReady) return;
    map.setStyle(satellite ? window.MAPBOX_STYLE_SATELLITE : window.MAPBOX_STYLE_DARK);
    // style swap clears markers; re-add when the new style is idle
    map.once("style.load", () => setMapReady((m) => m && true));
  }, [satellite]);

  const hoverOrSel = hover || sel;

  return (
    <div style={{ minHeight: "100%", background: "var(--night)", color: "var(--paper)", fontSize: 13 }}>
      <div style={{ padding: "16px 28px", borderBottom: "1px solid #2a2620", display: "flex", justifyContent: "space-between", alignItems: "center" }}>
        <div style={{ display: "flex", alignItems: "baseline", gap: 18 }}>
          <div className="serif" style={{ fontSize: 26, color: "var(--paper)" }}>Monette · Field Atlas</div>
          <div style={{ fontFamily: '"JetBrains Mono", monospace', fontSize: 10, letterSpacing: "0.1em", color: "#8a7f6e" }}>● LIVE · CCAA DAY 0 · APR 21, 2026</div>
        </div>
        <div style={{ display: "flex", gap: 12 }}>
          <button
            onClick={() => setSatellite((s) => !s)}
            className="btn"
            style={{
              background: satellite ? "var(--paper)" : "transparent",
              color: satellite ? "var(--ink)" : "var(--paper)",
              borderColor: satellite ? "var(--paper)" : "#3a342a",
            }}>
            {satellite ? "Dark" : "Satellite"}
          </button>
          <button className="btn btn-dark" style={{ background: "var(--paper)", color: "var(--ink)" }}>Submit tip</button>
        </div>
      </div>
      <HeadlineTicker dark />
      <div style={{ display: "grid", gridTemplateColumns: "320px 1fr 360px", minHeight: 780 }}>
        {/* Property index */}
        <div className="scroll" style={{ borderRight: "1px solid #2a2620", padding: "18px 20px", maxHeight: 780, overflowY: "auto" }}>
          <div style={{ fontSize: 10, letterSpacing: "0.12em", textTransform: "uppercase", color: "#8a7f6e", marginBottom: 12 }}>PROPERTIES</div>
          {D.properties.map((p) => {
            const active = sel?.id === p.id;
            const r = rollups[p.id];
            return (
              <div key={p.id}
                onMouseEnter={() => setHover(p)} onMouseLeave={() => setHover(null)}
                onClick={() => setSel(p)}
                style={{
                  padding: "10px 10px",
                  borderLeft: active ? `3px solid ${OWN["owned-monette"].color}` : "3px solid transparent",
                  background: active ? "#1e1b16" : "transparent",
                  cursor: "pointer", marginBottom: 2,
                }}>
                <div style={{ display: "flex", justifyContent: "space-between" }}>
                  <span className="serif" style={{ fontSize: 20 }}>{p.name}</span>
                  <span style={{ fontFamily: '"JetBrains Mono", monospace', fontSize: 10, color: "#8a7f6e" }}>{p.province}</span>
                </div>
                <div style={{ fontFamily: '"JetBrains Mono", monospace', fontSize: 10, color: "#8a7f6e", marginTop: 2 }}>{fmt(p.titled)} ac · {p.parcels} parcels</div>
                <div style={{ marginTop: 6, height: 4, display: "flex", background: "#2a2620" }}>
                  {[
                    ["owned",   r.owned,   OWN["owned-monette"].color],
                    ["rented",  r.rented,  OWN["rented-monette"].color],
                    ["sold",    r.sold,    OWN.sold.color],
                    ["unknown", r.unknown, OWN.unknown.color],
                  ].map(([k, v, c]) =>
                    v ? <div key={k} style={{ width: `${(v / (r.total || 1)) * 100}%`, background: c }} /> : null
                  )}
                </div>
              </div>
            );
          })}
        </div>

        {/* Atlas — real Mapbox GL JS map */}
        <div style={{ position: "relative", background: "#0e0c09", padding: 24 }}>
          <div style={{ height: "100%", background: "#13110e", border: "1px solid #2a2620", position: "relative", overflow: "hidden" }}>
            <div ref={mapContainerRef} className="mb-container" />

            <div style={{
              position: "absolute", top: 14, right: 14,
              fontFamily: '"JetBrains Mono", monospace', fontSize: 10,
              color: "#b48638",
              background: "rgba(19,17,14,0.85)",
              border: "1px solid #3a342a", padding: "4px 8px",
            }}>
              ● MAPBOX · LIVE
            </div>

            {hoverOrSel && (
              <div style={{ position: "absolute", top: 14, left: 14, background: "rgba(30,27,22,0.95)", border: "1px solid #3a342a", padding: 14, width: 280, pointerEvents: "none" }}>
                <div style={{ fontSize: 10, letterSpacing: "0.1em", textTransform: "uppercase", color: "#8a7f6e" }}>{hoverOrSel.province} · {hoverOrSel.region}</div>
                <div className="serif" style={{ fontSize: 30, lineHeight: 1, marginTop: 4, color: "var(--paper)" }}>{hoverOrSel.name}</div>
                <div style={{ marginTop: 10 }}><RollupBar rollup={rollups[hoverOrSel.id]} /></div>
                <div style={{ marginTop: 8, fontFamily: '"JetBrains Mono", monospace', fontSize: 10, color: "var(--paper)", display: "grid", gridTemplateColumns: "1fr 1fr", gap: 4 }}>
                  <span>Titled</span>   <span style={{ textAlign: "right" }}>{fmt(hoverOrSel.titled)}</span>
                  <span>Parcels</span>  <span style={{ textAlign: "right" }}>{hoverOrSel.parcels}</span>
                  <span>Seeded q</span> <span style={{ textAlign: "right", color: "#5a7a3a" }}>{rollups[hoverOrSel.id].seeded}</span>
                  <span>Sold q</span>   <span style={{ textAlign: "right", color: OWN.sold.color }}>{rollups[hoverOrSel.id].sold}</span>
                </div>
              </div>
            )}
          </div>
        </div>

        {/* Season feed */}
        <div style={{ borderLeft: "1px solid #2a2620", padding: "18px 20px" }}>
          <div style={{ fontSize: 10, letterSpacing: "0.12em", textTransform: "uppercase", color: "#8a7f6e", marginBottom: 12 }}>SEASON FEED · FIRST TO SEE IT</div>
          <div style={{ display: "grid", gap: 10 }}>
            {D.properties.slice(0, 6).map((p) => {
              const r = rollups[p.id];
              return (
                <div key={p.id} onClick={() => setSel(p)} style={{ padding: "10px 12px", border: "1px solid #2a2620", background: "#1a1813", cursor: "pointer" }}>
                  <div style={{ display: "flex", justifyContent: "space-between", alignItems: "baseline" }}>
                    <span className="serif" style={{ fontSize: 18, color: "var(--paper)" }}>{p.name}</span>
                    <span style={{ fontFamily: '"JetBrains Mono", monospace', fontSize: 9, color: "#8a7f6e" }}>{p.province}</span>
                  </div>
                  <div style={{ fontFamily: '"JetBrains Mono", monospace', fontSize: 10, color: "var(--paper)", marginTop: 6, display: "flex", gap: 10 }}>
                    <span style={{ color: r.seeded    ? "#5a7a3a" : "#8a7f6e" }}>{r.seeded}/{r.total} seeded</span>
                    <span style={{ color: r.sprayed   ? "#b48638" : "#8a7f6e" }}>{r.sprayed} sprayed</span>
                    <span style={{ color: r.harvested ? "#9a3a2a" : "#8a7f6e" }}>{r.harvested} harv.</span>
                  </div>
                </div>
              );
            })}
          </div>
        </div>
      </div>
      <PropertyDrawer prop={sel} onClose={() => setSel(null)} />
    </div>
  );
};
window.MapView = MapView;
