mirror of
https://github.com/nushell/nushell.git
synced 2025-04-23 20:58:19 +02:00
Add minor theme support (#2449)
* WIP - compiling but not working * semi-working * making progress * working except for table lines * fmt + clippy * cleaned up some comments * working line colors * fmt, clippy, updated sample config.toml * removed extra comments
This commit is contained in:
parent
860c2a606d
commit
adbbcafd30
@ -1,5 +1,6 @@
|
|||||||
use crate::commands::WholeStreamCommand;
|
use crate::commands::WholeStreamCommand;
|
||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
|
use ansi_term::Color;
|
||||||
use nu_errors::ShellError;
|
use nu_errors::ShellError;
|
||||||
use nu_protocol::{ReturnSuccess, Signature, SyntaxShape, UntaggedValue, Value};
|
use nu_protocol::{ReturnSuccess, Signature, SyntaxShape, UntaggedValue, Value};
|
||||||
|
|
||||||
@ -76,60 +77,56 @@ impl WholeStreamCommand for Ansi {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn str_to_ansi_color(s: String) -> Option<String> {
|
pub fn str_to_ansi_color(s: String) -> Option<String> {
|
||||||
match s.as_str() {
|
match s.as_str() {
|
||||||
"g" | "green" => Some(ansi_term::Color::Green.prefix().to_string()),
|
"g" | "green" => Some(Color::Green.prefix().to_string()),
|
||||||
"gb" | "green_bold" => Some(ansi_term::Color::Green.bold().prefix().to_string()),
|
"gb" | "green_bold" => Some(Color::Green.bold().prefix().to_string()),
|
||||||
"gu" | "green_underline" => Some(ansi_term::Color::Green.underline().prefix().to_string()),
|
"gu" | "green_underline" => Some(Color::Green.underline().prefix().to_string()),
|
||||||
"gi" | "green_italic" => Some(ansi_term::Color::Green.italic().prefix().to_string()),
|
"gi" | "green_italic" => Some(Color::Green.italic().prefix().to_string()),
|
||||||
"gd" | "green_dimmed" => Some(ansi_term::Color::Green.dimmed().prefix().to_string()),
|
"gd" | "green_dimmed" => Some(Color::Green.dimmed().prefix().to_string()),
|
||||||
"gr" | "green_reverse" => Some(ansi_term::Color::Green.reverse().prefix().to_string()),
|
"gr" | "green_reverse" => Some(Color::Green.reverse().prefix().to_string()),
|
||||||
"r" | "red" => Some(ansi_term::Color::Red.prefix().to_string()),
|
"r" | "red" => Some(Color::Red.prefix().to_string()),
|
||||||
"rb" | "red_bold" => Some(ansi_term::Color::Red.bold().prefix().to_string()),
|
"rb" | "red_bold" => Some(Color::Red.bold().prefix().to_string()),
|
||||||
"ru" | "red_underline" => Some(ansi_term::Color::Red.underline().prefix().to_string()),
|
"ru" | "red_underline" => Some(Color::Red.underline().prefix().to_string()),
|
||||||
"ri" | "red_italic" => Some(ansi_term::Color::Red.italic().prefix().to_string()),
|
"ri" | "red_italic" => Some(Color::Red.italic().prefix().to_string()),
|
||||||
"rd" | "red_dimmed" => Some(ansi_term::Color::Red.dimmed().prefix().to_string()),
|
"rd" | "red_dimmed" => Some(Color::Red.dimmed().prefix().to_string()),
|
||||||
"rr" | "red_reverse" => Some(ansi_term::Color::Red.reverse().prefix().to_string()),
|
"rr" | "red_reverse" => Some(Color::Red.reverse().prefix().to_string()),
|
||||||
"u" | "blue" => Some(ansi_term::Color::Blue.prefix().to_string()),
|
"u" | "blue" => Some(Color::Blue.prefix().to_string()),
|
||||||
"ub" | "blue_bold" => Some(ansi_term::Color::Blue.bold().prefix().to_string()),
|
"ub" | "blue_bold" => Some(Color::Blue.bold().prefix().to_string()),
|
||||||
"uu" | "blue_underline" => Some(ansi_term::Color::Blue.underline().prefix().to_string()),
|
"uu" | "blue_underline" => Some(Color::Blue.underline().prefix().to_string()),
|
||||||
"ui" | "blue_italic" => Some(ansi_term::Color::Blue.italic().prefix().to_string()),
|
"ui" | "blue_italic" => Some(Color::Blue.italic().prefix().to_string()),
|
||||||
"ud" | "blue_dimmed" => Some(ansi_term::Color::Blue.dimmed().prefix().to_string()),
|
"ud" | "blue_dimmed" => Some(Color::Blue.dimmed().prefix().to_string()),
|
||||||
"ur" | "blue_reverse" => Some(ansi_term::Color::Blue.reverse().prefix().to_string()),
|
"ur" | "blue_reverse" => Some(Color::Blue.reverse().prefix().to_string()),
|
||||||
"b" | "black" => Some(ansi_term::Color::Black.prefix().to_string()),
|
"b" | "black" => Some(Color::Black.prefix().to_string()),
|
||||||
"bb" | "black_bold" => Some(ansi_term::Color::Black.bold().prefix().to_string()),
|
"bb" | "black_bold" => Some(Color::Black.bold().prefix().to_string()),
|
||||||
"bu" | "black_underline" => Some(ansi_term::Color::Black.underline().prefix().to_string()),
|
"bu" | "black_underline" => Some(Color::Black.underline().prefix().to_string()),
|
||||||
"bi" | "black_italic" => Some(ansi_term::Color::Black.italic().prefix().to_string()),
|
"bi" | "black_italic" => Some(Color::Black.italic().prefix().to_string()),
|
||||||
"bd" | "black_dimmed" => Some(ansi_term::Color::Black.dimmed().prefix().to_string()),
|
"bd" | "black_dimmed" => Some(Color::Black.dimmed().prefix().to_string()),
|
||||||
"br" | "black_reverse" => Some(ansi_term::Color::Black.reverse().prefix().to_string()),
|
"br" | "black_reverse" => Some(Color::Black.reverse().prefix().to_string()),
|
||||||
"y" | "yellow" => Some(ansi_term::Color::Yellow.prefix().to_string()),
|
"y" | "yellow" => Some(Color::Yellow.prefix().to_string()),
|
||||||
"yb" | "yellow_bold" => Some(ansi_term::Color::Yellow.bold().prefix().to_string()),
|
"yb" | "yellow_bold" => Some(Color::Yellow.bold().prefix().to_string()),
|
||||||
"yu" | "yellow_underline" => {
|
"yu" | "yellow_underline" => Some(Color::Yellow.underline().prefix().to_string()),
|
||||||
Some(ansi_term::Color::Yellow.underline().prefix().to_string())
|
"yi" | "yellow_italic" => Some(Color::Yellow.italic().prefix().to_string()),
|
||||||
}
|
"yd" | "yellow_dimmed" => Some(Color::Yellow.dimmed().prefix().to_string()),
|
||||||
"yi" | "yellow_italic" => Some(ansi_term::Color::Yellow.italic().prefix().to_string()),
|
"yr" | "yellow_reverse" => Some(Color::Yellow.reverse().prefix().to_string()),
|
||||||
"yd" | "yellow_dimmed" => Some(ansi_term::Color::Yellow.dimmed().prefix().to_string()),
|
"p" | "purple" => Some(Color::Purple.prefix().to_string()),
|
||||||
"yr" | "yellow_reverse" => Some(ansi_term::Color::Yellow.reverse().prefix().to_string()),
|
"pb" | "purple_bold" => Some(Color::Purple.bold().prefix().to_string()),
|
||||||
"p" | "purple" => Some(ansi_term::Color::Purple.prefix().to_string()),
|
"pu" | "purple_underline" => Some(Color::Purple.underline().prefix().to_string()),
|
||||||
"pb" | "purple_bold" => Some(ansi_term::Color::Purple.bold().prefix().to_string()),
|
"pi" | "purple_italic" => Some(Color::Purple.italic().prefix().to_string()),
|
||||||
"pu" | "purple_underline" => {
|
"pd" | "purple_dimmed" => Some(Color::Purple.dimmed().prefix().to_string()),
|
||||||
Some(ansi_term::Color::Purple.underline().prefix().to_string())
|
"pr" | "purple_reverse" => Some(Color::Purple.reverse().prefix().to_string()),
|
||||||
}
|
"c" | "cyan" => Some(Color::Cyan.prefix().to_string()),
|
||||||
"pi" | "purple_italic" => Some(ansi_term::Color::Purple.italic().prefix().to_string()),
|
"cb" | "cyan_bold" => Some(Color::Cyan.bold().prefix().to_string()),
|
||||||
"pd" | "purple_dimmed" => Some(ansi_term::Color::Purple.dimmed().prefix().to_string()),
|
"cu" | "cyan_underline" => Some(Color::Cyan.underline().prefix().to_string()),
|
||||||
"pr" | "purple_reverse" => Some(ansi_term::Color::Purple.reverse().prefix().to_string()),
|
"ci" | "cyan_italic" => Some(Color::Cyan.italic().prefix().to_string()),
|
||||||
"c" | "cyan" => Some(ansi_term::Color::Cyan.prefix().to_string()),
|
"cd" | "cyan_dimmed" => Some(Color::Cyan.dimmed().prefix().to_string()),
|
||||||
"cb" | "cyan_bold" => Some(ansi_term::Color::Cyan.bold().prefix().to_string()),
|
"cr" | "cyan_reverse" => Some(Color::Cyan.reverse().prefix().to_string()),
|
||||||
"cu" | "cyan_underline" => Some(ansi_term::Color::Cyan.underline().prefix().to_string()),
|
"w" | "white" => Some(Color::White.prefix().to_string()),
|
||||||
"ci" | "cyan_italic" => Some(ansi_term::Color::Cyan.italic().prefix().to_string()),
|
"wb" | "white_bold" => Some(Color::White.bold().prefix().to_string()),
|
||||||
"cd" | "cyan_dimmed" => Some(ansi_term::Color::Cyan.dimmed().prefix().to_string()),
|
"wu" | "white_underline" => Some(Color::White.underline().prefix().to_string()),
|
||||||
"cr" | "cyan_reverse" => Some(ansi_term::Color::Cyan.reverse().prefix().to_string()),
|
"wi" | "white_italic" => Some(Color::White.italic().prefix().to_string()),
|
||||||
"w" | "white" => Some(ansi_term::Color::White.prefix().to_string()),
|
"wd" | "white_dimmed" => Some(Color::White.dimmed().prefix().to_string()),
|
||||||
"wb" | "white_bold" => Some(ansi_term::Color::White.bold().prefix().to_string()),
|
"wr" | "white_reverse" => Some(Color::White.reverse().prefix().to_string()),
|
||||||
"wu" | "white_underline" => Some(ansi_term::Color::White.underline().prefix().to_string()),
|
|
||||||
"wi" | "white_italic" => Some(ansi_term::Color::White.italic().prefix().to_string()),
|
|
||||||
"wd" | "white_dimmed" => Some(ansi_term::Color::White.dimmed().prefix().to_string()),
|
|
||||||
"wr" | "white_reverse" => Some(ansi_term::Color::White.reverse().prefix().to_string()),
|
|
||||||
"reset" => Some("\x1b[0m".to_owned()),
|
"reset" => Some("\x1b[0m".to_owned()),
|
||||||
_ => None,
|
_ => None,
|
||||||
}
|
}
|
||||||
|
@ -1,10 +1,12 @@
|
|||||||
use crate::commands::autoview::options::{ConfigExtensions, NuConfig as AutoViewConfiguration};
|
use crate::commands::autoview::options::{ConfigExtensions, NuConfig as AutoViewConfiguration};
|
||||||
use crate::commands::{UnevaluatedCallInfo, WholeStreamCommand};
|
use crate::commands::{UnevaluatedCallInfo, WholeStreamCommand};
|
||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
|
use crate::primitive::get_color_config;
|
||||||
use nu_data::value::format_leaf;
|
use nu_data::value::format_leaf;
|
||||||
use nu_errors::ShellError;
|
use nu_errors::ShellError;
|
||||||
use nu_protocol::hir::{self, Expression, ExternalRedirection, Literal, SpannedExpression};
|
use nu_protocol::hir::{self, Expression, ExternalRedirection, Literal, SpannedExpression};
|
||||||
use nu_protocol::{Primitive, Scope, Signature, UntaggedValue, Value};
|
use nu_protocol::{Primitive, Scope, Signature, UntaggedValue, Value};
|
||||||
|
use nu_table::TextStyle;
|
||||||
use parking_lot::Mutex;
|
use parking_lot::Mutex;
|
||||||
use std::sync::atomic::AtomicBool;
|
use std::sync::atomic::AtomicBool;
|
||||||
|
|
||||||
@ -92,6 +94,7 @@ pub async fn autoview(context: RunnableContext) -> Result<OutputStream, ShellErr
|
|||||||
|
|
||||||
let (mut input_stream, context) = RunnableContextWithoutInput::convert(context);
|
let (mut input_stream, context) = RunnableContextWithoutInput::convert(context);
|
||||||
let term_width = context.host.lock().width();
|
let term_width = context.host.lock().width();
|
||||||
|
let color_hm = get_color_config();
|
||||||
|
|
||||||
if let Some(x) = input_stream.next().await {
|
if let Some(x) = input_stream.next().await {
|
||||||
match input_stream.next().await {
|
match input_stream.next().await {
|
||||||
@ -256,11 +259,10 @@ pub async fn autoview(context: RunnableContext) -> Result<OutputStream, ShellErr
|
|||||||
entries.push(vec![
|
entries.push(vec![
|
||||||
nu_table::StyledString::new(
|
nu_table::StyledString::new(
|
||||||
key.to_string(),
|
key.to_string(),
|
||||||
nu_table::TextStyle {
|
TextStyle::new()
|
||||||
alignment: nu_table::Alignment::Left,
|
.alignment(nu_table::Alignment::Left)
|
||||||
color: Some(ansi_term::Color::Green),
|
.fg(ansi_term::Color::Green)
|
||||||
is_bold: true,
|
.bold(Some(true)),
|
||||||
},
|
|
||||||
),
|
),
|
||||||
nu_table::StyledString::new(
|
nu_table::StyledString::new(
|
||||||
format_leaf(value).plain_string(100_000),
|
format_leaf(value).plain_string(100_000),
|
||||||
@ -272,7 +274,7 @@ pub async fn autoview(context: RunnableContext) -> Result<OutputStream, ShellErr
|
|||||||
let table =
|
let table =
|
||||||
nu_table::Table::new(vec![], entries, nu_table::Theme::compact());
|
nu_table::Table::new(vec![], entries, nu_table::Theme::compact());
|
||||||
|
|
||||||
nu_table::draw_table(&table, term_width);
|
nu_table::draw_table(&table, term_width, &color_hm);
|
||||||
}
|
}
|
||||||
|
|
||||||
Value {
|
Value {
|
||||||
|
@ -1,10 +1,12 @@
|
|||||||
use crate::commands::table::options::{ConfigExtensions, NuConfig as TableConfiguration};
|
use crate::commands::table::options::{ConfigExtensions, NuConfig as TableConfiguration};
|
||||||
use crate::commands::WholeStreamCommand;
|
use crate::commands::WholeStreamCommand;
|
||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
|
use crate::primitive::get_color_config;
|
||||||
use nu_data::value::{format_leaf, style_leaf};
|
use nu_data::value::{format_leaf, style_leaf};
|
||||||
use nu_errors::ShellError;
|
use nu_errors::ShellError;
|
||||||
use nu_protocol::{Primitive, Signature, SyntaxShape, UntaggedValue, Value};
|
use nu_protocol::{Primitive, Signature, SyntaxShape, UntaggedValue, Value};
|
||||||
use nu_table::{draw_table, Alignment, StyledString, TextStyle};
|
use nu_table::{draw_table, Alignment, StyledString, TextStyle};
|
||||||
|
use std::collections::HashMap;
|
||||||
use std::time::Instant;
|
use std::time::Instant;
|
||||||
|
|
||||||
const STREAM_PAGE_SIZE: usize = 1000;
|
const STREAM_PAGE_SIZE: usize = 1000;
|
||||||
@ -44,19 +46,14 @@ pub fn from_list(
|
|||||||
values: &[Value],
|
values: &[Value],
|
||||||
configuration: &TableConfiguration,
|
configuration: &TableConfiguration,
|
||||||
starting_idx: usize,
|
starting_idx: usize,
|
||||||
|
color_hm: &HashMap<String, ansi_term::Style>,
|
||||||
) -> nu_table::Table {
|
) -> nu_table::Table {
|
||||||
let header_style = TextStyle {
|
let header_style = configuration.header_style();
|
||||||
is_bold: configuration.header_bold(),
|
|
||||||
alignment: configuration.header_alignment(),
|
|
||||||
color: configuration.header_color(),
|
|
||||||
};
|
|
||||||
|
|
||||||
let mut headers: Vec<StyledString> = nu_protocol::merge_descriptors(values)
|
let mut headers: Vec<StyledString> = nu_protocol::merge_descriptors(values)
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|x| StyledString::new(x, header_style.clone()))
|
.map(|x| StyledString::new(x, header_style))
|
||||||
.collect();
|
.collect();
|
||||||
let entries = values_to_entries(values, &mut headers, configuration, starting_idx);
|
let entries = values_to_entries(values, &mut headers, configuration, starting_idx, &color_hm);
|
||||||
|
|
||||||
nu_table::Table {
|
nu_table::Table {
|
||||||
headers,
|
headers,
|
||||||
data: entries,
|
data: entries,
|
||||||
@ -69,9 +66,9 @@ fn values_to_entries(
|
|||||||
headers: &mut Vec<StyledString>,
|
headers: &mut Vec<StyledString>,
|
||||||
configuration: &TableConfiguration,
|
configuration: &TableConfiguration,
|
||||||
starting_idx: usize,
|
starting_idx: usize,
|
||||||
|
color_hm: &HashMap<String, ansi_term::Style>,
|
||||||
) -> Vec<Vec<StyledString>> {
|
) -> Vec<Vec<StyledString>> {
|
||||||
let disable_indexes = configuration.disabled_indexes();
|
let disable_indexes = configuration.disabled_indexes();
|
||||||
|
|
||||||
let mut entries = vec![];
|
let mut entries = vec![];
|
||||||
|
|
||||||
if headers.is_empty() {
|
if headers.is_empty() {
|
||||||
@ -89,11 +86,11 @@ fn values_to_entries(
|
|||||||
..
|
..
|
||||||
} => StyledString::new(
|
} => StyledString::new(
|
||||||
format_leaf(&UntaggedValue::nothing()).plain_string(100_000),
|
format_leaf(&UntaggedValue::nothing()).plain_string(100_000),
|
||||||
style_leaf(&UntaggedValue::nothing()),
|
style_leaf(&UntaggedValue::nothing(), &color_hm),
|
||||||
),
|
),
|
||||||
_ => StyledString::new(
|
_ => StyledString::new(
|
||||||
format_leaf(value).plain_string(100_000),
|
format_leaf(value).plain_string(100_000),
|
||||||
style_leaf(value),
|
style_leaf(value, &color_hm),
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -106,12 +103,12 @@ fn values_to_entries(
|
|||||||
|
|
||||||
StyledString::new(
|
StyledString::new(
|
||||||
format_leaf(data.borrow()).plain_string(100_000),
|
format_leaf(data.borrow()).plain_string(100_000),
|
||||||
style_leaf(data.borrow()),
|
style_leaf(data.borrow(), &color_hm),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
_ => StyledString::new(
|
_ => StyledString::new(
|
||||||
format_leaf(&UntaggedValue::nothing()).plain_string(100_000),
|
format_leaf(&UntaggedValue::nothing()).plain_string(100_000),
|
||||||
style_leaf(&UntaggedValue::nothing()),
|
style_leaf(&UntaggedValue::nothing(), &color_hm),
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -119,16 +116,22 @@ fn values_to_entries(
|
|||||||
.collect();
|
.collect();
|
||||||
|
|
||||||
// Indices are green, bold, right-aligned:
|
// Indices are green, bold, right-aligned:
|
||||||
|
// unless we change them :)
|
||||||
if !disable_indexes {
|
if !disable_indexes {
|
||||||
row.insert(
|
row.insert(
|
||||||
0,
|
0,
|
||||||
StyledString::new(
|
StyledString::new(
|
||||||
(starting_idx + idx).to_string(),
|
(starting_idx + idx).to_string(),
|
||||||
TextStyle {
|
TextStyle::new().alignment(Alignment::Right).style(
|
||||||
alignment: Alignment::Right,
|
color_hm
|
||||||
color: Some(ansi_term::Color::Green),
|
.get("index_color")
|
||||||
is_bold: true,
|
.unwrap_or(
|
||||||
},
|
&ansi_term::Style::default()
|
||||||
|
.bold()
|
||||||
|
.fg(ansi_term::Color::Green),
|
||||||
|
)
|
||||||
|
.to_owned(),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -141,11 +144,10 @@ fn values_to_entries(
|
|||||||
0,
|
0,
|
||||||
StyledString::new(
|
StyledString::new(
|
||||||
"#".to_owned(),
|
"#".to_owned(),
|
||||||
TextStyle {
|
TextStyle::new()
|
||||||
alignment: Alignment::Center,
|
.alignment(Alignment::Center)
|
||||||
color: Some(ansi_term::Color::Green),
|
.fg(ansi_term::Color::Green)
|
||||||
is_bold: true,
|
.bold(Some(true)),
|
||||||
},
|
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -161,8 +163,14 @@ async fn table(
|
|||||||
let registry = registry.clone();
|
let registry = registry.clone();
|
||||||
let mut args = args.evaluate_once(®istry).await?;
|
let mut args = args.evaluate_once(®istry).await?;
|
||||||
let mut finished = false;
|
let mut finished = false;
|
||||||
|
// Ideally, get_color_config would get all the colors configured in the config.toml
|
||||||
|
// and create a style based on those settings. However, there are few places where
|
||||||
|
// this just won't work right now, like header styling, because a style needs to know
|
||||||
|
// more than just color, it needs fg & bg color, bold, dimmed, italic, underline,
|
||||||
|
// blink, reverse, hidden, strikethrough and most of those aren't available in the
|
||||||
|
// config.toml.... yet.
|
||||||
|
let color_hm = get_color_config();
|
||||||
|
|
||||||
// let host = args.host.clone();
|
|
||||||
let mut start_number = match args.get("start_number") {
|
let mut start_number = match args.get("start_number") {
|
||||||
Some(Value {
|
Some(Value {
|
||||||
value: UntaggedValue::Primitive(Primitive::Int(i)),
|
value: UntaggedValue::Primitive(Primitive::Int(i)),
|
||||||
@ -234,9 +242,9 @@ async fn table(
|
|||||||
let input: Vec<Value> = new_input.into();
|
let input: Vec<Value> = new_input.into();
|
||||||
|
|
||||||
if !input.is_empty() {
|
if !input.is_empty() {
|
||||||
let t = from_list(&input, &configuration, start_number);
|
let t = from_list(&input, &configuration, start_number, &color_hm);
|
||||||
|
|
||||||
draw_table(&t, term_width);
|
draw_table(&t, term_width, &color_hm);
|
||||||
}
|
}
|
||||||
|
|
||||||
start_number += input.len();
|
start_number += input.len();
|
||||||
|
@ -1,62 +1,51 @@
|
|||||||
pub use nu_data::config::NuConfig;
|
pub use nu_data::config::NuConfig;
|
||||||
|
use nu_data::primitive::lookup_ansi_color_style;
|
||||||
|
use nu_protocol::{UntaggedValue, Value};
|
||||||
|
use nu_source::Tag;
|
||||||
|
use nu_table::TextStyle;
|
||||||
use std::fmt::Debug;
|
use std::fmt::Debug;
|
||||||
|
|
||||||
pub trait ConfigExtensions: Debug + Send {
|
pub trait ConfigExtensions: Debug + Send {
|
||||||
fn header_alignment(&self) -> nu_table::Alignment;
|
|
||||||
fn header_color(&self) -> Option<ansi_term::Color>;
|
|
||||||
fn header_bold(&self) -> bool;
|
|
||||||
fn table_mode(&self) -> nu_table::Theme;
|
fn table_mode(&self) -> nu_table::Theme;
|
||||||
fn disabled_indexes(&self) -> bool;
|
fn disabled_indexes(&self) -> bool;
|
||||||
fn text_color(&self) -> Option<ansi_term::Color>;
|
fn header_style(&self) -> TextStyle;
|
||||||
fn line_color(&self) -> Option<ansi_term::Color>;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn header_alignment(config: &NuConfig) -> nu_table::Alignment {
|
pub fn header_alignment_from_value(align_value: Option<&Value>) -> nu_table::Alignment {
|
||||||
let vars = config.vars.lock();
|
match align_value {
|
||||||
|
Some(v) => match v
|
||||||
let alignment = vars.get("header_align");
|
.as_string()
|
||||||
|
.unwrap_or_else(|_| "none".to_string())
|
||||||
if alignment.is_none() {
|
.as_ref()
|
||||||
return nu_table::Alignment::Center;
|
{
|
||||||
}
|
"l" | "left" => nu_table::Alignment::Left,
|
||||||
|
"c" | "center" => nu_table::Alignment::Center,
|
||||||
alignment.map_or(nu_table::Alignment::Left, |a| {
|
"r" | "right" => nu_table::Alignment::Right,
|
||||||
a.as_string().map_or(nu_table::Alignment::Center, |a| {
|
_ => nu_table::Alignment::Center,
|
||||||
match a.to_lowercase().as_str() {
|
},
|
||||||
"center" | "c" => nu_table::Alignment::Center,
|
|
||||||
"right" | "r" => nu_table::Alignment::Right,
|
|
||||||
_ => nu_table::Alignment::Center,
|
_ => nu_table::Alignment::Center,
|
||||||
}
|
}
|
||||||
})
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_color_for_config_key(config: &NuConfig, key: &str) -> Option<ansi_term::Color> {
|
pub fn get_color_from_key_and_subkey(config: &NuConfig, key: &str, subkey: &str) -> Value {
|
||||||
let vars = config.vars.lock();
|
let vars = config.vars.lock();
|
||||||
|
|
||||||
Some(match vars.get(key) {
|
let mut v: Value =
|
||||||
Some(c) => match c.as_string() {
|
UntaggedValue::Primitive(nu_protocol::Primitive::String("nocolor".to_string()))
|
||||||
Ok(color) => match color.to_lowercase().as_str() {
|
.into_value(Tag::unknown());
|
||||||
"g" | "green" => ansi_term::Color::Green,
|
if let Some(config_vars) = vars.get(key) {
|
||||||
"r" | "red" => ansi_term::Color::Red,
|
for (kee, value) in config_vars.row_entries() {
|
||||||
"u" | "blue" => ansi_term::Color::Blue,
|
if kee == subkey {
|
||||||
"b" | "black" => ansi_term::Color::Black,
|
v = value.to_owned();
|
||||||
"y" | "yellow" => ansi_term::Color::Yellow,
|
}
|
||||||
"p" | "purple" => ansi_term::Color::Purple,
|
}
|
||||||
"c" | "cyan" => ansi_term::Color::Cyan,
|
}
|
||||||
"w" | "white" => ansi_term::Color::White,
|
|
||||||
_ => ansi_term::Color::Green,
|
v
|
||||||
},
|
|
||||||
_ => ansi_term::Color::Green,
|
|
||||||
},
|
|
||||||
_ => ansi_term::Color::Green,
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn header_bold(config: &NuConfig) -> bool {
|
pub fn header_bold_from_value(bold_value: Option<&Value>) -> bool {
|
||||||
let vars = config.vars.lock();
|
bold_value
|
||||||
|
|
||||||
vars.get("header_bold")
|
|
||||||
.map(|x| x.as_bool().unwrap_or(true))
|
.map(|x| x.as_bool().unwrap_or(true))
|
||||||
.unwrap_or(true)
|
.unwrap_or(true)
|
||||||
}
|
}
|
||||||
@ -84,24 +73,25 @@ pub fn disabled_indexes(config: &NuConfig) -> bool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl ConfigExtensions for NuConfig {
|
impl ConfigExtensions for NuConfig {
|
||||||
fn header_alignment(&self) -> nu_table::Alignment {
|
fn header_style(&self) -> TextStyle {
|
||||||
header_alignment(self)
|
// FIXME: I agree, this is the long way around, please suggest and alternative.
|
||||||
}
|
let head_color = get_color_from_key_and_subkey(self, "color_config", "header_color");
|
||||||
|
let head_color_style = lookup_ansi_color_style(
|
||||||
|
head_color
|
||||||
|
.as_string()
|
||||||
|
.unwrap_or_else(|_| "green".to_string()),
|
||||||
|
);
|
||||||
|
let head_bold = get_color_from_key_and_subkey(self, "color_config", "header_bold");
|
||||||
|
let head_bold_bool = header_bold_from_value(Some(&head_bold));
|
||||||
|
let head_align = get_color_from_key_and_subkey(self, "color_config", "header_align");
|
||||||
|
let head_alignment = header_alignment_from_value(Some(&head_align));
|
||||||
|
|
||||||
fn header_color(&self) -> Option<ansi_term::Color> {
|
TextStyle::new()
|
||||||
get_color_for_config_key(self, "header_color")
|
.alignment(head_alignment)
|
||||||
}
|
.bold(Some(head_bold_bool))
|
||||||
|
.fg(head_color_style
|
||||||
fn text_color(&self) -> Option<ansi_term::Color> {
|
.foreground
|
||||||
get_color_for_config_key(self, "text_color")
|
.unwrap_or(ansi_term::Color::Green))
|
||||||
}
|
|
||||||
|
|
||||||
fn line_color(&self) -> Option<ansi_term::Color> {
|
|
||||||
get_color_for_config_key(self, "line_color")
|
|
||||||
}
|
|
||||||
|
|
||||||
fn header_bold(&self) -> bool {
|
|
||||||
header_bold(self)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn table_mode(&self) -> nu_table::Theme {
|
fn table_mode(&self) -> nu_table::Theme {
|
||||||
|
@ -1,143 +0,0 @@
|
|||||||
use crate::config::nuconfig::NuConfig;
|
|
||||||
use std::fmt::Debug;
|
|
||||||
|
|
||||||
#[derive(PartialEq, Debug)]
|
|
||||||
pub enum AutoPivotMode {
|
|
||||||
Auto,
|
|
||||||
Always,
|
|
||||||
Never,
|
|
||||||
}
|
|
||||||
|
|
||||||
pub trait HasTableProperties: Debug + Send {
|
|
||||||
fn pivot_mode(&self) -> AutoPivotMode;
|
|
||||||
fn header_alignment(&self) -> nu_table::Alignment;
|
|
||||||
fn header_color(&self) -> Option<ansi_term::Color>;
|
|
||||||
fn header_bold(&self) -> bool;
|
|
||||||
fn table_mode(&self) -> nu_table::Theme;
|
|
||||||
fn disabled_indexes(&self) -> bool;
|
|
||||||
fn text_color(&self) -> Option<ansi_term::Color>;
|
|
||||||
fn line_color(&self) -> Option<ansi_term::Color>;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn pivot_mode(config: &NuConfig) -> AutoPivotMode {
|
|
||||||
let vars = config.vars.lock();
|
|
||||||
|
|
||||||
if let Some(mode) = vars.get("pivot_mode") {
|
|
||||||
let mode = match mode.as_string() {
|
|
||||||
Ok(m) if m.to_lowercase() == "auto" => AutoPivotMode::Auto,
|
|
||||||
Ok(m) if m.to_lowercase() == "always" => AutoPivotMode::Always,
|
|
||||||
Ok(m) if m.to_lowercase() == "never" => AutoPivotMode::Never,
|
|
||||||
_ => AutoPivotMode::Always,
|
|
||||||
};
|
|
||||||
|
|
||||||
return mode;
|
|
||||||
}
|
|
||||||
|
|
||||||
AutoPivotMode::Always
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn header_alignment(config: &NuConfig) -> nu_table::Alignment {
|
|
||||||
let vars = config.vars.lock();
|
|
||||||
|
|
||||||
let alignment = vars.get("header_align");
|
|
||||||
|
|
||||||
if alignment.is_none() {
|
|
||||||
return nu_table::Alignment::Center;
|
|
||||||
}
|
|
||||||
|
|
||||||
alignment.map_or(nu_table::Alignment::Left, |a| {
|
|
||||||
a.as_string().map_or(nu_table::Alignment::Center, |a| {
|
|
||||||
match a.to_lowercase().as_str() {
|
|
||||||
"center" | "c" => nu_table::Alignment::Center,
|
|
||||||
"right" | "r" => nu_table::Alignment::Right,
|
|
||||||
_ => nu_table::Alignment::Center,
|
|
||||||
}
|
|
||||||
})
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn get_color_for_config_key(config: &NuConfig, key: &str) -> Option<ansi_term::Color> {
|
|
||||||
let vars = config.vars.lock();
|
|
||||||
|
|
||||||
Some(match vars.get(key) {
|
|
||||||
Some(c) => match c.as_string() {
|
|
||||||
Ok(color) => match color.to_lowercase().as_str() {
|
|
||||||
"g" | "green" => ansi_term::Color::Green,
|
|
||||||
"r" | "red" => ansi_term::Color::Red,
|
|
||||||
"u" | "blue" => ansi_term::Color::Blue,
|
|
||||||
"b" | "black" => ansi_term::Color::Black,
|
|
||||||
"y" | "yellow" => ansi_term::Color::Yellow,
|
|
||||||
"p" | "purple" => ansi_term::Color::Purple,
|
|
||||||
"c" | "cyan" => ansi_term::Color::Cyan,
|
|
||||||
"w" | "white" => ansi_term::Color::White,
|
|
||||||
_ => ansi_term::Color::Green,
|
|
||||||
},
|
|
||||||
_ => ansi_term::Color::Green,
|
|
||||||
},
|
|
||||||
_ => ansi_term::Color::Green,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn header_bold(config: &NuConfig) -> bool {
|
|
||||||
let vars = config.vars.lock();
|
|
||||||
|
|
||||||
vars.get("header_bold")
|
|
||||||
.map(|x| x.as_bool().unwrap_or(true))
|
|
||||||
.unwrap_or(true)
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn table_mode(config: &NuConfig) -> nu_table::Theme {
|
|
||||||
let vars = config.vars.lock();
|
|
||||||
|
|
||||||
vars.get("table_mode")
|
|
||||||
.map_or(nu_table::Theme::compact(), |mode| match mode.as_string() {
|
|
||||||
Ok(m) if m == "basic" => nu_table::Theme::basic(),
|
|
||||||
Ok(m) if m == "compact" => nu_table::Theme::compact(),
|
|
||||||
Ok(m) if m == "light" => nu_table::Theme::light(),
|
|
||||||
Ok(m) if m == "thin" => nu_table::Theme::thin(),
|
|
||||||
Ok(m) if m == "with_love" => nu_table::Theme::with_love(),
|
|
||||||
Ok(m) if m == "compact_double" => nu_table::Theme::compact_double(),
|
|
||||||
_ => nu_table::Theme::compact(),
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn disabled_indexes(config: &NuConfig) -> bool {
|
|
||||||
let vars = config.vars.lock();
|
|
||||||
|
|
||||||
vars.get("disable_table_indexes")
|
|
||||||
.map_or(false, |x| x.as_bool().unwrap_or(false))
|
|
||||||
}
|
|
||||||
|
|
||||||
impl HasTableProperties for NuConfig {
|
|
||||||
fn pivot_mode(&self) -> AutoPivotMode {
|
|
||||||
pivot_mode(self)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn header_alignment(&self) -> nu_table::Alignment {
|
|
||||||
header_alignment(self)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn header_color(&self) -> Option<ansi_term::Color> {
|
|
||||||
get_color_for_config_key(self, "header_color")
|
|
||||||
}
|
|
||||||
|
|
||||||
fn text_color(&self) -> Option<ansi_term::Color> {
|
|
||||||
get_color_for_config_key(self, "text_color")
|
|
||||||
}
|
|
||||||
|
|
||||||
fn line_color(&self) -> Option<ansi_term::Color> {
|
|
||||||
get_color_for_config_key(self, "line_color")
|
|
||||||
}
|
|
||||||
|
|
||||||
fn header_bold(&self) -> bool {
|
|
||||||
header_bold(self)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn table_mode(&self) -> nu_table::Theme {
|
|
||||||
table_mode(self)
|
|
||||||
}
|
|
||||||
|
|
||||||
fn disabled_indexes(&self) -> bool {
|
|
||||||
disabled_indexes(self)
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,5 +1,8 @@
|
|||||||
use nu_protocol::{hir::Number, Primitive};
|
use ansi_term::{Color, Style};
|
||||||
use nu_table::TextStyle;
|
use nu_protocol::{hir::Number, Primitive, Value};
|
||||||
|
use nu_source::Tag;
|
||||||
|
use nu_table::{Alignment, TextStyle};
|
||||||
|
use std::collections::HashMap;
|
||||||
|
|
||||||
pub fn number(number: impl Into<Number>) -> Primitive {
|
pub fn number(number: impl Into<Number>) -> Primitive {
|
||||||
let number = number.into();
|
let number = number.into();
|
||||||
@ -10,10 +13,349 @@ pub fn number(number: impl Into<Number>) -> Primitive {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn style_primitive(primitive: &Primitive) -> TextStyle {
|
pub fn lookup_ansi_color_style(s: String) -> Style {
|
||||||
|
match s.as_str() {
|
||||||
|
"g" | "green" => Color::Green.normal(),
|
||||||
|
"gb" | "green_bold" => Color::Green.bold(),
|
||||||
|
"gu" | "green_underline" => Color::Green.underline(),
|
||||||
|
"gi" | "green_italic" => Color::Green.italic(),
|
||||||
|
"gd" | "green_dimmed" => Color::Green.dimmed(),
|
||||||
|
"gr" | "green_reverse" => Color::Green.reverse(),
|
||||||
|
"r" | "red" => Color::Red.normal(),
|
||||||
|
"rb" | "red_bold" => Color::Red.bold(),
|
||||||
|
"ru" | "red_underline" => Color::Red.underline(),
|
||||||
|
"ri" | "red_italic" => Color::Red.italic(),
|
||||||
|
"rd" | "red_dimmed" => Color::Red.dimmed(),
|
||||||
|
"rr" | "red_reverse" => Color::Red.reverse(),
|
||||||
|
"u" | "blue" => Color::Blue.normal(),
|
||||||
|
"ub" | "blue_bold" => Color::Blue.bold(),
|
||||||
|
"uu" | "blue_underline" => Color::Blue.underline(),
|
||||||
|
"ui" | "blue_italic" => Color::Blue.italic(),
|
||||||
|
"ud" | "blue_dimmed" => Color::Blue.dimmed(),
|
||||||
|
"ur" | "blue_reverse" => Color::Blue.reverse(),
|
||||||
|
"b" | "black" => Color::Black.normal(),
|
||||||
|
"bb" | "black_bold" => Color::Black.bold(),
|
||||||
|
"bu" | "black_underline" => Color::Black.underline(),
|
||||||
|
"bi" | "black_italic" => Color::Black.italic(),
|
||||||
|
"bd" | "black_dimmed" => Color::Black.dimmed(),
|
||||||
|
"br" | "black_reverse" => Color::Black.reverse(),
|
||||||
|
"y" | "yellow" => Color::Yellow.normal(),
|
||||||
|
"yb" | "yellow_bold" => Color::Yellow.bold(),
|
||||||
|
"yu" | "yellow_underline" => Color::Yellow.underline(),
|
||||||
|
"yi" | "yellow_italic" => Color::Yellow.italic(),
|
||||||
|
"yd" | "yellow_dimmed" => Color::Yellow.dimmed(),
|
||||||
|
"yr" | "yellow_reverse" => Color::Yellow.reverse(),
|
||||||
|
"p" | "purple" => Color::Purple.normal(),
|
||||||
|
"pb" | "purple_bold" => Color::Purple.bold(),
|
||||||
|
"pu" | "purple_underline" => Color::Purple.underline(),
|
||||||
|
"pi" | "purple_italic" => Color::Purple.italic(),
|
||||||
|
"pd" | "purple_dimmed" => Color::Purple.dimmed(),
|
||||||
|
"pr" | "purple_reverse" => Color::Purple.reverse(),
|
||||||
|
"c" | "cyan" => Color::Cyan.normal(),
|
||||||
|
"cb" | "cyan_bold" => Color::Cyan.bold(),
|
||||||
|
"cu" | "cyan_underline" => Color::Cyan.underline(),
|
||||||
|
"ci" | "cyan_italic" => Color::Cyan.italic(),
|
||||||
|
"cd" | "cyan_dimmed" => Color::Cyan.dimmed(),
|
||||||
|
"cr" | "cyan_reverse" => Color::Cyan.reverse(),
|
||||||
|
"w" | "white" => Color::White.normal(),
|
||||||
|
"wb" | "white_bold" => Color::White.bold(),
|
||||||
|
"wu" | "white_underline" => Color::White.underline(),
|
||||||
|
"wi" | "white_italic" => Color::White.italic(),
|
||||||
|
"wd" | "white_dimmed" => Color::White.dimmed(),
|
||||||
|
"wr" | "white_reverse" => Color::White.reverse(),
|
||||||
|
_ => Color::White.normal(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn string_to_lookup_value(str_prim: &str) -> String {
|
||||||
|
match str_prim {
|
||||||
|
"primitive_int" => "Primitive::Int".to_string(),
|
||||||
|
"primitive_decimal" => "Primitive::Decimal".to_string(),
|
||||||
|
"primitive_filesize" => "Primitive::Filesize".to_string(),
|
||||||
|
"primitive_string" => "Primitive::String".to_string(),
|
||||||
|
"primitive_line" => "Primitive::Line".to_string(),
|
||||||
|
"primitive_columnpath" => "Primitive::ColumnPath".to_string(),
|
||||||
|
"primitive_pattern" => "Primitive::Pattern".to_string(),
|
||||||
|
"primitive_boolean" => "Primitive::Boolean".to_string(),
|
||||||
|
"primitive_date" => "Primitive::Date".to_string(),
|
||||||
|
"primitive_duration" => "Primitive::Duration".to_string(),
|
||||||
|
"primitive_range" => "Primitive::Range".to_string(),
|
||||||
|
"primitive_path" => "Primitive::Path".to_string(),
|
||||||
|
"primitive_binary" => "Primitive::Binary".to_string(),
|
||||||
|
"separator_color" => "separator_color".to_string(),
|
||||||
|
"header_align" => "header_align".to_string(),
|
||||||
|
"header_color" => "header_color".to_string(),
|
||||||
|
"header_bold" => "header_bold".to_string(),
|
||||||
|
"header_style" => "header_style".to_string(),
|
||||||
|
"index_color" => "index_color".to_string(),
|
||||||
|
_ => "Primitive::Nothing".to_string(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn update_hashmap(key: &str, val: &Value, hm: &mut HashMap<String, Style>) {
|
||||||
|
if let Ok(var) = val.as_string() {
|
||||||
|
let color = lookup_ansi_color_style(var);
|
||||||
|
let prim = string_to_lookup_value(&key);
|
||||||
|
if let Some(v) = hm.get_mut(&prim) {
|
||||||
|
*v = color;
|
||||||
|
} else {
|
||||||
|
hm.insert(prim, color);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn get_color_config() -> HashMap<String, Style> {
|
||||||
|
// create the hashmap
|
||||||
|
let mut hm: HashMap<String, Style> = HashMap::new();
|
||||||
|
// set some defaults
|
||||||
|
hm.insert("primitive_int".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_decimal".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_filesize".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_string".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_line".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_columnpath".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_pattern".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_boolean".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_date".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_duration".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_range".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_path".to_string(), Color::White.normal());
|
||||||
|
hm.insert("primitive_binary".to_string(), Color::White.normal());
|
||||||
|
hm.insert("separator_color".to_string(), Color::White.normal());
|
||||||
|
hm.insert("header_align".to_string(), Color::White.normal());
|
||||||
|
hm.insert("header_color".to_string(), Color::White.normal());
|
||||||
|
hm.insert("header_bold".to_string(), Color::White.normal());
|
||||||
|
hm.insert("header_style".to_string(), Style::default());
|
||||||
|
hm.insert("index_color".to_string(), Color::Green.normal());
|
||||||
|
|
||||||
|
// populate hashmap from config values
|
||||||
|
if let Ok(config) = crate::config::config(Tag::unknown()) {
|
||||||
|
if let Some(primitive_color_vars) = config.get("color_config") {
|
||||||
|
for (key, value) in primitive_color_vars.row_entries() {
|
||||||
|
match key.as_ref() {
|
||||||
|
"primitive_int" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_decimal" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_filesize" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_string" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_line" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_columnpath" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_pattern" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_boolean" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_date" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_duration" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_range" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_path" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"primitive_binary" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"separator_color" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"header_align" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"header_color" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"header_bold" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"header_style" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
"index_color" => {
|
||||||
|
update_hashmap(&key, &value, &mut hm);
|
||||||
|
}
|
||||||
|
_ => (),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
hm
|
||||||
|
}
|
||||||
|
|
||||||
|
// This function will assign a text style to a primitive, or really any string that's
|
||||||
|
// in the hashmap. The hashmap actually contains the style to be applied.
|
||||||
|
pub fn style_primitive(primitive: &str, color_hm: &HashMap<String, Style>) -> TextStyle {
|
||||||
match primitive {
|
match primitive {
|
||||||
Primitive::Int(_) | Primitive::Filesize(_) | Primitive::Decimal(_) => {
|
"Int" => {
|
||||||
TextStyle::basic_right()
|
let style = color_hm.get("Primitive::Int");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Right, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Decimal" => {
|
||||||
|
let style = color_hm.get("Primitive::Decimal");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Right, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Filesize" => {
|
||||||
|
let style = color_hm.get("Primitive::Filesize");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Right, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"String" => {
|
||||||
|
let style = color_hm.get("Primitive::String");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Line" => {
|
||||||
|
let style = color_hm.get("Primitive::Line");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"ColumnPath" => {
|
||||||
|
let style = color_hm.get("Primitive::ColumnPath");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Pattern" => {
|
||||||
|
let style = color_hm.get("Primitive::Pattern");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Boolean" => {
|
||||||
|
let style = color_hm.get("Primitive::Boolean");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Date" => {
|
||||||
|
let style = color_hm.get("Primitive::Date");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Duration" => {
|
||||||
|
let style = color_hm.get("Primitive::Duration");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Range" => {
|
||||||
|
let style = color_hm.get("Primitive::Range");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Path" => {
|
||||||
|
let style = color_hm.get("Primitive::Path");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Binary" => {
|
||||||
|
let style = color_hm.get("Primitive::Binary");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"BeginningOfStream" => {
|
||||||
|
let style = color_hm.get("Primitive::BeginningOfStream");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"EndOfStream" => {
|
||||||
|
let style = color_hm.get("Primitive::EndOfStream");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"Nothing" => {
|
||||||
|
let style = color_hm.get("Primitive::Nothing");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"separator_color" => {
|
||||||
|
let style = color_hm.get("separator");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"header_align" => {
|
||||||
|
let style = color_hm.get("header_align");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"header_color" => {
|
||||||
|
let style = color_hm.get("header_color");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"header_bold" => {
|
||||||
|
let style = color_hm.get("header_bold");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"header_style" => {
|
||||||
|
let style = color_hm.get("header_style");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"index_color" => {
|
||||||
|
let style = color_hm.get("index_color");
|
||||||
|
match style {
|
||||||
|
Some(s) => TextStyle::with_style(Alignment::Left, *s),
|
||||||
|
None => TextStyle::basic_right(),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
_ => TextStyle::basic(),
|
_ => TextStyle::basic(),
|
||||||
}
|
}
|
||||||
|
@ -9,6 +9,7 @@ use nu_protocol::{Primitive, Type, UntaggedValue};
|
|||||||
use nu_source::{DebugDocBuilder, PrettyDebug, Span, Tagged};
|
use nu_source::{DebugDocBuilder, PrettyDebug, Span, Tagged};
|
||||||
use nu_table::TextStyle;
|
use nu_table::TextStyle;
|
||||||
use num_traits::Zero;
|
use num_traits::Zero;
|
||||||
|
use std::collections::HashMap;
|
||||||
|
|
||||||
pub struct Date;
|
pub struct Date;
|
||||||
|
|
||||||
@ -245,9 +246,20 @@ pub fn format_leaf<'a>(value: impl Into<&'a UntaggedValue>) -> DebugDocBuilder {
|
|||||||
InlineShape::from_value(value.into()).format().pretty()
|
InlineShape::from_value(value.into()).format().pretty()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn style_leaf<'a>(value: impl Into<&'a UntaggedValue>) -> TextStyle {
|
pub fn style_leaf<'a>(
|
||||||
|
value: impl Into<&'a UntaggedValue>,
|
||||||
|
color_hash_map: &HashMap<String, ansi_term::Style>,
|
||||||
|
) -> TextStyle {
|
||||||
match value.into() {
|
match value.into() {
|
||||||
UntaggedValue::Primitive(p) => style_primitive(p),
|
UntaggedValue::Primitive(p) => {
|
||||||
|
// This is just to return the name of the type so that style_primitive
|
||||||
|
// can work on a string versus a type like String("some_text")
|
||||||
|
let str: &str = &p.to_string();
|
||||||
|
let str_len = str.len();
|
||||||
|
let paren_index = str.find('(').unwrap_or(str_len - 1);
|
||||||
|
let prim_type = str[0..paren_index].to_string();
|
||||||
|
style_primitive(&prim_type, &color_hash_map)
|
||||||
|
}
|
||||||
_ => TextStyle::basic(),
|
_ => TextStyle::basic(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -192,6 +192,12 @@ impl From<chrono::Duration> for Primitive {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl std::fmt::Display for Primitive {
|
||||||
|
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
|
||||||
|
write!(f, "{:?}", self)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl ShellTypeName for Primitive {
|
impl ShellTypeName for Primitive {
|
||||||
/// Get the name of the type of a Primitive value
|
/// Get the name of the type of a Primitive value
|
||||||
fn type_name(&self) -> &'static str {
|
fn type_name(&self) -> &'static str {
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
use nu_table::{draw_table, StyledString, Table, TextStyle, Theme};
|
use nu_table::{draw_table, StyledString, Table, TextStyle, Theme};
|
||||||
|
use std::collections::HashMap;
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let args: Vec<_> = std::env::args().collect();
|
let args: Vec<_> = std::env::args().collect();
|
||||||
@ -23,5 +24,7 @@ fn main() {
|
|||||||
Theme::compact(),
|
Theme::compact(),
|
||||||
);
|
);
|
||||||
|
|
||||||
draw_table(&t, width);
|
// FIXME: Config isn't available from here so just put these here to compile
|
||||||
|
let color_hm: HashMap<String, ansi_term::Style> = HashMap::new();
|
||||||
|
draw_table(&t, width, &color_hm);
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
use crate::wrap::{column_width, split_sublines, wrap, Alignment, Subline, WrappedCell};
|
use crate::wrap::{column_width, split_sublines, wrap, Alignment, Subline, WrappedCell};
|
||||||
|
use ansi_term::{Color, Style};
|
||||||
|
use std::collections::HashMap;
|
||||||
|
|
||||||
enum SeparatorPosition {
|
enum SeparatorPosition {
|
||||||
Top,
|
Top,
|
||||||
@ -23,38 +25,240 @@ impl StyledString {
|
|||||||
pub fn new(contents: String, style: TextStyle) -> StyledString {
|
pub fn new(contents: String, style: TextStyle) -> StyledString {
|
||||||
StyledString { contents, style }
|
StyledString { contents, style }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn set_style(&mut self, style: TextStyle) {
|
||||||
|
self.style = style;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone, Copy)]
|
||||||
pub struct TextStyle {
|
pub struct TextStyle {
|
||||||
pub is_bold: bool,
|
|
||||||
pub alignment: Alignment,
|
pub alignment: Alignment,
|
||||||
pub color: Option<ansi_term::Colour>,
|
pub color_style: Option<Style>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl TextStyle {
|
impl TextStyle {
|
||||||
pub fn basic() -> TextStyle {
|
pub fn new() -> TextStyle {
|
||||||
TextStyle {
|
TextStyle {
|
||||||
is_bold: false,
|
|
||||||
alignment: Alignment::Left,
|
alignment: Alignment::Left,
|
||||||
color: None,
|
color_style: Some(Style::default()),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn bold(&self, bool_value: Option<bool>) -> TextStyle {
|
||||||
|
let bv = match bool_value {
|
||||||
|
Some(v) => v,
|
||||||
|
None => false,
|
||||||
|
};
|
||||||
|
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_bold: bv,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_bold(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_bold
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn dimmed(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_dimmed: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_dimmed(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_dimmed
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn italic(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_italic: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_italic(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_italic
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn underline(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_underline: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_underline(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_underline
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn blink(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_blink: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_blink(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_blink
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn reverse(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_reverse: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_reverse(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_reverse
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn hidden(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_hidden: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_hidden(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_hidden
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn strikethrough(&self) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
is_strikethrough: true,
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_strikethrough(&self) -> bool {
|
||||||
|
self.color_style.unwrap_or_default().is_strikethrough
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn fg(&self, foregound: Color) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
foreground: Some(foregound),
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn on(&self, background: Color) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
background: Some(background),
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn bg(&self, background: Color) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
background: Some(background),
|
||||||
|
..self.color_style.unwrap_or_default()
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn alignment(&self, align: Alignment) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: align,
|
||||||
|
color_style: self.color_style,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn style(&self, style: Style) -> TextStyle {
|
||||||
|
TextStyle {
|
||||||
|
alignment: self.alignment,
|
||||||
|
color_style: Some(Style {
|
||||||
|
foreground: style.foreground,
|
||||||
|
background: style.background,
|
||||||
|
is_bold: style.is_bold,
|
||||||
|
is_dimmed: style.is_dimmed,
|
||||||
|
is_italic: style.is_italic,
|
||||||
|
is_underline: style.is_underline,
|
||||||
|
is_blink: style.is_blink,
|
||||||
|
is_reverse: style.is_reverse,
|
||||||
|
is_hidden: style.is_hidden,
|
||||||
|
is_strikethrough: style.is_strikethrough,
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn basic() -> TextStyle {
|
||||||
|
TextStyle::new()
|
||||||
|
.alignment(Alignment::Left)
|
||||||
|
.style(Style::default())
|
||||||
|
}
|
||||||
|
|
||||||
pub fn basic_right() -> TextStyle {
|
pub fn basic_right() -> TextStyle {
|
||||||
TextStyle {
|
TextStyle::new()
|
||||||
is_bold: false,
|
.alignment(Alignment::Right)
|
||||||
alignment: Alignment::Right,
|
.style(Style::default())
|
||||||
color: None,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn default_header() -> TextStyle {
|
pub fn default_header() -> TextStyle {
|
||||||
TextStyle {
|
TextStyle::new()
|
||||||
is_bold: true,
|
.alignment(Alignment::Center)
|
||||||
alignment: Alignment::Center,
|
.fg(Color::Green)
|
||||||
color: Some(ansi_term::Colour::Green),
|
.bold(Some(true))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn with_attributes(bo: bool, al: Alignment, co: Color) -> TextStyle {
|
||||||
|
TextStyle::new().alignment(al).fg(co).bold(Some(bo))
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn with_style(al: Alignment, style: Style) -> TextStyle {
|
||||||
|
TextStyle::new().alignment(al).style(Style {
|
||||||
|
foreground: style.foreground,
|
||||||
|
background: style.background,
|
||||||
|
is_bold: style.is_bold,
|
||||||
|
is_dimmed: style.is_dimmed,
|
||||||
|
is_italic: style.is_italic,
|
||||||
|
is_underline: style.is_underline,
|
||||||
|
is_blink: style.is_blink,
|
||||||
|
is_reverse: style.is_reverse,
|
||||||
|
is_hidden: style.is_hidden,
|
||||||
|
is_strikethrough: style.is_strikethrough,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Default for TextStyle {
|
||||||
|
fn default() -> Self {
|
||||||
|
Self::new()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -300,71 +504,148 @@ pub struct WrappedTable {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl WrappedTable {
|
impl WrappedTable {
|
||||||
fn print_separator(&self, separator_position: SeparatorPosition) {
|
fn print_separator(
|
||||||
|
&self,
|
||||||
|
separator_position: SeparatorPosition,
|
||||||
|
color_hm: &HashMap<String, Style>,
|
||||||
|
) {
|
||||||
let column_count = self.column_widths.len();
|
let column_count = self.column_widths.len();
|
||||||
let mut output = String::new();
|
let mut output = String::new();
|
||||||
|
let sep_color = color_hm
|
||||||
|
.get("separator_color")
|
||||||
|
.unwrap_or(&Style::default())
|
||||||
|
.to_owned();
|
||||||
|
|
||||||
match separator_position {
|
match separator_position {
|
||||||
SeparatorPosition::Top => {
|
SeparatorPosition::Top => {
|
||||||
for column in self.column_widths.iter().enumerate() {
|
for column in self.column_widths.iter().enumerate() {
|
||||||
if column.0 == 0 && self.theme.print_left_border {
|
if column.0 == 0 && self.theme.print_left_border {
|
||||||
output.push(self.theme.top_left);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.top_left.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
for _ in 0..*column.1 {
|
for _ in 0..*column.1 {
|
||||||
output.push(self.theme.top_horizontal);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.top_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
output.push(self.theme.top_horizontal);
|
output.push_str(
|
||||||
output.push(self.theme.top_horizontal);
|
&sep_color
|
||||||
|
.paint(&self.theme.top_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.top_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
if column.0 == column_count - 1 {
|
if column.0 == column_count - 1 {
|
||||||
if self.theme.print_right_border {
|
if self.theme.print_right_border {
|
||||||
output.push(self.theme.top_right);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.top_right.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
output.push(self.theme.top_center);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.top_center.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
SeparatorPosition::Middle => {
|
SeparatorPosition::Middle => {
|
||||||
for column in self.column_widths.iter().enumerate() {
|
for column in self.column_widths.iter().enumerate() {
|
||||||
if column.0 == 0 && self.theme.print_left_border {
|
if column.0 == 0 && self.theme.print_left_border {
|
||||||
output.push(self.theme.middle_left);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.middle_left.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
for _ in 0..*column.1 {
|
for _ in 0..*column.1 {
|
||||||
output.push(self.theme.middle_horizontal);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.middle_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
output.push(self.theme.middle_horizontal);
|
output.push_str(
|
||||||
output.push(self.theme.middle_horizontal);
|
&sep_color
|
||||||
|
.paint(&self.theme.middle_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.middle_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
|
|
||||||
if column.0 == column_count - 1 {
|
if column.0 == column_count - 1 {
|
||||||
if self.theme.print_right_border {
|
if self.theme.print_right_border {
|
||||||
output.push(self.theme.middle_right);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.middle_right.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
output.push(self.theme.center);
|
output
|
||||||
|
.push_str(&sep_color.paint(&self.theme.center.to_string()).to_string());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
SeparatorPosition::Bottom => {
|
SeparatorPosition::Bottom => {
|
||||||
for column in self.column_widths.iter().enumerate() {
|
for column in self.column_widths.iter().enumerate() {
|
||||||
if column.0 == 0 && self.theme.print_left_border {
|
if column.0 == 0 && self.theme.print_left_border {
|
||||||
output.push(self.theme.bottom_left);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.bottom_left.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
for _ in 0..*column.1 {
|
for _ in 0..*column.1 {
|
||||||
output.push(self.theme.bottom_horizontal);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.bottom_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
output.push(self.theme.bottom_horizontal);
|
output.push_str(
|
||||||
output.push(self.theme.bottom_horizontal);
|
&sep_color
|
||||||
|
.paint(&self.theme.bottom_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.bottom_horizontal.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
|
|
||||||
if column.0 == column_count - 1 {
|
if column.0 == column_count - 1 {
|
||||||
if self.theme.print_right_border {
|
if self.theme.print_right_border {
|
||||||
output.push(self.theme.bottom_right);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.bottom_right.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
output.push(self.theme.bottom_center);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.bottom_center.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -373,15 +654,24 @@ impl WrappedTable {
|
|||||||
println!("{}", output);
|
println!("{}", output);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn print_cell_contents(&self, cells: &[WrappedCell]) {
|
fn print_cell_contents(&self, cells: &[WrappedCell], color_hm: &HashMap<String, Style>) {
|
||||||
|
let sep_color = color_hm
|
||||||
|
.get("separator_color")
|
||||||
|
.unwrap_or(&Style::default())
|
||||||
|
.to_owned();
|
||||||
|
|
||||||
for current_line in 0.. {
|
for current_line in 0.. {
|
||||||
let mut lines_printed = 0;
|
let mut lines_printed = 0;
|
||||||
|
|
||||||
let mut output = if self.theme.print_left_border {
|
let mut output = String::new();
|
||||||
self.theme.left_vertical.to_string()
|
if self.theme.print_left_border {
|
||||||
} else {
|
output.push_str(
|
||||||
String::new()
|
&sep_color
|
||||||
};
|
.paint(&self.theme.left_vertical.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
for column in cells.iter().enumerate() {
|
for column in cells.iter().enumerate() {
|
||||||
if let Some(line) = (column.1).lines.get(current_line) {
|
if let Some(line) = (column.1).lines.get(current_line) {
|
||||||
let remainder = self.column_widths[column.0] - line.width;
|
let remainder = self.column_widths[column.0] - line.width;
|
||||||
@ -389,13 +679,7 @@ impl WrappedTable {
|
|||||||
|
|
||||||
match column.1.style.alignment {
|
match column.1.style.alignment {
|
||||||
Alignment::Left => {
|
Alignment::Left => {
|
||||||
if let Some(color) = column.1.style.color {
|
if let Some(color) = column.1.style.color_style {
|
||||||
let color = if column.1.style.is_bold {
|
|
||||||
color.bold()
|
|
||||||
} else {
|
|
||||||
color.normal()
|
|
||||||
};
|
|
||||||
|
|
||||||
output.push_str(&color.paint(&line.line).to_string());
|
output.push_str(&color.paint(&line.line).to_string());
|
||||||
} else {
|
} else {
|
||||||
output.push_str(&line.line);
|
output.push_str(&line.line);
|
||||||
@ -408,13 +692,7 @@ impl WrappedTable {
|
|||||||
for _ in 0..remainder / 2 {
|
for _ in 0..remainder / 2 {
|
||||||
output.push(' ');
|
output.push(' ');
|
||||||
}
|
}
|
||||||
if let Some(color) = column.1.style.color {
|
if let Some(color) = column.1.style.color_style {
|
||||||
let color = if column.1.style.is_bold {
|
|
||||||
color.bold()
|
|
||||||
} else {
|
|
||||||
color.normal()
|
|
||||||
};
|
|
||||||
|
|
||||||
output.push_str(&color.paint(&line.line).to_string());
|
output.push_str(&color.paint(&line.line).to_string());
|
||||||
} else {
|
} else {
|
||||||
output.push_str(&line.line);
|
output.push_str(&line.line);
|
||||||
@ -427,13 +705,7 @@ impl WrappedTable {
|
|||||||
for _ in 0..remainder {
|
for _ in 0..remainder {
|
||||||
output.push(' ');
|
output.push(' ');
|
||||||
}
|
}
|
||||||
if let Some(color) = column.1.style.color {
|
if let Some(color) = column.1.style.color_style {
|
||||||
let color = if column.1.style.is_bold {
|
|
||||||
color.bold()
|
|
||||||
} else {
|
|
||||||
color.normal()
|
|
||||||
};
|
|
||||||
|
|
||||||
output.push_str(&color.paint(&line.line).to_string());
|
output.push_str(&color.paint(&line.line).to_string());
|
||||||
} else {
|
} else {
|
||||||
output.push_str(&line.line);
|
output.push_str(&line.line);
|
||||||
@ -448,9 +720,17 @@ impl WrappedTable {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if column.0 < cells.len() - 1 {
|
if column.0 < cells.len() - 1 {
|
||||||
output.push(self.theme.center_vertical);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.center_vertical.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
} else if self.theme.print_right_border {
|
} else if self.theme.print_right_border {
|
||||||
output.push(self.theme.right_vertical);
|
output.push_str(
|
||||||
|
&sep_color
|
||||||
|
.paint(&self.theme.right_vertical.to_string())
|
||||||
|
.to_string(),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if lines_printed == 0 {
|
if lines_printed == 0 {
|
||||||
@ -460,20 +740,21 @@ impl WrappedTable {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fn new_print_table(&self) {
|
|
||||||
|
fn new_print_table(&self, color_hm: &HashMap<String, Style>) {
|
||||||
if self.data.is_empty() {
|
if self.data.is_empty() {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.theme.print_top_border {
|
if self.theme.print_top_border {
|
||||||
self.print_separator(SeparatorPosition::Top);
|
self.print_separator(SeparatorPosition::Top, &color_hm);
|
||||||
}
|
}
|
||||||
|
|
||||||
let skip_headers = (self.headers.len() == 2 && self.headers[1].max_width == 0)
|
let skip_headers = (self.headers.len() == 2 && self.headers[1].max_width == 0)
|
||||||
|| (self.headers.len() == 1 && self.headers[0].max_width == 0);
|
|| (self.headers.len() == 1 && self.headers[0].max_width == 0);
|
||||||
|
|
||||||
if !self.headers.is_empty() && !skip_headers {
|
if !self.headers.is_empty() && !skip_headers {
|
||||||
self.print_cell_contents(&self.headers);
|
self.print_cell_contents(&self.headers, &color_hm);
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut first_row = true;
|
let mut first_row = true;
|
||||||
@ -481,21 +762,21 @@ impl WrappedTable {
|
|||||||
for row in &self.data {
|
for row in &self.data {
|
||||||
if !first_row {
|
if !first_row {
|
||||||
if self.theme.separate_rows {
|
if self.theme.separate_rows {
|
||||||
self.print_separator(SeparatorPosition::Middle);
|
self.print_separator(SeparatorPosition::Middle, &color_hm);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
first_row = false;
|
first_row = false;
|
||||||
|
|
||||||
if self.theme.separate_header && !self.headers.is_empty() && !skip_headers {
|
if self.theme.separate_header && !self.headers.is_empty() && !skip_headers {
|
||||||
self.print_separator(SeparatorPosition::Middle);
|
self.print_separator(SeparatorPosition::Middle, &color_hm);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
self.print_cell_contents(row);
|
self.print_cell_contents(row, &color_hm);
|
||||||
}
|
}
|
||||||
|
|
||||||
if self.theme.print_bottom_border {
|
if self.theme.print_bottom_border {
|
||||||
self.print_separator(SeparatorPosition::Bottom);
|
self.print_separator(SeparatorPosition::Bottom, &color_hm);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -507,7 +788,7 @@ fn process_table(table: &Table) -> ProcessedTable {
|
|||||||
for column in row {
|
for column in row {
|
||||||
out_row.push(ProcessedCell {
|
out_row.push(ProcessedCell {
|
||||||
contents: split_sublines(&column.contents),
|
contents: split_sublines(&column.contents),
|
||||||
style: column.style.clone(),
|
style: column.style,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
processed_data.push(out_row);
|
processed_data.push(out_row);
|
||||||
@ -517,7 +798,7 @@ fn process_table(table: &Table) -> ProcessedTable {
|
|||||||
for header in &table.headers {
|
for header in &table.headers {
|
||||||
processed_headers.push(ProcessedCell {
|
processed_headers.push(ProcessedCell {
|
||||||
contents: split_sublines(&header.contents),
|
contents: split_sublines(&header.contents),
|
||||||
style: header.style.clone(),
|
style: header.style,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -554,7 +835,7 @@ fn get_max_column_widths(processed_table: &ProcessedTable) -> Vec<usize> {
|
|||||||
output
|
output
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn draw_table(table: &Table, termwidth: usize) {
|
pub fn draw_table(table: &Table, termwidth: usize, color_hm: &HashMap<String, Style>) {
|
||||||
// Remove the edges, if used
|
// Remove the edges, if used
|
||||||
let termwidth = if table.theme.print_left_border && table.theme.print_right_border {
|
let termwidth = if table.theme.print_left_border && table.theme.print_right_border {
|
||||||
termwidth - 2
|
termwidth - 2
|
||||||
@ -603,7 +884,7 @@ pub fn draw_table(table: &Table, termwidth: usize) {
|
|||||||
|
|
||||||
let wrapped_table = wrap_cells(processed_table, max_column_width);
|
let wrapped_table = wrap_cells(processed_table, max_column_width);
|
||||||
|
|
||||||
wrapped_table.new_print_table();
|
wrapped_table.new_print_table(&color_hm);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn wrap_cells(processed_table: ProcessedTable, max_column_width: usize) -> WrappedTable {
|
fn wrap_cells(processed_table: ProcessedTable, max_column_width: usize) -> WrappedTable {
|
||||||
|
@ -2,7 +2,7 @@ use crate::table::TextStyle;
|
|||||||
use std::{fmt::Display, iter::Iterator};
|
use std::{fmt::Display, iter::Iterator};
|
||||||
use unicode_width::UnicodeWidthStr;
|
use unicode_width::UnicodeWidthStr;
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone, Copy)]
|
||||||
pub enum Alignment {
|
pub enum Alignment {
|
||||||
Left,
|
Left,
|
||||||
Center,
|
Center,
|
||||||
@ -135,7 +135,6 @@ pub fn wrap<'a>(
|
|||||||
let mut first = true;
|
let mut first = true;
|
||||||
let mut max_width = 0;
|
let mut max_width = 0;
|
||||||
loop {
|
loop {
|
||||||
// println!("{:?}", current_line);
|
|
||||||
match input.next() {
|
match input.next() {
|
||||||
Some(item) => {
|
Some(item) => {
|
||||||
if !first {
|
if !first {
|
||||||
|
@ -1,9 +1,11 @@
|
|||||||
|
skip_welcome_message = true
|
||||||
disable_table_indexes = false
|
disable_table_indexes = false
|
||||||
header_align = "l"
|
|
||||||
header_color = "c"
|
|
||||||
header_bold = true
|
|
||||||
nonzero_exit_errors = true
|
nonzero_exit_errors = true
|
||||||
startup = ["alias la [path] {ls --long $path}", "alias nudown [] {fetch https://api.github.com/repos/nushell/nushell/releases | get assets | select name download_count}"]
|
startup = [
|
||||||
|
"alias la [path] {ls --long $path}",
|
||||||
|
"alias nudown [] {fetch https://api.github.com/repos/nushell/nushell/releases | get assets | select name download_count}",
|
||||||
|
"alias nuver [] {version | insert nushell_features {get features | str collect ', '} | reject features}",
|
||||||
|
]
|
||||||
table_mode = "other"
|
table_mode = "other"
|
||||||
plugin_dirs = ["D:\\Src\\GitHub\\nu-plugin-lib\\samples\\Nu.Plugin.Len\\bin\\Debug\\netcoreapp3.1"]
|
plugin_dirs = ["D:\\Src\\GitHub\\nu-plugin-lib\\samples\\Nu.Plugin.Len\\bin\\Debug\\netcoreapp3.1"]
|
||||||
pivot_mode = "auto"
|
pivot_mode = "auto"
|
||||||
@ -12,14 +14,35 @@ complete_from_path = true
|
|||||||
rm_always_trash = true
|
rm_always_trash = true
|
||||||
prompt = "echo [ $(ansi gb) $(pwd) $(ansi reset) \"(\" $(ansi cb) $(do -i { git rev-parse --abbrev-ref HEAD | trim }) $(ansi reset) \")\" $(char newline) $(ansi yb) $(date --format \"%m/%d/%Y %I:%M:%S%.3f %p\" --raw) $(ansi reset) \"> \" ] | str collect"
|
prompt = "echo [ $(ansi gb) $(pwd) $(ansi reset) \"(\" $(ansi cb) $(do -i { git rev-parse --abbrev-ref HEAD | trim }) $(ansi reset) \")\" $(char newline) $(ansi yb) $(date --format \"%m/%d/%Y %I:%M:%S%.3f %p\" --raw) $(ansi reset) \"> \" ] | str collect"
|
||||||
|
|
||||||
|
[color_config]
|
||||||
|
primitive_int = "green"
|
||||||
|
primitive_decimal = "red"
|
||||||
|
primitive_filesize = "ur"
|
||||||
|
primitive_string = "pb"
|
||||||
|
primitive_line = "yellow"
|
||||||
|
primitive_columnpath = "cyan"
|
||||||
|
primitive_pattern = "white"
|
||||||
|
primitive_boolean = "green"
|
||||||
|
primitive_date = "ru"
|
||||||
|
primitive_duration = "blue"
|
||||||
|
primitive_range = "purple"
|
||||||
|
primitive_path = "yellow"
|
||||||
|
primitive_binary = "cyan"
|
||||||
|
separator_color = "purple"
|
||||||
|
header_align = "l" # left|l, right|r, center|c
|
||||||
|
header_color = "c" # green|g, red|r, blue|u, black|b, yellow|y, purple|p, cyan|c, white|w
|
||||||
|
header_bold = true
|
||||||
|
header_style = "cb"
|
||||||
|
index_color = "rd"
|
||||||
|
|
||||||
[line_editor]
|
[line_editor]
|
||||||
max_history_size = 100000
|
max_history_size = 100000
|
||||||
history_duplicates = "alwaysadd" # alwaysadd,ignoreconsecutive
|
history_duplicates = "ignoreconsecutive" # alwaysadd,ignoreconsecutive
|
||||||
history_ignore_space = true
|
history_ignore_space = false
|
||||||
completion_type = "circular" # circular, list, fuzzy
|
completion_type = "circular" # circular, list, fuzzy
|
||||||
completion_prompt_limit = 1
|
completion_prompt_limit = 100
|
||||||
keyseq_timeout_ms = 500 # ms
|
keyseq_timeout_ms = 500 # ms
|
||||||
edit_mode = "vi" # vi, emacs
|
edit_mode = "emacs" # vi, emacs
|
||||||
auto_add_history = true
|
auto_add_history = true
|
||||||
bell_style = "audible" # audible, none, visible
|
bell_style = "audible" # audible, none, visible
|
||||||
color_mode = "enabled" # enabled, forced, disabled
|
color_mode = "enabled" # enabled, forced, disabled
|
||||||
|
Loading…
Reference in New Issue
Block a user