UI.MD

Dropzone

A dashed area that takes dropped files or opens the file picker, checks type, size and count, and lists the files the app holds under it. It never uploads; the app does.

Installation

$
npx shadcn@latest add https://ui.mattdowney.com/r/dropzone.json

Usage

import { Dropzone, DropzoneFiles, DropzoneFile } from "@/components/ui/dropzone"

Examples

Default

Any file, up to 5 MB each. The app keeps what onFiles hands it and lists each one under the zone with DropzoneFile.

Drop files here or browseUp to 5 MB each

Images, with limits

accept, maxSize and maxFiles turn files away through onReject, each with its reason. Pass an image's object URL as preview to show it.

Drop images here or browsePNG, JPG or WebP, up to 2 MB. 4 left.

Invalid and disabled

invalid draws the failed edge when a file is required. disabled turns it off, for example once maxFiles is reached.

Add a file to continue
Drop files here or browse4 files at most. Remove one to add another.

API Reference

PropTypeDefaultDescription
onFiles(files: File[]) => void-The files that passed accept, maxSize and maxFiles, in the order given. The app uploads them.
onReject(rejections: { file: File; reason: "type" | "size" | "count" }[]) => void-The files turned away, each with its reason.
acceptstring-What it takes, in the file input's own syntax (image/*,.pdf). Any file when absent.
maxSizenumber-The largest file it takes, in bytes.
maxFilesnumber-How many more files it takes. Past this, the rest are turned away as count.
multiplebooleantrueSeveral files at a time. false takes one.
titleReact.ReactNode-The line in the zone. Default "Drop files here or browse".
hintReact.ReactNode-The quiet line under it. Defaults to the size and count limits, when set.
iconIconProp-Shown above the title. Default an upload arrow.
invalidboolean-Draws the failed edge.
disabledboolean-Takes no files and opens no picker.
nameDropzoneFilestring-The file's name, cut short with the full name on hover.
sizeDropzoneFilenumber-In bytes, shown as a person reads it (1.5 MB).
previewDropzoneFilestring-A picture of the file, such as an image's object URL. A file icon when absent.
statusDropzoneFile"uploading" | "done" | "error""done"uploading shows a spinner. error shows error in place of the size.
errorDropzoneFileReact.ReactNode-Why it failed. Default "Could not upload".
onRemoveDropzoneFile() => void-Shows a remove button.
onFiles(files: File[]) => voidThe files that passed accept, maxSize and maxFiles, in the order given. The app uploads them.
onReject(rejections: { file: File; reason: "type" | "size" | "count" }[]) => voidThe files turned away, each with its reason.
acceptstringWhat it takes, in the file input's own syntax (image/*,.pdf). Any file when absent.
maxSizenumberThe largest file it takes, in bytes.
maxFilesnumberHow many more files it takes. Past this, the rest are turned away as count.
multipleboolean = trueSeveral files at a time. false takes one.
titleReact.ReactNodeThe line in the zone. Default "Drop files here or browse".
hintReact.ReactNodeThe quiet line under it. Defaults to the size and count limits, when set.
iconIconPropShown above the title. Default an upload arrow.
invalidbooleanDraws the failed edge.
disabledbooleanTakes no files and opens no picker.
nameDropzoneFilestringThe file's name, cut short with the full name on hover.
sizeDropzoneFilenumberIn bytes, shown as a person reads it (1.5 MB).
previewDropzoneFilestringA picture of the file, such as an image's object URL. A file icon when absent.
statusDropzoneFile"uploading" | "done" | "error" = "done"uploading shows a spinner. error shows error in place of the size.
errorDropzoneFileReact.ReactNodeWhy it failed. Default "Could not upload".
onRemoveDropzoneFile() => voidShows a remove button.