Skip to content

Commit 5bc5c3f

Browse files
committed
color files with lscolors
1 parent e8015eb commit 5bc5c3f

5 files changed

Lines changed: 90 additions & 4 deletions

File tree

Cargo.lock

Lines changed: 10 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ time = "0.1.40"
2828
users = "0.8.0"
2929
chrono-humanize = "0.0.11"
3030
unicode-width = "0.1.5"
31+
lscolors = "0.5.0"
3132

3233
[dependencies.clap]
3334
features = ["suggestions", "color", "wrap_help"]

src/color.rs

Lines changed: 72 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
use ansi_term::{ANSIString, Colour, Style};
2+
use lscolors::{Indicator, LsColors};
23
use std::collections::HashMap;
34

45
#[allow(dead_code)]
@@ -62,6 +63,7 @@ pub enum Theme {
6263

6364
pub struct Colors {
6465
colors: Option<HashMap<Elem, Colour>>,
66+
lscolors: Option<LsColors>,
6567
}
6668

6769
impl Colors {
@@ -70,15 +72,55 @@ impl Colors {
7072
Theme::NoColor => None,
7173
Theme::Default => Some(Self::get_light_theme_colour_map()),
7274
};
75+
let lscolors = LsColors::from_env();
7376

74-
Self { colors }
77+
Self { colors, lscolors }
7578
}
7679

7780
pub fn colorize<'a>(&self, input: String, elem: &Elem) -> ColoredString<'a> {
7881
self.style(elem).paint(input)
7982
}
8083

84+
pub fn colorize_using_path<'a>(
85+
&self,
86+
input: String,
87+
path: &str,
88+
elem: &Elem,
89+
) -> ColoredString<'a> {
90+
let style_from_path = self.style_from_path(path);
91+
match style_from_path {
92+
Some(style_from_path) => style_from_path.paint(input),
93+
None => self.colorize(input, elem),
94+
}
95+
}
96+
97+
fn style_from_path(&self, path: &str) -> Option<Style> {
98+
match &self.lscolors {
99+
Some(lscolors) => lscolors
100+
.style_for_path(path)
101+
.map(lscolors::Style::to_ansi_term_style),
102+
None => None,
103+
}
104+
}
105+
81106
fn style(&self, elem: &Elem) -> Style {
107+
match &self.lscolors {
108+
Some(lscolors) => {
109+
match self.get_indicator_from_elem(elem) {
110+
Some(style) => {
111+
let style = lscolors.style_for_indicator(style);
112+
style
113+
.map(lscolors::Style::to_ansi_term_style)
114+
.unwrap_or_default()
115+
}
116+
None => self.style_default(elem),
117+
}
118+
}
119+
None => self.style_default(elem),
120+
}
121+
}
122+
123+
fn style_default(&self, elem: &Elem) -> Style {
82124
if let Some(ref colors) = self.colors {
83125
let style_fg = Style::default().fg(colors[elem]);
84126
if elem.has_suid() {
@@ -91,6 +133,35 @@ impl Colors {
91133
}
92134
}
93135

136+
fn get_indicator_from_elem(&self, elem: &Elem) -> Option<Indicator> {
137+
let indicator_string = match elem {
138+
Elem::File { exec, uid } => match (exec, uid) {
139+
(_, true) => None,
140+
(true, false) => Some("ex"),
141+
(false, false) => Some("fi"),
142+
},
143+
Elem::Dir { uid } => {
144+
if *uid {
145+
None
146+
} else {
147+
Some("di")
148+
}
149+
}
150+
Elem::SymLink => Some("ln"),
151+
Elem::Pipe => Some("pi"),
152+
Elem::Socket => Some("so"),
153+
Elem::BlockDevice => Some("bd"),
154+
Elem::CharDevice => Some("cd"),
155+
Elem::BrokenSymLink => Some("or"),
156+
_ => None,
157+
};
158+
159+
match indicator_string {
160+
Some(ids) => Indicator::from(ids),
161+
None => None,
162+
}
163+
}
164+
94165
// You can find the table for each color, code, and display at:
95166
//
96167
//https://jonasjacek.github.io/colors/

src/main.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ extern crate clap;
1010
extern crate ansi_term;
1111
extern crate chrono_humanize;
1212
extern crate libc;
13+
extern crate lscolors;
1314
#[cfg(test)]
1415
extern crate tempdir;
1516
extern crate term_grid;

src/meta/name.rs

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ use std::path::Path;
77
#[derive(Debug, Eq)]
88
pub struct Name {
99
name: String,
10+
path: String,
1011
extension: Option<String>,
1112
file_type: FileType,
1213
}
@@ -27,8 +28,11 @@ impl Name {
2728
);
2829
}
2930

31+
let path_string = path.to_string_lossy().to_string();
32+
3033
Self {
3134
name,
35+
path: path_string,
3236
extension,
3337
file_type,
3438
}
@@ -39,6 +43,7 @@ impl Name {
3943
let mut content = String::with_capacity(icon.len() + self.name.len() + 3 /* spaces */);
4044

4145
content += icon.as_str();
46+
content += &self.name;
4247

4348
let elem = match self.file_type {
4449
FileType::CharDevice => Elem::CharDevice,
@@ -51,9 +56,7 @@ impl Name {
5156
},
5257
};
5358

54-
content += &self.name;
55-
56-
colors.colorize(content, &elem)
59+
colors.colorize_using_path(content, &self.path, &elem)
5760
}
5861

5962
pub fn name(&self) -> String {

0 commit comments

Comments
 (0)