import { api } from "@fileone/convex/_generated/api" import type { PathComponent } from "@fileone/convex/model/filesystem" import { useMutation } from "@tanstack/react-query" import { Link } from "@tanstack/react-router" import { useMutation as useConvexMutation } from "convex/react" import { useAtom, useSetAtom } from "jotai" import { ChevronDownIcon, Loader2Icon, PlusIcon, UploadCloudIcon, } from "lucide-react" import React, { type ChangeEvent, Fragment, useContext, useRef } from "react" import { toast } from "sonner" import { ImagePreviewDialog } from "@/components/image-preview-dialog" import { DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuTrigger, } from "@/components/ui/dropdown-menu" import { DirectoryIcon } from "../../components/icons/directory-icon" import { TextFileIcon } from "../../components/icons/text-file-icon" import { Breadcrumb, BreadcrumbItem, BreadcrumbLink, BreadcrumbList, BreadcrumbPage, BreadcrumbSeparator, } from "../../components/ui/breadcrumb" import { Button } from "../../components/ui/button" import { DirectoryPageContext } from "./context" import { DirectoryContentTable } from "./directory-content-table" import { RenameFileDialog } from "./rename-file-dialog" import { newItemKindAtom, openedFileAtom } from "./state" export function DirectoryPage() { return ( <>
) } function FilePathBreadcrumb() { const { rootDirectory, directory } = useContext(DirectoryPageContext) console.log(directory.path) const breadcrumbItems: React.ReactNode[] = [] for (let i = 1; i < directory.path.length - 1; i++) { breadcrumbItems.push( , ) } return ( {rootDirectory._id === directory._id ? ( All Files ) : ( )} {breadcrumbItems} {directory.name}{" "} ) } function FilePathBreadcrumbItem({ component }: { component: PathComponent }) { return ( {component.name || "All Files"} ) } // tags: upload, uploadfile, uploadfilebutton, fileupload, fileuploadbutton function UploadFileButton() { const { directory } = useContext(DirectoryPageContext) const generateUploadUrl = useConvexMutation(api.files.generateUploadUrl) const saveFile = useConvexMutation(api.files.saveFile) const { mutate: uploadFile, isPending: isUploading } = useMutation({ mutationFn: async (file: File) => { const uploadUrl = await generateUploadUrl() const uploadResult = await fetch(uploadUrl, { method: "POST", body: file, headers: { "Content-Type": file.type, }, }) const { storageId } = await uploadResult.json() await saveFile({ storageId, name: file.name, size: file.size, mimeType: file.type, directoryId: directory._id, }) }, onSuccess: () => { toast.success("File uploaded successfully.") }, }) const fileInputRef = useRef(null) const handleClick = () => { fileInputRef.current?.click() } const onFileUpload = async (e: ChangeEvent) => { const file = e.target.files?.[0] if (file) { uploadFile(file) } } return ( <> ) } function NewDirectoryItemDropdown() { const setNewItemKind = useSetAtom(newItemKindAtom) const addNewDirectory = () => { setNewItemKind("directory") } return ( Text file Directory ) } function PreviewDialog() { const [openedFile, setOpenedFile] = useAtom(openedFileAtom) if (!openedFile) return null console.log("openedFile", openedFile) switch (openedFile.mimeType) { case "image/jpeg": case "image/png": case "image/gif": return ( setOpenedFile(null)} /> ) default: return null } }