| 189 pub struct OnCube { |
189 pub struct OnCube { |
| 190 face : Face, |
190 face : Face, |
| 191 point : Point, |
191 point : Point, |
| 192 } |
192 } |
| 193 |
193 |
| 194 impl ManifoldPoint for OnCube { |
194 impl OnCube { |
| 195 type Tangent = Point; |
195 /// Calculates both the logarithmic map and distance to another point |
| 196 |
196 fn log_dist(&self, other : &Self) -> (<Self as ManifoldPoint>::Tangent, f64) { |
| 197 fn exp(&self, tangent : &Self::Tangent) -> Self { |
|
| 198 let mut face = self.face; |
|
| 199 let mut point = self.point + tangent; |
|
| 200 loop { |
|
| 201 let next_face = face.find_crossing(&point); |
|
| 202 if next_face == face { |
|
| 203 break |
|
| 204 } |
|
| 205 point = next_face.convert_adjacent(face, &point).unwrap(); |
|
| 206 face = next_face; |
|
| 207 } |
|
| 208 OnCube { face, point } |
|
| 209 } |
|
| 210 |
|
| 211 fn log(&self, other : &Self) -> Self::Tangent { |
|
| 212 let mut best_len = f64::INFINITY; |
197 let mut best_len = f64::INFINITY; |
| 213 let mut best_tan = Loc([0.0, 0.0]); |
198 let mut best_tan = Loc([0.0, 0.0]); |
| 214 for path in self.face.paths(other.face) { |
199 for path in self.face.paths(other.face) { |
| 215 let tan = self.face.convert(&path, &other.point) - &self.point; |
200 let tan = self.face.convert(&path, &other.point) - &self.point; |
| 216 let len = tan.norm(L2); |
201 let len = tan.norm(L2); |
| 217 if len < best_len { |
202 if len < best_len { |
| 218 best_tan = tan; |
203 best_tan = tan; |
| 219 best_len = len; |
204 best_len = len; |
| 220 } |
205 } |
| 221 } |
206 } |
| 222 best_tan |
207 (best_tan, best_len) |
| |
208 } |
| |
209 } |
| |
210 |
| |
211 impl ManifoldPoint for OnCube { |
| |
212 type Tangent = Point; |
| |
213 |
| |
214 fn exp(&self, tangent : &Self::Tangent) -> Self { |
| |
215 let mut face = self.face; |
| |
216 let mut point = self.point + tangent; |
| |
217 loop { |
| |
218 let next_face = face.find_crossing(&point); |
| |
219 if next_face == face { |
| |
220 break |
| |
221 } |
| |
222 point = next_face.convert_adjacent(face, &point).unwrap(); |
| |
223 face = next_face; |
| |
224 } |
| |
225 OnCube { face, point } |
| |
226 } |
| |
227 |
| |
228 fn log(&self, other : &Self) -> Self::Tangent { |
| |
229 self.log_dist(other).0 |
| |
230 } |
| |
231 |
| |
232 fn dist_to(&self, other : &Self) -> f64 { |
| |
233 self.log_dist(other).1 |
| 223 } |
234 } |
| 224 } |
235 } |
| 225 |
236 |
| 226 #[cfg(test)] |
237 #[cfg(test)] |
| 227 mod tests { |
238 mod tests { |