import Text.Printf

class (Num a, Fractional a, RealFrac a) => Angle a where
  fullTurn :: a 
  mkAngle :: Double -> a
  value :: a -> Double
  fromTurn :: Double -> a
  toTurn :: a -> Double
  normalize :: a -> a

  
  fromTurn t = angle t * fullTurn
  toTurn a = value $ a / fullTurn

  
  normalize a = a `modulo` fullTurn
    where
      modulo x r | x == r = r
                 | x < 0 = signum x * abs x `modulo` r
                 | x >= 0 = x - fromInteger (floor (x / r)) * r 


angle :: Angle a => Double -> a
angle = normalize . mkAngle


from :: forall a b. (Angle a, Angle b) => a -> b
from = fromTurn . toTurn

to :: forall b a. (Angle a, Angle b) => a -> b
to = fromTurn . toTurn