shadcn.io is not affiliated with official shadcn/ui
Document Slots File Upload Block for Radix UI
Three required-document slots (passport scan, proof of funds, photo page), each its own drop zone with accepted formats, a Missing or Attached status and a Submit that waits for all three.
Installation
Overview
Ask for exactly the documents you need and show what is still missing, with this document intake panel for React with Radix UI. It is the document step of a visa application at Passagio, a visa document intake. A Progress meter reads "2 of 3 attached" over three slots: Passport scan, Proof of funds and Photo page. Each slot is its own File Upload zone for one file, with its accepted formats as Badges and an outline status that says Missing or Attached in words. A file of the wrong format or over 8 MB is refused with the reason under the zone. Once a file is attached the zone shows its name and size and is the Replace control, with a Remove button beside the reason line, and the zone keeps its height in both states. Submit is a Shine Button that stays aria-disabled until all three are in; pressed early, it names the first missing slot and moves focus to its zone. The panel is ruled by Guides. For visa and onboarding checklists and any form with required files.
FAQ
How do I change the documents?
Edit SLOTS. Each has an id, a label, a hint, the formats shown as badges and an accept string for the zone. The meter, the status and the Submit rule all follow the list, so adding a fourth slot needs no other change.
How are wrong files refused?
Each zone sets its own accept and an 8 MB maxFileSize. A refused file never replaces the one you have; the reason ("That format is not accepted for this document.") appears under that zone and the status line says which document was not attached.
Why can I press Submit while it looks off?
Submit uses aria-disabled instead of disabled, so it stays focusable and can explain itself. Pressed early it says which document to attach first and moves focus to that zone. Pressed with all three in, it says the submit happened in this demo.
What stays local, and how do I wire it for real?
Everything. Two slots start attached with typed file names so the first screen shows both states; a file you pick is listed by name and size and is never read or uploaded. To make it real, send each accepted file to your server from the accept handler, show progress in the slot, and check the type and contents there as well.