import React, { useState } from 'react'; import { useProfile } from "nostr-react"; import { nip19, } from "nostr-tools"; import { Card, SmallCardContent, } from "@/components/ui/card" import Link from 'next/link'; import Image from 'next/image'; import { Button } from '@/components/ui/button'; import { Eye, Play, PlayCircle } from 'lucide-react'; import { extractDimensions, getProxiedImageUrl, hasNsfwContent, getThumbnailUrl } from '@/utils/utils'; // Function to extract video URL from imeta tags const getVideoUrl = (tags: string[][]): string | null => { for (const tag of tags) { if (tag[0] === 'imeta') { for (let i = 1; i < tag.length; i++) { if (tag[i].startsWith('url ')) { return tag[i].substring(4).trim(); } } } } return null; }; interface QuickViewKind20NoteCardProps { pubkey: string; text: string; image: string; eventId: string; tags: string[][]; event: any; linkToNote: boolean; } const QuickViewKind20NoteCard: React.FC = ({ pubkey, text, image, eventId, tags, event, linkToNote }) => { const {data, isLoading} = useProfile({ pubkey, }); const [imageError, setImageError] = useState(false); const [tryWithoutProxy, setTryWithoutProxy] = useState(false); const [showSensitiveContent, setShowSensitiveContent] = useState(false); // Check if the event has nsfw content const isNsfwContent = hasNsfwContent(tags); // Check if this is a video const isVideo = event.kind === 21 || event.kind === 22; const videoUrl = isVideo ? getVideoUrl(tags) : null; const thumbnailUrl = isVideo ? getThumbnailUrl(tags) : null; // If no image is provided but we have a video URL, use the video URL as the image // For videos, prefer thumbnail URL if available, otherwise use video URL const displayImage = image || (isVideo && thumbnailUrl ? thumbnailUrl : videoUrl); // For video events, we don't need to check if the image starts with http // since video URLs are valid for display purposes if (!displayImage) return null; if (imageError && tryWithoutProxy && !isVideo) return null; const useImgProxy = process.env.NEXT_PUBLIC_ENABLE_IMGPROXY === "true" && !tryWithoutProxy; const processedImage = useImgProxy ? getProxiedImageUrl(displayImage, 500, 0) : displayImage; // For video events, don't process the text content const displayText = isVideo ? "" : text.replaceAll('\n', ' '); // Create nevent with relay hints const nevent = nip19.neventEncode({ id: event.id, relays: event.relays || [] }) const { width, height } = extractDimensions(event); // Toggle sensitive content visibility const toggleSensitiveContent = (e: React.MouseEvent) => { e.preventDefault(); e.stopPropagation(); setShowSensitiveContent(true); }; const card = (
{imageError && tryWithoutProxy && !isVideo ? ( // Fallback for failed images - show a placeholder with play button for videos
{isVideo ? (
) : (

Image unavailable

)}
) : ( <> {isVideo ? ( // For videos, use the video element to show the first frame
); return ( <> {linkToNote ? ( e.preventDefault() : undefined} > {card} ) : ( card )} ); } export default QuickViewKind20NoteCard;