Spaces:
Paused
Paused
File size: 2,618 Bytes
1c72248 |
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 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 |
import React, { useRef, useEffect, useState, ReactNode } from 'react';
import { sampleImageModalState } from '@/components/SampleImageModal';
import { isVideo } from '@/utils/basic';
interface SampleImageCardProps {
imageUrl: string;
alt: string;
numSamples: number;
sampleImages: string[];
children?: ReactNode;
className?: string;
onDelete?: () => void;
}
const SampleImageCard: React.FC<SampleImageCardProps> = ({
imageUrl,
alt,
numSamples,
sampleImages,
children,
className = '',
}) => {
const cardRef = useRef<HTMLDivElement>(null);
const [isVisible, setIsVisible] = useState<boolean>(false);
const [loaded, setLoaded] = useState<boolean>(false);
useEffect(() => {
// Create intersection observer to check visibility
const observer = new IntersectionObserver(
entries => {
if (entries[0].isIntersecting) {
setIsVisible(true);
observer.disconnect();
}
},
{ threshold: 0.1 },
);
if (cardRef.current) {
observer.observe(cardRef.current);
}
return () => {
observer.disconnect();
};
}, []);
const handleLoad = (): void => {
setLoaded(true);
};
console.log('imgurl',imageUrl.toLowerCase().slice(-4))
return (
<div className={`flex flex-col ${className}`}>
{/* Square image container */}
<div
ref={cardRef}
className="relative w-full cursor-pointer"
style={{ paddingBottom: '100%' }} // Make it square
onClick={() => sampleImageModalState.set({ imgPath: imageUrl, numSamples, sampleImages })}
>
<div className="absolute inset-0 rounded-t-lg shadow-md">
{isVisible && (
<>
{isVideo(imageUrl) ? (
<video
src={`/api/img/${encodeURIComponent(imageUrl)}`}
className={`w-full h-full object-cover`}
autoPlay={false}
loop
muted
playsInline
/>
) : (
<img
src={`/api/img/${encodeURIComponent(imageUrl)}`}
alt={alt}
onLoad={handleLoad}
className={`w-full h-full object-cover transition-opacity duration-300 ${
loaded ? 'opacity-100' : 'opacity-0'
}`}
/>
)}
</>
)}
{children && <div className="absolute inset-0 flex items-center justify-center">{children}</div>}
</div>
</div>
</div>
);
};
export default SampleImageCard;
|