implemented expanding and collapsing directories
parent
bec3e6b3be
commit
78b5a0e9a8
|
@ -80,6 +80,8 @@ impl Directory {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn insert(&mut self, name: String, is_file: bool) {
|
pub fn insert(&mut self, name: String, is_file: bool) {
|
||||||
|
self.selected_mut().expanded = true;
|
||||||
|
|
||||||
let current_depth = self.selected().depth;
|
let current_depth = self.selected().depth;
|
||||||
|
|
||||||
let depth = if self.selected().is_file {
|
let depth = if self.selected().is_file {
|
||||||
|
@ -322,8 +324,11 @@ impl Directory {
|
||||||
KeyCode::End => {
|
KeyCode::End => {
|
||||||
self.selection = u16::try_from(self.dirs.len()-1).unwrap_or(u16::MAX);
|
self.selection = u16::try_from(self.dirs.len()-1).unwrap_or(u16::MAX);
|
||||||
if self.selection > self.display_start + self.height {
|
if self.selection > self.display_start + self.height {
|
||||||
self.display_start = self.selection - self.height
|
self.display_start = self.selection - self.height;
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
KeyCode::Tab if !self.selected().is_file => {
|
||||||
|
self.selected_mut().expanded ^= true;
|
||||||
}
|
}
|
||||||
_ => (),
|
_ => (),
|
||||||
}
|
}
|
||||||
|
@ -373,9 +378,17 @@ impl Directory {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn display_lines(&self) -> impl Iterator<Item = String> + '_ {
|
fn display_lines(&self) -> impl Iterator<Item = String> + '_ {
|
||||||
self.dirs.iter().enumerate().scan(
|
let scan_fn = |(indent_parts, unexpanded_depth): &mut (Vec<TreePart>, Option<u8>), (i, current): (usize, &Item)| -> Option<String> {
|
||||||
Vec::new(),
|
if unexpanded_depth.is_some_and(|d| current.depth > d) {
|
||||||
|indent_parts, (i, current)| {
|
return Some(String::new());
|
||||||
|
}
|
||||||
|
|
||||||
|
if current.expanded {
|
||||||
|
*unexpanded_depth = None;
|
||||||
|
} else {
|
||||||
|
*unexpanded_depth = Some(current.depth);
|
||||||
|
}
|
||||||
|
|
||||||
let is_last_at_this_depth = is_last_at_this_depth(&self.dirs[i+1..], current.depth);
|
let is_last_at_this_depth = is_last_at_this_depth(&self.dirs[i+1..], current.depth);
|
||||||
let (new_part, continue_part) = if is_last_at_this_depth {
|
let (new_part, continue_part) = if is_last_at_this_depth {
|
||||||
(TreePart::Last, TreePart::Blank)
|
(TreePart::Last, TreePart::Blank)
|
||||||
|
@ -383,28 +396,39 @@ impl Directory {
|
||||||
(TreePart::First, TreePart::Wait)
|
(TreePart::First, TreePart::Wait)
|
||||||
};
|
};
|
||||||
|
|
||||||
if i == 0 { return Some(current.name.clone() + "/") }
|
let mut result = if i == 0 {
|
||||||
|
String::new()
|
||||||
|
} else {
|
||||||
if current.depth as usize > indent_parts.len() {
|
if current.depth as usize > indent_parts.len() {
|
||||||
indent_parts.push(continue_part);
|
indent_parts.push(continue_part);
|
||||||
} else {
|
} else {
|
||||||
indent_parts[current.depth as usize-1] = continue_part;
|
indent_parts[current.depth as usize-1] = continue_part;
|
||||||
}
|
}
|
||||||
|
|
||||||
let result = indent_parts[0 .. current.depth as usize - 1]
|
indent_parts[0 .. current.depth as usize - 1]
|
||||||
.iter()
|
.iter()
|
||||||
.fold(String::new(), |result, t| result + t.display())
|
.fold(String::new(), |result, t| result + t.display())
|
||||||
+ new_part.display()
|
+ new_part.display()
|
||||||
+ ¤t.name
|
};
|
||||||
+ if current.is_file {
|
|
||||||
""
|
result += ¤t.name;
|
||||||
} else {
|
|
||||||
"/"
|
if !current.is_file {
|
||||||
|
result += "/";
|
||||||
|
}
|
||||||
|
if !current.expanded {
|
||||||
|
result += "...";
|
||||||
};
|
};
|
||||||
|
|
||||||
Some(result)
|
Some(result)
|
||||||
}
|
};
|
||||||
)
|
|
||||||
|
let initial_state = (Vec::new(), None);
|
||||||
|
|
||||||
|
self.dirs.iter()
|
||||||
|
.enumerate()
|
||||||
|
.scan(initial_state, scan_fn)
|
||||||
|
.filter(|s| !s.is_empty())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue