/** * @file ImageLightbox.tsx * @description One image shown full size over the whole page; a click or * Escape closes it. Rendered into `document.body`, so no pane, its stacking * layer or a header drawn over a pane can cover it — opened from inside a * pane's Chat view, a `fixed` overlay would otherwise stay in that pane's * layer, under anything stacked above it. * @author Nguyễn Ngọc Trí Vĩ */ import { useEffect } from "react"; import { createPortal } from "react-dom"; export function ImageLightbox({ src, alt, onClose, }: { src: string; alt: string; onClose: () => void; }) { useEffect(() => { const onKey = (e: KeyboardEvent) => e.key === "Escape" && onClose(); document.addEventListener("keydown", onKey); return () => document.removeEventListener("keydown", onKey); }, [onClose]); return createPortal(
{alt}
, document.body ); }