// ========== WEATHER WIDGET ==========
(function() {
  const errorHandler = new ErrorHandler();
  // Inject modal HTML
  injectModal('weather-modal', `<div id="weather-modal" class="weather-modal"><div class="weather-modal-content"><h3>Weather Settings</h3>
    <label for="weather-location-input">Location:</label>
    <input type="text" id="weather-location-input" placeholder="City name or ZIP (e.g., Hamburg, 90210)" maxlength="100">
    <div style="font-size: 0.78rem; color: var(--muted); margin-top: 4px;">Enter a city name, postal code, or &ldquo;City, Country&rdquo;</div>
    <div style="margin-top: 14px; padding-top: 12px; border-top: 1px solid var(--border);">
      <label style="display: block; margin-bottom: 8px; font-weight: 600; color: var(--fg);">Units</label>
      <div style="display: flex; gap: 8px;">
        <label class="weather-unit-option"><input type="radio" name="weather-unit-radio" value="imperial"><span class="weather-unit-card">&deg;F / mph</span></label>
        <label class="weather-unit-option"><input type="radio" name="weather-unit-radio" value="metric"><span class="weather-unit-card">&deg;C / km/h</span></label>
      </div>
    </div>
    <div class="weather-modal-buttons"><button id="weather-cancel">Cancel</button><button id="weather-save">Save</button></div></div></div>`);

  /* Weather Widget — powered by Open-Meteo (free, no API key) */
  const LOCATION_KEY = 'weather-location';
  const LEGACY_KEY = 'weather-zip';
  const GEO_CACHE_KEY = 'weather-geo';
  const UNIT_KEY = 'weather-unit';

  // Migrate from old ZIP-only key
  if (!safeGet(LOCATION_KEY) && safeGet(LEGACY_KEY)) {
    safeSet(LOCATION_KEY, safeGet(LEGACY_KEY));
  }

  function getUnit() {
    return safeGet(UNIT_KEY) || 'imperial';
  }

  function getWeatherElements() {
    return {
      icon: document.querySelector('.weather-icon'),
      temp: document.querySelector('.weather-temp'),
      condition: document.querySelector('.weather-condition'),
      location: document.querySelector('.weather-location'),
      wind: document.querySelector('.weather-wind')
    };
  }

  // WMO Weather Code mapping
  const wmoDescriptions = {
    0: 'Clear sky', 1: 'Mainly clear', 2: 'Partly cloudy', 3: 'Overcast',
    45: 'Fog', 48: 'Rime fog',
    51: 'Light drizzle', 53: 'Drizzle', 55: 'Dense drizzle',
    56: 'Freezing drizzle', 57: 'Dense freezing drizzle',
    61: 'Light rain', 63: 'Moderate rain', 65: 'Heavy rain',
    66: 'Light freezing rain', 67: 'Heavy freezing rain',
    71: 'Light snow', 73: 'Moderate snow', 75: 'Heavy snow', 77: 'Snow grains',
    80: 'Light showers', 81: 'Moderate showers', 82: 'Violent showers',
    85: 'Light snow showers', 86: 'Heavy snow showers',
    95: 'Thunderstorm', 96: 'Thunderstorm with hail', 99: 'Severe thunderstorm'
  };

  const wmoIcons = {
    0: '☀️', 1: '🌤️', 2: '⛅', 3: '☁️',
    45: '🌫️', 48: '🌫️',
    51: '🌦️', 53: '🌦️', 55: '🌦️',
    56: '🌨️', 57: '🌨️',
    61: '🌦️', 63: '🌧️', 65: '🌧️',
    66: '🌨️', 67: '🌨️',
    71: '🌨️', 73: '❄️', 75: '❄️', 77: '❄️',
    80: '🌦️', 81: '🌧️', 82: '🌧️',
    85: '🌨️', 86: '❄️',
    95: '⛈️', 96: '⛈️', 99: '⛈️'
  };

  // Wind direction from degrees
  const windDirs = ['N','NNE','NE','ENE','E','ESE','SE','SSE','S','SSW','SW','WSW','W','WNW','NW','NNW'];
  function degToDir(deg) {
    return windDirs[Math.round(deg / 22.5) % 16];
  }

  // Geocode location via Open-Meteo, with localStorage cache
  async function geocodeLocation(query) {
    const cached = safeGet(GEO_CACHE_KEY);
    if (cached) {
      try {
        const geo = JSON.parse(cached);
        if (geo.query === query) return geo;
      } catch {}
    }
    const resp = await fetch(`https://geocoding-api.open-meteo.com/v1/search?name=${encodeURIComponent(query)}&count=1&language=en&format=json`);
    if (!resp.ok) throw new Error('Geocoding failed');
    const data = await resp.json();
    if (!data.results || !data.results.length) throw new Error('Location not found');
    const r = data.results[0];
    const geo = {
      query,
      lat: r.latitude,
      lon: r.longitude,
      city: r.name,
      state: r.admin1 || '',
      country: r.country || '',
      countryCode: r.country_code || ''
    };
    safeSet(GEO_CACHE_KEY, JSON.stringify(geo));
    return geo;
  }

  function formatLocation(geo) {
    // For US locations show "City, State", for others show "City, Country"
    if (geo.countryCode === 'US' && geo.state) {
      return `${geo.city}, ${geo.state}`;
    }
    if (geo.country) {
      return `${geo.city}, ${geo.country}`;
    }
    return geo.city;
  }

  async function fetchWeather(location) {
    try {
      const geo = await geocodeLocation(location);
      const unit = getUnit();
      const tempUnit = unit === 'metric' ? 'celsius' : 'fahrenheit';
      const windUnit = unit === 'metric' ? 'kmh' : 'mph';
      const url = `https://api.open-meteo.com/v1/forecast?latitude=${geo.lat}&longitude=${geo.lon}&current=temperature_2m,weather_code,wind_speed_10m,wind_direction_10m&temperature_unit=${tempUnit}&wind_speed_unit=${windUnit}`;
      const resp = await fetch(url);
      if (!resp.ok) throw new Error('Weather fetch failed');
      const data = await resp.json();
      const c = data.current;
      const code = c.weather_code;
      return {
        temp: Math.round(c.temperature_2m),
        condition: wmoDescriptions[code] || 'Unknown',
        icon: wmoIcons[code] || '🌤️',
        locationStr: formatLocation(geo),
        windSpeed: Math.round(c.wind_speed_10m),
        windDir: degToDir(c.wind_direction_10m),
        unit
      };
    } catch (error) {
      console.warn('Weather fetch failed:', error);
      return null;
    }
  }

  async function updateWeather() {
    const weatherWidget = getWeatherElements();
    if (!weatherWidget.icon || !weatherWidget.temp || !weatherWidget.condition || !weatherWidget.location || !weatherWidget.wind) {
      console.warn('Weather widget elements not found');
      return;
    }

    const location = safeGet(LOCATION_KEY);
    if (!location) {
      weatherWidget.location.textContent = 'Set Location';
      weatherWidget.temp.textContent = '--\u00B0';
      weatherWidget.condition.textContent = 'Click \u2699\uFE0F to configure';
      weatherWidget.wind.textContent = '--';
      weatherWidget.icon.innerHTML = '<span class="weather-emoji">\uD83C\uDF24\uFE0F</span>';
      return;
    }

    try {
      const weather = await fetchWeather(location);
      if (weather) {
        const tempSuffix = weather.unit === 'metric' ? '\u00B0C' : '\u00B0F';
        const windLabel = weather.unit === 'metric' ? 'km/h' : 'mph';
        weatherWidget.location.textContent = weather.locationStr;
        weatherWidget.temp.textContent = `${weather.temp}${tempSuffix}`;
        weatherWidget.condition.textContent = weather.condition;
        weatherWidget.wind.textContent = `Wind: ${weather.windSpeed} ${windLabel} ${weather.windDir}`;
        weatherWidget.icon.innerHTML = `<span class="weather-emoji">${escapeHtml(weather.icon)}</span>`;
      }
    } catch (error) {
      errorHandler.logError('[Weather] Update Error', error, { function: 'updateWeather' });
      weatherWidget.location.textContent = 'Weather Error';
      weatherWidget.temp.textContent = 'Error';
      weatherWidget.condition.textContent = 'Failed to load';
      weatherWidget.wind.textContent = '--';
    }
  }

  // Weather settings modal
  const modal = document.getElementById('weather-modal');
  const locationInput = document.getElementById('weather-location-input');

  document.getElementById('weather-settings')?.addEventListener('click', () => {
    locationInput.value = safeGet(LOCATION_KEY) || '';
    // Set unit radio
    const unit = getUnit();
    const radio = modal.querySelector(`input[name="weather-unit-radio"][value="${unit}"]`);
    if (radio) radio.checked = true;
    modal.classList.add('show');
    locationInput.focus();
  });

  document.getElementById('weather-cancel')?.addEventListener('click', () => {
    modal.classList.remove('show');
  });

  document.getElementById('weather-save')?.addEventListener('click', () => {
    const loc = locationInput.value.trim();
    if (loc) {
      // Clear geo cache when location changes so it re-geocodes
      const oldLoc = safeGet(LOCATION_KEY);
      if (oldLoc !== loc) safeSet(GEO_CACHE_KEY, '');
      safeSet(LOCATION_KEY, loc);
      // Save unit preference
      const unitRadio = modal.querySelector('input[name="weather-unit-radio"]:checked');
      const newUnit = unitRadio ? unitRadio.value : 'imperial';
      const oldUnit = getUnit();
      safeSet(UNIT_KEY, newUnit);
      // Clear geo cache if unit changed (need fresh weather data)
      if (oldUnit !== newUnit) safeSet(GEO_CACHE_KEY, '');
      modal.classList.remove('show');
      updateWeather();
    } else {
      showNotification('Please enter a location (e.g., Hamburg, London, 90210)', 'warning');
    }
  });

  wireModal(modal);

  // Close modal on Escape key
  document.addEventListener('keydown', (e) => {
    if (e.key === 'Escape' && modal.classList.contains('show')) {
      modal.classList.remove('show');
    }
  });

  // Initialize weather
  updateWeather();
  // Update weather every 10 minutes
  setInterval(updateWeather, DC.POLL.WEATHER);
})();
