1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
use std::collections::HashMap;
use std::ops::Deref;
use crate::serialize_hashmap_deterministic;
pub use self::bone_keyframe::*;
pub use self::sorted_keyframes::*;
mod bone_keyframe;
mod sample;
mod sorted_keyframes;
#[derive(Debug, PartialEq, Serialize, Deserialize, Default, Clone)]
pub struct BoneKeyframes {
frame_range_inclusive: Option<(u16, u16)>,
#[serde(serialize_with = "serialize_hashmap_deterministic")]
keyframes: HashMap<u8, SortedKeyframes>,
}
impl BoneKeyframes {
pub fn new() -> BoneKeyframes {
Self::default()
}
#[cfg(test)]
pub fn new_with_keyframes(mut keyframes: Vec<BoneKeyframe>) -> Self {
use crate::test_util::BONE_IDX;
let mut map = HashMap::new();
map.insert(BONE_IDX, SortedKeyframes::new(keyframes));
let mut keyframes = BoneKeyframes {
frame_range_inclusive: None,
keyframes: map,
};
keyframes.update_frame_range_inclusive();
keyframes
}
pub fn smallest_frame(&self) -> Option<u16> {
Some(self.frame_range_inclusive?.0)
}
pub fn largest_frame(&self) -> Option<u16> {
Some(self.frame_range_inclusive?.1)
}
pub fn frame_duration(&self) -> Option<u16> {
Some(self.largest_frame()? - self.smallest_frame()?)
}
pub fn frame_range_inclusive(&self) -> Option<(u16, u16)> {
self.frame_range_inclusive
}
pub fn insert_bone_keyframe(&mut self, bone_idx: u8, keyframe: BoneKeyframe) {
let keyframes = self.keyframes.entry(bone_idx).or_default();
keyframes.push(keyframe);
keyframes.sort_by(|a, b| a.frame().cmp(&b.frame()));
self.update_frame_range_inclusive();
}
fn update_frame_range_inclusive(&mut self) {
let mut frame_range_inclusive = None;
let mut frames_found = false;
let mut smallest_frame = u16::max_value();
let mut largest_frame = 0;
for (_, keyframes) in self.keyframes.iter_mut() {
for keyframe in keyframes.iter() {
frames_found = true;
smallest_frame = smallest_frame.min(keyframe.frame());
largest_frame = largest_frame.max(keyframe.frame());
}
keyframes.sort_by(|a, b| a.frame().cmp(&b.frame()));
}
if frames_found {
frame_range_inclusive = Some((smallest_frame, largest_frame));
}
self.frame_range_inclusive = frame_range_inclusive;
}
}
impl Deref for BoneKeyframes {
type Target = HashMap<u8, SortedKeyframes>;
fn deref(&self) -> &Self::Target {
&self.keyframes
}
}
impl BoneKeyframes {
pub(crate) fn keyframes_mut(&mut self) -> &mut HashMap<u8, SortedKeyframes> {
&mut self.keyframes
}
}