<?php
require_once __DIR__ . '/../helpers/auth.php';
require_role(['admin', 'staff']);

$delivery_id = (int)($_GET['id'] ?? 0);
if ($delivery_id <= 0) {
    http_response_code(400);
    die("Invalid delivery ID.");
}

$title = "Live Map - Delivery #$delivery_id";

require_once __DIR__ . '/../templates/header.php';
require_once __DIR__ . '/../templates/sidebar.php';
?>

<main class="col-12 col-md-9 col-lg-10 p-3 p-md-4">
  <div class="d-flex align-items-center justify-content-between mb-3">
    <div>
      <h4 class="mb-0">Live Map</h4>
      <div class="text-muted small">Delivery ID: <?= (int)$delivery_id ?></div>
    </div>
    <div class="d-flex gap-2">
      <a class="btn btn-outline-secondary btn-sm" href="delivery_view.php?id=<?= (int)$delivery_id ?>">Back to Delivery</a>
    </div>
  </div>

  <div class="row g-3">
    <div class="col-12 col-lg-8">
      <div class="card shadow-sm">
        <div class="card-body">
          <div id="map" style="height: 520px; width: 100%; border-radius: 8px;"></div>
        </div>
      </div>
    </div>

    <div class="col-12 col-lg-4">
      <div class="card shadow-sm">
        <div class="card-body">
          <h6 class="mb-3">Tracking Info</h6>

          <div class="mb-2"><b>Code:</b> <span id="code">-</span></div>
          <div class="mb-2"><b>Status:</b> <span class="badge text-bg-secondary" id="status">-</span></div>

          <div class="form-check form-switch mt-3">
            <input class="form-check-input" type="checkbox" role="switch" id="followDriver" checked>
            <label class="form-check-label" for="followDriver">Follow driver</label>
          </div>

          <hr>

          <div class="mb-2"><b>Last GPS:</b></div>
          <div class="small text-muted" id="lastTime">-</div>
          <div class="small" id="lastCoords">-</div>
          <div class="small text-muted" id="lastMeta">-</div>

          <hr>

          <div class="mb-2"><b>Distance to dropoff:</b></div>
          <div class="fw-semibold" id="distance">-</div>

          <div class="small text-muted mt-3">
            Auto-refresh: every <b>5 seconds</b>. Trail shows last <b>50 points</b>.
          </div>
        </div>
      </div>
    </div>
  </div>
</main>

<link rel="stylesheet" href="https://unpkg.com/leaflet@1.9.4/dist/leaflet.css">
<script src="https://unpkg.com/leaflet@1.9.4/dist/leaflet.js"></script>

<script>
const deliveryId = <?= (int)$delivery_id ?>;

const codeEl = document.getElementById('code');
const statusEl = document.getElementById('status');
const lastTimeEl = document.getElementById('lastTime');
const lastCoordsEl = document.getElementById('lastCoords');
const lastMetaEl = document.getElementById('lastMeta');
const distanceEl = document.getElementById('distance');
const followToggle = document.getElementById('followDriver');

const map = L.map('map').setView([14.5995, 120.9842], 13);
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
  maxZoom: 19,
  attribution: '&copy; OpenStreetMap contributors'
}).addTo(map);

let driverMarker = null;
let pickupMarker = null;
let dropoffMarker = null;
let trailLine = null;

let dropoffLatLng = null;
let firstFitDone = false;

function ensureMarker(existing, latlng, label) {
  if (!latlng) return existing;
  if (!existing) {
    existing = L.marker(latlng).addTo(map).bindPopup(label);
  } else {
    existing.setLatLng(latlng);
  }
  return existing;
}

function haversineMeters(a, b) {
  const R = 6371000;
  const toRad = d => d * Math.PI / 180;
  const dLat = toRad(b[0] - a[0]);
  const dLng = toRad(b[1] - a[1]);
  const lat1 = toRad(a[0]);
  const lat2 = toRad(b[0]);

  const sinDLat = Math.sin(dLat / 2);
  const sinDLng = Math.sin(dLng / 2);
  const h = sinDLat * sinDLat + Math.cos(lat1) * Math.cos(lat2) * sinDLng * sinDLng;
  const c = 2 * Math.atan2(Math.sqrt(h), Math.sqrt(1 - h));
  return R * c;
}

function formatDistance(m) {
  if (m === null || !isFinite(m)) return '-';
  if (m < 1000) return `${Math.round(m)} m`;
  return `${(m / 1000).toFixed(2)} km`;
}

async function fetchJson(url) {
  const res = await fetch(url, { headers: { 'Accept': 'application/json' } });
  const text = await res.text();
  try {
    return JSON.parse(text);
  } catch (e) {
    throw new Error(text.substring(0, 180));
  }
}

async function refreshLatest() {
  const data = await fetchJson(`location_latest.php?delivery_id=${encodeURIComponent(deliveryId)}`);
  if (!data.ok) throw new Error(data.error || 'Unknown error');

  codeEl.textContent = data.delivery.delivery_code || '-';
  statusEl.textContent = data.delivery.status || '-';

  const pLat = data.delivery.pickup_lat, pLng = data.delivery.pickup_lng;
  const dLat = data.delivery.dropoff_lat, dLng = data.delivery.dropoff_lng;

  if (pLat !== null && pLng !== null) {
    pickupMarker = ensureMarker(pickupMarker, [pLat, pLng], 'Pickup');
  }
  if (dLat !== null && dLng !== null) {
    dropoffLatLng = [dLat, dLng];
    dropoffMarker = ensureMarker(dropoffMarker, [dLat, dLng], 'Dropoff');
  }

  if (data.latest) {
    const lat = Number(data.latest.lat);
    const lng = Number(data.latest.lng);

    driverMarker = ensureMarker(driverMarker, [lat, lng], 'Driver (latest)');

    lastTimeEl.textContent = data.latest.recorded_at || '-';
    lastCoordsEl.textContent = `${lat.toFixed(6)}, ${lng.toFixed(6)}`;

    const acc = data.latest.accuracy_m !== null ? Math.round(data.latest.accuracy_m) + 'm' : '-';
    const spd = data.latest.speed_mps !== null ? Number(data.latest.speed_mps).toFixed(1) + ' m/s' : '-';
    const hdg = data.latest.heading_deg !== null ? Math.round(data.latest.heading_deg) + '°' : '-';
    lastMetaEl.textContent = `Accuracy: ${acc} | Speed: ${spd} | Heading: ${hdg}`;

    if (dropoffLatLng) {
      const dist = haversineMeters([lat, lng], dropoffLatLng);
      distanceEl.textContent = formatDistance(dist);
    } else {
      distanceEl.textContent = '-';
    }

    if (followToggle.checked) {
      map.setView([lat, lng], Math.max(map.getZoom(), 15));
    }
  } else {
    lastTimeEl.textContent = 'No GPS updates yet';
    lastCoordsEl.textContent = '-';
    lastMetaEl.textContent = '-';
    distanceEl.textContent = '-';
  }

  if (!firstFitDone) {
    const bounds = [];
    if (pickupMarker) bounds.push(pickupMarker.getLatLng());
    if (dropoffMarker) bounds.push(dropoffMarker.getLatLng());
    if (driverMarker) bounds.push(driverMarker.getLatLng());

    if (bounds.length >= 2) {
      map.fitBounds(L.latLngBounds(bounds), { padding: [30, 30] });
      firstFitDone = true;
    } else if (bounds.length === 1) {
      map.setView(bounds[0], 15);
      firstFitDone = true;
    }
  }
}

async function refreshTrail() {
  const data = await fetchJson(`location_points.php?delivery_id=${encodeURIComponent(deliveryId)}&limit=50`);
  if (!data.ok) return;

  const pts = data.points.map(p => [Number(p.lat), Number(p.lng)]);
  if (pts.length < 2) return;

  if (!trailLine) {
    trailLine = L.polyline(pts).addTo(map);
  } else {
    trailLine.setLatLngs(pts);
  }
}

async function refreshAll() {
  try {
    await refreshLatest();
    await refreshTrail();
  } catch (e) {
    lastTimeEl.textContent = 'Error: ' + e.message;
  }
}

refreshAll();
setInterval(refreshAll, 5000);
</script>

<?php require_once __DIR__ . '/../templates/footer.php'; ?>