Workspace tools
Task-specific tools: a file manager, a music studio and a collaborative canvas.
Installation & usage
npx @youj/cli add app-file-managerAlso installs app-page, async-button, badge, breadcrumb, button, checkbox, context-menu, counter, empty, icon-archive, icon-check, icon-cloud-upload, icon-copy, icon-download, icon-eye, icon-file, icon-file-text, icon-film, icon-folder, icon-image, icon-layout-grid, icon-layout-list, icon-link, icon-menu, icon-music, icon-search, icon-table, icon-trash, icon-upload, icon-x, illustrations, input-group, morph-label, presence-list, progress, resizable, select, sheet, skeleton, switch, toast, toggle-group, tree-view, typography, use-mobile, youj-core, youj-presets, youj-ui-core.
The CLI copies the block to blocks/app/file-manager.tsx with every component it uses, so it’s yours to edit.
Every prop is optional and falls back to the demo, so it renders as you see it until you pass your own. Give it your data, rewrite or translate its strings through copy, and connect its actions:
'use client'
import { FileManager, type FileManagerProps } from '@/blocks/app/file-manager'
export function FileManagerView({ files, folders, storage }: Pick<FileManagerProps, 'files' | 'folders' | 'storage'>) {
return (
<FileManager
files={files}
folders={folders}
storage={storage}
copy={{ titleSuffix: ' files' }}
onFolderChange={(folder) => {
// your code
}}
onViewChange={(view) => {
// your code
}}
onUpload={(file, folder, onProgress) => {
// your code
}}
/>
)
}Description
Browse, upload and preview files with folders and a choice of grid or list views; this story opens on the grid.
Browse, upload and preview files with folders and a choice of grid or list views; this story opens on the grid.
Run a music session from controls that float over the song: play, change the tempo, snap the grid and search for clips.
Run a music session from controls that float over the song: play, change the tempo, snap the grid and search for clips.
Let visitors choose a meeting time on a booking page that accounts for duration and time zone.
Code
File Manager, the File manager story: the files youj add writes.
blocks/app
Reference
Props28 props, 3 types
Props
| Prop | Type | |
|---|---|---|
theme | ThemeInputA theme to force on the block. Default: none, so it inherits the app's (YoujProvider or a ThemeScope around it). | – |
embedded | booleanA page in your app's frame: the shared page header (AppPage) with search and Upload, and the frame's gutter, with no top bar of its own. default true | true |
brand | { name: string; logo?: ReactNode }The product in the header, the breadcrumb root and the demo logo files. default Stash | Stash |
headingLevel | 1 | 2 | 3The title's level. default 1 | 1 |
copy | Partial<FileManagerCopy>Any of the block's strings, to rewrite or translate. | – |
locale | stringFormats dates and sizes. Default: | – |
files | FileManagerFile[]Every file, each naming its folder by id. Uploads and deletes change the list from here. default the demo's seventeen | the demo's seventeen |
folders | FileManagerFolder[]The folder tree. default Brand, Campaigns (Autumn 26, Orbit launch), Contracts, Research | Brand, Campaigns (Autumn 26, Orbit launch), Contracts, Research |
storage | FileManagerStorage[]What the storage meter splits the space used into. default media, documents, archives | media, documents, archives |
quota | numberThe storage quota, in bytes. default 100 GB | 100 GB |
now | Date | numberThe moment "Today" and "3 days ago" count from, in epoch ms. default a fixed demo date | a fixed demo date |
folder | stringThe open folder, to control it. Pair with | – |
defaultFolder | stringThe folder open at first, when uncontrolled. Default: Autumn 26 in the demo, else the first folder. | – |
onFolderChange | (folder: string) => voidCalled with the folder's id when the person opens another. | – |
view | 'grid' | 'list'Grid or list, to control it. Pair with | – |
defaultView | 'grid' | 'list'Grid or list at first, when uncontrolled. default 'grid' | 'grid' |
onViewChange | (view: 'grid' | 'list') => voidCalled when the person switches between grid and list. | – |
onUpload | (file: File, folder: string, onProgress: (percent: number) => void) => ReturnType<FileManagerUploadHandler>Uploads one dropped or picked file into the open folder; report progress and resolve with the stored file. A rejection drops it from the tray with its message. Default: a demo transfer. | – |
onDelete | (files: FileManagerFile[]) => Promise<unknown> | unknownMoves files to trash. They leave at once; a rejection puts them back and shows its message. | – |
onRestore | (files: FileManagerFile[]) => Promise<unknown> | unknownUndo after a delete: the files are back in the list. | – |
onDownload | (files: FileManagerFile[]) => Promise<unknown> | unknownDownloads one file (the preview) or the selection; resolve when it's done. Default: a demo wait. | – |
onCopyLink | (file: FileManagerFile) => Promise<unknown> | unknownCopies a file's link (the tile's menu); resolve when copied. Default: a "Link copied" toast. | – |
getShareUrl | (file: FileManagerFile) => stringThe share link the preview shows and copies. Default: a demo stash.app link. | – |
onOpen | (file: FileManagerFile) => voidCalled when a file's preview opens. | – |
loading | booleanShows skeleton tiles in place of the files while they load. default false | false |
error | ReactNodeA load failure, shown in place of the files, with Try again when | – |
onRetry | () => voidCalled from the error's Try again button. | – |
empty | ReactNodeReplaces the empty folder's state. Default: a drop hint from | – |
FileManagerFile
| Prop | Type | |
|---|---|---|
idRequired | string | – |
nameRequired | string | – |
folderRequired | stringThe id of the folder it sits in. | – |
kindRequired | Kind'image''video''doc''pdf''sheet''audio''archive' | – |
sizeRequired | numberIn bytes. | – |
modifiedRequired | numberWhen it last changed, in epoch milliseconds. | – |
ownerRequired | string | – |
scene | SceneThe scene that says what's inside. Default: its kind's. | – |
preview | 'wordmark' | 'wordmark-inverse' | 'swatches'Draws the content itself instead of a scene, for a file whose content is the point: a logo, a palette. | – |
length | stringA clip's running time, shown on its tile. | – |
FileManagerFolder
| Prop | Type | |
|---|---|---|
idRequired | string | – |
nameRequired | string | – |
children | FileManagerFolder[]Folders inside it, shown in the tree and as tiles above its files. | – |
FileManagerStorage
| Prop | Type | |
|---|---|---|
labelRequired | string | – |
bytesRequired | number | – |
toneRequired | stringThe meter cells' background class, e.g. 'bg-accent'. | – |
Strings57 keys for copy
Strings
copy takes any of these keys; the rest keep their defaults. A key whose text holds a value (a count, a name) takes a function.
titleSuffixsearchsearchPlaceholderuploadfoldersresizeFoldersstoragestorageOffilessortBysortModifiedsortNamesortSizeviewgridlistnoMatchTitlenoMatchDescriptionemptyTitleemptyDescriptionerrorTitleretrydropTopreviewselectdeselectselectFilecopyLinklinkCopiedcopieddeletemovedOnemovedManyundoactionFailedselectionselecteddownloaddownloadSelectedzippeddownloadeddeleteSelectedclearSelectionuploadsuploadinguploadingFileuploadFailedyoushareTitleshareSwitchlocationmodifiedownersizetodaykindslocaleAccessibilitylandmarks, toolbars, status
Accessibility
File manager is a main under a header with labelled toolbar controls, a selection bar and an upload tray; the preview opens in a sheet that traps focus and closes with Escape, and file actions sit in menus with arrow-key navigation. Music studio’s controls are a labelled group and its arrangement is a labelled ordered list. Collaborative canvas is a main named by its board, with breadcrumbs, a labelled group of who is here and a Share button that reports the copied link; the board is the Whiteboard, its shapes a listbox walked with Tab, its cards regions of their own, and each comment pin a button that opens its thread in a popover that takes and returns focus. Links and buttons are real a and button elements with the kit’s focus ring.
Meeting booking is a main with time slots that use aria-pressed, field errors in an alert and the confirmation in a status region.