use super::{ColumnDisplayInfo, DisplayInfos, helper::*};
use crate::{
Column, Table,
style::{ColumnConstraint, ColumnConstraint::*, Width},
};
pub fn evaluate(
table: &Table,
visible_columns: usize,
infos: &mut DisplayInfos,
column: &Column,
max_content_width: u16,
) {
match &column.constraint {
Some(ContentWidth) => {
let info = ColumnDisplayInfo::new(column, max_content_width);
infos.insert(column.index, info);
}
Some(Absolute(width)) => {
if let Some(width) = absolute_value_from_width(table, width, visible_columns) {
let width = absolute_width_with_padding(column, width);
let info = ColumnDisplayInfo::new(column, width);
infos.insert(column.index, info);
}
}
Some(Hidden) => {
let mut info = ColumnDisplayInfo::new(column, max_content_width);
info.is_hidden = true;
infos.insert(column.index, info);
}
_ => {}
}
if let Some(min_width) = min(table, &column.constraint, visible_columns) {
let max_width = max_content_width + column.padding_width();
if max_width <= min_width {
let width = absolute_width_with_padding(column, min_width);
let info = ColumnDisplayInfo::new(column, width);
infos.insert(column.index, info);
}
}
}
pub fn min(
table: &Table,
constraint: &Option<ColumnConstraint>,
visible_columns: usize,
) -> Option<u16> {
let constraint = if let Some(constraint) = constraint {
constraint
} else {
return None;
};
match constraint {
LowerBoundary(width) | Boundaries { lower: width, .. } => {
absolute_value_from_width(table, width, visible_columns)
}
_ => None,
}
}
pub fn max(
table: &Table,
constraint: &Option<ColumnConstraint>,
visible_columns: usize,
) -> Option<u16> {
let constraint = if let Some(constraint) = constraint {
constraint
} else {
return None;
};
match constraint {
UpperBoundary(width) | Boundaries { upper: width, .. } => {
absolute_value_from_width(table, width, visible_columns)
}
_ => None,
}
}
pub fn absolute_value_from_width(
table: &Table,
width: &Width,
visible_columns: usize,
) -> Option<u16> {
match width {
Width::Fixed(width) => Some(*width),
Width::Percentage(percent) => {
let table_width = table.width().map(usize::from)?;
let percent = std::cmp::min(*percent, 100u16);
let width = table_width.saturating_sub(count_border_columns(table, visible_columns));
let width = (width * usize::from(percent) / 100)
.try_into()
.unwrap_or(u16::MAX);
Some(width)
}
}
}