mirror of
https://github.com/Llewellynvdm/exa.git
synced 2024-12-25 17:51:10 +00:00
Measure, rather than calculating, cell widths
exa deals with cells and widths a lot: the items in a grid need to be aligned according to their *contents’* widths, rather than the length of their strings, which often included ANSI escape characters. As an optimisation, it used to calculate this separately based on the filename, and dealing with any extra characters (such as the classify ones) in that function too. Recently, though, file names have become a lot more complicated. Classification added zero to one extra characters, and now with escaped control characters in file names, it’s not so easy to calculate the display width of a filename. This commit removes the function that calculated the width, in favour of building the output string (it’s going to be displayed anyway) and just getting the width of what it displays instead.
This commit is contained in:
parent
28fce347ff
commit
a53c268c54
@ -5,8 +5,6 @@ use std::ops::{Add, Deref, DerefMut};
|
||||
use ansi_term::{Style, ANSIString, ANSIStrings};
|
||||
use unicode_width::UnicodeWidthStr;
|
||||
|
||||
use fs::File;
|
||||
|
||||
|
||||
/// An individual cell that holds text in a table, used in the details and
|
||||
/// lines views to store ANSI-terminal-formatted data before it is printed.
|
||||
@ -161,6 +159,11 @@ impl TextCellContents {
|
||||
pub fn strings(&self) -> ANSIStrings {
|
||||
ANSIStrings(&self.0)
|
||||
}
|
||||
|
||||
pub fn width(&self) -> DisplayWidth {
|
||||
let foo = self.0.iter().map(|anstr| anstr.chars().count()).sum();
|
||||
DisplayWidth(foo)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -180,19 +183,6 @@ impl TextCellContents {
|
||||
#[derive(PartialEq, Debug, Clone, Copy, Default)]
|
||||
pub struct DisplayWidth(usize);
|
||||
|
||||
impl DisplayWidth {
|
||||
pub fn from_file(file: &File, classify: bool) -> DisplayWidth {
|
||||
let name_width = *DisplayWidth::from(&*file.name);
|
||||
if classify {
|
||||
if file.is_executable_file() || file.is_directory() ||
|
||||
file.is_pipe() || file.is_link() || file.is_socket() {
|
||||
return DisplayWidth(name_width + 1);
|
||||
}
|
||||
}
|
||||
DisplayWidth(name_width)
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> From<&'a str> for DisplayWidth {
|
||||
fn from(input: &'a str) -> DisplayWidth {
|
||||
DisplayWidth(UnicodeWidthStr::width(input))
|
||||
|
@ -306,7 +306,9 @@ impl Details {
|
||||
for (index, egg) in file_eggs.into_iter().enumerate() {
|
||||
let mut files = Vec::new();
|
||||
let mut errors = egg.errors;
|
||||
let mut width = DisplayWidth::from_file(&egg.file, self.classify);
|
||||
|
||||
let filename = filename(&egg.file, &self.colours, true, self.classify);
|
||||
let mut width = filename.width();
|
||||
|
||||
if egg.file.dir.is_none() {
|
||||
if let Some(parent) = egg.file.path.parent() {
|
||||
@ -315,7 +317,7 @@ impl Details {
|
||||
}
|
||||
|
||||
let name = TextCell {
|
||||
contents: filename(&egg.file, &self.colours, true, self.classify),
|
||||
contents: filename,
|
||||
width: width,
|
||||
};
|
||||
|
||||
@ -456,7 +458,8 @@ impl<'a, U: Users+Groups+'a> Table<'a, U> {
|
||||
}
|
||||
|
||||
pub fn filename_cell(&self, file: File, links: bool) -> TextCell {
|
||||
let mut width = DisplayWidth::from_file(&file, self.opts.classify);
|
||||
let filename = filename(&file, &self.opts.colours, links, self.opts.classify);
|
||||
let mut width = filename.width();
|
||||
|
||||
if file.dir.is_none() {
|
||||
if let Some(parent) = file.path.parent() {
|
||||
@ -465,7 +468,7 @@ impl<'a, U: Users+Groups+'a> Table<'a, U> {
|
||||
}
|
||||
|
||||
TextCell {
|
||||
contents: filename(&file, &self.opts.colours, links, self.opts.classify),
|
||||
contents: filename,
|
||||
width: width,
|
||||
}
|
||||
}
|
||||
|
@ -29,8 +29,9 @@ impl Grid {
|
||||
grid.reserve(files.len());
|
||||
|
||||
for file in files.iter() {
|
||||
let mut width = DisplayWidth::from_file(file, self.classify);
|
||||
let filename = filename(file, &self.colours, false, self.classify);
|
||||
|
||||
let mut width = filename.width();
|
||||
if file.dir.is_none() {
|
||||
if let Some(parent) = file.path.parent() {
|
||||
width = width + 1 + DisplayWidth::from(parent.to_string_lossy().as_ref());
|
||||
@ -38,7 +39,7 @@ impl Grid {
|
||||
}
|
||||
|
||||
grid.add(grid::Cell {
|
||||
contents: filename(file, &self.colours, false, self.classify).strings().to_string(),
|
||||
contents: filename.strings().to_string(),
|
||||
width: *width,
|
||||
});
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user