/**
 * MissionsScreen — lista aktiva uppdrag nära mig, filter, sortering
 * Läser position från locationStore för live-avståndsuppdateringar
 */
import { useCallback, useEffect, useState } from 'react'
import {
  View, Text, FlatList, TouchableOpacity,
  StyleSheet, RefreshControl, ActivityIndicator,
  ScrollView,
} from 'react-native'
import { useNavigation } from '@react-navigation/native'
import { missions, type Mission, type MissionCategory } from '../lib/api'
import { useLocationStore } from '../src/stores/locationStore'

type SortKey = 'distance' | 'reward' | 'deadline'

const CATEGORIES: { key: MissionCategory | 'alla'; label: string; emoji: string }[] = [
  { key: 'alla', label: 'Alla', emoji: '🗺️' },
  { key: 'hamnar', label: 'Hamnar', emoji: '⚓' },
  { key: 'bryggor', label: 'Bryggor', emoji: '🚢' },
  { key: 'vägar', label: 'Vägar', emoji: '🛤️' },
  { key: 'infrastruktur', label: 'Infrastruktur', emoji: '🏗️' },
  { key: 'fritidshus', label: 'Fritidshus', emoji: '🏠' },
  { key: 'miljö', label: 'Miljö', emoji: '🌿' },
]

const STATUS_COLOR: Record<string, string> = {
  open: '#10b981',
  active: '#f59e0b',
  completed: '#6366f1',
  cancelled: '#ef4444',
  expired: '#6b7280',
}

function timeLeft(deadline: string | null): string {
  if (!deadline) return ''
  const diff = new Date(deadline).getTime() - Date.now()
  if (diff < 0) return 'Utgången'
  const h = Math.floor(diff / 3600000)
  if (h < 24) return `${h}h kvar`
  return `${Math.floor(h / 24)}d kvar`
}

/** Calculate distance between two coordinates in meters */
function haversineDistance(lat1: number, lng1: number, lat2: number, lng2: number): number {
  const R = 6371e3 // Earth radius in meters
  const φ1 = (lat1 * Math.PI) / 180
  const φ2 = (lat2 * Math.PI) / 180
  const Δφ = ((lat2 - lat1) * Math.PI) / 180
  const Δλ = ((lng2 - lng1) * Math.PI) / 180

  const a =
    Math.sin(Δφ / 2) * Math.sin(Δφ / 2) +
    Math.cos(φ1) * Math.cos(φ2) * Math.sin(Δλ / 2) * Math.sin(Δλ / 2)
  const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a))

  return R * c
}

function formatDistance(meters: number): string {
  if (meters < 1000) {
    return `${Math.round(meters)} m`
  }
  return `${(meters / 1000).toFixed(1)} km`
}

export function MissionsScreen() {
  const navigation = useNavigation<any>()

  // Read live position from store
  const { currentPosition } = useLocationStore()

  const [allMissions, setAllMissions] = useState<Mission[]>([])
  const [loading, setLoading] = useState(true)
  const [refreshing, setRefreshing] = useState(false)
  const [category, setCategory] = useState<MissionCategory | 'alla'>('alla')
  const [sort, setSort] = useState<SortKey>('distance')
  const [userLat, setUserLat] = useState<number | null>(null)
  const [userLng, setUserLng] = useState<number | null>(null)

  // Initialize with store position or fallback
  useEffect(() => {
    if (currentPosition) {
      setUserLat(currentPosition.coords.latitude)
      setUserLng(currentPosition.coords.longitude)
      loadMissions(currentPosition.coords.latitude, currentPosition.coords.longitude)
    } else {
      // Fallback to Stockholm archipelago if no GPS yet
      setUserLat(59.45)
      setUserLng(18.5)
      loadMissions(59.45, 18.5)
    }
  }, []) // Only on mount — subsequent updates come from currentPosition

  // Update user position when store updates
  useEffect(() => {
    if (currentPosition) {
      setUserLat(currentPosition.coords.latitude)
      setUserLng(currentPosition.coords.longitude)
    }
  }, [currentPosition])

  const loadMissions = async (lat: number, lng: number) => {
    try {
      const data = await missions.nearby(lat, lng, 80)
      setAllMissions(data)
    } catch {
      // silent — show empty
    } finally {
      setLoading(false)
      setRefreshing(false)
    }
  }

  const onRefresh = useCallback(() => {
    setRefreshing(true)
    const lat = userLat ?? 59.45
    const lng = userLng ?? 18.5
    loadMissions(lat, lng)
  }, [userLat, userLng])

  // Compute live distances using current position
  const missionsWithLiveDistance = allMissions.map(m => {
    if (userLat != null && userLng != null) {
      const liveDistance = haversineDistance(userLat, userLng, m.latitude, m.longitude)
      return { ...m, distance_meters: liveDistance }
    }
    return m
  })

  const filtered = missionsWithLiveDistance
    .filter(m => category === 'alla' || m.category === category)
    .sort((a, b) => {
      if (sort === 'reward') return b.reward_amount - a.reward_amount
      if (sort === 'deadline') {
        if (!a.deadline_at) return 1
        if (!b.deadline_at) return -1
        return new Date(a.deadline_at).getTime() - new Date(b.deadline_at).getTime()
      }
      // distance — use live-calculated distance
      return (a.distance_meters ?? Infinity) - (b.distance_meters ?? Infinity)
    })

  if (loading) {
    return (
      <View style={styles.center}>
        <ActivityIndicator color="#6366f1" size="large" />
        <Text style={styles.loadingText}>Hämtar uppdrag nära dig…</Text>
      </View>
    )
  }

  return (
    <View style={styles.container}>
      <Text style={styles.heading}>Uppdrag</Text>

      {/* Live position indicator */}
      {currentPosition && (
        <View style={styles.locationBar}>
          <Text style={styles.locationText}>
            📍 {currentPosition.coords.latitude.toFixed(4)}, {currentPosition.coords.longitude.toFixed(4)}
            {currentPosition.coords.accuracy && ` (±${Math.round(currentPosition.coords.accuracy)}m)`}
          </Text>
        </View>
      )}

      {/* Category filter */}
      <ScrollView
        horizontal
        showsHorizontalScrollIndicator={false}
        contentContainerStyle={styles.filterRow}
      >
        {CATEGORIES.map(c => (
          <TouchableOpacity
            key={c.key}
            style={[styles.chip, category === c.key && styles.chipActive]}
            onPress={() => setCategory(c.key)}
          >
            <Text style={styles.chipEmoji}>{c.emoji}</Text>
            <Text style={[styles.chipText, category === c.key && styles.chipTextActive]}>
              {c.label}
            </Text>
          </TouchableOpacity>
        ))}
      </ScrollView>

      {/* Sort bar */}
      <View style={styles.sortBar}>
        <Text style={styles.sortLabel}>Sortera:</Text>
        {(['distance', 'reward', 'deadline'] as SortKey[]).map(s => (
          <TouchableOpacity
            key={s}
            style={[styles.sortBtn, sort === s && styles.sortBtnActive]}
            onPress={() => setSort(s)}
          >
            <Text style={[styles.sortBtnText, sort === s && styles.sortBtnTextActive]}>
              {s === 'distance' ? 'Avstånd' : s === 'reward' ? 'Ersättning' : 'Deadline'}
            </Text>
          </TouchableOpacity>
        ))}
      </View>

      {/* Count */}
      <Text style={styles.count}>
        {filtered.length} uppdrag {category !== 'alla' ? `i "${category}"` : 'totalt'}
      </Text>

      <FlatList
        data={filtered}
        keyExtractor={m => m.id}
        contentContainerStyle={{ paddingBottom: 32 }}
        refreshControl={
          <RefreshControl refreshing={refreshing} onRefresh={onRefresh} tintColor="#6366f1" />
        }
        renderItem={({ item: m }) => (
          <TouchableOpacity
            style={styles.card}
            onPress={() => navigation.navigate('MissionDetail', { missionId: m.id })}
            activeOpacity={0.75}
          >
            <View style={styles.cardTop}>
              <View style={styles.cardMeta}>
                <View style={[styles.statusDot, { backgroundColor: STATUS_COLOR[m.status] ?? '#6b7280' }]} />
                <Text style={styles.category}>{m.category}</Text>
              </View>
              <Text style={styles.reward}>
                {(m.reward_amount / 100).toFixed(0)} SEK
              </Text>
            </View>

            <Text style={styles.title} numberOfLines={2}>{m.title}</Text>
            <Text style={styles.desc} numberOfLines={2}>{m.description}</Text>

            <View style={styles.cardFooter}>
              <Text style={styles.location}>
                📍 {m.city || 'Stockholms skärgård'}
                {m.distance_meters != null
                  ? `  ·  ${formatDistance(m.distance_meters)}`
                  : ''}
              </Text>
              {m.deadline_at && (
                <Text style={[
                  styles.deadline,
                  timeLeft(m.deadline_at) === 'Utgången' && { color: '#ef4444' },
                ]}>
                  ⏱ {timeLeft(m.deadline_at)}
                </Text>
              )}
            </View>
          </TouchableOpacity>
        )}
        ListEmptyComponent={
          <View style={styles.emptyWrap}>
            <Text style={styles.emptyEmoji}>🎯</Text>
            <Text style={styles.emptyTitle}>Inga uppdrag just nu</Text>
            <Text style={styles.emptyText}>Prova en annan kategori eller dra för att uppdatera.</Text>
          </View>
        }
      />
    </View>
  )
}

const styles = StyleSheet.create({
  container: { flex: 1, backgroundColor: '#0A0A1B', paddingTop: 56 },
  center: { flex: 1, backgroundColor: '#0A0A1B', alignItems: 'center', justifyContent: 'center', gap: 12 },
  loadingText: { color: 'rgba(255,255,255,0.4)', fontSize: 14 },

  heading: {
    color: '#fff', fontSize: 28, fontWeight: '800',
    marginHorizontal: 16, marginBottom: 8, letterSpacing: -0.5,
  },

  locationBar: {
    marginHorizontal: 16,
    marginBottom: 8,
    backgroundColor: 'rgba(99,102,241,0.1)',
    borderRadius: 8,
    paddingHorizontal: 10,
    paddingVertical: 6,
    borderWidth: 1,
    borderColor: 'rgba(99,102,241,0.2)',
  },
  locationText: {
    color: '#a5b4fc',
    fontSize: 11,
    fontWeight: '500',
  },

  filterRow: { paddingHorizontal: 16, gap: 8, paddingBottom: 4 },
  chip: {
    flexDirection: 'row', alignItems: 'center', gap: 6,
    backgroundColor: 'rgba(255,255,255,0.05)',
    borderWidth: 1, borderColor: 'rgba(255,255,255,0.08)',
    borderRadius: 20, paddingHorizontal: 14, paddingVertical: 8,
  },
  chipActive: { backgroundColor: 'rgba(99,102,241,0.2)', borderColor: '#6366f1' },
  chipEmoji: { fontSize: 14 },
  chipText: { color: 'rgba(255,255,255,0.5)', fontSize: 13, fontWeight: '500' },
  chipTextActive: { color: '#a5b4fc', fontWeight: '700' },

  sortBar: {
    flexDirection: 'row', alignItems: 'center', gap: 8,
    paddingHorizontal: 16, marginTop: 12, marginBottom: 4,
  },
  sortLabel: { color: 'rgba(255,255,255,0.3)', fontSize: 12, marginRight: 4 },
  sortBtn: {
    paddingHorizontal: 10, paddingVertical: 5,
    borderRadius: 8, backgroundColor: 'rgba(255,255,255,0.04)',
  },
  sortBtnActive: { backgroundColor: 'rgba(99,102,241,0.15)' },
  sortBtnText: { color: 'rgba(255,255,255,0.4)', fontSize: 12 },
  sortBtnTextActive: { color: '#a5b4fc', fontWeight: '600' },

  count: { color: 'rgba(255,255,255,0.25)', fontSize: 12, marginHorizontal: 16, marginBottom: 12 },

  card: {
    marginHorizontal: 16, marginBottom: 12,
    backgroundColor: 'rgba(255,255,255,0.04)',
    borderRadius: 18, padding: 16,
    borderWidth: 1, borderColor: 'rgba(255,255,255,0.07)',
  },
  cardTop: { flexDirection: 'row', justifyContent: 'space-between', alignItems: 'center', marginBottom: 8 },
  cardMeta: { flexDirection: 'row', alignItems: 'center', gap: 6 },
  statusDot: { width: 7, height: 7, borderRadius: 4 },
  category: { color: 'rgba(255,255,255,0.35)', fontSize: 12, textTransform: 'capitalize' },
  reward: { color: '#10b981', fontWeight: '800', fontSize: 16 },
  title: { color: '#fff', fontWeight: '700', fontSize: 16, marginBottom: 6, lineHeight: 22 },
  desc: { color: 'rgba(255,255,255,0.45)', fontSize: 14, lineHeight: 20, marginBottom: 12 },
  cardFooter: { flexDirection: 'row', justifyContent: 'space-between', alignItems: 'center' },
  location: { color: 'rgba(255,255,255,0.3)', fontSize: 12 },
  deadline: { color: '#f59e0b', fontSize: 12, fontWeight: '600' },

  emptyWrap: { alignItems: 'center', marginTop: 60, paddingHorizontal: 32 },
  emptyEmoji: { fontSize: 48, marginBottom: 16 },
  emptyTitle: { color: '#fff', fontSize: 18, fontWeight: '700', marginBottom: 8 },
  emptyText: { color: 'rgba(255,255,255,0.35)', fontSize: 14, textAlign: 'center', lineHeight: 20 },
})
