Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 | 2x 2x 2x 2x 7x 1x 7x 7x | "use client";
import { useMemo } from "react";
import Image from "next/image";
import { XMarkIcon } from "@/components/icons/XMark";
import { MusicalNoteIcon } from "@/components/icons/MusicalNote";
import type { FilePreviewType } from "@/utils/file-type";
type FilePreviewPanelProps = {
file: File;
type: FilePreviewType;
onClose: () => void;
};
function PreviewContent({ file, type, url }: { file: File; type: FilePreviewType; url: string }) {
switch (type) {
case "image":
return (
<Image
src={url}
alt={file.name}
width={500}
height={500}
unoptimized
className="h-auto max-h-full w-auto max-w-full rounded-lg object-contain shadow-md"
/>
);
case "video":
return <video src={url} controls className="max-h-full max-w-full rounded-lg shadow-md" />;
case "audio":
return (
<div className="flex w-full max-w-sm flex-col items-center gap-4">
<div className="flex h-20 w-20 items-center justify-center rounded-2xl bg-amber-500/15 text-amber-400 light:bg-amber-50 light:text-amber-500">
<MusicalNoteIcon className="size-10" />
</div>
<audio src={url} controls className="w-full" />
</div>
);
default:
return null;
}
}
export function FilePreviewPanel({ file, type, onClose }: FilePreviewPanelProps) {
const url = useMemo(() => URL.createObjectURL(file), [file]);
return (
<div className="flex h-full flex-1 flex-col overflow-hidden rounded-[1.75rem] border border-white/9 bg-panel backdrop-blur-[28px] shadow-navy-xl light:border-slate-200 light:shadow-glass-card-light animate-drawer-in">
<div className="flex items-center justify-between border-b border-white/8 px-5 py-3.5 light:border-slate-200">
<h4 className="truncate text-sm font-medium text-white/85 light:text-slate-800">{file.name}</h4>
<button
type="button"
aria-label="Close preview"
onClick={onClose}
className="ml-4 grid h-7 w-7 shrink-0 place-items-center rounded-lg text-white/40 transition hover:bg-rose-500/15 hover:text-rose-300 light:text-slate-400 light:hover:bg-rose-50 light:hover:text-rose-500"
>
<XMarkIcon className="size-4" />
</button>
</div>
<div className="min-h-0 flex-1 flex items-center justify-center bg-white/4 p-4 light:bg-slate-100">
<PreviewContent file={file} type={type} url={url} />
</div>
</div>
);
}
|