Neura UI

Loading…

 Logo

File Manager

Browse folders, select files, switch between list and grid, and open a details panel from the keyboard.

Files

Pass a tree to :items . Each node takes id , name , size , modified , mime , thumbnail , and children on folders.
javascript

selected

Drop to upload

<neura::file-manager :items="$tree" height="26rem" />

$tree = [
    [
        'id' => 'projects',
        'name' => 'Projects',
        'type' => 'folder',
        'modified' => '2026-07-21 09:12',
        'children' => [
            ['id' => 'brief', 'name' => 'brief.pdf', 'size' => 482310],
        ],
    ],
    ['id' => 'readme', 'name' => 'README.md', 'size' => 4096],
];

Grid

view sets the first layout. The toolbar still switches between list and grid.
blade

selected

Drop to upload

<neura::file-manager :items="$tree" view="grid" />

Compact

Turn off the actions you do not need when the browser sits in a side panel or a dialog.
blade

Drop to upload

<neura::file-manager
    :items="$tree"
    size="sm"
    :selectable="false"
    :details="false"
    :uploadable="false"
    :creatable="false"
    :deletable="false"
/>

Events

Every interaction dispatches a file-manager: event. Listen in Alpine or Livewire.
blade

selected

Drop to upload

Events

Select, open, or delete an item to see the events.

<div
    x-data="{ log: [] }"
    x-on:file-manager:open="log.unshift($event.detail.items[0].name)"
    x-on:file-manager:navigate="console.log($event.detail.path)"
    x-on:file-manager:select="console.log($event.detail.items)"
>
    <neura::file-manager :items="$tree" />
</div>

<neura::file-manager
    :items="$tree"
    x-on:file-manager:delete="$wire.deleteFiles($event.detail.items)"
    x-on:file-manager:navigate="$wire.loadFolder($event.detail.path)"
/>

Events

  • file-manager:open — double-click or Enter on a file
  • file-manager:navigate — folder change (path, folder)
  • file-manager:select — selection changed (items)
  • file-manager:download / file-manager:delete — actions on the selection
  • file-manager:new-folder / file-manager:upload-request — toolbar buttons
  • file-manager:upload — files dropped on the browser (files, path)
  • file-manager:sort / file-manager:view — display preferences
  • file-manager:reorder — drag to reorder (order, items, position)
  • file-manager:move — drop into a folder (items, target, position: inside)

Sort

Column headers and the sort menu cover name, size, modified, and kind. With sortable (on by default), drag items to reorder them, or drop them on the center of a folder to move them in. The sort then becomes manual .
blade

selected

Drop to upload

<neura::file-manager
    :items="$tree"
    sort="manual"
    x-on:file-manager:reorder="$wire.persistOrder($event.detail)"
    x-on:file-manager:move="$wire.moveItems($event.detail)"
/>

<neura::file-manager :items="$tree" :sortable="false" />

Context menu

A right-click on an item offers open, download, rename, and delete. On empty space it offers a new folder, upload, or select all. Dropping files on the browser shows a drop target and dispatches file-manager:upload .
blade

selected

Drop to upload

<neura::file-manager
    :items="$tree"
    :renamable="true"
    :deletable="true"
    x-on:file-manager:rename="$wire.rename($event.detail.items[0])"
    x-on:file-manager:upload="$wire.upload($event.detail.files)"
/>

Search

Search has three levers you can combine: searchScope (the current folder, or the whole tree), searchMatcher (your own match function), and searchMode (filter in the browser, or ask the server).

Your matcher

Pass the name of a function (entry, query, manager) => boolean , or a dotted path such as App.search.files so it does not sit on window . The demo below understands type:pdf , >10mb , and an extension.
javascript

selected

Drop to upload

window.searchFiles = (entry, query, manager) => {
    if (query.startsWith('type:')) return entry.kind === query.slice(5);
    if (query.startsWith('.')) return entry.extension.toLowerCase() === query.slice(1);

    return (entry.name + ' ' + (entry.tags ?? []).join(' '))
        .toLowerCase()
        .includes(query);
};

<neura::file-manager
    :items="$tree"
    search-matcher="searchFiles"
    search-scope="all"
    search-placeholder="type:pdf, .png…"
/>

What the function receives

  • entry — the decorated item: name, kind, extension, size, modifiedAt, isFolder, pathNames, plus your own fields
  • query — the input, already trimmed and lowercased
  • manager — the component, so you can read path, searchScope, and the rest

Server search

With search-mode="remote" the browser does not filter. The component dispatches file-manager:search after search-delay (300 ms by default) and shows a waiting state. Put the results back into items .
PHP
<neura::file-manager
    :items="$results"
    :loading="$searching"
    search-mode="remote"
    :search-delay="400"
    x-on:file-manager:search="$wire.searchFiles($event.detail.query, $event.detail.path)"
/>

public array $results = [];
public bool $searching = false;

public function searchFiles(string $query, array $path): void
{
    $this->searching = true;

    $this->results = Media::query()
        ->when($query, fn ($q) => $q->whereFullText('name', $query))
        ->get()
        ->map(fn ($m) => ['id' => $m->id, 'name' => $m->name, 'size' => $m->size])
        ->all();

    $this->searching = false;
}

Loading

:loading="true" shows a skeleton sized to the rows, so the layout does not jump when the data arrives.
blade

selected

Drop to upload

<neura::file-manager :items="$tree" :loading="$loading" />

Keyboard

Move the selection ↑ / ↓
Move in the grid ← / →
Open the folder or file Enter
Toggle the check Space
Go up one level Backspace
Select all Ctrl / ⌘ + A
Select a range Shift + click
Add to the selection Ctrl / ⌘ + click
Dispatch the delete action Delete
Clear the selection Escape

Props

Property Type Default Description
itemsarray[] The tree. Folders carry children.
viewstring'list' First layout: list or grid.
sizestring'md' Density: sm, md, or lg.
sortstring'name' First sort: name, size, modified, kind, or manual.
directionstring'asc' First sort direction.
sortablebooltrue Drag to reorder, or drop onto a folder to move.
selectablebooltrue Allow selecting items.
multiplebooltrue Allow Shift, Ctrl, and select-all.
searchablebooltrue Show the search field.
searchScopestring'folder' folder for the current folder, or all for the whole tree. Each result shows its path.
searchMatcherstring|nullnull Global name or dotted path of (entry, query, manager) => bool.
searchModestring'local' local filters in the browser. remote dispatches file-manager:search.
searchDelayint300 Wait before a remote search, in milliseconds.
searchPlaceholder / scopeTogglestring|null / boolnull / true Placeholder text, and whether the scope switch is shown.
detailsbooltrue Show the details panel.
uploadable / creatablebooltrue Show Upload and New folder.
downloadable / deletablebooltrue Show those actions on rows, the selection, and the context menu.
renamablebooltrue Show Rename in the context menu. Dispatches file-manager:rename.
loadingboolfalse Show the skeleton instead of the list.
rootLabelstring'Home' Root label in the breadcrumb.
heightstringnull Fixed height, for example 28rem.
rounded / shadowstringglobal Design-system overrides.