intuitive/components/
centered.rs

1use crate::{
2  component,
3  components::{children::Children, Embed, Empty, HStack, VStack},
4  event::KeyHandler,
5  on_key, render,
6};
7
8/// A component for centering its contents.
9///
10/// For example,
11/// ```rust
12/// # use intuitive::{component, components::{Centered, Section}, render};
13/// #
14/// #[component(Root)]
15/// fn render() {
16///   render! {
17///     Centered() {
18///       Section(title: "I'm centered")
19///     }
20///   }
21/// }
22/// ```
23#[component(Centered)]
24pub fn render(children: Children<1>, on_key: KeyHandler) {
25  let child = children[0].render();
26
27  let on_key = on_key! { [child, on_key]
28    event => on_key.handle_or(event, |event| child.on_key(event))
29  };
30
31  render! {
32    VStack(on_key) {
33      Empty()
34      HStack() {
35        Empty()
36        Embed(content: child)
37        Empty()
38      }
39      Empty()
40    }
41  }
42}
43
44#[cfg(test)]
45mod tests {
46  use super::*;
47  use crate::{components::Text, element::Any as AnyElement, state::State};
48
49  #[test]
50  fn centered_forwards_keys() {
51    pub use crate::event::{KeyCode::*, KeyEvent, KeyModifiers};
52
53    let called = State::new(false);
54    let on_key_called = called.clone();
55
56    let on_key = on_key! {
57      KeyEvent { code: Esc, .. } => on_key_called.set(true),
58    };
59
60    let centered: AnyElement = render! {
61      Centered() {
62        Text(on_key)
63      }
64    };
65
66    centered.on_key(KeyEvent::new(Esc, KeyModifiers::NONE));
67
68    assert_eq!(called.get(), true);
69  }
70}