1use json::ToJson;
2use serde_json::json;
3
4use crate::{
5 geometry::{rect::RectF, vector::Vector2F},
6 json, AfterLayoutContext, DebugContext, Element, ElementBox, Event, EventContext,
7 LayoutContext, PaintContext, SizeConstraint,
8};
9
10pub struct ConstrainedBox {
11 child: ElementBox,
12 constraint: SizeConstraint,
13}
14
15impl ConstrainedBox {
16 pub fn new(child: ElementBox) -> Self {
17 Self {
18 child,
19 constraint: SizeConstraint {
20 min: Vector2F::zero(),
21 max: Vector2F::splat(f32::INFINITY),
22 },
23 }
24 }
25
26 pub fn with_max_width(mut self, max_width: f32) -> Self {
27 self.constraint.max.set_x(max_width);
28 self
29 }
30
31 pub fn with_max_height(mut self, max_height: f32) -> Self {
32 self.constraint.max.set_y(max_height);
33 self
34 }
35
36 pub fn with_height(mut self, height: f32) -> Self {
37 self.constraint.min.set_y(height);
38 self.constraint.max.set_y(height);
39 self
40 }
41}
42
43impl Element for ConstrainedBox {
44 type LayoutState = ();
45 type PaintState = ();
46
47 fn layout(
48 &mut self,
49 mut constraint: SizeConstraint,
50 ctx: &mut LayoutContext,
51 ) -> (Vector2F, Self::LayoutState) {
52 constraint.min = constraint.min.max(self.constraint.min);
53 constraint.max = constraint.max.min(self.constraint.max);
54 let size = self.child.layout(constraint, ctx);
55 (size, ())
56 }
57
58 fn after_layout(
59 &mut self,
60 _: Vector2F,
61 _: &mut Self::LayoutState,
62 ctx: &mut AfterLayoutContext,
63 ) {
64 self.child.after_layout(ctx);
65 }
66
67 fn paint(
68 &mut self,
69 bounds: RectF,
70 _: &mut Self::LayoutState,
71 ctx: &mut PaintContext,
72 ) -> Self::PaintState {
73 self.child.paint(bounds.origin(), ctx);
74 }
75
76 fn dispatch_event(
77 &mut self,
78 event: &Event,
79 _: RectF,
80 _: &mut Self::LayoutState,
81 _: &mut Self::PaintState,
82 ctx: &mut EventContext,
83 ) -> bool {
84 self.child.dispatch_event(event, ctx)
85 }
86
87 fn debug(
88 &self,
89 _: RectF,
90 _: &Self::LayoutState,
91 _: &Self::PaintState,
92 ctx: &DebugContext,
93 ) -> json::Value {
94 json!({"type": "ConstrainedBox", "constraint": self.constraint.to_json(), "child": self.child.debug(ctx)})
95 }
96}