import { useMemo } from 'react'
import { useNavigate } from 'react-router-dom'
import { useHomeData, useLibraryItems } from '../hooks/use-jellyfin'
import { useTmdbTrending } from '../hooks/use-tmdb'
import ContentRow from '../components/ui/ContentRow'
import LazyMount, { RowBoundary } from '../components/ui/LazyMount'
import { getTmdbImageUrl } from '../api/tmdb'
import { usePreferencesStore } from '../stores/preferences-store'
import type { BaseItemDto } from '../api/types'
import { FeaturedCarousel } from './home/home-hero'
import { dailyBucket, seededShuffle, HomeSkeleton, EmptyHome } from './home/home-utils'
import { DecadeRow, GenreRow } from './home/rows/library'
import { HomeSections } from './home/rows/composite'

const FEATURED_GENRES = [
  { name: 'Action', subtitle: 'Bullets, fists, explosions' },
  { name: 'Drama', subtitle: 'Stories that hit deep' },
  { name: 'Comedy', subtitle: 'Light watching' },
  { name: 'Science Fiction', subtitle: 'Beyond the possible' },
  { name: 'Thriller', subtitle: 'Edge-of-your-seat tension' },
  { name: 'Horror', subtitle: 'Lights off' },
  { name: 'Documentary', subtitle: 'Real stories' },
  { name: 'Animation', subtitle: 'Drawn to perfection' },
]

export default function HomePage() {
  const navigate = useNavigate()
  const { continueWatching, nextUp, recentlyAdded } = useHomeData()
  const trending = useTmdbTrending('all', 'week')
  const hideAdult = usePreferencesStore(s => s.hideAdult)
  const prefs = usePreferencesStore()

  const topRated = useLibraryItems(undefined, {
    includeItemTypes: ['Movie', 'Series'],
    sortBy: ['CommunityRating'],
    sortOrder: ['Descending'],
    minCommunityRating: 7,
    limit: 20,
  })

  const surpriseMe = useLibraryItems(undefined, {
    includeItemTypes: ['Movie', 'Series'],
    sortBy: ['Random'],
    sortOrder: ['Descending'],
    limit: 20,
  })

  const recentlyPlayed = useLibraryItems(undefined, {
    includeItemTypes: ['Movie', 'Series'],
    sortBy: ['DatePlayed'],
    sortOrder: ['Descending'],
    filters: ['IsPlayed'],
    limit: 14,
  })

  const featuredPool = useMemo<BaseItemDto[]>(() => {
    const pool: BaseItemDto[] = []
    const isFeatureWorthy = (item: BaseItemDto) =>
      (item.Type === 'Movie' || item.Type === 'Series') &&
      !!item.BackdropImageTags?.length

    // Bias toward continue watching first (user is engaged with these)
    for (const item of continueWatching.data || []) if (isFeatureWorthy(item)) pool.push(item)
    for (const item of recentlyAdded.data || []) if (isFeatureWorthy(item)) pool.push(item)
    for (const item of topRated.data?.Items || []) if (isFeatureWorthy(item)) pool.push(item)

    const seen = new Set<string>()
    const unique = pool.filter(p => {
      if (!p.Id || seen.has(p.Id)) return false
      seen.add(p.Id)
      return true
    })

    // Day-bucketed shuffle so the order changes a few times a day but stays
    // stable within a session, then clamp to 8 slides max.
    return seededShuffle(unique, dailyBucket()).slice(0, 8)
  }, [continueWatching.data, recentlyAdded.data, topRated.data])

  const hasAnyData =
    (continueWatching.data?.length ?? 0) > 0 ||
    (nextUp.data?.length ?? 0) > 0 ||
    (recentlyAdded.data?.length ?? 0) > 0

  const allLoading =
    continueWatching.isLoading && nextUp.isLoading && recentlyAdded.isLoading

  if (allLoading) return <HomeSkeleton />

  if (!hasAnyData) return <EmptyHome />

  return (
    <div className="pb-12">
      {featuredPool.length > 0 && <FeaturedCarousel items={featuredPool} navigate={navigate} />}

      <div className="-mt-4 relative z-10">
        {prefs.home.show.continueWatching && continueWatching.data && continueWatching.data.length > 0 && (
          <RowBoundary>
            <ContentRow
              title="Continue watching"
              subtitle="Pick up where you left off"
              items={continueWatching.data}
              aspect="landscape"
            />
          </RowBoundary>
        )}

        {prefs.home.show.nextUp && nextUp.data && nextUp.data.length > 0 && (
          <RowBoundary>
            <ContentRow
              title="Next up"
              subtitle="The next episodes for shows you watch"
              items={nextUp.data}
            />
          </RowBoundary>
        )}

        {prefs.home.show.recentlyAdded && recentlyAdded.data && recentlyAdded.data.length > 0 && (
          <RowBoundary>
            <ContentRow
              title="Recently added"
              subtitle="Fresh from your library"
              items={recentlyAdded.data}
            />
          </RowBoundary>
        )}

        {prefs.home.show.trendingWeek && trending.data?.results && trending.data.results.length > 0 && (() => {
          const filtered = trending.data.results.filter(r => !hideAdult || !r.adult)
          if (filtered.length === 0) return null
          return (
            <RowBoundary>
              <ContentRow
                title="Trending this week"
                subtitle="What the world is watching on TMDB"
                items={filtered.map(r => ({
                  Id: `tmdb-${r.id}`,
                  Name: r.title || r.name,
                  Type: r.media_type === 'tv' ? 'Series' : 'Movie',
                  ProductionYear: r.release_date
                    ? parseInt(r.release_date)
                    : r.first_air_date
                      ? parseInt(r.first_air_date)
                      : undefined,
                  ImageTags: {},
                  ProviderIds: { Tmdb: String(r.id) },
                  _tmdbPoster: r.poster_path ? getTmdbImageUrl(r.poster_path, 'w342') : undefined,
                } as BaseItemDto))}
              />
            </RowBoundary>
          )
        })()}

        {prefs.home.show.topRated && topRated.data?.Items && topRated.data.Items.length > 0 && (
          <RowBoundary>
            <ContentRow
              title="Top rated in your library"
              subtitle="The cream of the crop"
              items={topRated.data.Items}
            />
          </RowBoundary>
        )}

        {prefs.home.show.watchedRecently && recentlyPlayed.data?.Items && recentlyPlayed.data.Items.length > 0 && (
          <RowBoundary>
            <ContentRow
              title="Watched recently"
              subtitle="Revisit something you've finished"
              items={recentlyPlayed.data.Items}
            />
          </RowBoundary>
        )}

        {prefs.home.show.surpriseMe && surpriseMe.data?.Items && surpriseMe.data.Items.length > 0 && (
          <RowBoundary>
            <ContentRow
              title="Surprise me"
              subtitle="A random shake-up from your library"
              items={surpriseMe.data.Items}
            />
          </RowBoundary>
        )}

        <HomeSections />

        {prefs.home.show.decadeRows && (
          <>
            <LazyMount><DecadeRow decade={1990} /></LazyMount>
            <LazyMount><DecadeRow decade={2000} /></LazyMount>
            <LazyMount><DecadeRow decade={2010} /></LazyMount>
          </>
        )}

        {prefs.home.show.featuredGenres &&
          FEATURED_GENRES.map(g => (
            <LazyMount key={g.name}>
              <GenreRow genre={g.name} subtitle={g.subtitle} />
            </LazyMount>
          ))}
      </div>
    </div>
  )
}
