From a78c80ac1c574c235233206ea5dc974c27d3de85 Mon Sep 17 00:00:00 2001 From: "andy.boot" Date: Fri, 6 Jun 2025 22:13:11 +0100 Subject: [PATCH 1/6] hack --- Cargo.lock | 35 ++++++++++++++++++++++++++ Cargo.toml | 1 + src/display.rs | 24 ++++++++++++------ src/main.rs | 66 ++++++++++++++++++++++++++++++++++++++++++-------- 4 files changed, 108 insertions(+), 18 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 74865366..6aa79ad5 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -344,6 +344,7 @@ dependencies = [ "sysinfo", "tempfile", "terminal_size", + "termion", "thousands", "unicode-width", "winapi-util", @@ -486,6 +487,7 @@ checksum = "1580801010e535496706ba011c15f8532df6b42297d2e471fec38ceadd8c0638" dependencies = [ "bitflags 2.9.1", "libc", + "redox_syscall", ] [[package]] @@ -562,6 +564,12 @@ dependencies = [ "autocfg", ] +[[package]] +name = "numtoa" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6aa2c4e539b869820a2b82e1aef6ff40aa85e65decdd5185e83fb4b1249cd00f" + [[package]] name = "once_cell" version = "1.21.3" @@ -657,6 +665,21 @@ dependencies = [ "crossbeam-utils", ] +[[package]] +name = "redox_syscall" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0d04b7d0ee6b4a0207a0a7adb104d23ecb0b47d6beae7152d0fa34b692b29fd6" +dependencies = [ + "bitflags 2.9.1", +] + +[[package]] +name = "redox_termios" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "20145670ba436b55d91fc92d25e71160fbfbdd57831631c8d7d36377a476f1cb" + [[package]] name = "redox_users" version = "0.4.6" @@ -841,6 +864,18 @@ dependencies = [ "windows-sys 0.48.0", ] +[[package]] +name = "termion" +version = "4.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3669a69de26799d6321a5aa713f55f7e2cd37bd47be044b50f2acafc42c122bb" +dependencies = [ + "libc", + "libredox", + "numtoa", + "redox_termios", +] + [[package]] name = "termtree" version = "0.5.1" diff --git a/Cargo.toml b/Cargo.toml index 6df4d122..30bd8946 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -43,6 +43,7 @@ directories = "4" sysinfo = "0.27" ctrlc = "3.4" chrono = "0.4" +termion="4" [target.'cfg(not(target_has_atomic = "64"))'.dependencies] portable-atomic = "1.4" diff --git a/src/display.rs b/src/display.rs index d24af1d4..d907a381 100644 --- a/src/display.rs +++ b/src/display.rs @@ -4,14 +4,17 @@ use crate::node::FileTime; use ansi_term::Colour::Red; use lscolors::{LsColors, Style}; +use termion::raw::RawTerminal; use unicode_width::UnicodeWidthStr; use stfu8::encode_u8; +use std::io::{Write}; use chrono::{DateTime, Local, TimeZone, Utc}; use std::cmp::max; use std::cmp::min; use std::fs; +use std::io::Stdout; use std::iter::repeat_n; use std::path::Path; use thousands::Separable; @@ -129,6 +132,7 @@ pub fn draw_it( no_percent_bars: bool, terminal_width: usize, skip_total: bool, + stdout: &mut RawTerminal, ) { let num_chars_needed_on_left_most = if idd.by_filecount { let max_size = root_node.size; @@ -143,6 +147,8 @@ pub fn draw_it( terminal_width > num_chars_needed_on_left_most + 2, "Not enough terminal width" ); + // write!(stdout, "{}{}Hello!", termion::clear::All, termion::cursor::Goto(1, 1)).unwrap(); + // write!(stdout, "{}", termion::cursor::Goto(2, 1)).unwrap(); let allowed_width = terminal_width - num_chars_needed_on_left_most - 2; let num_indent_chars = 3; @@ -171,7 +177,7 @@ pub fn draw_it( }; if !skip_total { - display_node(root_node, &draw_data, true, true); + display_node(root_node, stdout, &draw_data, true, true); } else { for (count, c) in root_node .get_children_from_node(draw_data.display_data.initial.is_reversed) @@ -179,7 +185,7 @@ pub fn draw_it( { let is_biggest = display_data.is_biggest(count, root_node.num_siblings()); let was_i_last = display_data.is_last(count, root_node.num_siblings()); - display_node(c, &draw_data, is_biggest, was_i_last); + display_node(c, stdout, &draw_data, is_biggest, was_i_last); } } } @@ -218,22 +224,24 @@ fn find_longest_dir_name( .fold(longest, max) } -fn display_node(node: &DisplayNode, draw_data: &DrawData, is_biggest: bool, is_last: bool) { +fn display_node(node: &DisplayNode, + stdout: &mut RawTerminal, + draw_data: &DrawData, is_biggest: bool, is_last: bool) { // hacky way of working out how deep we are in the tree let indent = draw_data.get_new_indent(!node.children.is_empty(), is_last); let level = ((indent.chars().count() - 1) / 2) - 1; let bar_text = draw_data.generate_bar(node, level); - let to_print = format_string(node, &indent, &bar_text, is_biggest, draw_data.display_data); + let to_print = format_string(node, &indent, &bar_text, is_biggest, &draw_data.display_data); if !draw_data.display_data.initial.is_reversed { - println!("{to_print}") + write!(stdout, "{to_print}").unwrap() } let dd = DrawData { indent: clean_indentation_string(&indent), percent_bar: bar_text, - display_data: draw_data.display_data, + display_data:draw_data.display_data, }; let num_siblings = node.num_siblings(); @@ -244,11 +252,11 @@ fn display_node(node: &DisplayNode, draw_data: &DrawData, is_biggest: bool, is_l { let is_biggest = dd.display_data.is_biggest(count, num_siblings); let was_i_last = dd.display_data.is_last(count, num_siblings); - display_node(c, &dd, is_biggest, was_i_last); + display_node( c, stdout, &dd, is_biggest, was_i_last); } if draw_data.display_data.initial.is_reversed { - println!("{to_print}") + write!(stdout, "{to_print}").unwrap() } } diff --git a/src/main.rs b/src/main.rs index bbc7c005..fdc6c82a 100644 --- a/src/main.rs +++ b/src/main.rs @@ -20,10 +20,14 @@ use display::InitialDisplayData; use filter::AggregateData; use progress::PIndicator; use regex::Error; +use termion::raw::RawTerminal; use std::collections::HashSet; use std::env; use std::fs::read_to_string; use std::io; +use std::io::stdin; +use std::io::stdout; +use std::io::Stdout; use std::panic; use std::process; use std::sync::Arc; @@ -31,6 +35,11 @@ use std::sync::Mutex; use sysinfo::{System, SystemExt}; use utils::canonicalize_absolute_path; +use termion::event::{Key, Event}; +use termion::input::{TermRead}; +use termion::raw::IntoRawMode; +use std::io::{Write}; + use self::display::draw_it; use config::get_config; use dir_walker::walk_it; @@ -309,24 +318,60 @@ fn main() { let print_errors = config.get_print_errors(&options); print_any_errors(print_errors, walk_data.errors); + let stdin = stdin(); + let mut out = stdout().into_raw_mode().unwrap(); + + write!(out, "{}{}Dust interactive (q to quit)", termion::clear::All, termion::cursor::Goto(1, 1)).unwrap(); + write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); + print_output( + &config, + &options, + &tree, + is_colors, + terminal_width, + &mut out, + ); + out.flush().unwrap(); + + for c in stdin.events() { + write!(out, "{}{}Dust interactive (q to quit)", termion::clear::All, termion::cursor::Goto(1, 1)).unwrap(); + write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); + let evt = c.unwrap(); + match evt { + Event::Key(Key::Char('q')) => break, + Event::Key(Key::Char(x)) => { + // println!("{}key ", x); + }, + Event::Key(Key::Left) =>{ + // println!("left "); + } + Event::Key(Key::Right) =>{ + // println!("right "); + }, + _ => {} + } print_output( - config, - options, - tree, - walk_data.by_filecount, + &config, + &options, + &tree, is_colors, terminal_width, - ) - }); + &mut out, + ); + out.flush().unwrap(); + + } + + } fn print_output( - config: Config, - options: Cli, - tree: DisplayNode, - by_filecount: bool, + config: &Config, + options: &Cli, + tree: &DisplayNode, is_colors: bool, terminal_width: usize, + stdout: &mut RawTerminal ) { let output_format = config.get_output_format(&options); @@ -353,6 +398,7 @@ fn print_output( config.get_no_bars(&options), terminal_width, config.get_skip_total(&options), + stdout, ) } } From fff669579850cce6f6f28439429cdf6ad678c339 Mon Sep 17 00:00:00 2001 From: "andy.boot" Date: Fri, 6 Jun 2025 22:13:43 +0100 Subject: [PATCH 2/6] hack --- src/display.rs | 22 ++++++++++++++----- src/main.rs | 59 +++++++++++++++++++++++++++++--------------------- 2 files changed, 50 insertions(+), 31 deletions(-) diff --git a/src/display.rs b/src/display.rs index d907a381..9d1ce63d 100644 --- a/src/display.rs +++ b/src/display.rs @@ -9,12 +9,12 @@ use unicode_width::UnicodeWidthStr; use stfu8::encode_u8; -use std::io::{Write}; use chrono::{DateTime, Local, TimeZone, Utc}; use std::cmp::max; use std::cmp::min; use std::fs; use std::io::Stdout; +use std::io::Write; use std::iter::repeat_n; use std::path::Path; use thousands::Separable; @@ -224,15 +224,25 @@ fn find_longest_dir_name( .fold(longest, max) } -fn display_node(node: &DisplayNode, +fn display_node( + node: &DisplayNode, stdout: &mut RawTerminal, - draw_data: &DrawData, is_biggest: bool, is_last: bool) { + draw_data: &DrawData, + is_biggest: bool, + is_last: bool, +) { // hacky way of working out how deep we are in the tree let indent = draw_data.get_new_indent(!node.children.is_empty(), is_last); let level = ((indent.chars().count() - 1) / 2) - 1; let bar_text = draw_data.generate_bar(node, level); - let to_print = format_string(node, &indent, &bar_text, is_biggest, &draw_data.display_data); + let to_print = format_string( + node, + &indent, + &bar_text, + is_biggest, + &draw_data.display_data, + ); if !draw_data.display_data.initial.is_reversed { write!(stdout, "{to_print}").unwrap() @@ -241,7 +251,7 @@ fn display_node(node: &DisplayNode, let dd = DrawData { indent: clean_indentation_string(&indent), percent_bar: bar_text, - display_data:draw_data.display_data, + display_data: draw_data.display_data, }; let num_siblings = node.num_siblings(); @@ -252,7 +262,7 @@ fn display_node(node: &DisplayNode, { let is_biggest = dd.display_data.is_biggest(count, num_siblings); let was_i_last = dd.display_data.is_last(count, num_siblings); - display_node( c, stdout, &dd, is_biggest, was_i_last); + display_node(c, stdout, &dd, is_biggest, was_i_last); } if draw_data.display_data.initial.is_reversed { diff --git a/src/main.rs b/src/main.rs index fdc6c82a..1c74d422 100644 --- a/src/main.rs +++ b/src/main.rs @@ -20,25 +20,25 @@ use display::InitialDisplayData; use filter::AggregateData; use progress::PIndicator; use regex::Error; -use termion::raw::RawTerminal; use std::collections::HashSet; use std::env; use std::fs::read_to_string; use std::io; +use std::io::Stdout; use std::io::stdin; use std::io::stdout; -use std::io::Stdout; use std::panic; use std::process; use std::sync::Arc; use std::sync::Mutex; use sysinfo::{System, SystemExt}; +use termion::raw::RawTerminal; use utils::canonicalize_absolute_path; -use termion::event::{Key, Event}; -use termion::input::{TermRead}; +use std::io::Write; +use termion::event::{Event, Key}; +use termion::input::TermRead; use termion::raw::IntoRawMode; -use std::io::{Write}; use self::display::draw_it; use config::get_config; @@ -321,33 +321,45 @@ fn main() { let stdin = stdin(); let mut out = stdout().into_raw_mode().unwrap(); - write!(out, "{}{}Dust interactive (q to quit)", termion::clear::All, termion::cursor::Goto(1, 1)).unwrap(); - write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); - print_output( - &config, - &options, - &tree, - is_colors, - terminal_width, - &mut out, - ); - out.flush().unwrap(); + write!( + out, + "{}{}Dust interactive (q to quit)", + termion::clear::All, + termion::cursor::Goto(1, 1) + ) + .unwrap(); + write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); + print_output( + &config, + &options, + &tree, + is_colors, + terminal_width, + &mut out, + ); + out.flush().unwrap(); for c in stdin.events() { - write!(out, "{}{}Dust interactive (q to quit)", termion::clear::All, termion::cursor::Goto(1, 1)).unwrap(); + write!( + out, + "{}{}Dust interactive (q to quit)", + termion::clear::All, + termion::cursor::Goto(1, 1) + ) + .unwrap(); write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); let evt = c.unwrap(); match evt { Event::Key(Key::Char('q')) => break, Event::Key(Key::Char(x)) => { // println!("{}key ", x); - }, - Event::Key(Key::Left) =>{ + } + Event::Key(Key::Left) => { // println!("left "); } - Event::Key(Key::Right) =>{ + Event::Key(Key::Right) => { // println!("right "); - }, + } _ => {} } print_output( @@ -359,10 +371,7 @@ fn main() { &mut out, ); out.flush().unwrap(); - } - - } fn print_output( @@ -371,7 +380,7 @@ fn print_output( tree: &DisplayNode, is_colors: bool, terminal_width: usize, - stdout: &mut RawTerminal + stdout: &mut RawTerminal, ) { let output_format = config.get_output_format(&options); From 69ba3adcfc733c0083ac355529254ee02a68bdf2 Mon Sep 17 00:00:00 2001 From: "andy.boot" Date: Sun, 15 Jun 2025 22:44:49 +0100 Subject: [PATCH 3/6] hack --- src/main.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main.rs b/src/main.rs index 1c74d422..72aaff02 100644 --- a/src/main.rs +++ b/src/main.rs @@ -403,7 +403,7 @@ fn print_output( draw_it( idd, - &tree, + tree, config.get_no_bars(&options), terminal_width, config.get_skip_total(&options), From 9957cd3d9cac92048d40c5468fb3822d8b5ee342 Mon Sep 17 00:00:00 2001 From: "andy.boot" Date: Sun, 6 Jul 2025 10:17:26 +0100 Subject: [PATCH 4/6] hack --- src/main.rs | 76 +++++++++++++++++++++++++++-------------------------- 1 file changed, 39 insertions(+), 37 deletions(-) diff --git a/src/main.rs b/src/main.rs index 72aaff02..4f17d7fc 100644 --- a/src/main.rs +++ b/src/main.rs @@ -318,28 +318,9 @@ fn main() { let print_errors = config.get_print_errors(&options); print_any_errors(print_errors, walk_data.errors); - let stdin = stdin(); - let mut out = stdout().into_raw_mode().unwrap(); - - write!( - out, - "{}{}Dust interactive (q to quit)", - termion::clear::All, - termion::cursor::Goto(1, 1) - ) - .unwrap(); - write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); - print_output( - &config, - &options, - &tree, - is_colors, - terminal_width, - &mut out, - ); - out.flush().unwrap(); + let stdin = stdin(); + let mut out = stdout().into_raw_mode().unwrap(); - for c in stdin.events() { write!( out, "{}{}Dust interactive (q to quit)", @@ -348,20 +329,6 @@ fn main() { ) .unwrap(); write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); - let evt = c.unwrap(); - match evt { - Event::Key(Key::Char('q')) => break, - Event::Key(Key::Char(x)) => { - // println!("{}key ", x); - } - Event::Key(Key::Left) => { - // println!("left "); - } - Event::Key(Key::Right) => { - // println!("right "); - } - _ => {} - } print_output( &config, &options, @@ -371,7 +338,42 @@ fn main() { &mut out, ); out.flush().unwrap(); - } + + for c in stdin.events() { + write!( + out, + "{}{}Dust interactive (q to quit)", + termion::clear::All, + termion::cursor::Goto(1, 1) + ) + .unwrap(); + write!(out, "{}", termion::cursor::Goto(1, 2)).unwrap(); + let evt = c.unwrap(); + match evt { + Event::Key(Key::Char('q')) => break, + Event::Key(Key::Char(x)) => { + write!(out,"{x} key\n" ); + } + Event::Key(Key::Left) => { + write!(out,"left\n"); + } + Event::Key(Key::Right) => { + write!(out,"right\n"); + } + _ => {} + } + write!(out, "{}", termion::cursor::Goto(1, 3)).unwrap(); + print_output( + &config, + &options, + &tree, + is_colors, + terminal_width, + &mut out, + ); + out.flush().unwrap(); + } + }) } fn print_output( @@ -394,7 +396,7 @@ fn print_output( short_paths: !config.get_full_paths(&options), is_reversed: !config.get_reverse(&options), colors_on: is_colors, - by_filecount, + by_filecount: options.filecount, by_filetime: config.get_filetime(&options), is_screen_reader: config.get_screen_reader(&options), output_format, From 5057337340b0644d276c6138785cce3e237c7cb5 Mon Sep 17 00:00:00 2001 From: "andy.boot" Date: Mon, 7 Jul 2025 22:19:16 +0100 Subject: [PATCH 5/6] hack --- src/display.rs | 79 ++++++++++++++++++++++++++++++++++++++++++++------ src/main.rs | 27 ++++++++++++----- 2 files changed, 90 insertions(+), 16 deletions(-) diff --git a/src/display.rs b/src/display.rs index 9d1ce63d..cb924480 100644 --- a/src/display.rs +++ b/src/display.rs @@ -32,6 +32,7 @@ pub struct InitialDisplayData { pub is_screen_reader: bool, pub output_format: String, pub bars_on_right: bool, + pub selected_index: i32, } pub struct DisplayData { @@ -84,6 +85,16 @@ struct DrawData<'a> { display_data: &'a DisplayData, } +struct State { + test: i32, +} + +impl State { + fn decrement(&mut self) { + self.test -= 1; + } +} + impl DrawData<'_> { fn get_new_indent(&self, has_children: bool, was_i_last: bool) -> String { let chars = self.display_data.get_tree_chars(was_i_last, has_children); @@ -175,9 +186,10 @@ pub fn draw_it( percent_bar: first_size_bar, display_data: &display_data, }; + let mut state = State { test: 0 }; if !skip_total { - display_node(root_node, stdout, &draw_data, true, true); + display_node(root_node, stdout, &draw_data, true, true, &mut state); } else { for (count, c) in root_node .get_children_from_node(draw_data.display_data.initial.is_reversed) @@ -185,7 +197,7 @@ pub fn draw_it( { let is_biggest = display_data.is_biggest(count, root_node.num_siblings()); let was_i_last = display_data.is_last(count, root_node.num_siblings()); - display_node(c, stdout, &draw_data, is_biggest, was_i_last); + display_node(c, stdout, &draw_data, is_biggest, was_i_last, &mut state); } } } @@ -224,27 +236,44 @@ fn find_longest_dir_name( .fold(longest, max) } +fn recursive_child_count(node: &DisplayNode) -> i32 { + let mut total = 1; + for n in node.children.iter() { + total += recursive_child_count(&n); + } + return total; +} + fn display_node( node: &DisplayNode, stdout: &mut RawTerminal, draw_data: &DrawData, is_biggest: bool, is_last: bool, + state: &mut State, ) { // hacky way of working out how deep we are in the tree let indent = draw_data.get_new_indent(!node.children.is_empty(), is_last); let level = ((indent.chars().count() - 1) / 2) - 1; let bar_text = draw_data.generate_bar(node, level); + let cnt = if draw_data.display_data.initial.is_reversed { + recursive_child_count(node) + } else { + 0 + }; + let to_print = format_string( node, &indent, &bar_text, is_biggest, &draw_data.display_data, + state.test - cnt, ); if !draw_data.display_data.initial.is_reversed { + state.test -= 1; // works if reversed write!(stdout, "{to_print}").unwrap() } @@ -262,10 +291,15 @@ fn display_node( { let is_biggest = dd.display_data.is_biggest(count, num_siblings); let was_i_last = dd.display_data.is_last(count, num_siblings); - display_node(c, stdout, &dd, is_biggest, was_i_last); + + display_node(c, stdout, &dd, is_biggest, was_i_last, state); } if draw_data.display_data.initial.is_reversed { + // for (c) in node.get_children_from_node(draw_data.display_data.initial.is_reversed){ + // state.decrement(); + // } + state.test -= 1; write!(stdout, "{to_print}").unwrap() } } @@ -343,18 +377,21 @@ pub fn format_string( bars: &str, is_biggest: bool, display_data: &DisplayData, + test: i32, ) -> String { let (percent, name_and_padding) = get_name_percent(node, indent, bars, display_data); - let pretty_size = get_pretty_size(node, is_biggest, display_data); + let pretty_size = get_pretty_size(node, is_biggest, display_data, test); let pretty_name = get_pretty_name(node, name_and_padding, display_data); + let marked = get_name_if_marked(test, &pretty_name); + // we can clean this and the method below somehow, not sure yet if display_data.initial.is_screen_reader { // if screen_reader then bars is 'depth' - format!("{pretty_name} {bars} {pretty_size}{percent}") + format!("{marked} {bars} {pretty_size}{percent}") } else if display_data.initial.by_filetime.is_some() { - format!("{pretty_size} {indent}{pretty_name}") + format!("{pretty_size} {indent}{marked}") } else { - format!("{pretty_size} {indent} {pretty_name}{percent}") + format!("{pretty_size} {indent} {marked}{percent}") } } @@ -384,13 +421,19 @@ fn get_name_percent( } } -fn get_pretty_size(node: &DisplayNode, is_biggest: bool, display_data: &DisplayData) -> String { +fn get_pretty_size( + node: &DisplayNode, + is_biggest: bool, + display_data: &DisplayData, + n: i32, +) -> String { let output = if display_data.initial.by_filecount { node.size.separate_with_commas() } else if display_data.initial.by_filetime.is_some() { get_pretty_file_modified_time(node.size as i64) } else { - human_readable_number(node.size, &display_data.initial.output_format) + // human_readable_number(n, &display_data.initial.output_format) + format!("{n}") }; let spaces_to_add = display_data.num_chars_needed_on_left_most - output.chars().count(); let output = " ".repeat(spaces_to_add) + output.as_str(); @@ -410,6 +453,24 @@ fn get_pretty_file_modified_time(timestamp: i64) -> String { local_datetime.format("%Y-%m-%dT%H:%M:%S").to_string() } +fn get_name_if_marked(test: i32, name: &str) -> String { + if test == -9 { + let mut new_name = String::new(); + for c in name.chars() { + if c == ' ' { + new_name.push(BLOCKS[0]) + // new_name.push('x') + } else { + new_name.push(c) + } + } + new_name + } else { + name.into() + // format!("{name}{:?}", {state.test}) + } +} + fn get_pretty_name( node: &DisplayNode, name_and_padding: String, diff --git a/src/main.rs b/src/main.rs index 4f17d7fc..695b838e 100644 --- a/src/main.rs +++ b/src/main.rs @@ -336,13 +336,15 @@ fn main() { is_colors, terminal_width, &mut out, + -1, ); out.flush().unwrap(); + let mut state = 0; for c in stdin.events() { write!( out, - "{}{}Dust interactive (q to quit)", + "{}{}Dust interactive (q to quit) {state}", termion::clear::All, termion::cursor::Goto(1, 1) ) @@ -351,14 +353,22 @@ fn main() { let evt = c.unwrap(); match evt { Event::Key(Key::Char('q')) => break, - Event::Key(Key::Char(x)) => { - write!(out,"{x} key\n" ); + Event::Key(Key::Up | Key::Char('k')) => { + write!(out, "up\n").unwrap(); + state -= 1; + } + Event::Key(Key::Down | Key::Char('j')) => { + write!(out, "down\n").unwrap(); + state += 1; } - Event::Key(Key::Left) => { - write!(out,"left\n"); + Event::Key(Key::Left | Key::Char('h')) => { + write!(out, "left\n").unwrap(); } - Event::Key(Key::Right) => { - write!(out,"right\n"); + Event::Key(Key::Right | Key::Char('l')) => { + write!(out, "right\n").unwrap(); + } + Event::Key(Key::Char(x)) => { + write!(out, "{x} key\n").unwrap(); } _ => {} } @@ -370,6 +380,7 @@ fn main() { is_colors, terminal_width, &mut out, + state, ); out.flush().unwrap(); } @@ -383,6 +394,7 @@ fn print_output( is_colors: bool, terminal_width: usize, stdout: &mut RawTerminal, + selected_index: i32, ) { let output_format = config.get_output_format(&options); @@ -401,6 +413,7 @@ fn print_output( is_screen_reader: config.get_screen_reader(&options), output_format, bars_on_right: config.get_bars_on_right(&options), + selected_index: selected_index, }; draw_it( From d7fa260bba973bd0206a21356ea4939fcbc72fee Mon Sep 17 00:00:00 2001 From: "andy.boot" Date: Mon, 7 Jul 2025 23:11:17 +0100 Subject: [PATCH 6/6] hack --- src/display.rs | 68 +++++++++++++++++++++++++++++--------------------- src/main.rs | 18 ++++++++++--- 2 files changed, 55 insertions(+), 31 deletions(-) diff --git a/src/display.rs b/src/display.rs index cb924480..2b4c62fd 100644 --- a/src/display.rs +++ b/src/display.rs @@ -85,15 +85,6 @@ struct DrawData<'a> { display_data: &'a DisplayData, } -struct State { - test: i32, -} - -impl State { - fn decrement(&mut self) { - self.test -= 1; - } -} impl DrawData<'_> { fn get_new_indent(&self, has_children: bool, was_i_last: bool) -> String { @@ -158,8 +149,6 @@ pub fn draw_it( terminal_width > num_chars_needed_on_left_most + 2, "Not enough terminal width" ); - // write!(stdout, "{}{}Hello!", termion::clear::All, termion::cursor::Goto(1, 1)).unwrap(); - // write!(stdout, "{}", termion::cursor::Goto(2, 1)).unwrap(); let allowed_width = terminal_width - num_chars_needed_on_left_most - 2; let num_indent_chars = 3; @@ -186,10 +175,15 @@ pub fn draw_it( percent_bar: first_size_bar, display_data: &display_data, }; - let mut state = State { test: 0 }; + + let mut test = if display_data.initial.is_reversed { + recursive_child_count(root_node) + } else { + 0 + }; if !skip_total { - display_node(root_node, stdout, &draw_data, true, true, &mut state); + display_node(root_node, stdout, &draw_data, true, true, test); } else { for (count, c) in root_node .get_children_from_node(draw_data.display_data.initial.is_reversed) @@ -197,7 +191,13 @@ pub fn draw_it( { let is_biggest = display_data.is_biggest(count, root_node.num_siblings()); let was_i_last = display_data.is_last(count, root_node.num_siblings()); - display_node(c, stdout, &draw_data, is_biggest, was_i_last, &mut state); + display_node(c, stdout, &draw_data, is_biggest, was_i_last, test); + // not yet tested: + if display_data.initial.is_reversed { + test += recursive_child_count(c); + } else { + test += recursive_child_count(c); + } } } } @@ -236,7 +236,7 @@ fn find_longest_dir_name( .fold(longest, max) } -fn recursive_child_count(node: &DisplayNode) -> i32 { +pub fn recursive_child_count(node: &DisplayNode) -> i32 { let mut total = 1; for n in node.children.iter() { total += recursive_child_count(&n); @@ -250,7 +250,7 @@ fn display_node( draw_data: &DrawData, is_biggest: bool, is_last: bool, - state: &mut State, + test: i32, ) { // hacky way of working out how deep we are in the tree let indent = draw_data.get_new_indent(!node.children.is_empty(), is_last); @@ -269,11 +269,12 @@ fn display_node( &bar_text, is_biggest, &draw_data.display_data, - state.test - cnt, + test - cnt, ); + let mut tt = test; if !draw_data.display_data.initial.is_reversed { - state.test -= 1; // works if reversed + tt += 1; write!(stdout, "{to_print}").unwrap() } @@ -292,14 +293,15 @@ fn display_node( let is_biggest = dd.display_data.is_biggest(count, num_siblings); let was_i_last = dd.display_data.is_last(count, num_siblings); - display_node(c, stdout, &dd, is_biggest, was_i_last, state); + display_node(c, stdout, &dd, is_biggest, was_i_last, tt); + if draw_data.display_data.initial.is_reversed { + tt -= recursive_child_count(c) + } else { + tt += recursive_child_count(c) + } } if draw_data.display_data.initial.is_reversed { - // for (c) in node.get_children_from_node(draw_data.display_data.initial.is_reversed){ - // state.decrement(); - // } - state.test -= 1; write!(stdout, "{to_print}").unwrap() } } @@ -382,7 +384,8 @@ pub fn format_string( let (percent, name_and_padding) = get_name_percent(node, indent, bars, display_data); let pretty_size = get_pretty_size(node, is_biggest, display_data, test); let pretty_name = get_pretty_name(node, name_and_padding, display_data); - let marked = get_name_if_marked(test, &pretty_name); + let marked = get_name_if_marked(test==display_data.initial.selected_index, pretty_name); + let indent = get_indent_if_marked(test==display_data.initial.selected_index, indent); // we can clean this and the method below somehow, not sure yet if display_data.initial.is_screen_reader { @@ -453,13 +456,23 @@ fn get_pretty_file_modified_time(timestamp: i64) -> String { local_datetime.format("%Y-%m-%dT%H:%M:%S").to_string() } -fn get_name_if_marked(test: i32, name: &str) -> String { - if test == -9 { +fn get_indent_if_marked(test: bool, indent: &str) -> String { + if test { + let mut new_name = String::new(); + for _ in indent.chars() { + new_name.push(BLOCKS[0]) + } + new_name + } else { + indent.into() + } +} +fn get_name_if_marked(test: bool, name: String) -> String { + if test { let mut new_name = String::new(); for c in name.chars() { if c == ' ' { new_name.push(BLOCKS[0]) - // new_name.push('x') } else { new_name.push(c) } @@ -467,7 +480,6 @@ fn get_name_if_marked(test: i32, name: &str) -> String { new_name } else { name.into() - // format!("{name}{:?}", {state.test}) } } diff --git a/src/main.rs b/src/main.rs index 695b838e..24bb3639 100644 --- a/src/main.rs +++ b/src/main.rs @@ -12,6 +12,7 @@ mod utils; use crate::cli::Cli; use crate::config::Config; +use crate::display::recursive_child_count; use crate::display_node::DisplayNode; use crate::progress::RuntimeErrors; use clap::Parser; @@ -20,6 +21,7 @@ use display::InitialDisplayData; use filter::AggregateData; use progress::PIndicator; use regex::Error; +use std::cmp::min; use std::collections::HashSet; use std::env; use std::fs::read_to_string; @@ -336,7 +338,7 @@ fn main() { is_colors, terminal_width, &mut out, - -1, + 0, ); out.flush().unwrap(); @@ -355,11 +357,19 @@ fn main() { Event::Key(Key::Char('q')) => break, Event::Key(Key::Up | Key::Char('k')) => { write!(out, "up\n").unwrap(); - state -= 1; + if !config.get_reverse(&options){ + state += 1; + } else { + state -= 1; + } } Event::Key(Key::Down | Key::Char('j')) => { write!(out, "down\n").unwrap(); - state += 1; + if !config.get_reverse(&options){ + state -= 1; + } else { + state += 1; + } } Event::Key(Key::Left | Key::Char('h')) => { write!(out, "left\n").unwrap(); @@ -372,6 +382,8 @@ fn main() { } _ => {} } + state = max(0, state); + state = min(recursive_child_count(&tree)-1, state); write!(out, "{}", termion::cursor::Goto(1, 3)).unwrap(); print_output( &config,