mirror of
https://github.com/nushell/nushell
synced 2024-12-27 05:23:11 +00:00
Merge pull request #297 from jonathandturner/table_constraint_solve
Switch to constraint solving the table
This commit is contained in:
commit
37000c7c31
2 changed files with 65 additions and 17 deletions
|
@ -72,13 +72,14 @@ impl TableView {
|
|||
current_row_max = entries[row][head].len();
|
||||
}
|
||||
}
|
||||
max_per_column.push(current_row_max);
|
||||
max_per_column.push(std::cmp::max(current_row_max, headers[head].len()));
|
||||
}
|
||||
|
||||
let termwidth = textwrap::termwidth() - 9;
|
||||
// Different platforms want different amounts of buffer, not sure why
|
||||
let termwidth = std::cmp::max(textwrap::termwidth(), 20);
|
||||
|
||||
// Make sure we have enough space for the columns we have
|
||||
let max_num_of_columns = termwidth / 7;
|
||||
let max_num_of_columns = termwidth / 10;
|
||||
|
||||
// If we have too many columns, truncate the table
|
||||
if max_num_of_columns < headers.len() {
|
||||
|
@ -93,29 +94,77 @@ impl TableView {
|
|||
}
|
||||
}
|
||||
|
||||
// Measure how big our columns need to be
|
||||
let max_naive_column_width = termwidth / headers.len();
|
||||
// Measure how big our columns need to be (accounting for separators also)
|
||||
let max_naive_column_width = (termwidth - 3 * (headers.len() - 1)) / headers.len();
|
||||
|
||||
// Measure how much space we have once we subtract off the columns who are small enough
|
||||
let mut num_overages = 0;
|
||||
let mut underage_sum = 0;
|
||||
let mut overage_separator_sum = 0;
|
||||
for idx in 0..headers.len() {
|
||||
if max_per_column[idx] > max_naive_column_width {
|
||||
num_overages += 1;
|
||||
if idx != (headers.len() - 1) {
|
||||
overage_separator_sum += 3;
|
||||
}
|
||||
if idx == 0 {
|
||||
overage_separator_sum += 1;
|
||||
}
|
||||
} else {
|
||||
underage_sum += max_per_column[idx];
|
||||
// if column isn't last, add 3 for its separator
|
||||
if idx != (headers.len() - 1) {
|
||||
underage_sum += 3;
|
||||
}
|
||||
if idx == 0 {
|
||||
underage_sum += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// This gives us the max column width
|
||||
let max_column_width = if num_overages > 0 {
|
||||
(termwidth - 1 - underage_sum - overage_separator_sum) / num_overages
|
||||
} else {
|
||||
99999
|
||||
};
|
||||
|
||||
// This width isn't quite right, as we're rounding off some of our space
|
||||
num_overages = 0;
|
||||
overage_separator_sum = 0;
|
||||
for idx in 0..headers.len() {
|
||||
if max_per_column[idx] > max_naive_column_width {
|
||||
if max_per_column[idx] <= max_column_width {
|
||||
underage_sum += max_per_column[idx];
|
||||
// if column isn't last, add 3 for its separator
|
||||
if idx != (headers.len() - 1) {
|
||||
underage_sum += 3;
|
||||
}
|
||||
if idx == 0 {
|
||||
underage_sum += 1;
|
||||
}
|
||||
} else {
|
||||
// Column is still too large, so let's count it
|
||||
num_overages += 1;
|
||||
if idx != (headers.len() - 1) {
|
||||
overage_separator_sum += 3;
|
||||
}
|
||||
if idx == 0 {
|
||||
overage_separator_sum += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
// This should give us the final max column width
|
||||
let max_column_width = if num_overages > 0 {
|
||||
(termwidth - 1 - underage_sum - overage_separator_sum) / num_overages
|
||||
} else {
|
||||
99999
|
||||
};
|
||||
|
||||
// Wrap cells as needed
|
||||
for head in 0..headers.len() {
|
||||
if max_per_column[head] > max_naive_column_width {
|
||||
let max_column_width = (termwidth - underage_sum) / num_overages;
|
||||
//Account for the separator
|
||||
let max_column_width = if max_column_width > 1 {
|
||||
max_column_width - 2
|
||||
} else {
|
||||
max_column_width
|
||||
};
|
||||
headers[head] = fill(&headers[head], max_column_width);
|
||||
for row in 0..entries.len() {
|
||||
entries[row][head] = fill(&entries[row][head], max_column_width);
|
||||
|
|
|
@ -5,7 +5,6 @@ use crate::object::TaggedDictBuilder;
|
|||
use crate::parser::{hir, Operator};
|
||||
use crate::prelude::*;
|
||||
use crate::Text;
|
||||
use ansi_term::Color;
|
||||
use chrono::{DateTime, Utc};
|
||||
use chrono_humanize::Humanize;
|
||||
use derive_new::new;
|
||||
|
@ -87,15 +86,15 @@ impl Primitive {
|
|||
|
||||
pub fn format(&self, field_name: Option<&String>) -> String {
|
||||
match self {
|
||||
Primitive::Nothing => format!("{}", Color::Black.bold().paint("-")),
|
||||
Primitive::BeginningOfStream => format!("{}", Color::Black.bold().paint("-")),
|
||||
Primitive::EndOfStream => format!("{}", Color::Black.bold().paint("-")),
|
||||
Primitive::Nothing => String::new(),
|
||||
Primitive::BeginningOfStream => String::new(),
|
||||
Primitive::EndOfStream => String::new(),
|
||||
Primitive::Path(p) => format!("{}", p.display()),
|
||||
Primitive::Bytes(b) => {
|
||||
let byte = byte_unit::Byte::from_bytes(*b as u128);
|
||||
|
||||
if byte.get_bytes() == 0u128 {
|
||||
return Color::Black.bold().paint("Empty".to_string()).to_string();
|
||||
return "<empty>".to_string();
|
||||
}
|
||||
|
||||
let byte = byte.get_appropriate_unit(false);
|
||||
|
|
Loading…
Reference in a new issue