1use libm::round;
2
3use crate::{
4 GetXY, GetZ, MValue, Point, Point3D, PointOrPoint3D, PrimitiveValue, STPoint, Value,
5 ValuePrimitive, ValuePrimitiveType, ValueType, VectorPoint,
6};
7
8pub trait Interpolate {
10 fn interpolate(&self, other: &Self, t: f64) -> Self;
12}
13impl Interpolate for u64 {
14 fn interpolate(&self, other: &Self, t: f64) -> Self {
15 round((*self as f64) + ((*other as f64) - (*self as f64)) * t) as u64
16 }
17}
18impl Interpolate for i64 {
19 fn interpolate(&self, other: &Self, t: f64) -> Self {
20 round((*self as f64) + ((*other as f64) - (*self as f64)) * t) as i64
21 }
22}
23impl Interpolate for f32 {
24 fn interpolate(&self, other: &Self, t: f64) -> Self {
25 ((*self as f64) + ((*other as f64) - (*self as f64)) * t) as f32
26 }
27}
28impl Interpolate for f64 {
29 fn interpolate(&self, other: &Self, t: f64) -> Self {
30 self + (other - self) * t
31 }
32}
33impl<M: Interpolate> Interpolate for Option<M> {
34 fn interpolate(&self, other: &Self, t: f64) -> Self {
35 match (self, other) {
36 (Some(a), Some(b)) => Some(a.interpolate(b, t)),
37 _ => None,
38 }
39 }
40}
41impl Interpolate for Point {
42 fn interpolate(&self, other: &Self, t: f64) -> Self {
43 Point(self.x().interpolate(&other.x(), t), self.y().interpolate(&other.y(), t))
44 }
45}
46impl Interpolate for Point3D {
47 fn interpolate(&self, other: &Self, t: f64) -> Self {
48 Point3D(
49 self.0.interpolate(&other.0, t),
50 self.1.interpolate(&other.1, t),
51 self.2.interpolate(&other.2, t),
52 )
53 }
54}
55impl Interpolate for PointOrPoint3D {
56 fn interpolate(&self, other: &Self, t: f64) -> Self {
57 PointOrPoint3D(
58 self.x().interpolate(&other.x(), t),
59 self.y().interpolate(&other.y(), t),
60 self.z().interpolate(&other.z(), t),
61 )
62 }
63}
64impl<M: Interpolate> Interpolate for STPoint<M> {
65 fn interpolate(&self, other: &Self, t: f64) -> Self {
66 Self {
67 face: self.face,
68 s: self.s.interpolate(&other.s, t),
69 t: self.t.interpolate(&other.t, t),
70 z: self.z.interpolate(&other.z, t),
71 m: self.m.interpolate(&other.m, t),
72 }
73 }
74}
75impl<M: Interpolate + Clone> Interpolate for VectorPoint<M> {
76 fn interpolate(&self, other: &Self, t: f64) -> Self {
77 VectorPoint {
78 x: self.x.interpolate(&other.x, t),
79 y: self.y.interpolate(&other.y, t),
80 z: self.z.interpolate(&other.z, t),
81 m: self.m.interpolate(&other.m, t),
82 t: self.t.interpolate(&other.t, t),
83 }
84 }
85}
86impl Interpolate for Value {
87 fn interpolate(&self, other: &Self, t: f64) -> Self {
88 let mut res = MValue::new();
89
90 for (a, b) in self.iter().zip(other.iter()) {
92 res.insert(a.0.clone(), a.1.interpolate(b.1, t));
93 }
94 for (k, v) in self.iter() {
96 if !res.contains_key(k) {
97 res.insert(k.clone(), v.clone());
98 }
99 }
100 for (k, v) in other.iter() {
102 if !res.contains_key(k) {
103 res.insert(k.clone(), v.clone());
104 }
105 }
106
107 res
108 }
109}
110impl Interpolate for ValueType {
111 fn interpolate(&self, other: &Self, t: f64) -> Self {
112 match (self, other) {
113 (ValueType::Primitive(a), ValueType::Primitive(b)) => {
114 ValueType::Primitive(a.interpolate(b, t))
115 }
116 (ValueType::Array(a), ValueType::Array(b)) => {
117 ValueType::Array(a.iter().zip(b.iter()).map(|(a, b)| a.interpolate(b, t)).collect())
118 }
119 (ValueType::Nested(a), ValueType::Nested(b)) => ValueType::Nested(a.interpolate(b, t)),
120 _ => ValueType::Primitive(PrimitiveValue::Null),
121 }
122 }
123}
124impl Interpolate for ValuePrimitiveType {
125 fn interpolate(&self, other: &Self, t: f64) -> Self {
126 match (self, other) {
127 (ValuePrimitiveType::Primitive(a), ValuePrimitiveType::Primitive(b)) => {
128 ValuePrimitiveType::Primitive(a.interpolate(b, t))
129 }
130 (ValuePrimitiveType::NestedPrimitive(a), ValuePrimitiveType::NestedPrimitive(b)) => {
131 ValuePrimitiveType::NestedPrimitive(a.interpolate(b, t))
132 }
133 _ => ValuePrimitiveType::Primitive(PrimitiveValue::Null),
134 }
135 }
136}
137impl Interpolate for ValuePrimitive {
138 fn interpolate(&self, other: &Self, t: f64) -> Self {
139 let mut res = ValuePrimitive::new();
140
141 for (a, b) in self.iter().zip(other.iter()) {
143 res.insert(a.0.clone(), a.1.interpolate(b.1, t));
144 }
145 for (k, v) in self.iter() {
147 if !res.contains_key(k) {
148 res.insert(k.clone(), v.clone());
149 }
150 }
151 for (k, v) in other.iter() {
153 if !res.contains_key(k) {
154 res.insert(k.clone(), v.clone());
155 }
156 }
157
158 res
159 }
160}
161impl Interpolate for PrimitiveValue {
162 fn interpolate(&self, other: &Self, t: f64) -> Self {
163 match (self, other) {
164 (PrimitiveValue::U64(a), PrimitiveValue::U64(b)) => {
165 PrimitiveValue::U64(a.interpolate(b, t))
166 }
167 (PrimitiveValue::I64(a), PrimitiveValue::I64(b)) => {
168 PrimitiveValue::I64(a.interpolate(b, t))
169 }
170 (PrimitiveValue::F32(a), PrimitiveValue::F32(b)) => {
171 PrimitiveValue::F32(a.interpolate(b, t))
172 }
173 (PrimitiveValue::F64(a), PrimitiveValue::F64(b)) => {
174 PrimitiveValue::F64(a.interpolate(b, t))
175 }
176 (PrimitiveValue::String(a), PrimitiveValue::String(b)) => {
177 PrimitiveValue::String(if t <= 0.5 { a.clone() } else { b.clone() })
178 }
179 (PrimitiveValue::Bool(a), PrimitiveValue::Bool(b)) => {
180 PrimitiveValue::Bool(if t <= 0.5 { *a } else { *b })
181 }
182 _ => self.clone(),
183 }
184 }
185}