Build a cross-platform TUI application in Rust to copy files/folders with configurable string replacements in paths and file contents.
Important
Library Choice: I am planning to use ratatui (the community fork of tui-rs) as it is currently the standard for Rust TUIs, along with crossterm for backend event handling.
File System: The app will perform real file system operations. The "Copy Replace" action will be destructive if the destination exists (though we will prompt/warn).
- Update
read_directoryto handle partial paths:- If path is a directory, list contents (existing behavior).
- If path is not a directory, try to find the parent directory.
- If parent exists, list contents of parent that start with the file name part of the input path.
- Filter key events to only process
KeyEventKind::Pressto prevent double input. - Add
Event::Mousehandling to the event loop.
- Add
Rectfields toAppstruct to store layout areas for mouse hit testing. - Implement
on_mousemethod inAppto handle mouse clicks and update focus. - Update
enter_charto triggerupdate_explorerwhen typing inSourceInput.
- Change
uifunction signature to accept&mut App. - Update
App'sRectfields during rendering to reflect current layout.
- Double Input: Run the app and type characters. Verify only one character appears per key press.
- Explorer Sync: Type a valid path in Source Input and verify Explorer updates immediately (or on valid path).
- Mouse Support: Click on different sections (Source, Explorer, Destination, etc.) and verify focus changes. Click buttons to verify actions.
- Directory Filtering: Type a partial path (e.g.,
C:\D) and verify that directories starting withDinC:\are listed. - Explorer Mouse Click: Click on a directory in the Explorer and verify that the Source Directory input updates and the explorer refreshes.
- Explorer Navigation: Verify Up/Down arrows scroll the list. Verify Right enters a directory, Left goes to parent.
- Parent Directory: Verify
..appears in the list and navigating to it goes to the parent directory. - Files Panel: Verify a new panel appears to the right of Explorer showing files. Verify scrolling works.
- Update
read_directoryto return a tuple(Vec<PathBuf>, Vec<PathBuf>)containing(directories, files). - Or add a separate
read_filesfunction. Given the existing structure, modifyingread_directoryor returning a structDirectoryContentmight be cleaner. Let's returnResult<(Vec<PathBuf>, Vec<PathBuf>)>.
- Add
file_items: Vec<PathBuf>toApp. - Add
file_list_state: ListStatetoApp. - Add
files_area: RecttoApp. - Add
Focus::Filesenum variant. - Update
update_explorerto populatefile_items. - Update
on_keyto handleFocus::Filesscrolling. - Update
next_focus/previous_focusto includeFocus::Files.
- Split the Explorer area (currently
left_chunks[1]) into two horizontal chunks. - Render "Source Directory Explorer" (Directories) in the left chunk.
- Render "Files in Folder" in the right chunk.
- Use
render_stateful_widgetfor the files list.