import { useState } from 'react'; import { Pressable, Text, View } from 'react-native'; import { CircleCheckBig, CircleDot, Pencil, Trash2, Users, } from 'lucide-react-native'; import { cn } from '@/lib/utils'; import { BottomSheet } from '@/components/BottomSheet'; export type StreamActionId = | 'toggle-status' | 'rename' | 'members' | 'edit-particle' | 'delete-particle'; interface StreamActionsSheetProps { open: boolean; onClose: () => void; onSelect: (action: StreamActionId) => void; streamStatus: 'open' | 'closed'; isCreator: boolean; /** True when the *current* particle is a text particle this user authored. */ canEditParticle: boolean; /** True when the *current* particle is one this user can soft-delete. */ canDeleteParticle: boolean; } export function StreamActionsSheet({ open, onClose, onSelect, streamStatus, isCreator, canEditParticle, canDeleteParticle, }: StreamActionsSheetProps) { // Hold the picked action until the sheet's Modal has fully unmounted, then // dispatch. Follow-ups like rename/members open another Modal and "delete // particle" shows an Alert — both are iOS Modals, and iOS will not present // a second Modal while another is still on screen. Without this defer, the // tap appears to do nothing and the app feels frozen behind a phantom // overlay until the close animation finishes. const [pending, setPending] = useState(null); const choose = (id: StreamActionId) => { setPending(id); onClose(); }; const handleClosed = () => { if (pending) { onSelect(pending); setPending(null); } }; return ( ) : ( ) } label={streamStatus === 'open' ? 'Close stream' : 'Reopen stream'} onPress={() => choose('toggle-status')} /> } label="Members" onPress={() => choose('members')} /> {isCreator ? ( } label="Rename stream" onPress={() => choose('rename')} /> ) : null} {canEditParticle ? ( } label="Edit particle" onPress={() => choose('edit-particle')} /> ) : null} {canDeleteParticle ? ( } label="Delete particle" tone="destructive" onPress={() => choose('delete-particle')} /> ) : null} Cancel ); } function ActionRow({ icon, label, onPress, tone = 'default', }: { icon: React.ReactNode; label: string; onPress: () => void; tone?: 'default' | 'destructive'; }) { return ( {icon} {label} ); }