import { useEffect, useMemo, useState } from 'react'
import { DayPicker } from 'react-day-picker'
import type { DateRange } from 'react-day-picker'
import { ru } from 'date-fns/locale/ru'
import { CalendarDays, ChevronDown } from 'lucide-react'

import './MapTrackPeriodControl.scss'

type PeriodPreset = 'today' | 'yesterday' | 'week' | 'month' | 'custom'

export type MapTrackPeriodValue = {
  preset: PeriodPreset
  periodStart: Date
  periodEnd: Date
}

type MapTrackPeriodControlProps = {
  onChange?: (value: MapTrackPeriodValue) => void
}

const presetTabs: Array<{
  value: PeriodPreset
  label: string
}> = [
  { value: 'today', label: 'Сегодня' },
  { value: 'yesterday', label: 'Вчера' },
  { value: 'week', label: 'Неделя' },
  { value: 'month', label: 'Месяц' },
]

function startOfDay(date: Date) {
  const result = new Date(date)
  result.setHours(0, 0, 0, 0)
  return result
}

function endOfDay(date: Date) {
  const result = new Date(date)
  result.setHours(23, 59, 59, 999)
  return result
}

function addDays(date: Date, days: number) {
  const result = new Date(date)
  result.setDate(result.getDate() + days)
  return result
}

function addMonths(date: Date, months: number) {
  const result = new Date(date)
  result.setMonth(result.getMonth() + months)
  return result
}

function getPresetRange(preset: PeriodPreset) {
  const now = new Date()

  if (preset === 'today') {
    return {
      start: startOfDay(now),
      end: now,
    }
  }

  if (preset === 'yesterday') {
    const yesterday = addDays(now, -1)

    return {
      start: startOfDay(yesterday),
      end: endOfDay(yesterday),
    }
  }

  if (preset === 'week') {
    return {
      start: startOfDay(addDays(now, -6)),
      end: now,
    }
  }

  if (preset === 'month') {
    return {
      start: startOfDay(addMonths(now, -1)),
      end: now,
    }
  }

  return {
    start: startOfDay(now),
    end: now,
  }
}

function formatDate(date: Date) {
  return new Intl.DateTimeFormat('ru-RU', {
    day: '2-digit',
    month: '2-digit',
    year: 'numeric',
  }).format(date)
}

export function MapTrackPeriodControl({ onChange }: MapTrackPeriodControlProps) {
  const initialRange = useMemo(() => getPresetRange('today'), [])

  const [preset, setPreset] = useState<PeriodPreset>('today')
  const [isCalendarOpen, setIsCalendarOpen] = useState(false)

  const [periodStart, setPeriodStart] = useState(initialRange.start)
  const [periodEnd, setPeriodEnd] = useState(initialRange.end)

  const [calendarRange, setCalendarRange] = useState<DateRange | undefined>({
    from: initialRange.start,
    to: initialRange.end,
  })

  function applyPeriod(nextPreset: PeriodPreset, start: Date, end: Date) {
    setPreset(nextPreset)
    setPeriodStart(start)
    setPeriodEnd(end)

    setCalendarRange({
      from: start,
      to: end,
    })
  }

  function handlePresetClick(nextPreset: PeriodPreset) {
    const nextRange = getPresetRange(nextPreset)
    applyPeriod(nextPreset, nextRange.start, nextRange.end)
  }

  function handleCalendarSelect(nextRange: DateRange | undefined) {
    setCalendarRange(nextRange)

    if (!nextRange?.from) return

    const from = startOfDay(nextRange.from)
    const to = nextRange.to ? endOfDay(nextRange.to) : endOfDay(nextRange.from)

    applyPeriod('custom', from, to)
  }

  useEffect(() => {
    onChange?.({
      preset,
      periodStart,
      periodEnd,
    })
  }, [preset, periodStart, periodEnd, onChange])

  return (
    <div className="history-period-control">
      <div className="history-period-control__top">
        <div className="history-period-tabs">
          {presetTabs.map((tab) => (
            <button
              key={tab.value}
              className={
                preset === tab.value
                  ? 'history-period-tabs__item is-active'
                  : 'history-period-tabs__item'
              }
              type="button"
              onClick={() => handlePresetClick(tab.value)}
            >
              {tab.label}
            </button>
          ))}
        </div>

        <div className="history-date-picker">
          <button
            className={
              preset === 'custom'
                ? 'history-date-picker__trigger is-active'
                : 'history-date-picker__trigger'
            }
            type="button"
            onClick={() => setIsCalendarOpen((prev) => !prev)}
          >
            <CalendarDays size={16} />

            <span>
              {formatDate(periodStart)} — {formatDate(periodEnd)}
            </span>

            <ChevronDown size={16} />
          </button>

          {isCalendarOpen && (
            <div className="history-date-picker__dropdown">
              <DayPicker
                mode="range"
                locale={ru}
                selected={calendarRange}
                onSelect={handleCalendarSelect}
                numberOfMonths={1}
                defaultMonth={periodStart}
                weekStartsOn={1}
                showOutsideDays
              />
            </div>
          )}
        </div>
      </div>
    </div>
  )
}
