/**
 * Convert a Maidenhead grid locator to lat/lon (center of the square).
 * Supports 4, 6, or 8 character locators (e.g. JN03, JN03ef, JN03ef12).
 * Returns { lat, lon } in decimal degrees, or null if invalid.
 */
export function maidenheadToLatLon(locator) {
  const loc = locator.trim().toUpperCase()
  if (!/^[A-R]{2}[0-9]{2}([A-X]{2}([0-9]{2})?)?$/.test(loc)) return null

  // Field (A-R) → 0-17, each = 20°
  const lonBase = (loc.charCodeAt(0) - 65) * 20 - 180
  const latBase = (loc.charCodeAt(1) - 65) * 10 - 90

  // Square (0-9) → each = 2° lon, 1° lat
  let lon = lonBase + parseInt(loc[2]) * 2
  let lat = latBase + parseInt(loc[3]) * 1

  // Subsquare (a-x) → each = 5' lon, 2.5' lat
  if (loc.length >= 6) {
    lon += (loc.charCodeAt(4) - 65) * (2 / 24)
    lat += (loc.charCodeAt(5) - 65) * (1 / 24)
    // Center of subsquare
    lon += 1 / 24
    lat += 0.5 / 24
  } else {
    // Center of square
    lon += 1
    lat += 0.5
  }

  // Extended subsquare (0-9)
  if (loc.length >= 8) {
    lon += parseInt(loc[6]) * (2 / 240)
    lat += parseInt(loc[7]) * (1 / 240)
    lon += 1 / 240
    lat += 0.5 / 240
  }

  return { lat: parseFloat(lat.toFixed(6)), lon: parseFloat(lon.toFixed(6)) }
}

/**
 * Convert lat/lon to a 6-character Maidenhead locator.
 */
export function latLonToMaidenhead(lat, lon) {
  lon += 180
  lat += 90
  const A = 'ABCDEFGHIJKLMNOPQRSTUVWX'
  const f = String.fromCharCode(65 + Math.floor(lon / 20))
  const s = String.fromCharCode(65 + Math.floor(lat / 10))
  const n1 = Math.floor((lon % 20) / 2)
  const n2 = Math.floor(lat % 10)
  const ss1 = A[Math.floor((lon % 2) / (2 / 24))]
  const ss2 = A[Math.floor((lat % 1) / (1 / 24))]
  return `${f}${s}${n1}${n2}${ss1.toLowerCase()}${ss2.toLowerCase()}`
}