1use freya_core::prelude::*;
2use torin::prelude::*;
3
4#[derive(Debug, Default, PartialEq, Clone, Copy)]
5pub enum TileStatus {
6 #[default]
7 Idle,
8 Hovering,
9}
10
11#[derive(Clone, PartialEq)]
20pub struct Tile {
21 children: Vec<Element>,
22 leading: Option<Element>,
23 on_select: Option<EventHandler<()>>,
24 key: DiffKey,
25}
26
27impl KeyExt for Tile {
28 fn write_key(&mut self) -> &mut DiffKey {
29 &mut self.key
30 }
31}
32
33impl Default for Tile {
34 fn default() -> Self {
35 Self::new()
36 }
37}
38
39impl ChildrenExt for Tile {
40 fn get_children(&mut self) -> &mut Vec<Element> {
41 &mut self.children
42 }
43}
44
45impl Tile {
46 pub fn new() -> Self {
47 Self {
48 children: Vec::new(),
49 leading: None,
50 on_select: None,
51 key: DiffKey::None,
52 }
53 }
54
55 pub fn leading(mut self, leading: impl Into<Element>) -> Self {
56 self.leading = Some(leading.into());
57 self
58 }
59
60 pub fn on_select(mut self, on_select: impl Into<EventHandler<()>>) -> Self {
61 self.on_select = Some(on_select.into());
62 self
63 }
64
65 pub fn key(mut self, key: impl Into<DiffKey>) -> Self {
66 self.key = key.into();
67 self
68 }
69}
70
71impl Component for Tile {
72 fn render(&self) -> impl IntoElement {
73 let mut status = use_state(|| TileStatus::Idle);
74
75 let on_press = {
76 let on_select = self.on_select.clone();
77 move |e: Event<PressEventData>| {
78 if let Some(on_select) = &on_select {
79 e.stop_propagation();
80 on_select.call(());
81 }
82 }
83 };
84
85 let on_pointer_enter = {
86 move |_| {
87 *status.write() = TileStatus::Hovering;
88 }
89 };
90
91 let on_pointer_leave = {
92 move |_| {
93 *status.write() = TileStatus::Idle;
94 }
95 };
96
97 rect()
98 .direction(Direction::Horizontal)
99 .padding(8.)
100 .spacing(8.)
101 .cross_align(Alignment::center())
102 .on_press(on_press)
103 .on_pointer_enter(on_pointer_enter)
104 .on_pointer_leave(on_pointer_leave)
105 .maybe_child(
106 self.leading
107 .clone()
108 .map(|leading| rect().padding(Gaps::new_all(4.0)).child(leading)),
109 )
110 .children(self.children.clone())
111 }
112
113 fn render_key(&self) -> DiffKey {
114 self.key.clone().or(self.default_key())
115 }
116}