Skip to main content

aura_anim_core/
presence.rs

1//! Animated visibility lifecycle management.
2
3use crate::{
4    runtime::{Motion, MotionRuntime},
5    timing::Timing,
6    traits::{Animatable, Animation},
7};
8
9/// Coordinates mounting and visibility around enter and exit animations.
10///
11/// # Examples
12///
13/// ```
14/// use aura_anim_core::{MotionRuntime, Presence, timing::Timing};
15/// use std::time::Duration;
16///
17/// let mut runtime = MotionRuntime::new();
18/// let mut presence = Presence::new(&mut runtime, 0.0_f32, 1.0, Timing::new(100.0));
19///
20/// presence.show(&mut runtime);
21/// assert!(presence.is_mounted());
22/// runtime.tick(Duration::from_millis(100));
23/// assert_eq!(*presence.value(&runtime), 1.0);
24///
25/// presence.hide(&mut runtime);
26/// runtime.tick(Duration::from_millis(100));
27/// presence.sync(&runtime);
28/// assert!(!presence.is_mounted());
29/// ```
30pub struct Presence<T: Animatable> {
31    motion: Motion<T>,
32    visible: T,
33    hidden: T,
34    mounted: bool,
35    shown: bool,
36}
37
38impl<T: Animatable> Presence<T> {
39    /// Creates a hidden, unmounted presence controller.
40    #[must_use]
41    pub fn new(runtime: &mut MotionRuntime, hidden: T, visible: T, timing: Timing) -> Self {
42        Self {
43            motion: runtime.motion_with(hidden.clone(), timing),
44            visible,
45            hidden,
46            mounted: false,
47            shown: false,
48        }
49    }
50
51    /// Returns the runtime motion controlled by this presence value.
52    pub fn motion(&self) -> Motion<T> {
53        self.motion
54    }
55
56    /// Returns the current animated value.
57    #[must_use]
58    pub fn value<'a>(&self, runtime: &'a MotionRuntime) -> &'a T {
59        self.motion.value_ref(runtime)
60    }
61
62    /// Returns whether the associated content should be mounted.
63    #[must_use]
64    pub const fn is_mounted(&self) -> bool {
65        self.mounted
66    }
67
68    /// Returns whether the presence target is visible.
69    #[must_use]
70    pub const fn is_visible(&self) -> bool {
71        self.shown
72    }
73
74    /// Mounts the content and transitions toward the visible value.
75    pub fn show(&mut self, runtime: &mut MotionRuntime) {
76        self.mounted = true;
77        self.shown = true;
78        self.motion.transition_to(self.visible.clone(), runtime);
79    }
80
81    /// Transitions toward the hidden value.
82    pub fn hide(&mut self, runtime: &mut MotionRuntime) {
83        self.shown = false;
84        self.motion.transition_to(self.hidden.clone(), runtime);
85    }
86
87    /// Mounts the content and plays a custom enter animation.
88    pub fn show_with(&mut self, animation: impl Animation<T>, runtime: &mut MotionRuntime) {
89        self.mounted = true;
90        self.shown = true;
91        self.motion.play(animation, runtime);
92    }
93
94    /// Plays a custom exit animation.
95    pub fn hide_with(&mut self, animation: impl Animation<T>, runtime: &mut MotionRuntime) {
96        self.shown = false;
97        self.motion.play(animation, runtime);
98    }
99
100    /// Unmounts hidden content after its animation completes.
101    pub fn sync(&mut self, runtime: &MotionRuntime) {
102        if !self.shown && self.motion.is_completed(runtime) {
103            self.mounted = false;
104        }
105    }
106}