boxy_cli/
constructs.rs

1//! The main datatypes and enums used by the `Boxy` struct.
2
3use std::fmt::Display;
4
5/// Defines the border style for the text box.
6///
7/// Each variant represents a different visual style for the box borders.
8///
9/// # Examples
10///
11/// ```
12/// use boxy_cli::prelude::*;
13///
14/// let mut box1 = Boxy::new(BoxType::Double, "#00ffff");
15/// let mut box2 = Boxy::new(BoxType::Rounded, "#00ffff");
16/// let mut box3 = Boxy::new(BoxType::Bold, "#00ffff");
17/// ```
18#[derive(Debug, Default)]
19pub enum BoxType{
20    /// Simple ASCII-style box using `+` for corners and `-` for borders
21    Classic,
22    /// Default style using single-line Unicode box drawing characters
23    #[default]
24    Single,
25    /// Double horizontal lines with single vertical lines
26    DoubleHorizontal,
27    /// Double vertical lines with single horizontal lines
28    DoubleVertical,
29    /// Double lines for all borders
30    Double,
31    /// Thicker/bold lines for all borders
32    Bold,
33    /// Box with rounded corners
34    Rounded,
35    /// Box with bold corners and normal edges
36    BoldCorners
37}
38
39// Added Display Fucntion to resolve type errors in the macro
40impl Display for BoxType{
41    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
42        let str = match &self {
43            BoxType::Classic => "classic".to_string(),
44            BoxType::Single => "single".to_string(),
45            BoxType::DoubleHorizontal => "double_horizontal".to_string(),
46            BoxType::DoubleVertical => "double_vertical".to_string(),
47            BoxType::Double => "double".to_string(),
48            BoxType::Bold => "bold".to_string(),
49            BoxType::Rounded => "rounded".to_string(),
50            BoxType::BoldCorners => "bold_corners".to_string(),
51        };
52        write!(f, "{}", str)
53    }
54}
55
56/// Specifies the alignment of text within the text box or the box itself within the terminal.
57///
58/// This enum is used in two contexts:
59/// 1. To control the alignment of text segments within the box
60/// 2. To control the alignment of the entire box within the terminal width
61///
62/// # Examples
63///
64/// ```
65/// use boxy_cli::prelude::*;
66///
67/// let mut my_box = Boxy::new(BoxType::Single, "#00ffff");
68///
69/// // Center the box in the terminal
70/// my_box.set_align(BoxAlign::Center);
71///
72/// // Add a left-aligned text segment
73/// my_box.add_text_sgmt("Left aligned text", "#ffffff", BoxAlign::Left);
74///
75/// // Add a right-aligned text segment
76/// my_box.add_text_sgmt("Right aligned text", "#ffffff", BoxAlign::Right);
77/// ```
78#[derive(Debug, Default)]
79pub enum BoxAlign {
80    /// Align to the left side
81    Left,
82    /// Center alignment (default)
83    #[default]
84    Center,
85    /// Align to the right side
86    Right,
87}
88
89// Added Display Fucntion to resolve type errors in the macro
90impl Display for BoxAlign {
91    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
92        let str = match self {
93            BoxAlign::Left => "left".to_string(),
94            BoxAlign::Center => "center".to_string(),
95            BoxAlign::Right => "right".to_string(),
96        };
97        write!(f, "{}", str)
98    }
99}
100
101
102/// Represents padding values for the text box in all four directions.
103///
104/// `BoxPad` is used to specify padding between:
105/// - The box border and the contained text (internal padding)
106/// - The terminal edges and the box itself (external padding)
107///
108/// # Examples
109///
110/// ```
111/// use boxy_cli::prelude::*;
112///
113/// // Create uniform padding of 2 spaces on all sides
114/// let uniform_padding = BoxPad::uniform(2);
115///
116/// // Create custom padding for each side
117/// let custom_padding = BoxPad::from_tldr(1, 3, 1, 3); // top, left, down, right
118///
119/// // Create horizontal/vertical padding
120/// let h_v_padding = BoxPad::vh(1, 3); // 1 vertical, 3 horizontal
121/// ```
122#[derive(Debug)]
123pub struct BoxPad {
124    /// Padding at the top
125    pub top: usize,
126    /// Padding at the bottom
127    pub down: usize,
128    /// Padding on the left side
129    pub left: usize,
130    /// Padding on the right side
131    pub right: usize,
132}
133
134impl Default for BoxPad {
135    fn default() -> Self {
136        Self::new()
137    }
138}
139
140impl BoxPad {
141    /// Creates a new `BoxPad` instance with zero padding on all sides.
142    ///
143    /// # Examples
144    ///
145    /// ```
146    /// use boxy_cli::prelude::*;
147    ///
148    /// let padding = BoxPad::new();
149    /// // Equivalent to BoxPad { top: 0, down: 0, left: 0, right: 0 }
150    /// ```
151    pub fn new() -> Self {
152        BoxPad{
153            top: 0,
154            down: 0,
155            left: 0,
156            right: 0
157        }
158    }
159    /// Creates a new `BoxPad` with specific values for each side.
160    ///
161    /// The parameter order follows the mnemonic "tldr" (top, left, down, right).
162    ///
163    /// # Arguments
164    ///
165    /// * `top` - Padding at the top
166    /// * `left` - Padding on the left side
167    /// * `down` - Padding at the bottom
168    /// * `right` - Padding on the right side
169    ///
170    /// # Examples
171    ///
172    /// ```
173    /// use boxy_cli::prelude::*;
174    ///
175    /// // Create padding with different values on each side
176    /// let padding = BoxPad::from_tldr(2, 4, 2, 4);
177    /// // top: 2, left: 4, down: 2, right: 4
178    /// ```
179    pub fn from_tldr(top: usize, left: usize, down: usize, right: usize) -> Self {
180        BoxPad{
181            top,
182            down,
183            left,
184            right
185        }
186    }
187
188    /// Creates a new `BoxPad` with the same padding value on all sides.
189    ///
190    /// # Arguments
191    ///
192    /// * `pad` - The padding value to use for all sides
193    ///
194    /// # Examples
195    ///
196    /// ```
197    /// use boxy_cli::prelude::*;
198    ///
199    /// // Create uniform padding of 3 spaces on all sides
200    /// let padding = BoxPad::uniform(3);
201    /// // Equivalent to BoxPad { top: 3, down: 3, left: 3, right: 3 }
202    /// ```
203    pub fn uniform(pad: usize) -> Self{
204        BoxPad{
205            top: pad,
206            down: pad,
207            left: pad,
208            right: pad
209        }
210    }
211    /// Creates a new `BoxPad` with separate values for vertical and horizontal padding.
212    ///
213    /// This is a convenience method that applies the same padding to top/bottom
214    /// and left/right sides.
215    ///
216    /// # Arguments
217    ///
218    /// * `vertical` - Padding for top and bottom
219    /// * `horizontal` - Padding for left and right
220    ///
221    /// # Examples
222    ///
223    /// ```
224    /// use boxy_cli::prelude::*;
225    ///
226    /// // Create padding with 1 space vertically and 3 spaces horizontally
227    /// let padding = BoxPad::vh(1, 3);
228    /// // Equivalent to BoxPad { top: 1, down: 1, left: 3, right: 3 }
229    /// ```
230    pub fn vh(vertical: usize, horizontal: usize) -> Self{
231        BoxPad{
232            top: vertical,
233            down: vertical,
234            left: horizontal,
235            right: horizontal
236        }
237    }
238    /// returns the total padidng on either side. used for text wrapping and display time calculations
239    pub fn lr(&self) -> usize{
240        self.right + self.left
241    }
242}