tabled/settings/width/justify.rs
1//! This module contains [`Justify`] structure, used to set an exact width to each column.
2
3use crate::{
4 grid::{
5 config::{ColoredConfig, Entity},
6 records::{ExactRecords, IntoRecords, PeekableRecords, Records, RecordsMut},
7 },
8 settings::{
9 measurement::{Max, Measurement, Min},
10 CellOption, TableOption, Width,
11 },
12};
13
14/// Justify sets all columns widths to the set value.
15///
16/// Be aware that it doesn't consider padding.
17/// So if you want to set a exact width you might need to use [`Padding`] to set it to 0.
18///
19/// ## Examples
20///
21/// ```
22/// use tabled::{Table, settings::{Width, Style, object::Segment, Padding, Modify}};
23///
24/// let data = ["Hello", "World", "!"];
25///
26/// let table = Table::new(&data)
27/// .with(Style::markdown())
28/// .with(Modify::new(Segment::all()).with(Padding::zero()))
29/// .with(Width::justify(3));
30/// ```
31///
32/// [`Max`] usage to justify by a max column width.
33///
34/// ```
35/// use tabled::{Table, settings::{width::Justify, Style}};
36///
37/// let data = ["Hello", "World", "!"];
38///
39/// let table = Table::new(&data)
40/// .with(Style::markdown())
41/// .with(Justify::max());
42/// ```
43///
44/// [`Padding`]: crate::settings::Padding
45#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord)]
46pub struct Justify<W> {
47 width: W,
48}
49
50impl<W> Justify<W>
51where
52 W: Measurement<Width>,
53{
54 /// Creates a new [`Justify`] instance.
55 ///
56 /// Be aware that [`Padding`] is not considered when comparing the width.
57 ///
58 /// [`Padding`]: crate::settings::Padding
59 pub fn new(width: W) -> Self {
60 Self { width }
61 }
62}
63
64impl Justify<Max> {
65 /// Creates a new Justify instance with a Max width used as a value.
66 pub fn max() -> Self {
67 Self { width: Max }
68 }
69}
70
71impl Justify<Min> {
72 /// Creates a new Justify instance with a Min width used as a value.
73 pub fn min() -> Self {
74 Self { width: Min }
75 }
76}
77
78impl<R, D, W> TableOption<R, ColoredConfig, D> for Justify<W>
79where
80 W: Measurement<Width>,
81 R: Records + ExactRecords + PeekableRecords + RecordsMut<String>,
82 for<'a> &'a R: Records,
83 for<'a> <<&'a R as Records>::Iter as IntoRecords>::Cell: AsRef<str>,
84{
85 fn change(self, records: &mut R, cfg: &mut ColoredConfig, _: &mut D) {
86 let width = self.width.measure(&*records, cfg);
87
88 let count_rows = records.count_rows();
89 let count_columns = records.count_columns();
90
91 for row in 0..count_rows {
92 for col in 0..count_columns {
93 let pos = Entity::Cell(row, col);
94 CellOption::change(Width::increase(width), records, cfg, pos);
95 CellOption::change(Width::truncate(width), records, cfg, pos);
96 }
97 }
98 }
99}
100
101// TODO: explore whether it's actually usefull
102// Maybe rework it?