tawasuyu

tawasuyu/taffy

A high performance rust-powered UI layout library

Rust 1077HTML 1008Markdown 12TOML 83209 Definitions

⎇ 7e3ababdbb970183819ef07221c64d509ff39807 src/style.rs Rust · 323 lines · 7.7 KB History Who touched what raw

Remove dead Overflow type (#112) 7e3ababdb · Alice Cecile ·

1use crate::geometry::{Rect, Size};
2use crate::number::Number;
3
4#[derive(Copy, Clone, PartialEq, Eq, Debug)]
5#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
6pub enum AlignItems {
7    FlexStart,
8    FlexEnd,
9    Center,
10    Baseline,
11    Stretch,
12}
13
14impl Default for AlignItems {
15    fn default() -> Self {
16        Self::Stretch
17    }
18}
19
20#[derive(Copy, Clone, PartialEq, Eq, Debug)]
21#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
22pub enum AlignSelf {
23    Auto,
24    FlexStart,
25    FlexEnd,
26    Center,
27    Baseline,
28    Stretch,
29}
30
31impl Default for AlignSelf {
32    fn default() -> Self {
33        Self::Auto
34    }
35}
36
37#[derive(Copy, Clone, PartialEq, Eq, Debug)]
38#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
39pub enum AlignContent {
40    FlexStart,
41    FlexEnd,
42    Center,
43    Stretch,
44    SpaceBetween,
45    SpaceAround,
46}
47
48impl Default for AlignContent {
49    fn default() -> Self {
50        Self::Stretch
51    }
52}
53
54#[derive(Copy, Clone, PartialEq, Eq, Debug)]
55#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
56pub enum Display {
57    #[cfg_attr(feature = "serde", serde(rename = "flex"))]
58    Flex,
59    #[cfg_attr(feature = "serde", serde(rename = "none"))]
60    None,
61}
62
63impl Default for Display {
64    fn default() -> Self {
65        Self::Flex
66    }
67}
68
69#[derive(Copy, Clone, PartialEq, Eq, Debug)]
70#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
71pub enum FlexDirection {
72    Row,
73    Column,
74    RowReverse,
75    ColumnReverse,
76}
77
78impl Default for FlexDirection {
79    fn default() -> Self {
80        Self::Row
81    }
82}
83
84impl FlexDirection {
85    #[inline]
86    pub(crate) fn is_row(self) -> bool {
87        matches!(self, Self::Row | Self::RowReverse)
88    }
89
90    #[inline]
91    pub(crate) fn is_column(self) -> bool {
92        matches!(self, Self::Column | Self::ColumnReverse)
93    }
94
95    #[inline]
96    pub(crate) fn is_reverse(self) -> bool {
97        matches!(self, Self::RowReverse | Self::ColumnReverse)
98    }
99}
100
101#[derive(Copy, Clone, PartialEq, Eq, Debug)]
102#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
103pub enum JustifyContent {
104    FlexStart,
105    FlexEnd,
106    Center,
107    SpaceBetween,
108    SpaceAround,
109    SpaceEvenly,
110}
111
112impl Default for JustifyContent {
113    fn default() -> Self {
114        Self::FlexStart
115    }
116}
117
118#[derive(Copy, Clone, PartialEq, Eq, Debug)]
119#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
120pub enum PositionType {
121    Relative,
122    Absolute,
123}
124
125impl Default for PositionType {
126    fn default() -> Self {
127        Self::Relative
128    }
129}
130
131#[derive(Copy, Clone, PartialEq, Eq, Debug)]
132#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
133pub enum FlexWrap {
134    NoWrap,
135    Wrap,
136    WrapReverse,
137}
138
139impl Default for FlexWrap {
140    fn default() -> Self {
141        Self::NoWrap
142    }
143}
144
145#[derive(Copy, Clone, PartialEq, Debug)]
146#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
147pub enum Dimension {
148    Undefined,
149    Auto,
150    Points(f32),
151    Percent(f32),
152}
153
154impl Default for Dimension {
155    fn default() -> Self {
156        Self::Undefined
157    }
158}
159
160impl Dimension {
161    pub(crate) fn resolve(self, parent_dim: Number) -> Number {
162        match self {
163            Dimension::Points(points) => Number::Defined(points),
164            Dimension::Percent(percent) => parent_dim * percent,
165            _ => Number::Undefined,
166        }
167    }
168
169    pub(crate) fn is_defined(self) -> bool {
170        matches!(self, Dimension::Points(_) | Dimension::Percent(_))
171    }
172}
173
174impl Default for Rect<Dimension> {
175    fn default() -> Self {
176        Self { start: Default::default(), end: Default::default(), top: Default::default(), bottom: Default::default() }
177    }
178}
179
180impl Default for Size<Dimension> {
181    fn default() -> Self {
182        Self { width: Dimension::Auto, height: Dimension::Auto }
183    }
184}
185
186#[derive(Copy, Clone, PartialEq, Debug)]
187#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
188#[cfg_attr(feature = "serde", serde(default))]
189pub struct Style {
190    pub display: Display,
191    pub position_type: PositionType,
192    pub flex_direction: FlexDirection,
193    pub flex_wrap: FlexWrap,
194    pub align_items: AlignItems,
195    pub align_self: AlignSelf,
196    pub align_content: AlignContent,
197    pub justify_content: JustifyContent,
198    pub position: Rect<Dimension>,
199    pub margin: Rect<Dimension>,
200    pub padding: Rect<Dimension>,
201    pub border: Rect<Dimension>,
202    pub flex_grow: f32,
203    pub flex_shrink: f32,
204    pub flex_basis: Dimension,
205    pub size: Size<Dimension>,
206    pub min_size: Size<Dimension>,
207    pub max_size: Size<Dimension>,
208    pub aspect_ratio: Number,
209}
210
211impl Default for Style {
212    fn default() -> Self {
213        Self {
214            display: Default::default(),
215            position_type: Default::default(),
216            flex_direction: Default::default(),
217            flex_wrap: Default::default(),
218            align_items: Default::default(),
219            align_self: Default::default(),
220            align_content: Default::default(),
221            justify_content: Default::default(),
222            position: Default::default(),
223            margin: Default::default(),
224            padding: Default::default(),
225            border: Default::default(),
226            flex_grow: 0.0,
227            flex_shrink: 1.0,
228            flex_basis: Dimension::Auto,
229            size: Default::default(),
230            min_size: Default::default(),
231            max_size: Default::default(),
232            aspect_ratio: Default::default(),
233        }
234    }
235}
236
237impl Style {
238    pub(crate) fn min_main_size(&self, direction: FlexDirection) -> Dimension {
239        if direction.is_row() {
240            self.min_size.width
241        } else {
242            self.min_size.height
243        }
244    }
245
246    pub(crate) fn max_main_size(&self, direction: FlexDirection) -> Dimension {
247        if direction.is_row() {
248            self.max_size.width
249        } else {
250            self.max_size.height
251        }
252    }
253
254    pub(crate) fn main_margin_start(&self, direction: FlexDirection) -> Dimension {
255        if direction.is_row() {
256            self.margin.start
257        } else {
258            self.margin.top
259        }
260    }
261
262    pub(crate) fn main_margin_end(&self, direction: FlexDirection) -> Dimension {
263        if direction.is_row() {
264            self.margin.end
265        } else {
266            self.margin.bottom
267        }
268    }
269
270    pub(crate) fn cross_size(&self, direction: FlexDirection) -> Dimension {
271        if direction.is_row() {
272            self.size.height
273        } else {
274            self.size.width
275        }
276    }
277
278    pub(crate) fn min_cross_size(&self, direction: FlexDirection) -> Dimension {
279        if direction.is_row() {
280            self.min_size.height
281        } else {
282            self.min_size.width
283        }
284    }
285
286    pub(crate) fn max_cross_size(&self, direction: FlexDirection) -> Dimension {
287        if direction.is_row() {
288            self.max_size.height
289        } else {
290            self.max_size.width
291        }
292    }
293
294    pub(crate) fn cross_margin_start(&self, direction: FlexDirection) -> Dimension {
295        if direction.is_row() {
296            self.margin.top
297        } else {
298            self.margin.start
299        }
300    }
301
302    pub(crate) fn cross_margin_end(&self, direction: FlexDirection) -> Dimension {
303        if direction.is_row() {
304            self.margin.bottom
305        } else {
306            self.margin.end
307        }
308    }
309
310    pub(crate) fn align_self(&self, parent: &Style) -> AlignSelf {
311        if self.align_self == AlignSelf::Auto {
312            match parent.align_items {
313                AlignItems::FlexStart => AlignSelf::FlexStart,
314                AlignItems::FlexEnd => AlignSelf::FlexEnd,
315                AlignItems::Center => AlignSelf::Center,
316                AlignItems::Baseline => AlignSelf::Baseline,
317                AlignItems::Stretch => AlignSelf::Stretch,
318            }
319        } else {
320            self.align_self
321        }
322    }
323}