more granular control over wrapping

This commit is contained in:
griffi-gh 2024-03-25 12:57:45 +01:00
parent f6ff5e7269
commit adc5cb5f3b
2 changed files with 48 additions and 11 deletions

View file

@ -4,10 +4,10 @@ use derive_setters::Setters;
use glam::{Vec2, vec2}; use glam::{Vec2, vec2};
use crate::{ use crate::{
element::{ElementList, MeasureContext, ProcessContext, UiElement}, element::{ElementList, MeasureContext, ProcessContext, UiElement},
layout::{Alignment, Alignment2d, Direction, LayoutInfo, Size, Size2d},
frame::{Frame, FrameRect}, frame::{Frame, FrameRect},
layout::{Alignment, Alignment2d, Direction, LayoutInfo, Size, Size2d, WrapBehavior},
measure::{Hints, Response}, measure::{Hints, Response},
rect::{Sides, FillColor}, rect::Sides,
}; };
//XXX: add Order/Direction::Forward/Reverse or sth? //XXX: add Order/Direction::Forward/Reverse or sth?
@ -52,13 +52,9 @@ pub struct Container {
#[setters(skip)] #[setters(skip)]
pub background_frame: Box<dyn Frame>, pub background_frame: Box<dyn Frame>,
/// Set this to `true` to allow the elements wrap automatically /// Controls if wrapping is enabled
/// #[setters(into)]
/// Disabling/enabling this does not affect explicit wrapping\ pub wrap: WrapBehavior,
/// (for example, `Br`, or any other element with `should_wrap` set to `true`)
///
/// This is an experimental feature and may not work as expected
pub wrap: bool,
/// List of children elements /// List of children elements
#[setters(skip)] #[setters(skip)]
@ -86,7 +82,7 @@ impl Default for Container {
padding: Sides::all(0.), padding: Sides::all(0.),
align: Alignment2d::default(), align: Alignment2d::default(),
background_frame: Box::<FrameRect>::default(), background_frame: Box::<FrameRect>::default(),
wrap: false, wrap: WrapBehavior::Allow,
children: ElementList(Vec::new()), children: ElementList(Vec::new()),
} }
} }
@ -189,7 +185,8 @@ impl UiElement for Container {
}; };
//Wrap the element if it exceeds container's size and is not the first element in the line //Wrap the element if it exceeds container's size and is not the first element in the line
if ((self.wrap && (end_pos_pri > max_line_pri)) || measure.should_wrap) && (line_element_count > 0) { let should_wrap_overflow = self.wrap.is_enabled() && (end_pos_pri > max_line_pri);
if self.wrap.is_allowed() && line_element_count > 0 && (measure.should_wrap || should_wrap_overflow) {
// >>>>>>> WRAP THAT B*TCH! // >>>>>>> WRAP THAT B*TCH!
//Negate the leftover gap from the previous element //Negate the leftover gap from the previous element

View file

@ -2,6 +2,46 @@
use glam::{vec2, Vec2}; use glam::{vec2, Vec2};
/// Controls wrapping behavior of elements
#[derive(Clone, Copy, PartialEq, Eq, Debug, PartialOrd, Ord, Default)]
pub enum WrapBehavior {
/// No wrapping is allowed, even if explicit line breaks is requested by the element
Disable = 0,
/// Allow wrapping if the element explicitly requests it (default behavior)
#[default]
Allow = 1,
/// Elements will be wrapped automatically when they reach the maximum width/height of the container
Enable = 2,
}
impl From<bool> for WrapBehavior {
#[inline]
fn from(value: bool) -> Self {
match value {
true => Self::Enable,
false => Self::Disable,
}
}
}
impl WrapBehavior {
/// Check if wrapping is allowed for the element
#[inline]
pub fn is_allowed(&self) -> bool {
*self != Self::Disable
}
/// Check if wrapping is enabled for the element
///
/// (Wrapping will be done automatically when the element reaches the maximum width/height)
#[inline]
pub fn is_enabled(&self) -> bool {
*self == Self::Enable
}
}
/// Alignment along a single axis /// Alignment along a single axis
#[derive(Clone, Copy, PartialEq, Eq, Debug, Default, PartialOrd, Ord)] #[derive(Clone, Copy, PartialEq, Eq, Debug, Default, PartialOrd, Ord)]
pub enum Alignment { pub enum Alignment {