Skip to main content

Crate tui_file_explorer

Crate tui_file_explorer 

Source
Expand description

§tui-file-explorer

A self-contained, keyboard-driven file-browser widget for Ratatui.

§Design goals

  • Layered API — use FileExplorer, DualPane, or the complete App behind the full-app feature.
  • Lightweight core — with default features disabled, only ratatui, crossterm, and platform filesystem bindings are required.
  • Host control — semantic commands, custom filesystems, typed outcomes, and area-aware rendering integrate with an existing event loop.
  • Extension filtering — pass a list of allowed extensions so that only relevant files are selectable (e.g. ["iso", "img"]); directories are always navigable.
  • Keyboard-driven — ↑/↓/←/→ scroll the list, Enter / l to descend or confirm, Backspace / h to ascend, / to search, s to cycle sort, n to create a new folder, N to create a new file, Esc / q to dismiss.
  • Searchable — press / to enter incremental search; entries are filtered live as you type. Esc clears the query; a second Esc dismisses the explorer.
  • Sortable — press s to cycle through Name, Size ↓, and Extension sort modes, or set one programmatically via FileExplorer::set_sort_mode.
  • Themeable — every colour is overridable via Theme and render_themed.
  • Dual-pane — DualPane owns two independent FileExplorers, manages focus switching (Tab), and supports a single-pane toggle (w).

§Quick start

use tui_file_explorer::{FileExplorer, ExplorerOutcome, SortMode, render};
use crossterm::event::{KeyCode, KeyEvent, KeyModifiers};

// 1. Create once (e.g. in your App::new).
let mut explorer = FileExplorer::builder(std::env::current_dir().unwrap())
    .allow_extension("iso")
    .allow_extension("img")
    .sort_mode(SortMode::SizeDesc)
    .build();

// 2. In your Terminal::draw closure:
//    render(&mut explorer, frame, frame.area());

// 3. In your key-handler:
match explorer.handle_key(key) {
    ExplorerOutcome::Selected(path) => println!("chosen: {}", path.display()),
    ExplorerOutcome::Dismissed      => { /* close the overlay */ }
    _                               => {}
}

§Builder / configuration

Use FileExplorer::builder for a more ergonomic construction API:

use tui_file_explorer::{FileExplorer, SortMode};

let explorer = FileExplorer::builder(std::env::current_dir().unwrap())
    .allow_extension("rs")
    .allow_extension("toml")
    .show_hidden(true)
    .sort_mode(SortMode::Extension)
    .build();

Press / to activate search mode. Subsequent keystrokes append to the query and the entry list is filtered live (case-insensitive substring match on the file name). Backspace removes the last character; an extra Backspace on an empty query deactivates search. Esc clears the query and deactivates search without dismissing the explorer; a second Esc (when search is already inactive) dismisses it.

Search state is also accessible programmatically:

use tui_file_explorer::FileExplorer;

let explorer = FileExplorer::new(std::env::current_dir().unwrap(), vec![]);
println!("searching: {}", explorer.is_searching());
println!("query    : {}", explorer.search_query());

§Sort modes

Press s to cycle through the three sort modes, or set one directly:

use tui_file_explorer::{FileExplorer, SortMode};

let mut explorer = FileExplorer::new(std::env::current_dir().unwrap(), vec![]);
explorer.set_sort_mode(SortMode::SizeDesc); // largest files first

println!("{}", explorer.sort_mode().label()); // "size ↓"

§Theming

Every colour is customisable via Theme and render_themed:

use tui_file_explorer::{FileExplorer, Theme, render_themed};
use ratatui::style::Color;

let theme = Theme::default()
    .brand(Color::Magenta)
    .accent(Color::Cyan)
    .dir(Color::LightYellow);

// terminal.draw(|frame| {
//     render_themed(&mut explorer, frame, frame.area(), &theme);
// });

§Named presets

All 90 tui-nuances built-in themes are available as shared themes, converted with Theme::from:

use tui_file_explorer::Theme;

let t = Theme::from(&tui_nuances::Theme::dracula());
let t = Theme::from(&tui_nuances::Theme::nord());
let t = Theme::from(&tui_nuances::Theme::catppuccin_mocha());
let t = Theme::from(&tui_nuances::Theme::tokyo_night());
let t = Theme::from(&tui_nuances::Theme::gruvbox());
let t = Theme::from(&tui_nuances::Theme::kanagawa_wave());
let t = Theme::from(&tui_nuances::Theme::oxocarbon());

// Iterate the full catalogue (name, theme):
for (name, _theme) in Theme::presets() {
    println!("{name}");
}

The full list is tui_nuances::Theme::names() (also tfe --list-themes).

§Key bindings reference

KeyAction
↑ / kMove cursor up
↓ / jMove cursor down
PgUp / PgDnJump 10 entries
Home / gJump to top
End / GJump to bottom
→ / l / EnterDescend into directory; on a file → moves cursor down, l/Enter confirm
← / h / BackspaceAscend to parent directory
SpaceToggle space-mark on current entry and advance cursor
/Activate incremental search
sCycle sort mode (Name → Size ↓ → Extension)
.Toggle hidden (dot-file) entries
nCreate a new folder (type name → Enter confirm, Esc cancel)
NCreate a new file (type name → Enter confirm, Esc cancel)
rRename current entry (pre-filled with current name → Enter confirm, Esc cancel)
EscClear search / cancel mkdir / cancel touch / cancel rename (if active), then dismiss
qDismiss (when search / mkdir / touch / rename is not active)

§Dual-pane quick start

use tui_file_explorer::{DualPane, DualPaneOutcome, render_dual_pane_themed, Theme};
use crossterm::event::{Event, KeyCode, KeyModifiers, self};

// 1. Create once — left pane defaults to cwd; right pane mirrors it.
let mut dual = DualPane::builder(std::env::current_dir().unwrap())
    .right_dir(std::path::PathBuf::from("/tmp"))
    .build();

let theme = Theme::default();

// 2. In your Terminal::draw closure:
// terminal.draw(|frame| {
//     render_dual_pane_themed(&mut dual, frame, frame.area(), &theme);
// }).unwrap();

// 3. In your event loop:
match dual.handle_key(key) {
    DualPaneOutcome::Selected(path) => println!("chosen: {}", path.display()),
    DualPaneOutcome::Dismissed      => { /* close the overlay */ }
    _                               => {}
}

§Extra key bindings provided by DualPane

KeyAction
TabSwitch focus between left and right pane
wToggle single-pane / dual-pane mode
SpaceMark current entry (forwarded to active pane)

All standard FileExplorer bindings continue to work on whichever pane is currently active.

§Folder and file creation

§New folder — n

Press n to enter mkdir mode. Type the new folder name, then press Enter to create it (using the configured FileSystem, so nested paths like a/b/c work) or Esc to cancel without creating anything. On success ExplorerOutcome::MkdirCreated is returned and the cursor moves to the new directory.

§New file — N

Press N (Shift+N) to enter touch mode. Type the new file name (including extension), then press Enter to create it or Esc to cancel. Parent directories are created automatically when the name contains /. An existing file at the target path is left untouched (no truncation). On success ExplorerOutcome::TouchCreated is returned and the cursor moves to the new file.

Both modes are also accessible programmatically:

use tui_file_explorer::FileExplorer;

let explorer = FileExplorer::new(std::env::current_dir().unwrap(), vec![]);
println!("mkdir active : {}", explorer.is_mkdir_active());
println!("mkdir input  : {}", explorer.mkdir_input());
println!("touch active : {}", explorer.is_touch_active());
println!("touch input  : {}", explorer.touch_input());

§Module layout

ModuleContents
typesFsEntry, ExplorerOutcome, SortMode
palettePalette constants (all pub) + Theme builder + 43 named presets
explorerFileExplorer, FileExplorerBuilder, entry_icon, fmt_size
filesystemFileSystem, StdFileSystem, and virtual backend support
dual_paneDualPane, DualPaneBuilder, DualPaneActive, DualPaneOutcome
renderrender(), render_themed, render_dual_pane, render_dual_pane_themed — pure rendering, no I/O
previewPreviewState, PreviewContent, render_preview — optional text, image, binary hex dump, and directory preview support
inline_editorInlineEditor, EditorAction, render_inline_editor — built-in text editor

Re-exports§

pub use dual_pane::DualPane;
pub use dual_pane::DualPaneActive;
pub use dual_pane::DualPaneBuilder;
pub use dual_pane::DualPaneCommand;
pub use dual_pane::DualPaneOutcome;
pub use explorer::ExplorerError;
pub use explorer::FileExplorer;
pub use explorer::FileExplorerBuilder;
pub use explorer::PAGE_SIZE;
pub use explorer::entry_icon;
pub use explorer::fmt_size;
pub use filesystem::TrashFileSystem;
pub use filesystem::FileSystem;
pub use filesystem::SharedFileSystem;
pub use filesystem::StdFileSystem;
pub use filesystem::TRASH_SUPPORTED;
pub use filesystem::VirtualEntry;
pub use filesystem::local_filesystem;
pub use filesystem::std_filesystem;
pub use nuances::ThemeBuilder;
pub use nuances::render_dual_pane_nuanced;
pub use nuances::render_nuanced;
pub use palette::Theme;
pub use render::FOOTER_HEIGHT;
pub use render::HEADER_HEIGHT;
pub use render::MARK_INDICATOR;
pub use render::SCROLLBAR_CHAR;
pub use render::render;
pub use render::render_dual_pane;
pub use render::render_dual_pane_themed;
pub use render::render_themed;
pub use types::DiskUsage;
pub use types::ExplorerCommand;
pub use types::ExplorerOutcome;
pub use types::FsEntry;
pub use types::Prompt;
pub use types::PromptKind;
pub use types::SelectionMode;
pub use types::SortMode;
pub use app::App;
pub use app::AppBuildError;
pub use app::AppBuilder;
pub use app::AppCommand;
pub use app::AppEvent;
pub use app::AppOptions;
pub use app::AppOutcome;
pub use app::ClipOp;
pub use app::ClipboardItem;
pub use app::CopyProgress;
pub use app::Editor;
pub use app::FileOperation;
pub use app::KeyBinding;
pub use app::KeyBindings;
pub use app::Modal;
pub use app::OperationApplyError;
pub use app::OperationFailure;
pub use app::OperationId;
pub use app::OperationMode;
pub use app::OperationProgress;
pub use app::OperationRequest;
pub use app::OperationResult;
pub use app::PaneOptions;
pub use app::Snackbar;
pub use app::execute_operation;
pub use app::execute_operation_with;
pub use app::execute_operation_with_progress;
pub use fs_util::copy_dir_all;
pub use fs_util::resolve_output_path;
pub use git::GitMark;
pub use git::GitStatus;
pub use inline_editor::EditorAction;
pub use inline_editor::InlineEditor;
pub use inline_editor::render_inline_editor;
pub use keymap::ChordMods;
pub use keymap::KeyChord;
pub use keymap::Keymap;
pub use keymap::KeymapError;
pub use keymap::KeymapConfig;
pub use keymap::default_keymap_toml;
pub use keymap::keymap_path;
pub use keymap::load_keymap_config;
pub use keymap::parse_keymap_config;
pub use persistence::AppState;
pub use persistence::load_state;
pub use persistence::load_state_from;
pub use persistence::resolve_theme_idx;
pub use persistence::save_state;
pub use persistence::save_state_to;
pub use persistence::try_load_state_from;
pub use persistence::try_save_state;
pub use picker::Picker;
pub use picker::PickerAction;
pub use picker::PickerItem;
pub use picker::PickerKind;
pub use picker::fuzzy_match;
pub use picker::render_picker;
pub use preview::PreviewContent;
pub use preview::PreviewState;
pub use preview::render_preview;
pub use ui::AppViewOptions;
pub use ui::HintLayout;
pub use ui::draw;
pub use ui::draw_in;
pub use ui::draw_in_with_options;
pub use ui::render_action_bar;
pub use ui::render_copy_progress;
pub use ui::render_editor_panel;
pub use ui::render_modal;
pub use ui::render_modal_for;
pub use ui::render_nav_hints;
pub use ui::render_options_panel;
pub use ui::render_snackbar;
pub use ui::render_theme_panel;
pub use tui_nuances;

Modules§

app
Application state for the tfe binary.
archive
Archive support: list (for previews) and extract .zip, .tar, .tar.gz / .tgz.
bulk_rename
Bulk rename: edit many names at once in a text editor.
dual_pane
Dual-pane file-explorer widget.
explorer
FileExplorer state machine, FileExplorerBuilder, and filesystem helpers.
filesystem
Filesystem backends: the FileSystem trait the explorer browses through, the local and trash-backed implementations, and VirtualEntry for virtual backends.
fs_util
Filesystem helpers for the tfe binary.
git
Lightweight git status integration: a per-entry change marker.
inline_editor
Inline text editor for the TUI file explorer.
keymap
Key chords and the explorer keymap.
nuances
Shared theming via tui_nuances.
palette
Default colour palette used by the file-explorer widget.
persistence
Persist application state between sessions.
picker
A filter-as-you-type list overlay with fuzzy matching.
preview
File preview pane for the TUI file explorer.
render
Ratatui rendering functions for the file-explorer widget.
types
Public data types exposed by the tui-file-explorer crate.
ui
Terminal UI drawing functions for the tfe binary.
worker
Tiny background-task primitive used to keep slow filesystem work (folder sizes, previews, tree walks, git status) off the UI thread.

Structs§

NuancesSwitcher
A wrapping cursor over a list of themes.
NuancesTheme
A named set of colors shared by every widget of an application.

Traits§

ThemeProvider
Implemented by application theme types to expose them as a Theme.
Themed
Implemented by widgets that can restyle themselves from a Theme.