summaryrefslogtreecommitdiffstats
path: root/src/commands
diff options
context:
space:
mode:
authorJiayi Zhao <jeff.no.zhao@gmail.com>2020-09-19 21:21:33 -0400
committerJiayi Zhao <jeff.no.zhao@gmail.com>2020-09-19 21:21:33 -0400
commit7b4c611ed4d804bd52aeda0a619a54bea9b1e13d (patch)
tree7ba31fff7d5de171aadfc32c67f81dd64428b3ba /src/commands
parent7741d4d2c8798ad0bb609e97fb3bda86c5318a36 (diff)
Change command to use an enum instead of polymorphism
Diffstat (limited to 'src/commands')
-rw-r--r--src/commands/bulk_rename.rs221
-rw-r--r--src/commands/change_directory.rs65
-rw-r--r--src/commands/command_keybind.rs27
-rw-r--r--src/commands/command_line.rs64
-rw-r--r--src/commands/cursor_move.rs307
-rw-r--r--src/commands/delete_files.rs135
-rw-r--r--src/commands/file_ops.rs48
-rw-r--r--src/commands/file_ops/copy.rs40
-rw-r--r--src/commands/file_ops/cut.rs40
-rw-r--r--src/commands/file_ops/mod.rs7
-rw-r--r--src/commands/file_ops/paste.rs57
-rw-r--r--src/commands/key_command.rs347
-rw-r--r--src/commands/mod.rs264
-rw-r--r--src/commands/new_directory.rs44
-rw-r--r--src/commands/open_file.rs281
-rw-r--r--src/commands/parent_directory.rs42
-rw-r--r--src/commands/quit.rs82
-rw-r--r--src/commands/reload.rs47
-rw-r--r--src/commands/reload_dir.rs71
-rw-r--r--src/commands/rename_file.rs215
-rw-r--r--src/commands/search.rs161
-rw-r--r--src/commands/selection.rs90
-rw-r--r--src/commands/set_mode.rs106
-rw-r--r--src/commands/shell.rs89
-rw-r--r--src/commands/show_hidden.rs42
-rw-r--r--src/commands/sort.rs76
-rw-r--r--src/commands/tab_operations.rs93
-rw-r--r--src/commands/tab_ops.rs56
-rw-r--r--src/commands/tab_switch.rs53
29 files changed, 1207 insertions, 1963 deletions
diff --git a/src/commands/bulk_rename.rs b/src/commands/bulk_rename.rs
index ee3a519..4171b01 100644
--- a/src/commands/bulk_rename.rs
+++ b/src/commands/bulk_rename.rs
@@ -4,146 +4,125 @@ use std::process;
use rand::Rng;
-use crate::commands::{JoshutoCommand, JoshutoRunnable, ReloadDirList};
use crate::context::JoshutoContext;
use crate::error::{JoshutoError, JoshutoErrorKind, JoshutoResult};
use crate::ui::TuiBackend;
+use super::reload;
+
const ENV_EDITOR: &str = "EDITOR";
-#[derive(Clone, Debug)]
-pub struct BulkRename;
+pub fn _bulk_rename(context: &mut JoshutoContext) -> JoshutoResult<()> {
+ const PREFIX: &str = "joshuto-";
+ let editor = match std::env::var(ENV_EDITOR) {
+ Ok(s) => s,
+ Err(_) => {
+ return Err(JoshutoError::new(
+ JoshutoErrorKind::EnvVarNotPresent,
+ format!("{} environment variable not set", ENV_EDITOR),
+ ));
+ }
+ };
+
+ /* generate a random file name to write to */
+ let mut rand_str = String::with_capacity(PREFIX.len() + 10);
+ rand_str.push_str(PREFIX);
+ rand::thread_rng()
+ .sample_iter(&rand::distributions::Alphanumeric)
+ .take(10)
+ .for_each(|ch| rand_str.push(ch));
+
+ /* create this file in a temporary folder */
+ let mut file_path = path::PathBuf::from("/tmp");
+ file_path.push(rand_str);
+
+ let paths = {
+ let curr_tab = context.tab_context_ref().curr_tab_ref();
+ match curr_tab.curr_list_ref() {
+ Some(s) => s.get_selected_paths(),
+ None => vec![],
+ }
+ };
+ {
+ let mut file = std::fs::File::create(&file_path)?;
+ for path in paths.iter() {
+ let file_name = path.file_name().unwrap();
+ let file_name_as_bytes = file_name.to_str().unwrap().as_bytes();
+ file.write_all(file_name_as_bytes)?;
+ file.write_all(&[b'\n'])?;
+ }
+ }
+
+ let mut command = process::Command::new(editor);
+ command.arg(&file_path);
-impl BulkRename {
- pub fn new() -> Self {
- BulkRename {}
+ let time = std::time::SystemTime::now();
+ {
+ let mut handle = command.spawn()?;
+ handle.wait()?;
}
- pub const fn command() -> &'static str {
- "bulk_rename"
+ let metadata = std::fs::metadata(&file_path)?;
+ if time >= metadata.modified()? {
+ return Ok(());
}
- pub fn bulk_rename(context: &mut JoshutoContext) -> JoshutoResult<()> {
- const PREFIX: &str = "joshuto-";
- let editor = match std::env::var(ENV_EDITOR) {
- Ok(s) => s,
- Err(_) => {
- return Err(JoshutoError::new(
- JoshutoErrorKind::EnvVarNotPresent,
- format!("{} environment variable not set", ENV_EDITOR),
- ));
- }
- };
-
- /* generate a random file name to write to */
- let mut rand_str = String::with_capacity(PREFIX.len() + 10);
- rand_str.push_str(PREFIX);
- rand::thread_rng()
- .sample_iter(&rand::distributions::Alphanumeric)
- .take(10)
- .for_each(|ch| rand_str.push(ch));
-
- /* create this file in a temporary folder */
- let mut file_path = path::PathBuf::from("/tmp");
- file_path.push(rand_str);
-
- let paths = {
- let curr_tab = context.tab_context_ref().curr_tab_ref();
- match curr_tab.curr_list_ref() {
- Some(s) => s.get_selected_paths(),
- None => vec![],
- }
- };
- {
- let mut file = std::fs::File::create(&file_path)?;
- for path in paths.iter() {
- let file_name = path.file_name().unwrap();
- let file_name_as_bytes = file_name.to_str().unwrap().as_bytes();
- file.write_all(file_name_as_bytes)?;
- file.write_all(&[b'\n'])?;
+ let mut paths_renamed: Vec<path::PathBuf> = Vec::with_capacity(paths.len());
+ {
+ let file = std::fs::File::open(&file_path)?;
+
+ let reader = std::io::BufReader::new(file);
+ for line in reader.lines() {
+ let line2 = line?;
+ let line = line2.trim();
+ if line.is_empty() {
+ continue;
}
+ let path = path::PathBuf::from(line);
+ paths_renamed.push(path);
}
+ std::fs::remove_file(&file_path)?;
+ }
+ if paths_renamed.len() < paths.len() {
+ return Err(JoshutoError::new(
+ JoshutoErrorKind::IOInvalidInput,
+ "Insufficient inputs".to_string(),
+ ));
+ }
- let mut command = process::Command::new(editor);
- command.arg(&file_path);
-
- let time = std::time::SystemTime::now();
- {
- let mut handle = command.spawn()?;
- handle.wait()?;
- }
- let metadata = std::fs::metadata(&file_path)?;
- if time >= metadata.modified()? {
- return Ok(());
- }
+ for (p, q) in paths.iter().zip(paths_renamed.iter()) {
+ println!("{:?} -> {:?}", p, q);
+ }
+ print!("Continue with rename? (Y/n): ");
+ std::io::stdout().flush()?;
- let mut paths_renamed: Vec<path::PathBuf> = Vec::with_capacity(paths.len());
- {
- let file = std::fs::File::open(&file_path)?;
-
- let reader = std::io::BufReader::new(file);
- for line in reader.lines() {
- let line2 = line?;
- let line = line2.trim();
- if line.is_empty() {
- continue;
- }
- let path = path::PathBuf::from(line);
- paths_renamed.push(path);
- }
- std::fs::remove_file(&file_path)?;
- }
- if paths_renamed.len() < paths.len() {
- return Err(JoshutoError::new(
- JoshutoErrorKind::IOInvalidInput,
- "Insufficient inputs".to_string(),
- ));
- }
+ let mut user_input = String::with_capacity(4);
+ std::io::stdin().read_line(&mut user_input)?;
+ user_input = user_input.to_lowercase();
+ let user_input_trimmed = user_input.trim();
+ if user_input_trimmed != "n" || user_input_trimmed != "no" {
for (p, q) in paths.iter().zip(paths_renamed.iter()) {
- println!("{:?} -> {:?}", p, q);
- }
- print!("Continue with rename? (Y/n): ");
- std::io::stdout().flush()?;
-
- let mut user_input = String::with_capacity(4);
- std::io::stdin().read_line(&mut user_input)?;
- user_input = user_input.to_lowercase();
-
- let user_input_trimmed = user_input.trim();
- if user_input_trimmed != "n" || user_input_trimmed != "no" {
- for (p, q) in paths.iter().zip(paths_renamed.iter()) {
- let mut handle = process::Command::new("mv")
- .arg("-iv")
- .arg("--")
- .arg(p)
- .arg(q)
- .spawn()?;
- handle.wait()?;
- }
+ let mut handle = process::Command::new("mv")
+ .arg("-iv")
+ .arg("--")
+ .arg(p)
+ .arg(q)
+ .spawn()?;
+ handle.wait()?;
}
- print!("Press ENTER to continue...");
- std::io::stdout().flush()?;
- std::io::stdin().read_line(&mut user_input)?;
-
- std::fs::remove_file(file_path)?;
- Ok(())
}
-}
+ print!("Press ENTER to continue...");
+ std::io::stdout().flush()?;
+ std::io::stdin().read_line(&mut user_input)?;
-impl JoshutoCommand for BulkRename {}
-
-impl std::fmt::Display for BulkRename {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{}", Self::command())
- }
+ std::fs::remove_file(file_path)?;
+ Ok(())
}
-impl JoshutoRunnable for BulkRename {
- fn execute(&self, context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
- backend.terminal_drop();
- let res = Self::bulk_rename(context);
- backend.terminal_restore()?;
- ReloadDirList::reload(context.tab_context_ref().get_index(), context)?;
- res
- }
+pub fn bulk_rename(context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
+ backend.terminal_drop();
+ let res = _bulk_rename(context);
+ backend.terminal_restore()?;
+ reload::reload(context, context.tab_context_ref().get_index())?;
+ res
}
diff --git a/src/commands/change_directory.rs b/src/commands/change_directory.rs
index 7559c52..1094111 100644
--- a/src/commands/change_directory.rs
+++ b/src/commands/change_directory.rs
@@ -1,61 +1,30 @@
use std::path;
-use crate::commands::{JoshutoCommand, JoshutoRunnable};
use crate::context::JoshutoContext;
use crate::error::JoshutoResult;
use crate::history::DirectoryHistory;
-use crate::ui::TuiBackend;
use crate::util::load_child::LoadChild;
-#[derive(Clone, Debug)]
-pub struct ChangeDirectory {
- path: path::PathBuf,
+pub fn cd(path: &path::Path, context: &mut JoshutoContext) -> std::io::Result<()> {
+ std::env::set_current_dir(path)?;
+ context.tab_context_mut().curr_tab_mut().set_pwd(path);
+ Ok(())
}
-impl ChangeDirectory {
- pub fn new(path: path::PathBuf) -> Self {
- ChangeDirectory { path }
- }
- pub const fn command() -> &'static str {
- "cd"
- }
+pub fn change_directories(path: &path::Path, context: &mut JoshutoContext) -> std::io::Result<()> {
+ cd(path, context)?;
+ let sort_options = context.config_t.sort_option.clone();
+ context
+ .tab_context_mut()
+ .curr_tab_mut()
+ .history_mut()
+ .populate_to_root(&path, &sort_options)?;
- pub fn cd(path: &path::Path, context: &mut JoshutoContext) -> std::io::Result<()> {
- std::env::set_current_dir(path)?;
- context.tab_context_mut().curr_tab_mut().set_pwd(path);
- Ok(())
- }
-
- pub fn change_directories(
- path: &path::Path,
- context: &mut JoshutoContext,
- ) -> std::io::Result<()> {
- Self::cd(path, context)?;
-
- let sort_options = context.config_t.sort_option.clone();
- context
- .tab_context_mut()
- .curr_tab_mut()
- .history_mut()
- .populate_to_root(&path, &sort_options)?;
-
- Ok(())
- }
+ Ok(())
}
-impl JoshutoCommand for ChangeDirectory {}
-
-impl std::fmt::Display for ChangeDirectory {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{} {}", Self::command(), self.path.to_str().unwrap())
- }
-}
-
-impl JoshutoRunnable for ChangeDirectory {
- fn execute(&self, context: &mut JoshutoContext, _: &mut TuiBackend) -> JoshutoResult<()> {
- Self::change_directories(&self.path, context)?;
- LoadChild::load_child(context)?;
-
- Ok(())
- }
+pub fn change_directory(context: &mut JoshutoContext, path: &path::Path) -> JoshutoResult<()> {
+ change_directories(path, context)?;
+ LoadChild::load_child(context)?;
+ Ok(())
}
diff --git a/src/commands/command_keybind.rs b/src/commands/command_keybind.rs
new file mode 100644
index 0000000..8fc8132
--- /dev/null
+++ b/src/commands/command_keybind.rs
@@ -0,0 +1,27 @@
+use crate::config::JoshutoCommandMapping;
+use crate::context::JoshutoContext;
+use crate::error::JoshutoResult;
+use crate::ui::TuiBackend;
+
+use super::KeyCommand;
+
+#[derive(Debug)]
+pub enum CommandKeybind {
+ SimpleKeybind(KeyCommand),
+ CompositeKeybind(JoshutoCommandMapping),
+}
+
+impl std::fmt::Display for CommandKeybind {
+ fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
+ match self {
+ CommandKeybind::SimpleKeybind(s) => write!(f, "{}", s),
+ CommandKeybind::CompositeKeybind(_) => write!(f, "..."),
+ }
+ }
+}
+
+pub trait JoshutoRunnable {
+ fn execute(&self, context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()>;
+}
+
+pub trait JoshutoCommand: JoshutoRunnable + std::fmt::Display + std::fmt::Debug {}
diff --git a/src/commands/command_line.rs b/src/commands/command_line.rs
index 52a5925..0e7c3b2 100644
--- a/src/commands/command_line.rs
+++ b/src/commands/command_line.rs
@@ -1,54 +1,28 @@
-use crate::commands::{self, JoshutoCommand, JoshutoRunnable};
+use crate::commands::KeyCommand;
use crate::context::JoshutoContext;
use crate::error::JoshutoResult;
use crate::ui::widgets::TuiTextField;
use crate::ui::TuiBackend;
-#[derive(Clone, Debug)]
-pub struct CommandLine {
- pub prefix: String,
- pub suffix: String,
-}
-
-impl CommandLine {
- pub fn new(prefix: String, suffix: String) -> Self {
- CommandLine { prefix, suffix }
- }
- pub const fn command() -> &'static str {
- "console"
- }
-
- pub fn readline(
- &self,
- context: &mut JoshutoContext,
- backend: &mut TuiBackend,
- ) -> JoshutoResult<()> {
- let user_input: Option<String> = TuiTextField::default()
- .prompt(":")
- .prefix(self.prefix.as_str())
- .suffix(self.suffix.as_str())
- .get_input(backend, context);
+use super::JoshutoRunnable;
- if let Some(s) = user_input {
- let trimmed = s.trim_start();
- let command = commands::parse_command(trimmed)?;
- command.execute(context, backend)
- } else {
- Ok(())
- }
- }
-}
-
-impl JoshutoCommand for CommandLine {}
-
-impl std::fmt::Display for CommandLine {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{}: {} {}", Self::command(), self.prefix, self.suffix)
- }
-}
+pub fn readline(
+ context: &mut JoshutoContext,
+ backend: &mut TuiBackend,
+ prefix: &str,
+ suffix: &str,
+) -> JoshutoResult<()> {
+ let user_input: Option<String> = TuiTextField::default()
+ .prompt(":")
+ .prefix(prefix)
+ .suffix(suffix)
+ .get_input(backend, context);
-impl JoshutoRunnable for CommandLine {
- fn execute(&self, context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
- self.readline(context, backend)
+ if let Some(s) = user_input {
+ let trimmed = s.trim_start();
+ let command = KeyCommand::parse_command(trimmed)?;
+ command.execute(context, backend)
+ } else {
+ Ok(())
}
}
diff --git a/src/commands/cursor_move.rs b/src/commands/cursor_move.rs
index 6a4ec19..bad885f 100644
--- a/src/commands/cursor_move.rs
+++ b/src/commands/cursor_move.rs
@@ -1,10 +1,8 @@
-use std::path::PathBuf;
-
-use crate::commands::{JoshutoCommand, JoshutoRunnable};
use crate::context::JoshutoContext;
use crate::error::JoshutoResult;
use crate::history::DirectoryHistory;
use crate::ui::TuiBackend;
+use std::path::PathBuf;
pub fn cursor_move(new_index: usize, context: &mut JoshutoContext) -> JoshutoResult<()> {
let mut path: Option<PathBuf> = None;
@@ -37,259 +35,112 @@ pub fn cursor_move(new_index: usize, context: &mut JoshutoContext) -> JoshutoRes
Ok(())
}
-#[derive(Clone, Debug)]
-pub struct CursorMoveDown {
- movement: usize,
-}
-
-impl CursorMoveDown {
- pub fn new(movement: usize) -> Self {
- Self { movement }
- }
- pub const fn command() -> &'static str {
- "cursor_move_up"
- }
-}
-
-impl JoshutoCommand for CursorMoveDown {}
-
-impl std::fmt::Display for CursorMoveDown {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{} {}", Self::command(), self.movement)
- }
-}
-
-impl JoshutoRunnable for CursorMoveDown {
- fn execute(&self, context: &mut JoshutoContext, _: &mut TuiBackend) -> JoshutoResult<()> {
- let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
- Some(curr_list) => curr_list.index.map(|idx| idx + self.movement),
- None => None,
- };
-
- if let Some(s) = movement {
- cursor_move(s, context)?;
- }
- Ok(())
- }
-}
-
-#[derive(Clone, Debug)]
-pub struct CursorMoveUp {
- movement: usize,
-}
-
-impl CursorMoveUp {
- pub fn new(movement: usize) -> Self {
- Self { movement }
- }
- pub const fn command() -> &'static str {
- "cursor_move_down"
- }
-}
-
-impl JoshutoCommand for CursorMoveUp {}
-
-impl std::fmt::Display for CursorMoveUp {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{} {}", Self::command(), self.movement)
- }
-}
-
-impl JoshutoRunnable for CursorMoveUp {
- fn execute(&self, context: &mut JoshutoContext, _: &mut TuiBackend) -> JoshutoResult<()> {
- let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
- Some(curr_list) => curr_list.index.map(|idx| {
- if idx > self.movement {
- idx - self.movement
- } else {
- 0
- }
- }),
- None => None,
- };
+pub fn up(context: &mut JoshutoContext, u: usize) -> JoshutoResult<()> {
+ let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
+ Some(curr_list) => curr_list.index.map(|idx| if idx > u { idx - u } else { 0 }),
+ None => None,
+ };
- if let Some(s) = movement {
- cursor_move(s, context)?;
- }
- Ok(())
- }
-}
-
-#[derive(Clone, Debug)]
-pub struct CursorMovePageUp;
-
-impl CursorMovePageUp {
- pub fn new() -> Self {
- Self
- }
- pub const fn command() -> &'static str {
- "cursor_move_page_up"
+ if let Some(s) = movement {
+ cursor_move(s, context)?;
}
+ Ok(())
}
-impl JoshutoCommand for CursorMovePageUp {}
-
-impl std::fmt::Display for CursorMovePageUp {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{}", Self::command())
+pub fn down(context: &mut JoshutoContext, u: usize) -> JoshutoResult<()> {
+ let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
+ Some(curr_list) => curr_list.index.map(|idx| idx + u),
+ None => None,
+ };
+ if let Some(s) = movement {
+ cursor_move(s, context)?;
}
+ Ok(())
}
-impl JoshutoRunnable for CursorMovePageUp {
- fn execute(&self, context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
- let half_page = {
- match backend.terminal.as_ref().unwrap().size() {
- Ok(rect) => rect.height as usize - 2,
- _ => 10,
- }
- };
-
- let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
- Some(curr_list) => {
- curr_list
- .index
- .map(|idx| if idx > half_page { idx - half_page } else { 0 })
+pub fn home(context: &mut JoshutoContext) -> JoshutoResult<()> {
+ let movement: Option<usize> = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
+ Some(curr_list) => {
+ let len = curr_list.contents.len();
+ if len == 0 {
+ None
+ } else {
+ Some(0)
}
- None => None,
- };
-
- if let Some(s) = movement {
- cursor_move(s, context)?;
}
- Ok(())
- }
-}
-
-#[derive(Clone, Debug)]
-pub struct CursorMovePageDown;
-
-impl CursorMovePageDown {
- pub fn new() -> Self {
- Self
- }
- pub const fn command() -> &'static str {
- "cursor_move_page_down"
- }
-}
-
-impl JoshutoCommand for CursorMovePageDown {}
+ None => None,
+ };
-impl std::fmt::Display for CursorMovePageDown {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{}", Self::command())
+ if let Some(s) = movement {
+ cursor_move(s, context)?;
}
+ Ok(())
}
-impl JoshutoRunnable for CursorMovePageDown {
- fn execute(&self, context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
- let half_page = {
- match backend.terminal.as_ref().unwrap().size() {
- Ok(rect) => rect.height as usize - 2,
- _ => 10,
- }
- };
-
- let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
- Some(curr_list) => {
- let dir_len = curr_list.contents.len();
- curr_list.index.map(|idx| {
- if idx + half_page > dir_len - 1 {
- dir_len - 1
- } else {
- idx + half_page
- }
- })
+pub fn end(context: &mut JoshutoContext) -> JoshutoResult<()> {
+ let movement: Option<usize> = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
+ Some(curr_list) => {
+ let len = curr_list.contents.len();
+ if len == 0 {
+ None
+ } else {
+ Some(len - 1)
}
- None => None,
- };
-
- if let Some(s) = movement {
- cursor_move(s, context)?;
}
- Ok(())
- }
-}
-
-#[derive(Clone, Debug)]
-pub struct CursorMoveHome;
-
-impl CursorMoveHome {
- pub fn new() -> Self {
- Self
- }
- pub const fn command() -> &'static str {
- "cursor_move_home"
- }
-}
-
-impl JoshutoCommand for CursorMoveHome {}
+ None => None,
+ };
-impl std::fmt::Display for CursorMoveHome {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{}", Self::command())
+ if let Some(s) = movement {
+ cursor_move(s, context)?;
}
+ Ok(())
}
-impl JoshutoRunnable for CursorMoveHome {
- fn execute(&self, context: &mut JoshutoContext, _: &mut TuiBackend) -> JoshutoResult<()> {
- let movement: Option<usize> = match context.tab_context_ref().curr_tab_ref().curr_list_ref()
- {
- Some(curr_list) => {
- let len = curr_list.contents.len();
- if len == 0 {
- None
- } else {
- Some(0)
- }
- }
- None => None,
- };
-
- if let Some(s) = movement {
- cursor_move(s, context)?;
+pub fn page_up(context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
+ let half_page = {
+ match backend.terminal.as_ref().unwrap().size() {
+ Ok(rect) => rect.height as usize - 2,
+ _ => 10,
}
- Ok(())
- }
-}
+ };
-#[derive(Clone, Debug)]
-pub struct CursorMoveEnd;
+ let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
+ Some(curr_list) => curr_list
+ .index
+ .map(|idx| if idx > half_page { idx - half_page } else { 0 }),
+ None => None,
+ };
-impl CursorMoveEnd {
- pub fn new() -> Self {
- Self
- }
- pub const fn command() -> &'static str {
- "cursor_move_end"
+ if let Some(s) = movement {
+ cursor_move(s, context)?;
}
+ Ok(())
}
-impl JoshutoCommand for CursorMoveEnd {}
-
-impl std::fmt::Display for CursorMoveEnd {
- fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
- write!(f, "{}", Self::command())
- }
-}
+pub fn page_down(context: &mut JoshutoContext, backend: &mut TuiBackend) -> JoshutoResult<()> {
+ let half_page = {
+ match backend.terminal.as_ref().unwrap().size() {
+ Ok(rect) => rect.height as usize - 2,
+ _ => 10,
+ }
+ };
-impl JoshutoRunnable for CursorMoveEnd {
- fn execute(&self, context: &mut JoshutoContext, _: &mut TuiBackend) -> JoshutoResult<()> {
- let movement: Option<usize> = match context.tab_context_ref().curr_tab_ref().curr_list_ref()
- {
- Some(curr_list) => {
- let len = curr_list.contents.len();
- if len == 0 {
- None
+ let movement = match context.tab_context_ref().curr_tab_ref().curr_list_ref() {
+ Some(curr_list) => {
+ let dir_len = curr_list.contents.len();
+ curr_list.index.map(|idx| {
+ if idx + half_page > dir_len - 1 {
+ dir_len - 1
} else {
- Some(len - 1)
+ idx + half_page
}
- }
- None => None,
- };
-
- if let Some(s) = movement {
- cursor_move(s, context)?;
+ })
}
- Ok(())
+ None => None,
+ };
+
+ if let Some(s) = movement {
+ cursor_move(s, context)?;
}
+ Ok(())
}
diff --git a/src/commands/delete_files.rs b/src/commands/delete_files.rs
index 25a13f8..bc070f1 100644
--- a/src/commands/delete_files.rs
+++ b/src/commands/delete_files.rs
@@ -3,104 +3,85 @@ use std::path;
use termion::event::Key;
-use crate::commands::{JoshutoCommand, JoshutoRunnable, ReloadDirList};
use crate::context::JoshutoContext;
-use crate::error::JoshutoResult;
use crate::history::DirectoryHistory;
use crate::ui::widgets::TuiPrompt;
use crate::ui::TuiBackend;
use crate::util::load_child::LoadChild;
-#[derive(Clone, Debug)]
-pub struct DeleteFiles;
+use super::reload;
-impl DeleteFiles {
- pub fn new() -> Self {
- DeleteFiles
- }
- pub const fn command() -> &'static str {
- "delete_files"
- }
-
- pub fn remove_files<'a, I>(paths: I) -> std::io::Result<()>
- where
- I: Iterator<Item = &'a path::Path>,
- {
- for path in paths {
- if let Ok(metadata) = fs::symlink_metadata(path) {
- if metadata.is_dir() {
- fs::remove_dir_all(&path)?;
- } else {
- fs::remove_file(&path)?;
- }
+pub fn remove_files<'a, I>(paths: I) -> std::io::Result<()>
+where
+ I: Iterator<Item = &'a path::Path>,