import { useEffect, useRef, type MutableRefObject } from 'react';
import L from 'leaflet';
import 'leaflet/dist/leaflet.css';

type Punto = { lat: number; lng: number };

const iconDestino = L.divIcon({
  className: '',
  iconSize: [30, 30],
  iconAnchor: [15, 30],
  html:
    '<div style="position:relative;width:30px;height:30px;">' +
    '<div style="position:absolute;left:5px;top:0;width:20px;height:20px;border-radius:50% 50% 50% 0;transform:rotate(-45deg);background:#dc2626;border:2px solid #fff;box-shadow:0 1px 4px rgba(0,0,0,.4)"></div>' +
    '<div style="position:absolute;left:11px;top:6px;width:8px;height:8px;border-radius:50%;background:#fff"></div>' +
    '</div>',
});

const iconRepartidor = L.divIcon({
  className: '',
  iconSize: [18, 18],
  iconAnchor: [9, 9],
  html:
    '<div style="width:16px;height:16px;border-radius:50%;background:#2563eb;border:2px solid #fff;box-shadow:0 0 0 4px rgba(37,99,235,.25)"></div>',
});

/**
 * Mapa interactivo dentro de la pagina. Muestra el destino de la entrega y,
 * si se le pasa `posRef`, la posicion en vivo del repartidor (se mueve sola).
 * No saca al repartidor a otra app.
 */
export default function MapaEntrega({
  destino,
  posRef,
  alto = 180,
  className = '',
}: {
  destino: Punto;
  posRef?: MutableRefObject<Punto>;
  alto?: number | string;
  className?: string;
}) {
  const contRef = useRef<HTMLDivElement>(null);
  const mapRef = useRef<L.Map | null>(null);

  useEffect(() => {
    const cont = contRef.current;
    if (!cont || mapRef.current) return;

    const map = L.map(cont, { attributionControl: false, zoomControl: true });
    mapRef.current = map;
    L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
      maxZoom: 19,
      attribution: '© OpenStreetMap',
    }).addTo(map);
    L.control.attribution({ prefix: false, position: 'bottomright' }).addTo(map);

    L.marker([destino.lat, destino.lng], { icon: iconDestino }).addTo(map);

    let repMarker: L.Marker | null = null;
    if (posRef) {
      repMarker = L.marker([posRef.current.lat, posRef.current.lng], { icon: iconRepartidor }).addTo(map);
      map.fitBounds(
        L.latLngBounds([
          [destino.lat, destino.lng],
          [posRef.current.lat, posRef.current.lng],
        ]),
        { padding: [40, 40], maxZoom: 16 },
      );
    } else {
      map.setView([destino.lat, destino.lng], 15);
    }

    // Mueve el marcador del repartidor cada 3s sin re-renderizar la pagina.
    const timer = window.setInterval(() => {
      if (posRef && repMarker) repMarker.setLatLng([posRef.current.lat, posRef.current.lng]);
    }, 3000);
    // Recalcula el tamano (por si el contenedor entra animado / en un modal).
    const inval = window.setTimeout(() => map.invalidateSize(), 150);

    return () => {
      window.clearInterval(timer);
      window.clearTimeout(inval);
      map.remove();
      mapRef.current = null;
    };
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, []);

  return <div ref={contRef} className={className} style={{ height: alto, width: '100%' }} />;
}
