vizia_core/animation/
animation_state.rs

1use crate::animation::Interpolator;
2use hashbrown::HashSet;
3
4use crate::prelude::*;
5
6use super::TimingFunction;
7
8/// A keyframe in an animation state.
9#[derive(Debug, Clone)]
10pub(crate) struct Keyframe<T: Interpolator> {
11    pub time: f32,
12    pub value: T,
13    pub timing_function: TimingFunction,
14}
15
16/// Represents an animation of a property with type `T`.
17#[derive(Clone, Debug)]
18pub(crate) struct AnimationState<T: Interpolator> {
19    /// ID of the animation description.
20    pub id: Animation,
21    /// The start time of the animation.
22    pub start_time: Instant,
23    /// The duration of the animation.
24    pub duration: Duration,
25    /// The delay before the animation starts.
26    pub delay: Duration,
27    /// List of animation keyframes as (normalized time, value).
28    pub keyframes: Vec<Keyframe<T>>,
29    /// The output of value of the animation.
30    pub output: Option<T>,
31    /// Whether the animation should persist after finishing.
32    pub persistent: bool,
33    /// How far through the animation between 0.0 and 1.0.
34    pub t: f32,
35
36    pub dt: f32,
37
38    pub active: bool,
39
40    /// For transitions. The starting rule for this transition.
41    pub from_rule: usize,
42    /// For tansitions. The ending rule for this transition.
43    pub to_rule: usize,
44
45    /// List of entities connected to this animation (used when animation is removed from active list)
46    pub entities: HashSet<Entity>,
47}
48
49impl<T> AnimationState<T>
50where
51    T: Interpolator,
52{
53    /// Create a new animation state with the given [Animation] id.
54    pub(crate) fn new(id: Animation) -> Self {
55        AnimationState {
56            id,
57            start_time: Instant::now(),
58            duration: Duration::new(0, 0),
59            delay: Duration::new(0, 0),
60            keyframes: Vec::new(),
61            output: None,
62            persistent: false,
63            t: 0.0,
64            dt: 0.0,
65            active: false,
66            entities: HashSet::new(),
67            from_rule: usize::MAX,
68            to_rule: usize::MAX,
69        }
70    }
71
72    pub(crate) fn with_duration(mut self, duration: Duration) -> Self {
73        self.duration = duration;
74
75        self
76    }
77
78    pub(crate) fn with_delay(mut self, delay: Duration) -> Self {
79        self.delay = delay;
80
81        self
82    }
83
84    pub(crate) fn with_keyframe(mut self, key: Keyframe<T>) -> Self {
85        self.keyframes.push(key);
86
87        self
88    }
89
90    pub(crate) fn get_output(&self) -> Option<&T> {
91        self.output.as_ref()
92    }
93
94    pub(crate) fn play(&mut self, entity: Entity) {
95        self.active = true;
96        self.t = 0.0;
97        self.start_time = Instant::now();
98        self.entities.insert(entity);
99    }
100
101    pub(crate) fn is_transition(&self) -> bool {
102        !(self.from_rule == usize::MAX && self.to_rule == usize::MAX)
103    }
104}
105
106impl<Prop> Default for AnimationState<Prop>
107where
108    Prop: Interpolator,
109{
110    fn default() -> Self {
111        AnimationState {
112            id: Animation::null(),
113            start_time: Instant::now(),
114            duration: Duration::new(0, 0),
115            delay: Duration::new(0, 0),
116            keyframes: Vec::new(),
117            output: None,
118            persistent: true,
119            t: 0.0,
120            dt: 0.0,
121            active: false,
122            entities: HashSet::new(),
123            from_rule: usize::MAX,
124            to_rule: usize::MAX,
125        }
126    }
127}