diff --git a/Cargo.toml b/Cargo.toml index b97e5f6..2df43df 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -15,4 +15,5 @@ mime-detective = "*" rayon = "1.0.3" dirs-2 = "1.1.0" users = "0.8" -chrono = "0.4" \ No newline at end of file +chrono = "0.4" +libc = "*" \ No newline at end of file diff --git a/src/main.rs b/src/main.rs index c4a0cb6..8acfeed 100644 --- a/src/main.rs +++ b/src/main.rs @@ -9,6 +9,7 @@ extern crate users; extern crate chrono; extern crate mime_detective; extern crate rayon; +extern crate libc; use termion::input::MouseTerminal; use termion::raw::IntoRawMode; diff --git a/src/preview.rs b/src/preview.rs index ce64a99..59fa675 100644 --- a/src/preview.rs +++ b/src/preview.rs @@ -1,5 +1,6 @@ use std::io::Write; use std::sync::Mutex; +use std::sync::Arc; use crate::coordinates::{Coordinates, Position, Size}; use crate::files::{File, Files, Kind}; @@ -8,22 +9,31 @@ use crate::textview::TextView; use crate::widget::Widget; -pub struct InstanceCounter(Mutex); -impl PartialEq for InstanceCounter { - fn eq(&self, other: &Self) -> bool { - let instance = self.0.lock().unwrap(); - let other = other.0.lock().unwrap(); - *instance == *other - } +lazy_static! { + static ref PIDS: Arc>> = { Arc::new(Mutex::new(vec![])) }; + static ref CURFILE: Arc>> = { Arc::new(Mutex::new(None)) }; } +fn kill_procs() { + let mut pids = PIDS.lock().unwrap(); + for pid in &*pids { + let msg = format!("KILLING PROC: {}", pid); + unsafe { libc::kill(*pid, 9); } + } + pids.clear(); +} + +fn is_current(file: &File) -> bool { + CURFILE.lock().unwrap().as_ref().unwrap() == file +} + + #[derive(PartialEq)] pub struct Previewer { pub file: Option, pub buffer: String, pub coordinates: Coordinates, - pub instances: InstanceCounter } impl Previewer { @@ -32,30 +42,29 @@ impl Previewer { file: None, buffer: String::new(), coordinates: Coordinates::new(), - instances: InstanceCounter(Mutex::new(0)) } } pub fn set_file(&mut self, file: &File) { - //return; - let mut instance = self.instances.0.try_lock().unwrap(); - if *instance > 2 { return } - *instance = *instance + 1; let coordinates = self.coordinates.clone(); let file = file.clone(); let redraw = crate::term::reset() + &self.get_redraw_empty_list(0); + *CURFILE.lock().unwrap() = Some(file.clone()); - //self.threads.install(|| { std::thread::spawn(move || { + kill_procs(); match &file.kind { Kind::Directory => match Files::new_from_path(&file.path) { Ok(files) => { + if !is_current(&file) { return } let len = files.len(); if len == 0 { return }; let mut file_list = ListView::new(files); file_list.set_coordinates(&coordinates); file_list.refresh(); + if !is_current(&file) { return } file_list.animate_slide_up(); + } Err(err) => { crate::window::show_status(&format!("Can't preview because: {}", err)); @@ -65,21 +74,34 @@ impl Previewer { _ => { if file.get_mime() == Some("text".to_string()) { let mut textview = TextView::new_from_file(&file); + if !is_current(&file) { return } textview.set_coordinates(&coordinates); textview.refresh(); + if !is_current(&file) { return } textview.animate_slide_up(); } else { - let output = - std::process::Command::new("scope.sh").arg(&file.name) + let process = + std::process::Command::new("scope.sh") + .arg(&file.name) .arg("10".to_string()) .arg("10".to_string()) .arg("".to_string()) .arg("false".to_string()) - .output().unwrap(); + .stdin(std::process::Stdio::null()) + .stdout(std::process::Stdio::piped()) + .stderr(std::process::Stdio::null()) + .spawn().unwrap(); + let pid = process.id(); + PIDS.lock().unwrap().push(pid as i32); + if !is_current(&file) { return } - if output.status.code().unwrap() == 0 { + let output = process.wait_with_output().unwrap(); + + let status = output.status.code().unwrap(); + + if status == 0 || status == 5 && is_current(&file) { let output = std::str::from_utf8(&output.stdout) .unwrap() .to_string(); @@ -95,12 +117,11 @@ impl Previewer { { write!(std::io::stdout(), "{}", redraw).unwrap(); } + PIDS.lock().unwrap().pop(); } - } } }); - *instance = *instance - 1; } }