import React, { useMemo } from 'react'; import { Button } from "@/components/ui/button"; import { DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuTrigger, } from "@/components/ui/dropdown-menu"; import { Drawer, DrawerClose, DrawerContent, DrawerDescription, DrawerFooter, DrawerHeader, DrawerTitle, DrawerTrigger, } from "@/components/ui/drawer"; import { Textarea } from "./ui/textarea"; import { DotsVerticalIcon, CodeIcon, Share1Icon } from "@radix-ui/react-icons"; import { Input } from "./ui/input"; import { useRef, useState } from 'react'; import { useToast } from "./ui/use-toast"; import { Event as NostrEvent, nip19 } from "nostr-tools"; import { Trash2 } from "lucide-react"; import { useNostr } from "nostr-react"; import { signEvent } from "@/utils/utils"; interface CardOptionsDropdownProps { event: NostrEvent; } export default function CardOptionsDropdown({ event }: CardOptionsDropdownProps) { const jsonEvent = useMemo(() => JSON.stringify(event, null, 2), [event]); const inputRef = useRef(null); const inputRefID = useRef(null); const { toast } = useToast(); const { publish } = useNostr(); const [dropdownOpen, setDropdownOpen] = useState(false); const [shareDrawerOpen, setShareDrawerOpen] = useState(false); const [rawDrawerOpen, setRawDrawerOpen] = useState(false); const [deleteDrawerOpen, setDeleteDrawerOpen] = useState(false); const [deleteReason, setDeleteReason] = useState(''); const handleCopyLink = async () => { try { await navigator.clipboard.writeText(window.location.href); toast({ description: 'URL copied to clipboard', title: 'Copied' }); } catch (err) { toast({ description: 'Error copying URL to clipboard', title: 'Error', variant: 'destructive' }); } }; const handleCopyNoteId = async () => { try { await navigator.clipboard.writeText(nip19.noteEncode(event.id)); toast({ description: 'Note ID copied to clipboard', title: 'Copied' }); } catch (err) { toast({ description: 'Error copying Note ID to clipboard', title: 'Error', variant: 'destructive' }); } }; const handleRequestDeletion = async () => { // Check if the user is the owner of the event const userPubkey = window.localStorage.getItem('pubkey'); if (!userPubkey) { toast({ description: 'You need to be logged in to request deletion', title: 'Error', variant: 'destructive' }); return; } if (userPubkey !== event.pubkey) { toast({ description: 'You can only request deletion of your own posts', title: 'Error', variant: 'destructive' }); return; } const loginType = window.localStorage.getItem('loginType'); if (!loginType) { toast({ description: 'Login type is missing. Please log in again.', title: 'Error', variant: 'destructive' }); return; } // Create a kind 5 event (deletion request) as per NIP-09 const deletionEvent: NostrEvent = { kind: 5, created_at: Math.floor(Date.now() / 1000), content: deleteReason, tags: [ ["e", event.id], ["k", event.kind.toString()] ], pubkey: "", id: "", sig: "", }; // Sign the event const signedEvent = await signEvent(loginType, deletionEvent); if (signedEvent) { // Publish the deletion request publish(signedEvent); toast({ description: 'Deletion request has been published', title: 'Success' }); setDeleteDrawerOpen(false); } else { toast({ description: 'Failed to sign deletion request', title: 'Error', variant: 'destructive' }); } }; return ( <> {/* Share option */} { setDropdownOpen(false); setTimeout(() => setShareDrawerOpen(true), 100); }} > Share {/* View Raw option */} { setDropdownOpen(false); setTimeout(() => setRawDrawerOpen(true), 100); }} > View Raw {/* Delete option (only visible for the owner) */} {window.localStorage.getItem('pubkey') === event.pubkey && ( { setDropdownOpen(false); setTimeout(() => setDeleteDrawerOpen(true), 100); }} > Request Deletion )} {/* Share Drawer */} Share this Note Share this Note with others.
{/* Raw Event Drawer */} Raw Event This shows the raw event data.