79 lines
2.7 KiB
TypeScript
79 lines
2.7 KiB
TypeScript
'use client';
|
|
|
|
import { useEffect, useCallback } from 'react';
|
|
import { createPortal } from 'react-dom';
|
|
import { motion, AnimatePresence } from 'framer-motion';
|
|
import { X } from 'lucide-react';
|
|
|
|
interface DemoVideoModalProps {
|
|
isOpen: boolean;
|
|
onClose: () => void;
|
|
}
|
|
|
|
export function DemoVideoModal({ isOpen, onClose }: DemoVideoModalProps) {
|
|
const handleKeyDown = useCallback(
|
|
(e: KeyboardEvent) => {
|
|
if (e.key === 'Escape') onClose();
|
|
},
|
|
[onClose]
|
|
);
|
|
|
|
useEffect(() => {
|
|
if (!isOpen) return;
|
|
document.addEventListener('keydown', handleKeyDown);
|
|
document.body.style.overflow = 'hidden';
|
|
return () => {
|
|
document.removeEventListener('keydown', handleKeyDown);
|
|
document.body.style.overflow = '';
|
|
};
|
|
}, [isOpen, handleKeyDown]);
|
|
|
|
if (typeof document === 'undefined') return null;
|
|
|
|
return createPortal(
|
|
<AnimatePresence>
|
|
{isOpen && (
|
|
<motion.div
|
|
initial={{ opacity: 0 }}
|
|
animate={{ opacity: 1 }}
|
|
exit={{ opacity: 0 }}
|
|
transition={{ duration: 0.25 }}
|
|
className="fixed inset-0 z-[100] flex items-center justify-center bg-brand-navy/90 backdrop-blur-sm p-4 sm:p-8"
|
|
onClick={onClose}
|
|
role="dialog"
|
|
aria-modal="true"
|
|
aria-label="Démonstration Xpeditis"
|
|
>
|
|
<motion.div
|
|
initial={{ opacity: 0, scale: 0.95, y: 20 }}
|
|
animate={{ opacity: 1, scale: 1, y: 0 }}
|
|
exit={{ opacity: 0, scale: 0.95, y: 20 }}
|
|
transition={{ duration: 0.3, ease: 'easeOut' }}
|
|
className="relative w-full max-w-5xl"
|
|
onClick={e => e.stopPropagation()}
|
|
>
|
|
<button
|
|
onClick={onClose}
|
|
aria-label="Fermer"
|
|
className="absolute -top-12 right-0 p-2 text-white/80 hover:text-white transition-colors rounded-full hover:bg-white/10"
|
|
>
|
|
<X className="w-7 h-7" />
|
|
</button>
|
|
<div className="rounded-2xl overflow-hidden shadow-2xl ring-1 ring-white/20 bg-black aspect-video">
|
|
{/* Le WebM 2026 passe en premier : le navigateur retient la
|
|
premiere source qu'il sait lire, et c'est la seule a jour du
|
|
design actuel. Le MP4 de juillet reste en dernier recours
|
|
pour Safari, qui ne lit pas le VP8. */}
|
|
<video controls autoPlay playsInline className="w-full h-full object-contain">
|
|
<source src="/assets/videos/demo-xpeditis-2026.webm" type="video/webm" />
|
|
<source src="/assets/videos/demo-xpeditis.mp4" type="video/mp4" />
|
|
</video>
|
|
</div>
|
|
</motion.div>
|
|
</motion.div>
|
|
)}
|
|
</AnimatePresence>,
|
|
document.body
|
|
);
|
|
}
|