ferroui_base/utilities/
boolean_boxes.rs1use crate::BoxedValue;
5use std::rc::Rc;
6
7crate::ferro_thread_local! {
8 static TRUE: BoxedValue = Rc::new(true);
9 static FALSE: BoxedValue = Rc::new(false);
10}
11
12pub struct BooleanBoxes;
14
15impl BooleanBoxes {
16 pub fn true_() -> BoxedValue {
18 TRUE.with(Clone::clone)
19 }
20
21 pub fn false_() -> BoxedValue {
23 FALSE.with(Clone::clone)
24 }
25
26 pub fn box_(value: bool) -> BoxedValue {
28 if value {
29 Self::true_()
30 } else {
31 Self::false_()
32 }
33 }
34
35 pub fn box_value<T: PartialEq + Clone + 'static>(value: &T) -> BoxedValue {
38 let any: &dyn std::any::Any = value;
39 match any.downcast_ref::<bool>() {
40 Some(value) => Self::box_(*value),
41 None => Rc::new(value.clone()),
42 }
43 }
44}
45
46#[cfg(test)]
47mod tests {
48 use super::*;
49
50 #[test]
51 fn booleans_share_their_boxes() {
52 assert!(Rc::ptr_eq(&BooleanBoxes::box_(true), &BooleanBoxes::true_()));
53 assert!(Rc::ptr_eq(&BooleanBoxes::box_(false), &BooleanBoxes::false_()));
54 assert!(!Rc::ptr_eq(&BooleanBoxes::box_(true), &BooleanBoxes::box_(false)));
55 assert_eq!(BooleanBoxes::box_(true).downcast_ref::<bool>(), Some(&true));
56 assert_eq!(BooleanBoxes::box_(false).downcast_ref::<bool>(), Some(&false));
57 assert!(Rc::ptr_eq(&BooleanBoxes::box_value(&true), &BooleanBoxes::box_value(&true)));
58 let (a, b) = (BooleanBoxes::box_value(&1i32), BooleanBoxes::box_value(&1i32));
59 assert!(!Rc::ptr_eq(&a, &b));
60 assert_eq!(a.downcast_ref::<i32>(), Some(&1));
61 }
62}