module Geometry.Trajectory.PathSimplifier.Radial (
module Geometry.Trajectory.PathSimplifier.Radial
) where
import Data.Sequential
import qualified Data.Vector as V
import Geometry.Core
simplifyTrajectoryRadial
:: Sequential vector
=> Double
-> vector Vec2
-> [Vec2]
simplifyTrajectoryRadial :: forall (vector :: * -> *).
Sequential vector =>
Double -> vector Vec2 -> [Vec2]
simplifyTrajectoryRadial Double
minimumNeighbourDistance = Double -> (Vec2 -> Vec2) -> Vector Vec2 -> [Vec2]
forall (vector :: * -> *) a.
Sequential vector =>
Double -> (a -> Vec2) -> vector a -> [a]
simplifyTrajectoryRadialBy Double
minimumNeighbourDistance Vec2 -> Vec2
forall a. a -> a
id (Vector Vec2 -> [Vec2])
-> (vector Vec2 -> Vector Vec2) -> vector Vec2 -> [Vec2]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. vector Vec2 -> Vector Vec2
forall a. vector a -> Vector a
forall (f :: * -> *) a. Sequential f => f a -> Vector a
toVector
simplifyTrajectoryRadialBy
:: Sequential vector
=> Double
-> (a -> Vec2)
-> vector a
-> [a]
simplifyTrajectoryRadialBy :: forall (vector :: * -> *) a.
Sequential vector =>
Double -> (a -> Vec2) -> vector a -> [a]
simplifyTrajectoryRadialBy Double
minimumNeighbourDistance a -> Vec2
vec2in = Vector a -> [a]
go (Vector a -> [a]) -> (vector a -> Vector a) -> vector a -> [a]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. vector a -> Vector a
forall a. vector a -> Vector a
forall (f :: * -> *) a. Sequential f => f a -> Vector a
toVector
where
tooClose :: a -> a -> Bool
tooClose a
pivot a
candidate = Vec2 -> Double
normSquare (a -> Vec2
vec2in a
pivot Vec2 -> Vec2 -> Vec2
forall v. VectorSpace v => v -> v -> v
-. a -> Vec2
vec2in a
candidate) Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
<= Double
minimumNeighbourDistanceDouble -> Integer -> Double
forall a b. (Num a, Integral b) => a -> b -> a
^Integer
2
go :: Vector a -> [a]
go Vector a
trajectory = case Vector a -> Maybe (a, Vector a)
forall a. Vector a -> Maybe (a, Vector a)
V.uncons Vector a
trajectory of
Maybe (a, Vector a)
Nothing -> []
Just (a
pivot,Vector a
xs)
| Vector a -> Bool
forall a. Vector a -> Bool
V.null Vector a
rest Bool -> Bool -> Bool
&& Vector a -> Bool
forall a. Vector a -> Bool
V.null Vector a
toDrop -> [a
pivot]
| Vector a -> Bool
forall a. Vector a -> Bool
V.null Vector a
rest -> [a
pivot, Vector a -> a
forall a. Vector a -> a
V.last Vector a
toDrop]
| Bool
otherwise -> a
pivot a -> [a] -> [a]
forall a. a -> [a] -> [a]
: Vector a -> [a]
go Vector a
rest
where (Vector a
toDrop, Vector a
rest) = (a -> Bool) -> Vector a -> (Vector a, Vector a)
forall a. (a -> Bool) -> Vector a -> (Vector a, Vector a)
V.span (a -> a -> Bool
tooClose a
pivot) Vector a
xs