File count
Use maxFiles to cap how many files can be attached at once. The default is
0, which means unlimited.
<DropUpload maxFiles={3} />The limit applies to the whole attached list, not to a single drop: if two
files are already attached and maxFiles={3}, the next drop only accepts one
more.
Feedback for the user
When maxFiles is set, the drop area's description line ends with the limit
("Up to 3 files"), alongside the format and size hints — so the cap is visible
before anything is dropped.
Because files over the limit never join the list, a drop that is entirely
turned away would otherwise look like nothing happened. To avoid that, the
component shows a short-lived notice under the drop area ("You can only attach
up to 3 files") whenever a selection hits the cap. It is announced to screen
readers (role="status"), and after 4 seconds it fades out while collapsing
its own height, so the file list underneath glides back up on the same spring
the drop area and the list already use.
Both strings come from the active locale and can be replaced through
translations:
<DropUpload
maxFiles={3}
translations={{
maxFilesLabel: (max) => `${max} files tops`,
maxFilesReached: (max) => `That's ${max} already — remove one first`,
}}
/>What happens to the extra files
Files beyond the limit are never attached — unlike size or format
rejections, they don't show up in the list as rejected entries, since the
whole point of maxFiles is to keep the list capped. They are reported
through onFilesRejected with the reason
"tooManyFiles":
<DropUpload
maxFiles={3}
onFilesRejected={(rejected) => {
const overflow = rejected.filter((file) => file.reason === "tooManyFiles")
if (overflow.length) {
toast.error(`Only 3 files allowed — ${overflow.length} were ignored`)
}
}}
/>Files rejected for other reasons (too large, wrong type, spoofed) do stay in the list flagged as rejected, so they still take up one of the available slots. Discard one to free it up again.
Single-file uploads
With maxFiles={1} the underlying <input type="file"> drops its multiple
attribute, so the browser's file picker only lets the user choose one file.
Dropping several files at once still works — only the first one is taken.
<DropUpload maxFiles={1} allowedFormats={["image/*"]} autoHideDropArea />The avatar variant is the exception to all of this: it
pins maxFiles to 1 and a new image replaces the one in the circle instead of
being turned away.
Like every other validation here, the limit is enforced in the browser and can be bypassed. Cap the number of files on your server too.