'use client';

import React, { useEffect, useRef, useState } from 'react';

import { useTranslations } from 'next-intl';

import { useMediaQuery } from 'react-responsive';

import type { HomepageCollectionTextFields } from '@/services/homeCollections';

import Section from '@/components/common/Section';
import HomepageVideoCard from '@/components/home/components/HomepageVideoCard';
import SectionHeader from '@/components/home/components/SectionHeader';
import AppSwiper, { AppSwiperSlide } from '@/components/swiper/AppSwiper';
import CarouselControls from '@/components/swiper/CarouselControls';
import { useAppSwiper } from '@/components/swiper/useAppSwiper';

import {
  HOMEPAGE_CAROUSEL_INTERVAL_MS,
  HOMEPAGE_CAROUSEL_STOP_ON_INTERACTION,
} from '@/config/homepageCarousel';

interface HomepageFeaturedVideosProps {
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
  videos?: any[];
  textFields?: HomepageCollectionTextFields | null;
}

const wrapIndex = (value: number, total: number) =>
  total > 0 ? ((value % total) + total) % total : 0;
const DESKTOP_3D_BREAKPOINT_PX = 768;

const HomepageFeaturedVideos: React.FC<HomepageFeaturedVideosProps> = ({ videos, textFields }) => {
  const t = useTranslations('home');
  const tCommon = useTranslations('common');
  const isDesktop = useMediaQuery({ minWidth: DESKTOP_3D_BREAKPOINT_PX });
  const slideCount = videos?.length ?? 0;
  const [initialIndex, setInitialIndex] = useState(0);
  const controller = useAppSwiper({ slideCount, initialIndex });
  const [desktopIndex, setDesktopIndex] = useState(0);
  const [desktopAutoPaused, setDesktopAutoPaused] = useState(false);
  const videoSlide = isDesktop ? desktopIndex : controller.activeIndex;
  const [videoResetToken, setVideoResetToken] = useState(0);
  const hasMountedRef = useRef(false);
  const desktopIndexRef = useRef(0);

  useEffect(() => {
    if (slideCount <= 1) {
      setInitialIndex(0);
      return;
    }
    setInitialIndex(Math.floor(Math.random() * slideCount));
  }, [slideCount]);

  useEffect(() => {
    if (!isDesktop) return;
    setDesktopIndex(wrapIndex(controller.activeIndex, slideCount));
  }, [controller.activeIndex, isDesktop, slideCount]);

  useEffect(() => {
    setDesktopIndex((prev) => wrapIndex(prev, slideCount));
  }, [slideCount]);

  useEffect(() => {
    desktopIndexRef.current = desktopIndex;
  }, [desktopIndex]);

  useEffect(() => {
    if (!isDesktop || desktopAutoPaused || slideCount <= 1) return;

    const timer = window.setInterval(() => {
      const nextIndex = wrapIndex(desktopIndexRef.current + 1, slideCount);
      desktopIndexRef.current = nextIndex;
      setDesktopIndex(nextIndex);
      controller.goTo(nextIndex);
    }, HOMEPAGE_CAROUSEL_INTERVAL_MS);

    return () => window.clearInterval(timer);
  }, [controller.goTo, desktopAutoPaused, isDesktop, slideCount]);

  useEffect(() => {
    if (!hasMountedRef.current) {
      hasMountedRef.current = true;
      return;
    }
    // Any slide change should stop currently playing embedded videos.
    setVideoResetToken((prevToken) => prevToken + 1);
  }, [videoSlide]);

  const handlePrev = () => {
    if (slideCount <= 1) return;
    if (!isDesktop) {
      controller.prev();
      return;
    }
    if (HOMEPAGE_CAROUSEL_STOP_ON_INTERACTION) {
      setDesktopAutoPaused(true);
    }
    const nextIndex = wrapIndex(videoSlide - 1, slideCount);
    setDesktopIndex(nextIndex);
    controller.goTo(nextIndex);
  };

  const handleNext = () => {
    if (slideCount <= 1) return;
    if (!isDesktop) {
      controller.next();
      return;
    }
    if (HOMEPAGE_CAROUSEL_STOP_ON_INTERACTION) {
      setDesktopAutoPaused(true);
    }
    const nextIndex = wrapIndex(videoSlide + 1, slideCount);
    setDesktopIndex(nextIndex);
    controller.goTo(nextIndex);
  };

  const handleSelect = (index: number) => {
    const nextIndex = wrapIndex(index, slideCount);
    if (isDesktop) {
      if (HOMEPAGE_CAROUSEL_STOP_ON_INTERACTION) {
        setDesktopAutoPaused(true);
      }
      setDesktopIndex(nextIndex);
    }
    controller.goTo(nextIndex);
  };

  const handleVideoPlayStart = () => {
    if (isDesktop) {
      setDesktopAutoPaused(true);
    }
    controller.pauseAutoplay();
  };

  const getWrappedDistance = (index: number, activeIndex: number, total: number) => {
    if (total <= 1) return 0;
    const raw = index - activeIndex;
    const half = Math.floor(total / 2);
    if (raw > half) return raw - total;
    if (raw < -half) return raw + total;
    return raw;
  };

  const getVideoCardStyle = (index: number, activeIndex: number, total: number) => {
    const distance = getWrappedDistance(index, activeIndex, total);
    const absDistance = Math.abs(distance);
    const baseTransition = 'transform 500ms ease, opacity 500ms ease, visibility 500ms ease';

    if (distance === 0) {
      return {
        opacity: 1,
        transform: 'translateX(0px) translateZ(0px) rotateY(0deg)',
        zIndex: 10,
        transition: baseTransition,
      };
    }

    if (distance === -1) {
      return {
        opacity: 1,
        transform: 'translateX(-320px) translateZ(-240px) rotateY(28deg)',
        zIndex: 9,
        transition: baseTransition,
      };
    }

    if (distance === 1) {
      return {
        opacity: 1,
        transform: 'translateX(320px) translateZ(-240px) rotateY(-28deg)',
        zIndex: 9,
        transition: baseTransition,
      };
    }

    if (distance === -2) {
      return {
        opacity: 0.75,
        transform: 'translateX(-620px) translateZ(-380px) rotateY(28deg)',
        zIndex: 8,
        transition: baseTransition,
      };
    }

    if (distance === 2) {
      return {
        opacity: 0.75,
        transform: 'translateX(620px) translateZ(-380px) rotateY(-28deg)',
        zIndex: 8,
        transition: baseTransition,
      };
    }

    if (absDistance > 2) {
      return {
        opacity: 0,
        transform:
          distance < 0
            ? 'translateX(-760px) translateZ(-520px) rotateY(28deg)'
            : 'translateX(760px) translateZ(-520px) rotateY(-28deg)',
        zIndex: 7,
        transition: baseTransition,
      };
    }

    return {
      opacity: 0,
      transform: 'translateX(0px) translateZ(-520px) rotateY(0deg)',
      zIndex: 7,
      transition: baseTransition,
    };
  };

  if (!videos || !videos.length) {
    return null;
  }

  return (
    <Section
      surface="ink"
      clip
      className="bg-[#0f172a]"
      backdrop={
        <>
          <div className="pointer-events-none absolute inset-0 opacity-40">
            <div className="absolute -left-24 -top-24 h-72 w-72 rounded-full bg-mma-cyan/30 blur-3xl" />
            <div className="absolute right-0 top-1/3 h-96 w-96 rounded-full bg-mma-yellow/20 blur-[120px]" />
          </div>
        </>
      }
    >
      <div className="flex flex-col gap-4 lg:flex-row lg:items-end lg:justify-between">
        <SectionHeader
          eyebrow={textFields?.blockLabel || ''}
          eyebrowUrl="/videok"
          title={textFields?.blockTitle || ''}
          description={textFields?.blockSubtitle || ''}
          maxWidth
        />
        <div className="hidden sm:block">
          <CarouselControls
            total={videos.length}
            activeIndex={videoSlide}
            onPrev={handlePrev}
            onNext={handleNext}
            onSelect={handleSelect}
            prevLabel={tCommon('previous')}
            nextLabel={tCommon('next')}
            inverted
            showDots={false}
            className="justify-end"
          />
        </div>
      </div>

      <div className="relative overflow-hidden md:hidden">
        <AppSwiper
          slideCount={videos.length}
          controller={controller}
          autoplay={!isDesktop}
          swiperOptions={{
            speed: 700,
            effect: 'coverflow',
            centeredSlides: true,
            slidesPerView: 1,
            spaceBetween: 8,
            grabCursor: true,
            watchSlidesProgress: true,
            coverflowEffect: {
              rotate: 0,
              stretch: -12,
              depth: 140,
              modifier: 1,
              slideShadows: false,
            },
          }}
        >
          {videos.map((item) => (
            <AppSwiperSlide key={item.id}>
              <HomepageVideoCard
                item={item}
                videoResetToken={videoResetToken}
                onVideoPlayStart={handleVideoPlayStart}
              />
            </AppSwiperSlide>
          ))}
        </AppSwiper>
      </div>

      <div className="relative hidden md:block -mt-6 pb-2">
        {videos.length > 0 && (
          <div
            className="relative mx-auto h-[520px] w-full max-w-[1240px]"
            style={{
              perspective: '1200px',
              transformStyle: 'preserve-3d',
            }}
          >
            {videos.map((item, index) => {
              const distance = getWrappedDistance(index, videoSlide, videos.length);
              return (
                <div
                  key={item.id}
                  className={
                    distance === 0
                      ? 'absolute inset-0 flex items-center justify-center pointer-events-auto'
                      : 'absolute inset-0 flex items-center justify-center pointer-events-none'
                  }
                  style={getVideoCardStyle(index, videoSlide, videos.length)}
                >
                  <div className="w-[500px] xl:w-[520px]">
                    <HomepageVideoCard
                      item={item}
                      videoResetToken={videoResetToken}
                      onVideoPlayStart={handleVideoPlayStart}
                    />
                  </div>
                </div>
              );
            })}
          </div>
        )}
      </div>

      <CarouselControls
        total={videos.length}
        activeIndex={videoSlide}
        onPrev={handlePrev}
        onNext={handleNext}
        onSelect={handleSelect}
        prevLabel={tCommon('previous')}
        nextLabel={tCommon('next')}
        inverted
        getDotLabel={(index) => t('featuredVideos.pagerLabel', { index: index + 1 })}
        showArrows={false}
        className="justify-start"
      />
    </Section>
  );
};

export default HomepageFeaturedVideos;
