mirror of
https://github.com/Llewellynvdm/exa.git
synced 2024-11-26 05:47:32 +00:00
parent
b235b64060
commit
8d6f62840a
9
Cargo.lock
generated
9
Cargo.lock
generated
@ -13,6 +13,7 @@ dependencies = [
|
|||||||
"num_cpus 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)",
|
"num_cpus 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"number_prefix 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
"number_prefix 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"pad 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
"pad 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"term_grid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"threadpool 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
"threadpool 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"unicode-width 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
"unicode-width 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"users 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)",
|
"users 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
@ -259,6 +260,14 @@ dependencies = [
|
|||||||
"rand 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
|
"rand 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "term_grid"
|
||||||
|
version = "0.1.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
dependencies = [
|
||||||
|
"unicode-width 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "threadpool"
|
name = "threadpool"
|
||||||
version = "0.1.4"
|
version = "0.1.4"
|
||||||
|
@ -17,6 +17,7 @@ natord = "1.0.7"
|
|||||||
num_cpus = "*"
|
num_cpus = "*"
|
||||||
number_prefix = "0.2.3"
|
number_prefix = "0.2.3"
|
||||||
pad = "0.1.1"
|
pad = "0.1.1"
|
||||||
|
term_grid = "*"
|
||||||
threadpool = "*"
|
threadpool = "*"
|
||||||
unicode-width = "*"
|
unicode-width = "*"
|
||||||
users = "0.4.0"
|
users = "0.4.0"
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
#![feature(convert, fs_mode)]
|
#![feature(convert, fs_mode)]
|
||||||
#![feature(slice_extras, iter_arith, vec_resize)]
|
#![feature(slice_extras, vec_resize)]
|
||||||
|
|
||||||
extern crate ansi_term;
|
extern crate ansi_term;
|
||||||
extern crate datetime;
|
extern crate datetime;
|
||||||
@ -10,6 +10,7 @@ extern crate natord;
|
|||||||
extern crate num_cpus;
|
extern crate num_cpus;
|
||||||
extern crate number_prefix;
|
extern crate number_prefix;
|
||||||
extern crate pad;
|
extern crate pad;
|
||||||
|
extern crate term_grid;
|
||||||
extern crate threadpool;
|
extern crate threadpool;
|
||||||
extern crate unicode_width;
|
extern crate unicode_width;
|
||||||
extern crate users;
|
extern crate users;
|
||||||
|
@ -1,12 +1,8 @@
|
|||||||
use std::cmp::max;
|
|
||||||
use std::iter::repeat;
|
|
||||||
|
|
||||||
use colours::Colours;
|
use colours::Colours;
|
||||||
use column::Alignment::Left;
|
|
||||||
use file::File;
|
use file::File;
|
||||||
use filetype::file_colour;
|
use filetype::file_colour;
|
||||||
|
|
||||||
use super::lines::Lines;
|
use term_grid as grid;
|
||||||
|
|
||||||
|
|
||||||
#[derive(PartialEq, Debug, Copy, Clone)]
|
#[derive(PartialEq, Debug, Copy, Clone)]
|
||||||
@ -17,91 +13,32 @@ pub struct Grid {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Grid {
|
impl Grid {
|
||||||
fn fit_into_grid(&self, files: &[File]) -> Option<(usize, Vec<usize>)> {
|
|
||||||
// TODO: this function could almost certainly be optimised...
|
|
||||||
// surely not *all* of the numbers of lines are worth searching through!
|
|
||||||
|
|
||||||
// Instead of numbers of columns, try to find the fewest number of *lines*
|
|
||||||
// that the output will fit in.
|
|
||||||
for num_lines in 1 .. files.len() {
|
|
||||||
|
|
||||||
// The number of columns is the number of files divided by the number
|
|
||||||
// of lines, *rounded up*.
|
|
||||||
let mut num_columns = files.len() / num_lines;
|
|
||||||
if files.len() % num_lines != 0 {
|
|
||||||
num_columns += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Early abort: if there are so many columns that the width of the
|
|
||||||
// *column separators* is bigger than the width of the screen, then
|
|
||||||
// don't even try to tabulate it.
|
|
||||||
// This is actually a necessary check, because the width is stored as
|
|
||||||
// a usize, and making it go negative makes it huge instead, but it
|
|
||||||
// also serves as a speed-up.
|
|
||||||
let separator_width = (num_columns - 1) * 2;
|
|
||||||
if self.console_width < separator_width {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Remove the separator width from the available space.
|
|
||||||
let adjusted_width = self.console_width - separator_width;
|
|
||||||
|
|
||||||
// Find the width of each column by adding the lengths of the file
|
|
||||||
// names in that column up.
|
|
||||||
let mut column_widths: Vec<usize> = repeat(0).take(num_columns).collect();
|
|
||||||
for (index, file) in files.iter().enumerate() {
|
|
||||||
let index = if self.across {
|
|
||||||
index % num_columns
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
index / num_lines
|
|
||||||
};
|
|
||||||
column_widths[index] = max(column_widths[index], file.file_name_width());
|
|
||||||
}
|
|
||||||
|
|
||||||
// If they all fit in the terminal, combined, then success!
|
|
||||||
if column_widths.iter().map(|&x| x).sum::<usize>() < adjusted_width {
|
|
||||||
return Some((num_lines, column_widths));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// If you get here you have really long file names.
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn view(&self, files: &[File]) {
|
pub fn view(&self, files: &[File]) {
|
||||||
if let Some((num_lines, widths)) = self.fit_into_grid(files) {
|
let direction = if self.across { grid::Direction::LeftToRight }
|
||||||
for y in 0 .. num_lines {
|
else { grid::Direction::TopToBottom };
|
||||||
for x in 0 .. widths.len() {
|
|
||||||
let num = if self.across {
|
|
||||||
y * widths.len() + x
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
y + num_lines * x
|
|
||||||
};
|
|
||||||
|
|
||||||
// Show whitespace in the place of trailing files
|
let mut grid = grid::Grid::new(grid::GridOptions {
|
||||||
if num >= files.len() {
|
direction: direction,
|
||||||
continue;
|
separator_width: 2,
|
||||||
|
});
|
||||||
|
|
||||||
|
grid.reserve(files.len());
|
||||||
|
|
||||||
|
for file in files.iter() {
|
||||||
|
grid.add(grid::Cell {
|
||||||
|
contents: file_colour(&self.colours, file).paint(&file.name).to_string(),
|
||||||
|
width: file.file_name_width(),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
let ref file = files[num];
|
if let Some(display) = grid.fit_into_width(self.console_width) {
|
||||||
let styled_name = file_colour(&self.colours, file).paint(&file.name).to_string();
|
print!("{}", display);
|
||||||
if x == widths.len() - 1 {
|
|
||||||
// The final column doesn't need to have trailing spaces
|
|
||||||
print!("{}", styled_name);
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
assert!(widths[x] >= file.file_name_width());
|
// File names too long for a grid - drop down to just listing them!
|
||||||
print!("{}", Left.pad_string(&styled_name, widths[x] - file.file_name_width() + 2));
|
for file in files.iter() {
|
||||||
|
println!("{}", file_colour(&self.colours, file).paint(&file.name));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
print!("\n");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
// Drop down to lines view if the file names are too big for a grid
|
|
||||||
Lines { colours: self.colours }.view(files);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user