import { memo, useState } from 'react' import { motion, AnimatePresence } from 'framer-motion' import { fmtMD, fmtYMD, dayBadge } from './config' function CardItem({ item, cfg }) { const badge = dayBadge(item, cfg) const start = item[cfg.dateStartKey] const end = item[cfg.dateEndKey] const startMD = fmtMD(start || item.date) const endMD = fmtMD(end || item.date) const dateText = (item.ongoing_flag === 'true' || item.ongoing_flag === true) ? '์ƒ์‹œํŒ๋งค' : start || end ? (startMD === endMD ? startMD : `${startMD} ~ ${endMD}`) : fmtYMD(item.date) const badgeBg = { emerald: 'var(--badge-emerald-bg)', amber: 'var(--badge-amber-bg)', gray: 'var(--badge-gray-bg)', }[badge?.tone] return (
{item.thumbnail_url ? ( ) : (
๐Ÿ“ข
)} {badge && ( {badge.label} )}
{item.title}
{dateText}
) } function CarouselSection({ cfg, items, isMaintenance, isLoading }) { const [page, setPage] = useState(0) const pages = Math.max(1, Math.ceil(items.length / cfg.pageSize)) const clamped = Math.min(page, pages - 1) const slice = items.slice(clamped * cfg.pageSize, (clamped + 1) * cfg.pageSize) const navBtn = "w-7 h-7 rounded-md border flex items-center justify-center border-[var(--btn-border)] bg-[var(--btn-bg)] hover:bg-[var(--btn-bg-hover)] hover:border-[var(--btn-border-hover)] disabled:opacity-30 disabled:hover:bg-[var(--btn-bg)] disabled:hover:border-[var(--btn-border)]" return (

{cfg.label}

{pages > 1 && (
{clamped + 1} / {pages}
)}
{isLoading ? (
{Array.from({ length: cfg.pageSize }).map((_, i) => (
))}
) : isMaintenance ? (
๋„ฅ์Šจ Open API ์ ๊ฒ€์ค‘
) : slice.length === 0 ? (
{cfg.filterOngoing ? `์ง„ํ–‰์ค‘์ธ ${cfg.label}์ด ์—†์Šต๋‹ˆ๋‹ค` : `๋“ฑ๋ก๋œ ${cfg.label}์ด ์—†์Šต๋‹ˆ๋‹ค`}
) : ( {slice.map((it) => )} )}
) } export default memo(CarouselSection)