'use client';

import { useEffect, useState } from 'react';
import Autoplay from 'embla-carousel-autoplay';
import {
	Carousel,
	CarouselApi,
	CarouselContent,
	CarouselItem,
	CarouselNext,
	CarouselPrevious,
} from '@/components/ui/carousel';
import type { BannerItem } from '@/types/response/banner/active-list';

type Props = {
	items: BannerItem[];
};

export default function HomeBannerCarousel({ items }: Props)
{
	const [api, setApi] = useState<CarouselApi|null>(null);
	const [selectedIndex, setSelectedIndex] = useState(0);
	const [slideCount, setSlideCount] = useState(0);

	useEffect(() => {
		if (!api) {
			return;
		}

		setSlideCount(api.scrollSnapList().length);
		setSelectedIndex(api.selectedScrollSnap());

		const handleSelect = () => {
			setSelectedIndex(api.selectedScrollSnap());
		};

		api.on('select', handleSelect);
		api.on('reInit', handleSelect);

		return () => {
			api.off('select', handleSelect);
			api.off('reInit', handleSelect);
		};
	}, [api]);

	if (items.length === 0) {
		return null;
	}

	return (
		<section
			className="home__banner"
			aria-label="프로모션 배너"
		>
			<Carousel
				setApi={setApi}
				opts={{ loop: items.length > 1, align: 'start' }}
				plugins={items.length > 1 ? [Autoplay({ delay: 5000, stopOnInteraction: false, stopOnMouseEnter: true })] : []}
				className="relative"
			>
				<CarouselContent className="-ml-0">
					{items.map((banner, idx) => (
						<CarouselItem key={banner.id} className="pl-0 basis-full">
							<BannerSlide banner={banner} index={idx} total={items.length} />
						</CarouselItem>
					))}
				</CarouselContent>

				{items.length > 1 && (
					<>
						<CarouselPrevious
							className="left-3 top-1/2 -translate-y-1/2 size-10 bg-black/40 hover:bg-black/60 border-0 text-white"
							aria-label="이전 배너"
						/>
						<CarouselNext
							className="right-3 top-1/2 -translate-y-1/2 size-10 bg-black/40 hover:bg-black/60 border-0 text-white"
							aria-label="다음 배너"
						/>

						<div
							className="absolute bottom-3 left-1/2 -translate-x-1/2 flex gap-2 z-10"
							role="tablist"
							aria-label="배너 인디케이터"
						>
							{Array.from({ length: slideCount }).map((_, idx) => (
								<button
									key={idx}
									type="button"
									onClick={() => api?.scrollTo(idx)}
									aria-label={`${idx + 1}번째 배너로 이동`}
									aria-selected={idx === selectedIndex}
									role="tab"
									className={`h-2 rounded-full transition-all ${idx === selectedIndex ? 'w-6 bg-white' : 'w-2 bg-white/50 hover:bg-white/70'}`}
								/>
							))}
						</div>
					</>
				)}
			</Carousel>
		</section>
	);
}

type SlideProps = {
	banner: BannerItem;
	index: number;
	total: number;
};

function BannerSlide({ banner, index, total }: SlideProps)
{
	const desktop = banner.desktopImage;
	const mobile = banner.mobileImage ?? banner.desktopImage;

	const content = (
		<picture className="home__banner-picture">
			{mobile && (
				<source media="(max-width: 768px)" srcSet={mobile} />
			)}
			{desktop && (
				// eslint-disable-next-line @next/next/no-img-element
				<img
					src={desktop}
					alt={banner.subject}
					loading={index === 0 ? 'eager' : 'lazy'}
					decoding="async"
					className="home__banner-image"
				/>
			)}
		</picture>
	);

	const ariaLabel = `${banner.subject} (${index + 1}/${total})`;

	if (banner.link) {
		return (
			<a
				href={banner.link}
				target={banner.link.startsWith('http') ? '_blank' : undefined}
				rel={banner.link.startsWith('http') ? 'noopener noreferrer' : undefined}
				aria-label={ariaLabel}
				className="home__banner-slide"
			>
				{content}
			</a>
		);
	}

	return (
		<div aria-label={ariaLabel} className="home__banner-slide">
			{content}
		</div>
	);
}
