{
  "name": "file-upload-fill-progress-demo",
  "type": "registry:example",
  "dependencies": [
    "lucide-react"
  ],
  "registryDependencies": [
    "button",
    "file-upload"
  ],
  "files": [
    {
      "path": "examples/file-upload-fill-progress-demo.tsx",
      "type": "registry:example",
      "content": "\"use client\";\n\nimport { Upload, X } from \"lucide-react\";\nimport * as React from \"react\";\nimport { toast } from \"sonner\";\n\nimport { Button } from \"@/registry/bases/radix/ui/button\";\nimport {\n  FileUpload,\n  FileUploadDropzone,\n  FileUploadItem,\n  FileUploadItemDelete,\n  FileUploadItemMetadata,\n  FileUploadItemPreview,\n  FileUploadItemProgress,\n  FileUploadList,\n  FileUploadTrigger,\n} from \"@/registry/bases/radix/ui/file-upload\";\n\nexport default function FileUploadFillProgressDemo() {\n  const [files, setFiles] = React.useState<File[]>([]);\n\n  const onUpload = React.useCallback(\n    async (\n      files: File[],\n      {\n        onProgress,\n        onSuccess,\n        onError,\n      }: {\n        onProgress: (file: File, progress: number) => void;\n        onSuccess: (file: File) => void;\n        onError: (file: File, error: Error) => void;\n      },\n    ) => {\n      try {\n        // Process each file individually\n        const uploadPromises = files.map(async (file) => {\n          try {\n            // Simulate file upload with progress\n            const totalChunks = 10;\n            let uploadedChunks = 0;\n\n            // Simulate chunk upload with delays\n            for (let i = 0; i < totalChunks; i++) {\n              // Simulate network delay (100-300ms per chunk)\n              await new Promise((resolve) =>\n                setTimeout(resolve, Math.random() * 200 + 100),\n              );\n\n              // Update progress for this specific file\n              uploadedChunks++;\n              const progress = (uploadedChunks / totalChunks) * 100;\n              onProgress(file, progress);\n            }\n\n            // Simulate server processing delay\n            await new Promise((resolve) => setTimeout(resolve, 500));\n            onSuccess(file);\n          } catch (error) {\n            onError(\n              file,\n              error instanceof Error ? error : new Error(\"Upload failed\"),\n            );\n          }\n        });\n\n        // Wait for all uploads to complete\n        await Promise.all(uploadPromises);\n      } catch (error) {\n        // This handles any error that might occur outside the individual upload processes\n        console.error(\"Unexpected error during upload:\", error);\n      }\n    },\n    [],\n  );\n\n  const onFileReject = React.useCallback((file: File, message: string) => {\n    toast(message, {\n      description: `\"${file.name.length > 20 ? `${file.name.slice(0, 20)}...` : file.name}\" has been rejected`,\n    });\n  }, []);\n\n  return (\n    <FileUpload\n      value={files}\n      onValueChange={setFiles}\n      maxFiles={10}\n      maxSize={5 * 1024 * 1024}\n      className=\"w-full max-w-md\"\n      onUpload={onUpload}\n      onFileReject={onFileReject}\n      multiple\n    >\n      <FileUploadDropzone>\n        <div className=\"flex flex-col items-center gap-1 text-center\">\n          <div className=\"flex items-center justify-center rounded-full border p-2.5\">\n            <Upload className=\"size-6 text-muted-foreground\" />\n          </div>\n          <p className=\"text-sm font-medium\">Drag & drop files here</p>\n          <p className=\"text-xs text-muted-foreground\">\n            Or click to browse (max 10 files, up to 5MB each)\n          </p>\n        </div>\n        <FileUploadTrigger asChild>\n          <Button variant=\"outline\" size=\"sm\" className=\"mt-2 w-fit\">\n            Browse files\n          </Button>\n        </FileUploadTrigger>\n      </FileUploadDropzone>\n      <FileUploadList orientation=\"horizontal\">\n        {files.map((file, index) => (\n          <FileUploadItem key={index} value={file} className=\"p-0\">\n            <FileUploadItemPreview className=\"size-20\">\n              <FileUploadItemProgress variant=\"fill\" />\n            </FileUploadItemPreview>\n            <FileUploadItemMetadata className=\"sr-only\" />\n            <FileUploadItemDelete asChild>\n              <Button\n                variant=\"secondary\"\n                size=\"icon\"\n                className=\"absolute -top-1 -right-1 size-5 rounded-full\"\n              >\n                <X className=\"size-3\" />\n              </Button>\n            </FileUploadItemDelete>\n          </FileUploadItem>\n        ))}\n      </FileUploadList>\n    </FileUpload>\n  );\n}\n",
      "target": ""
    }
  ]
}