Find dialog in view

This commit is contained in:
veeso 2021-03-25 22:59:42 +01:00
parent 8a22259eba
commit 08b855e779
8 changed files with 404 additions and 17 deletions

View file

@ -32,6 +32,7 @@ Released on FIXME: date
- Fixed a bug causing termscp to show two equal bookmarks when overwriting one.
- Dependencies:
- Removed `unicode-width`
- Added `wildmatch 1.0.13`
- For developers:
- Activity refactoring
- Developed an internal library used to create components, components are then nested inside a View

View file

@ -127,6 +127,13 @@ impl FileExplorer {
self.sort();
}
/// ### del_entry
///
/// Delete file at provided index
pub fn del_entry(&mut self, idx: usize) {
self.files.remove(idx);
}
/*
/// ### count
///
@ -627,6 +634,23 @@ mod tests {
assert!(GroupDirs::from_str("omar").is_err());
}
#[test]
fn test_fs_explorer_del_entry() {
let mut explorer: FileExplorer = FileExplorer::default();
// Create files (files are then sorted by name)
explorer.set_files(vec![
make_fs_entry("CONTRIBUTING.md", false),
make_fs_entry("docs/", true),
make_fs_entry("src/", true),
make_fs_entry("README.md", false),
]);
explorer.del_entry(0);
assert_eq!(explorer.files.len(), 3);
assert_eq!(explorer.files[0].get_name(), "docs/");
explorer.del_entry(5);
assert_eq!(explorer.files.len(), 3);
}
fn make_fs_entry(name: &str, is_dir: bool) -> FsEntry {
let t_now: SystemTime = SystemTime::now();
match is_dir {

View file

@ -24,7 +24,7 @@
*/
// locals
use super::{FileTransferActivity, FsEntry, LogLevel};
use super::{FileExplorerTab, FileTransferActivity, FsEntry, LogLevel};
use crate::ui::layout::Payload;
// externals
use std::path::PathBuf;
@ -485,6 +485,124 @@ impl FileTransferActivity {
}
}
pub(super) fn action_local_find(&mut self, input: String) -> Result<Vec<FsEntry>, String> {
match self.context.as_mut().unwrap().local.find(input.as_str()) {
Ok(entries) => Ok(entries),
Err(err) => Err(format!("Could not search for files: {}", err)),
}
}
pub(super) fn action_remote_find(&mut self, input: String) -> Result<Vec<FsEntry>, String> {
match self.client.as_mut().find(input.as_str()) {
Ok(entries) => Ok(entries),
Err(err) => Err(format!("Could not search for files: {}", err)),
}
}
pub(super) fn action_find_changedir(&mut self, idx: usize) {
// Match entry
if let Some(entry) = self.found.as_ref().unwrap().get(idx) {
// Get path: if a directory, use directory path; if it is a File, get parent path
let path: PathBuf = match entry {
FsEntry::Directory(dir) => dir.abs_path.clone(),
FsEntry::File(file) => match file.abs_path.parent() {
None => PathBuf::from("."),
Some(p) => p.to_path_buf(),
},
};
// Change directory
match self.tab {
FileExplorerTab::FindLocal | FileExplorerTab::Local => {
self.local_changedir(path.as_path(), true)
}
FileExplorerTab::FindRemote | FileExplorerTab::Remote => {
self.remote_changedir(path.as_path(), true)
}
}
}
}
pub(super) fn action_find_transfer(&mut self, idx: usize, name: Option<String>) {
let entry: Option<FsEntry> = match self.found.as_ref().unwrap().get(idx) {
None => None,
Some(e) => Some(e.clone()),
};
if let Some(entry) = entry {
// Download file
match self.tab {
FileExplorerTab::FindLocal | FileExplorerTab::Local => {
let wrkdir: PathBuf = self.remote.wrkdir.clone();
self.filetransfer_send(&entry.get_realfile(), wrkdir.as_path(), name);
}
FileExplorerTab::FindRemote | FileExplorerTab::Remote => {
let wrkdir: PathBuf = self.local.wrkdir.clone();
self.filetransfer_recv(&entry.get_realfile(), wrkdir.as_path(), name);
}
}
}
}
pub(super) fn action_find_delete(&mut self, idx: usize) {
let entry: Option<FsEntry> = match self.found.as_ref().unwrap().get(idx) {
None => None,
Some(e) => Some(e.clone()),
};
if let Some(entry) = entry {
// Download file
match self.tab {
FileExplorerTab::FindLocal | FileExplorerTab::Local => {
let full_path: PathBuf = entry.get_abs_path();
// Delete file or directory and report status as popup
match self.context.as_mut().unwrap().local.remove(&entry) {
Ok(_) => {
// Reload files
let p: PathBuf = self.local.wrkdir.clone();
self.local_scan(p.as_path());
// Log
self.log(
LogLevel::Info,
format!("Removed file \"{}\"", full_path.display()).as_ref(),
);
}
Err(err) => {
self.log_and_alert(
LogLevel::Error,
format!(
"Could not delete file \"{}\": {}",
full_path.display(),
err
),
);
}
}
}
FileExplorerTab::FindRemote | FileExplorerTab::Remote => {
let full_path: PathBuf = entry.get_abs_path();
// Delete file
match self.client.remove(&entry) {
Ok(_) => {
self.reload_remote_dir();
self.log(
LogLevel::Info,
format!("Removed file \"{}\"", full_path.display()).as_ref(),
);
}
Err(err) => {
self.log_and_alert(
LogLevel::Error,
format!(
"Could not delete file \"{}\": {}",
full_path.display(),
err
),
);
}
}
}
}
}
}
/// ### get_local_file_entry
///
/// Get local file entry

View file

@ -111,6 +111,19 @@ impl FileTransferActivity {
}
}
/// ### build_found_explorer
///
/// Build explorer reading from `ConfigClient`, for found result (has some differences)
pub(super) fn build_found_explorer() -> FileExplorer {
FileExplorerBuilder::new()
.with_file_sorting(FileSorting::ByName)
.with_group_dirs(Some(GroupDirs::First))
.with_hidden_files(true)
.with_stack_size(0)
.with_formatter(Some("{NAME} {SYMLINK}"))
.build()
}
/// ### setup_text_editor
///
/// Set text editor to use

View file

@ -63,23 +63,25 @@ const STORAGE_LOGBOX_WIDTH: &str = "LOGBOX_WIDTH";
const COMPONENT_EXPLORER_LOCAL: &str = "EXPLORER_LOCAL";
const COMPONENT_EXPLORER_REMOTE: &str = "EXPLORER_REMOTE";
const COMPONENT_EXPLORER_FIND: &str = "EXPLORER_FIND";
const COMPONENT_LOG_BOX: &str = "LOG_BOX";
const COMPONENT_PROGRESS_BAR: &str = "PROGRESS_BAR";
const COMPONENT_TEXT_HELP: &str = "TEXT_HELP";
const COMPONENT_TEXT_ERROR: &str = "TEXT_ERROR";
const COMPONENT_TEXT_WAIT: &str = "TEXT_WAIT";
const COMPONENT_TEXT_FATAL: &str = "TEXT_FATAL";
const COMPONENT_TEXT_HELP: &str = "TEXT_HELP";
const COMPONENT_TEXT_WAIT: &str = "TEXT_WAIT";
const COMPONENT_INPUT_COPY: &str = "INPUT_COPY";
const COMPONENT_INPUT_EXEC: &str = "INPUT_EXEC";
const COMPONENT_INPUT_MKDIR: &str = "INPUT_MKDIR";
const COMPONENT_INPUT_FIND: &str = "INPUT_FIND";
const COMPONENT_INPUT_GOTO: &str = "INPUT_GOTO";
const COMPONENT_INPUT_SAVEAS: &str = "INPUT_SAVEAS";
const COMPONENT_INPUT_MKDIR: &str = "INPUT_MKDIR";
const COMPONENT_INPUT_NEWFILE: &str = "INPUT_NEWFILE";
const COMPONENT_INPUT_RENAME: &str = "INPUT_RENAME";
const COMPONENT_RADIO_QUIT: &str = "RADIO_QUIT";
const COMPONENT_RADIO_DISCONNECT: &str = "RADIO_DISCONNECT";
const COMPONENT_RADIO_SORTING: &str = "RADIO_SORTING";
const COMPONENT_INPUT_SAVEAS: &str = "INPUT_SAVEAS";
const COMPONENT_RADIO_DELETE: &str = "RADIO_DELETE";
const COMPONENT_RADIO_DISCONNECT: &str = "RADIO_DISCONNECT";
const COMPONENT_RADIO_QUIT: &str = "RADIO_QUIT";
const COMPONENT_RADIO_SORTING: &str = "RADIO_SORTING";
const COMPONENT_LIST_FILEINFO: &str = "LIST_FILEINFO";
/// ## FileExplorerTab
@ -88,6 +90,8 @@ const COMPONENT_LIST_FILEINFO: &str = "LIST_FILEINFO";
enum FileExplorerTab {
Local,
Remote,
FindLocal, // Find result tab
FindRemote, // Find result tab
}
/// ## LogLevel
@ -206,6 +210,7 @@ pub struct FileTransferActivity {
client: Box<dyn FileTransfer>, // File transfer client
local: FileExplorer, // Local File explorer state
remote: FileExplorer, // Remote File explorer state
found: Option<FileExplorer>, // File explorer for find result
tab: FileExplorerTab, // Current selected tab
log_index: usize, // Current log index entry selected
log_records: VecDeque<LogRecord>, // Log records
@ -235,6 +240,7 @@ impl FileTransferActivity {
},
local: Self::build_explorer(config_client.as_ref()),
remote: Self::build_explorer(config_client.as_ref()),
found: None,
tab: FileExplorerTab::Local,
log_index: 0,
log_records: VecDeque::with_capacity(256), // 256 events is enough I guess

View file

@ -27,9 +27,10 @@
extern crate bytesize;
// locals
use super::{
FileExplorerTab, FileTransferActivity, LogLevel, COMPONENT_EXPLORER_LOCAL,
COMPONENT_EXPLORER_REMOTE, COMPONENT_INPUT_COPY, COMPONENT_INPUT_EXEC, COMPONENT_INPUT_GOTO,
COMPONENT_INPUT_MKDIR, COMPONENT_INPUT_NEWFILE, COMPONENT_INPUT_RENAME, COMPONENT_INPUT_SAVEAS,
FileExplorerTab, FileTransferActivity, LogLevel, COMPONENT_EXPLORER_FIND,
COMPONENT_EXPLORER_LOCAL, COMPONENT_EXPLORER_REMOTE, COMPONENT_INPUT_COPY,
COMPONENT_INPUT_EXEC, COMPONENT_INPUT_FIND, COMPONENT_INPUT_GOTO, COMPONENT_INPUT_MKDIR,
COMPONENT_INPUT_NEWFILE, COMPONENT_INPUT_RENAME, COMPONENT_INPUT_SAVEAS,
COMPONENT_LIST_FILEINFO, COMPONENT_LOG_BOX, COMPONENT_PROGRESS_BAR, COMPONENT_RADIO_DELETE,
COMPONENT_RADIO_DISCONNECT, COMPONENT_RADIO_QUIT, COMPONENT_RADIO_SORTING,
COMPONENT_TEXT_ERROR, COMPONENT_TEXT_FATAL, COMPONENT_TEXT_HELP,
@ -37,7 +38,9 @@ use super::{
use crate::fs::explorer::FileSorting;
use crate::fs::FsEntry;
use crate::ui::activities::keymap::*;
use crate::ui::layout::props::{PropValue, TableBuilder, TextParts, TextSpan, TextSpanBuilder};
use crate::ui::layout::props::{
PropValue, PropsBuilder, TableBuilder, TextParts, TextSpan, TextSpanBuilder,
};
use crate::ui::layout::{Msg, Payload};
// externals
use bytesize::ByteSize;
@ -314,6 +317,11 @@ impl FileTransferActivity {
self.mount_mkdir();
None
}
(COMPONENT_EXPLORER_LOCAL, &MSG_KEY_CHAR_F)
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_CHAR_F) => {
self.mount_find_input();
None
}
(COMPONENT_EXPLORER_LOCAL, &MSG_KEY_CHAR_G)
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_CHAR_G) => {
self.mount_goto();
@ -342,7 +350,8 @@ impl FileTransferActivity {
None
}
(COMPONENT_EXPLORER_LOCAL, &MSG_KEY_CHAR_S)
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_CHAR_S) => {
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_CHAR_S)
| (COMPONENT_EXPLORER_FIND, &MSG_KEY_CHAR_S) => {
// Mount save as
self.mount_saveas();
None
@ -362,10 +371,50 @@ impl FileTransferActivity {
(COMPONENT_EXPLORER_LOCAL, &MSG_KEY_DEL)
| (COMPONENT_EXPLORER_LOCAL, &MSG_KEY_CHAR_E)
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_DEL)
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_CHAR_E) => {
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_CHAR_E)
| (COMPONENT_EXPLORER_FIND, &MSG_KEY_DEL)
| (COMPONENT_EXPLORER_FIND, &MSG_KEY_CHAR_E) => {
self.mount_radio_delete();
None
}
// -- find result explorer
(COMPONENT_EXPLORER_FIND, &MSG_KEY_ESC) => {
// Umount find
self.umount_find();
// Finalize find
self.finalize_find();
None
}
(COMPONENT_EXPLORER_FIND, Msg::OnSubmit(Payload::Unsigned(idx))) => {
// Find changedir
self.action_find_changedir(*idx);
// Umount find
self.umount_find();
// Finalize find
self.finalize_find();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
(COMPONENT_EXPLORER_FIND, &MSG_KEY_SPACE) => {
// Get entry
match self.view.get_value(COMPONENT_EXPLORER_FIND) {
Some(Payload::Unsigned(idx)) => {
self.action_find_transfer(idx, None);
// Reload files
match self.tab {
// NOTE: swapped by purpose
FileExplorerTab::FindLocal => self.update_remote_filelist(),
FileExplorerTab::FindRemote => self.update_local_filelist(),
_ => None,
}
}
_ => None,
}
}
// -- switch to log
(COMPONENT_EXPLORER_LOCAL, &MSG_KEY_TAB)
| (COMPONENT_EXPLORER_REMOTE, &MSG_KEY_TAB) => {
@ -387,12 +436,14 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_copy(input.to_string()),
FileExplorerTab::Remote => self.action_remote_copy(input.to_string()),
_ => panic!("Found tab doesn't support COPY"),
}
self.umount_copy();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- exec popup
@ -405,14 +456,53 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_exec(input.to_string()),
FileExplorerTab::Remote => self.action_remote_exec(input.to_string()),
_ => panic!("Found tab doesn't support EXEC"),
}
self.umount_exec();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- find popup
(COMPONENT_INPUT_FIND, &MSG_KEY_ESC) => {
self.umount_find_input();
None
}
(COMPONENT_INPUT_FIND, Msg::OnSubmit(Payload::Text(input))) => {
self.umount_find_input();
// Find
let res: Result<Vec<FsEntry>, String> = match self.tab {
FileExplorerTab::Local => self.action_local_find(input.to_string()),
FileExplorerTab::Remote => self.action_remote_find(input.to_string()),
_ => panic!("Trying to search for files, while already in a find result"),
};
// Match result
match res {
Err(err) => {
// Mount error
self.mount_error(err.as_str());
}
Ok(files) => {
// Create explorer and load files
let mut explorer = Self::build_found_explorer();
explorer.set_files(files);
self.found = Some(explorer);
// Mount result widget
self.mount_find(input);
self.update_find_list();
// Initialize tab
self.tab = match self.tab {
FileExplorerTab::Local => FileExplorerTab::FindLocal,
FileExplorerTab::Remote => FileExplorerTab::FindRemote,
_ => FileExplorerTab::FindLocal,
};
}
}
None
}
// -- goto popup
(COMPONENT_INPUT_GOTO, &MSG_KEY_ESC) => {
self.umount_goto();
@ -422,6 +512,7 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_change_local_dir(input.to_string()),
FileExplorerTab::Remote => self.action_change_remote_dir(input.to_string()),
_ => panic!("Found tab doesn't support GOTO"),
}
// Umount
self.umount_goto();
@ -429,6 +520,7 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- make directory
@ -440,12 +532,14 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_mkdir(input.to_string()),
FileExplorerTab::Remote => self.action_remote_mkdir(input.to_string()),
_ => panic!("Found tab doesn't support MKDIR"),
}
self.umount_mkdir();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- new file
@ -457,12 +551,14 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_newfile(input.to_string()),
FileExplorerTab::Remote => self.action_remote_newfile(input.to_string()),
_ => panic!("Found tab doesn't support NEWFILE"),
}
self.umount_newfile();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- rename
@ -474,12 +570,14 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_rename(input.to_string()),
FileExplorerTab::Remote => self.action_remote_rename(input.to_string()),
_ => panic!("Found tab doesn't support RENAME"),
}
self.umount_rename();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- save as
@ -491,6 +589,14 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_saveas(input.to_string()),
FileExplorerTab::Remote => self.action_remote_saveas(input.to_string()),
FileExplorerTab::FindLocal | FileExplorerTab::FindRemote => {
// Get entry
if let Some(Payload::Unsigned(idx)) =
self.view.get_value(COMPONENT_EXPLORER_FIND)
{
self.action_find_transfer(idx, Some(input.to_string()));
}
}
}
self.umount_saveas();
// Reload files
@ -498,6 +604,8 @@ impl FileTransferActivity {
// NOTE: Swapped is intentional
FileExplorerTab::Local => self.update_remote_filelist(),
FileExplorerTab::Remote => self.update_local_filelist(),
FileExplorerTab::FindLocal => self.update_remote_filelist(),
FileExplorerTab::FindRemote => self.update_local_filelist(),
}
}
// -- fileinfo
@ -517,12 +625,25 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.action_local_delete(),
FileExplorerTab::Remote => self.action_remote_delete(),
FileExplorerTab::FindLocal | FileExplorerTab::FindRemote => {
// Get entry
if let Some(Payload::Unsigned(idx)) =
self.view.get_value(COMPONENT_EXPLORER_FIND)
{
self.action_find_delete(idx);
// Reload entries
self.found.as_mut().unwrap().del_entry(idx);
self.update_find_list();
}
}
}
self.umount_radio_delete();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
FileExplorerTab::FindLocal => self.update_local_filelist(),
FileExplorerTab::FindRemote => self.update_remote_filelist(),
}
}
// -- disconnect
@ -547,6 +668,7 @@ impl FileTransferActivity {
self.umount_quit();
None
}
// -- sorting
(COMPONENT_RADIO_SORTING, &MSG_KEY_ESC) => {
self.umount_file_sorting();
None
@ -562,12 +684,14 @@ impl FileTransferActivity {
match self.tab {
FileExplorerTab::Local => self.local.sort_by(sorting),
FileExplorerTab::Remote => self.remote.sort_by(sorting),
_ => panic!("Found result doesn't support SORTING"),
}
self.umount_file_sorting();
// Reload files
match self.tab {
FileExplorerTab::Local => self.update_local_filelist(),
FileExplorerTab::Remote => self.update_remote_filelist(),
_ => None,
}
}
// -- error
@ -809,6 +933,43 @@ impl FileTransferActivity {
}
}
/// ### finalize_find
///
/// Finalize find process
fn finalize_find(&mut self) {
// Set found to none
self.found = None;
// Restore tab
self.tab = match self.tab {
FileExplorerTab::FindLocal => FileExplorerTab::Local,
FileExplorerTab::FindRemote => FileExplorerTab::Remote,
_ => FileExplorerTab::Local,
};
}
fn update_find_list(&mut self) -> Option<(String, Msg)> {
match self.view.get_props(COMPONENT_EXPLORER_FIND).as_mut() {
None => None,
Some(props) => {
let props = props.build();
let title: String = props.texts.title.clone().unwrap_or(String::new());
let mut props = PropsBuilder::from(props.clone());
// Prepare files
let file_texts: Vec<TextSpan> = self
.found
.as_ref()
.unwrap()
.iter_files()
.map(|x: &FsEntry| TextSpan::from(self.found.as_ref().unwrap().fmt_file(x)))
.collect();
let props = props
.with_texts(TextParts::new(Some(title), Some(file_texts)))
.build();
self.view.update(COMPONENT_EXPLORER_FIND, props)
}
}
}
/// ### elide_wrkdir_path
///
/// Elide working directory path if longer than width + host.len

View file

@ -33,7 +33,7 @@ use super::{Context, FileExplorerTab, FileTransferActivity};
use crate::fs::explorer::FileSorting;
use crate::fs::FsEntry;
use crate::ui::layout::components::{
msgbox::MsgBox, file_list::FileList, input::Input, logbox::LogBox, progress_bar::ProgressBar,
file_list::FileList, input::Input, logbox::LogBox, msgbox::MsgBox, progress_bar::ProgressBar,
radio_group::RadioGroup, table::Table,
};
use crate::ui::layout::props::{
@ -138,6 +138,14 @@ impl FileTransferActivity {
// Draw log box
self.view.render(super::COMPONENT_LOG_BOX, f, chunks[1]);
// Draw popups
if let Some(mut props) = self.view.get_props(super::COMPONENT_EXPLORER_FIND) {
if props.build().visible {
let popup = draw_area_in(f.size(), 60, 80);
f.render_widget(Clear, popup);
// make popup
self.view.render(super::COMPONENT_EXPLORER_FIND, f, popup);
}
}
if let Some(mut props) = self.view.get_props(super::COMPONENT_INPUT_COPY) {
if props.build().visible {
let popup = draw_area_in(f.size(), 40, 10);
@ -146,6 +154,14 @@ impl FileTransferActivity {
self.view.render(super::COMPONENT_INPUT_COPY, f, popup);
}
}
if let Some(mut props) = self.view.get_props(super::COMPONENT_INPUT_FIND) {
if props.build().visible {
let popup = draw_area_in(f.size(), 40, 10);
f.render_widget(Clear, popup);
// make popup
self.view.render(super::COMPONENT_INPUT_FIND, f, popup);
}
}
if let Some(mut props) = self.view.get_props(super::COMPONENT_INPUT_GOTO) {
if props.build().visible {
let popup = draw_area_in(f.size(), 40, 10);
@ -435,6 +451,55 @@ impl FileTransferActivity {
self.view.umount(super::COMPONENT_INPUT_EXEC);
}
pub(super) fn mount_find(&mut self, search: &str) {
// Get color
let color: Color = match self.tab {
FileExplorerTab::Local | FileExplorerTab::FindLocal => Color::Yellow,
FileExplorerTab::Remote | FileExplorerTab::FindRemote => Color::LightBlue,
};
// Mount component
self.view.mount(
super::COMPONENT_EXPLORER_FIND,
Box::new(FileList::new(
PropsBuilder::default()
.with_texts(TextParts::new(
Some(format!("Search results for \"{}\"", search)),
Some(vec![]),
))
.with_background(color)
.with_foreground(color)
.build(),
)),
);
// Give focus to explorer findd
self.view.active(super::COMPONENT_EXPLORER_FIND);
}
pub(super) fn umount_find(&mut self) {
self.view.umount(super::COMPONENT_EXPLORER_FIND);
}
pub(super) fn mount_find_input(&mut self) {
self.view.mount(
super::COMPONENT_INPUT_FIND,
Box::new(Input::new(
PropsBuilder::default()
.with_texts(TextParts::new(
Some(String::from("Search files by name")),
None,
))
.build(),
)),
);
// Give focus to input find
self.view.active(super::COMPONENT_INPUT_FIND);
}
pub(super) fn umount_find_input(&mut self) {
// Umount input find
self.view.umount(super::COMPONENT_INPUT_FIND);
}
pub(super) fn mount_goto(&mut self) {
self.view.mount(
super::COMPONENT_INPUT_GOTO,
@ -543,6 +608,7 @@ impl FileTransferActivity {
let sorting: FileSorting = match self.tab {
FileExplorerTab::Local => self.local.get_file_sorting(),
FileExplorerTab::Remote => self.remote.get_file_sorting(),
_ => panic!("You can't mount file sorting when in found result"),
};
let index: usize = match sorting {
FileSorting::ByCreationTime => 2,

View file

@ -91,12 +91,10 @@ pub const MSG_KEY_CHAR_E: Msg = Msg::OnKey(KeyEvent {
code: KeyCode::Char('e'),
modifiers: KeyModifiers::NONE,
});
/*
pub const MSG_KEY_CHAR_F: Msg = Msg::OnKey(KeyEvent {
code: KeyCode::Char('f'),
modifiers: KeyModifiers::NONE,
});
*/
pub const MSG_KEY_CHAR_G: Msg = Msg::OnKey(KeyEvent {
code: KeyCode::Char('g'),
modifiers: KeyModifiers::NONE,