use crate::layout::{DialogItem, GenericLayout, layout_dialog};
use ratatui_core::layout::{Constraint, Flex, Layout, Position, Rect, Size};
use ratatui_widgets::block::Padding;
#[derive(Debug, Default, Clone)]
pub struct LayoutOuter {
pub left: Option<Constraint>,
pub top: Option<Constraint>,
pub right: Option<Constraint>,
pub bottom: Option<Constraint>,
pub position: Option<Position>,
pub width: Option<Constraint>,
pub height: Option<Constraint>,
pub size: Option<Size>,
}
impl LayoutOuter {
pub fn new() -> Self {
Self::default()
}
pub fn left(mut self, left: Constraint) -> Self {
self.left = Some(left);
self
}
pub fn top(mut self, top: Constraint) -> Self {
self.top = Some(top);
self
}
pub fn right(mut self, right: Constraint) -> Self {
self.right = Some(right);
self
}
pub fn bottom(mut self, bottom: Constraint) -> Self {
self.bottom = Some(bottom);
self
}
pub fn position(mut self, pos: Position) -> Self {
self.position = Some(pos);
self
}
pub fn width(mut self, width: Constraint) -> Self {
self.width = Some(width);
self
}
pub fn height(mut self, height: Constraint) -> Self {
self.height = Some(height);
self
}
pub fn size(mut self, size: Size) -> Self {
self.size = Some(size);
self
}
#[inline]
pub fn layout(&self, area: Rect) -> Rect {
let mut hor = [
Constraint::Length(0),
Constraint::Fill(1),
Constraint::Length(0),
];
let mut ver = [
Constraint::Length(0),
Constraint::Fill(1),
Constraint::Length(0),
];
if let Some(left) = self.left {
hor[0] = left;
}
if let Some(top) = self.top {
ver[0] = top;
}
if let Some(right) = self.right {
hor[2] = right;
}
if let Some(bottom) = self.bottom {
ver[2] = bottom;
}
if let Some(pos) = self.position {
ver[0] = Constraint::Length(pos.y);
hor[0] = Constraint::Length(pos.x);
}
if let Some(width) = self.width {
hor[1] = width;
hor[2] = Constraint::Fill(1);
}
if let Some(height) = self.height {
ver[1] = height;
ver[2] = Constraint::Fill(1);
}
if let Some(size) = self.size {
ver[1] = Constraint::Length(size.height);
ver[2] = Constraint::Fill(1);
hor[1] = Constraint::Length(size.width);
hor[2] = Constraint::Fill(1);
}
let h_layout = Layout::horizontal(hor).split(area);
let v_layout = Layout::vertical(ver).split(h_layout[1]);
v_layout[1]
}
#[inline]
pub fn layout_dialog<const N: usize>(
&self,
area: Rect,
padding: Padding,
buttons: [Constraint; N],
button_spacing: u16,
button_flex: Flex,
) -> GenericLayout<DialogItem> {
let inner = self.layout(area);
layout_dialog(inner, padding, buttons, button_spacing, button_flex)
}
}