import { useState, useRef, useEffect } from 'react' import { useQuery } from '@tanstack/react-query' import { useNavigate } from 'react-router-dom' import { useTranslation } from 'react-i18next' import { promoApi } from '../api/promo' const SparklesIcon = () => ( ) const ClockIcon = () => ( ) const formatTimeLeft = (expiresAt: string, t: (key: string) => string): string => { const now = new Date() const expires = new Date(expiresAt) const diffMs = expires.getTime() - now.getTime() if (diffMs <= 0) return '' const hours = Math.floor(diffMs / (1000 * 60 * 60)) const minutes = Math.floor((diffMs % (1000 * 60 * 60)) / (1000 * 60)) if (hours > 24) { const days = Math.floor(hours / 24) return `${days}${t('promo.time.days')}` } if (hours > 0) { return `${hours}${t('promo.time.hours')} ${minutes}${t('promo.time.minutes')}` } return `${minutes}${t('promo.time.minutes')}` } export default function PromoDiscountBadge() { const { t } = useTranslation() const navigate = useNavigate() const [isOpen, setIsOpen] = useState(false) const dropdownRef = useRef(null) const { data: activeDiscount } = useQuery({ queryKey: ['active-discount'], queryFn: promoApi.getActiveDiscount, staleTime: 30000, refetchInterval: 60000, // Refresh every minute }) // Close dropdown on click outside useEffect(() => { function handleClickOutside(event: MouseEvent) { if (dropdownRef.current && !dropdownRef.current.contains(event.target as Node)) { setIsOpen(false) } } document.addEventListener('mousedown', handleClickOutside) return () => document.removeEventListener('mousedown', handleClickOutside) }, []) // Don't render if no active discount if (!activeDiscount || !activeDiscount.is_active || !activeDiscount.discount_percent) { return null } const timeLeft = activeDiscount.expires_at ? formatTimeLeft(activeDiscount.expires_at, t) : null const handleClick = () => { setIsOpen(!isOpen) } const handleGoToSubscription = () => { setIsOpen(false) navigate('/subscription') } return ( {/* Badge button */} {/* Animated sparkle effect */} -{activeDiscount.discount_percent}% {/* Notification dot */} {/* Dropdown - mobile: fixed centered, desktop: absolute right */} {isOpen && ( <> {/* Mobile backdrop */} setIsOpen(false)} /> {/* Header */} {t('promo.discountActive')} -{activeDiscount.discount_percent}% {/* Content */} {t('promo.discountDescription')} {/* Time remaining */} {timeLeft && ( {t('promo.expiresIn')}: {timeLeft} )} {/* CTA Button */} {t('promo.useNow')} > )} ) }
{t('promo.discountDescription')}