Safe Haskell | Safe-Inferred |
---|
CG library (minus).
- data Pt a = Pt {}
- data Vc a = Vc {}
- data Ln a = Ln {}
- type Ls a = [Pt a]
- data Wn a = Wn {}
- type R = Double
- epsilon :: Floating n => n
- (~=) :: (Floating a, Ord a) => a -> a -> Bool
- r_to_radians :: R -> R
- r_from_radians :: R -> R
- r_constrain :: (R, R) -> R -> R
- mag_sq :: Num a => a -> a -> a
- mag :: Floating c => c -> c -> c
- pt' :: (a, a) -> Pt a
- pt_xy :: Pt t -> (t, t)
- pt_origin :: Num a => Pt a
- pt_uop :: (a -> b) -> Pt a -> Pt b
- pt_binop :: (a -> b -> c) -> Pt a -> Pt b -> Pt c
- pt_from_scalar :: Num a => a -> Pt a
- pt_clipu :: (Ord a, Num a) => a -> Pt a -> Pt a
- pt_swap :: Pt a -> Pt a
- pt_negate_y :: Num a => Pt a -> Pt a
- pt_to_radians :: Pt R -> Pt R
- pt_to_polar :: Pt R -> Pt R
- pt_from_polar :: Pt R -> Pt R
- pt_offset :: Num a => a -> Pt a -> Pt a
- pt_scale :: Num a => a -> Pt a -> Pt a
- pt_min :: Ord a => Pt a -> Pt a -> Pt a
- pt_max :: Ord a => Pt a -> Pt a -> Pt a
- pt_ternary_f :: (a -> a -> b -> b -> c -> c -> d) -> Pt a -> Pt b -> Pt c -> d
- pt_minmax :: Ord a => (Pt a, Pt a) -> Pt a -> (Pt a, Pt a)
- pt_constrain :: (Pt R, Pt R) -> Pt R -> Pt R
- pt_angle_o :: Pt R -> R
- pt_angle :: Pt R -> Pt R -> R
- pt_translate :: (Num a, Eq a) => Pt a -> Vc a -> Pt a
- pt_from_i :: (Integral i, Num a) => Pt i -> Pt a
- pt_mag_sq :: Num a => Pt a -> a
- pt_mag :: Floating a => Pt a -> a
- pt_distance :: (Floating a, Eq a) => Pt a -> Pt a -> a
- pt_is_normal :: (Ord a, Num a) => Pt a -> Bool
- pt_rotate :: Floating a => a -> Pt a -> Pt a
- vc_uop :: (a -> b) -> Vc a -> Vc b
- vc_binop :: (a -> b -> c) -> Vc a -> Vc b -> Vc c
- vc_mag_sq :: Floating c => Vc c -> c
- vc_mag :: Floating c => Vc c -> c
- vc_scale :: Num a => a -> Vc a -> Vc a
- vc_dot :: Num a => Vc a -> Vc a -> a
- vc_unit :: (Ord a, Floating a) => Vc a -> Vc a
- vc_angle :: Vc R -> Vc R -> R
- ln' :: (Num a, Eq a) => (a, a) -> (a, a) -> Ln a
- ln_vc :: (Num a, Eq a) => Ln a -> Vc a
- ln_uop :: (Pt a -> Pt b) -> Ln a -> Ln b
- ln_scale :: Num b => b -> Ln b -> Ln b
- ln_angle :: Ln R -> R
- ln_pt :: (Num a, Eq a) => Ln a -> (Pt a, Pt a)
- ln_pt' :: (Num a, Eq a) => Ln a -> ((a, a), (a, a))
- ln_midpoint :: (Fractional a, Eq a) => Ln a -> Pt a
- cc_midpoint :: (Maybe (Pt R), Maybe (Pt R)) -> Pt R
- ln_magnitude :: Ln R -> R
- ln_sort :: (Num a, Ord a) => Ln a -> Ln a
- ln_adjust :: (Floating a, Ord a) => a -> Ln a -> Ln a
- ln_extend :: R -> Ln R -> Ln R
- ln_extend_ :: R -> Ln R -> Ln R
- pt_linear_extension :: R -> Ln R -> Pt R
- pt_on_line :: Ln R -> Pt R -> Bool
- ln_intersect :: (Eq t, Fractional t) => Ln t -> Ln t -> Maybe (t, t)
- ln_pt_along :: (Eq a, Num a) => a -> Ln a -> Pt a
- ln_intersection :: (Ord a, Fractional a) => Ln a -> Ln a -> Maybe (Pt a)
- ln_intersection_ :: (Ord a, Fractional a) => Ln a -> Ln a -> Maybe (Pt a)
- ln_intersect_p :: (Ord a, Fractional a) => Ln a -> Ln a -> Bool
- ln_slope :: (Fractional a, Eq a) => Ln a -> Maybe a
- ln_parallel :: (Ord a, Fractional a) => Ln a -> Ln a -> Bool
- ln_parallel_ :: Ln R -> Ln R -> Bool
- vc_same_direction :: (Ord a, Floating a) => Vc a -> Vc a -> Bool
- ln_same_direction :: (Ord a, Floating a) => Ln a -> Ln a -> Bool
- ln_parallel__ :: Ln R -> Ln R -> Bool
- ln_horizontal :: (Fractional a, Eq a) => Ln a -> Bool
- ln_vertical :: (Fractional a, Eq a) => Ln a -> Bool
- lns_minmax :: [Ln R] -> (Pt R, Pt R)
- lns_normalise :: R -> [Ln R] -> [Ln R]
- ls :: [Pt a] -> Ls a
- ls' :: [(a, a)] -> Ls a
- ls_negate_y :: Num a => Ls a -> Ls a
- ls_minmax :: Ord a => Ls a -> (Pt a, Pt a)
- ls_separate :: (Ord a, Num a) => Vc a -> Ls a -> [Ls a]
- ls_tolerate :: (Ord a, Num a) => Vc a -> Ls a -> Ls a
- ls_tolerate' :: (Ord a, Num a) => Maybe (Vc a) -> Ls a -> Ls a
- ls_pt_inside :: Ls R -> Pt R -> Bool
- ls_pt_inside' :: Ls R -> Pt R -> Bool
- ls_check_normalised :: (Ord a, Num a) => Ls a -> Bool
- ls_xy :: Ls a -> [a]
- wn' :: Num a => (a, a) -> (a, a) -> Wn a
- wn_extract :: Wn a -> ((a, a), (a, a))
- wn_show :: Int -> Wn R -> String
- pt_in_window :: (Ord a, Num a) => Wn a -> Pt a -> Bool
- wn_from_extent :: (Num a, Ord a) => (Pt a, Pt a) -> Wn a
- ls_window :: (Num a, Ord a) => Ls a -> Wn a
- wn_join :: (Num a, Ord a) => Wn a -> Wn a -> Wn a
- wn_intersect :: (Num a, Ord a) => Wn a -> Wn a -> Bool
- ls_in_window :: Wn R -> Ls R -> Bool
- ls_enters_window :: Wn R -> Ls R -> Bool
- ls_not_in_window :: Wn R -> Ls R -> Bool
- ls_segment_window :: Wn R -> Ls R -> [Ls R]
- wn_normalise_f :: Wn R -> Pt R -> Pt R
- ls_normalise_w :: Wn R -> Ls R -> Ls R
- ln_normalise_w :: Wn R -> Ln R -> Ln R
- pt_shift_w :: Num a => Pt a -> Wn a -> Wn a
- wn_negate_y :: Num a => Wn a -> Wn a
- data Matrix n = Matrix n n n n n n
- data Matrix_Index
- mx_row :: Num n => Matrix n -> Matrix_Index -> (n, n, n)
- mx_col :: Num n => Matrix n -> Matrix_Index -> (n, n, n)
- mx_multiply :: Num n => Matrix n -> Matrix n -> Matrix n
- mx_uop :: (n -> n) -> Matrix n -> Matrix n
- mx_binop :: (n -> n -> n) -> Matrix n -> Matrix n -> Matrix n
- mx_translation :: Num n => n -> n -> Matrix n
- mx_scaling :: Num n => n -> n -> Matrix n
- mx_rotation :: Floating n => n -> Matrix n
- mx_identity :: Num n => Matrix n
- mx_translate :: Num n => n -> n -> Matrix n -> Matrix n
- mx_scale :: Num n => n -> n -> Matrix n -> Matrix n
- mx_rotate :: Floating n => n -> Matrix n -> Matrix n
- mx_scalar_multiply :: Num n => n -> Matrix n -> Matrix n
- mx_adjoint :: Num n => Matrix n -> Matrix n
- mx_invert :: Fractional n => Matrix n -> Matrix n
- mx_list :: Matrix n -> [n]
- pt_transform :: Num n => Matrix n -> Pt n -> Pt n
- bezier3 :: Num n => Pt n -> Pt n -> Pt n -> n -> Pt n
- bezier4 :: Num n => Pt n -> Pt n -> Pt n -> Pt n -> n -> Pt n
- in_range :: Ord a => a -> a -> a -> Bool
- split_f :: (a -> a -> Bool) -> [a] -> ([a], [a])
- segment_f :: (a -> a -> Bool) -> [a] -> [[a]]
- delete_f :: (a -> a -> Bool) -> [a] -> [a]
- pairs :: [x] -> [(x, x)]
Types
Two-dimensional point.
Pt are Num
, pointwise, ie:
Pt 1 2 + Pt 3 4 == Pt 4 6 Pt 1 2 * Pt 3 4 == Pt 3 8 negate (Pt 0 1) == Pt 0 (-1) abs (Pt (-1) 1) == Pt 1 1 signum (Pt (-1/2) (1/2)) == Pt (-1) 1
Two-dimensional line.
R(eal) functions
r_to_radians :: R -> RSource
Degrees to radians.
map r_to_radians [-180,-90,0,90,180] == [-pi,-pi/2,0,pi/2,pi]
r_from_radians :: R -> RSource
Radians to degrees, inverse of r_to_radians
.
map r_from_radians [-pi,-pi/2,0,pi/2,pi] == [-180,-90,0,90,180]
r_constrain :: (R, R) -> R -> RSource
R
modulo within range.
map (r_constrain (3,5)) [2.75,5.25] == [4.75,3.25]
Pt functions
pt_from_scalar :: Num a => a -> Pt aSource
Pt
at (n,n).
pt_from_scalar 1 == Pt 1 1
pt_clipu :: (Ord a, Num a) => a -> Pt a -> Pt aSource
Clip x and y to lie in (0,n).
pt_clipu 1 (Pt 0.5 1.5) == Pt 0.5 1
pt_to_radians :: Pt R -> Pt RSource
Pt
variant of r_to_radians
.
pt_to_radians (Pt 90 270) == Pt (pi/2) (pi*(3/2))
pt_from_polar :: Pt R -> Pt RSource
Polar to cartesian, inverse of pt_to_polar
.
pt_from_polar (Pt pi (pi/2)) ~= Pt 0 pi
pt_ternary_f :: (a -> a -> b -> b -> c -> c -> d) -> Pt a -> Pt b -> Pt c -> dSource
Apply function to x and y fields of three Pt
.
pt_minmax :: Ord a => (Pt a, Pt a) -> Pt a -> (Pt a, Pt a)Source
Given a (minima,maxima) pair, expand so as to include p.
pt_minmax (Pt 0 0,Pt 1 1) (Pt (-1) 2) == (Pt (-1) 0,Pt 1 2)
pt_angle_o :: Pt R -> RSource
Angle to origin.
pt_angle_o (Pt 0 1) == pi / 2
pt_angle :: Pt R -> Pt R -> RSource
Angle from p to q.
pt_angle (Pt 0 (-1)) (Pt 0 1) == pi/2 pt_angle (Pt 1 0) (Pt 0 1) == pi * 3/4 pt_angle (Pt 0 1) (Pt 0 1) == 0
pt_translate :: (Num a, Eq a) => Pt a -> Vc a -> Pt aSource
Pointwise +
.
pt_translate (Pt 0 0) (vc 1 1) == pt 1 1
pt_is_normal :: (Ord a, Num a) => Pt a -> BoolSource
Are x and y of Pt
p in range (0,1).
map pt_is_normal [Pt 0 0,Pt 1 1,Pt 2 2] == [True,True,False]
pt_rotate :: Floating a => a -> Pt a -> Pt aSource
Rotate Pt
n radians.
pt_rotate pi (Pt 1 0) ~= Pt (-1) 0
Vc functions
vc_scale :: Num a => a -> Vc a -> Vc aSource
Multiply Vc
pointwise by scalar.
vc_scale 2 (Vc 3 4) == Vc 6 8
vc_unit :: (Ord a, Floating a) => Vc a -> Vc aSource
Scale Vc
to have unit magnitude (to within tolerance).
vc_unit (Vc 1 1) ~= let x = (sqrt 2) / 2 in Vc x x
vc_angle :: Vc R -> Vc R -> RSource
The angle between two vectors on a plane. The angle is from v1 to v2, positive anticlockwise. The result is in (-pi,pi)
Line functions
ln_vc :: (Num a, Eq a) => Ln a -> Vc aSource
Vc
that pt_translate
s start Pt
to end Pt
of Ln
.
let l = Ln (Pt 0 0) (Pt 1 1) in ln_start l `pt_translate` ln_vc l == Pt 1 1
The angle, in radians, anti-clockwise from the x-axis.
ln_angle (ln' (0,0) (0,0)) == 0 ln_angle (ln' (0,0) (1,1)) == pi/4 ln_angle (ln' (0,0) (0,1)) == pi/2 ln_angle (ln' (0,0) (-1,1)) == pi * 3/4
ln_pt :: (Num a, Eq a) => Ln a -> (Pt a, Pt a)Source
Start and end points of Ln
.
ln_pt (Ln (Pt 1 0) (Pt 0 0)) == (Pt 1 0,Pt 0 0)
ln_pt' :: (Num a, Eq a) => Ln a -> ((a, a), (a, a))Source
Variant of ln_pt
giving co-ordinates as duples.
ln_pt' (Ln (Pt 1 0) (Pt 0 0)) == ((1,0),(0,0))
ln_midpoint :: (Fractional a, Eq a) => Ln a -> Pt aSource
Midpoint of a Ln
.
ln_midpoint (Ln (Pt 0 0) (Pt 2 1)) == Pt 1 (1/2)
cc_midpoint :: (Maybe (Pt R), Maybe (Pt R)) -> Pt RSource
Variant on ln_midpoint
.
cc_midpoint (Just (Pt 0 0),Nothing) == Pt 0 0 cc_midpoint (Nothing,Just (Pt 2 1)) == Pt 2 1 cc_midpoint (Just (Pt 0 0),Just (Pt 2 1)) == Pt 1 (1/2)
ln_magnitude :: Ln R -> RSource
Magnitude of Ln
, ie. length of line.
ln_magnitude (Ln (Pt 0 0) (Pt 1 1)) == sqrt 2 pt_x (pt_to_polar (Pt 1 1)) == sqrt 2
ln_extend :: R -> Ln R -> Ln RSource
Extend Ln
by R
, ie. ln_adjust
with n added to
ln_magnitude
.
ln_extend (sqrt 2) (Ln (Pt 0 0) (Pt 1 1)) ~= Ln (Pt 0 0) (Pt 2 2)
ln_extend_ :: R -> Ln R -> Ln RSource
Variant definition of ln_extend
.
ln_extend_ (sqrt 2) (Ln (Pt 0 0) (Pt 1 1)) == Ln (Pt 0 0) (Pt 2 2)
pt_linear_extension :: R -> Ln R -> Pt RSource
Calculate the point that extends a line by length n
.
pt_linear_extension (sqrt 2) (Ln (Pt 1 1) (Pt 2 2)) ~= Pt 3 3 pt_linear_extension 1 (Ln (Pt 1 1) (Pt 1 2)) ~= Pt 1 3
Intersection
ln_intersect :: (Eq t, Fractional t) => Ln t -> Ln t -> Maybe (t, t)Source
ln_intersection :: (Ord a, Fractional a) => Ln a -> Ln a -> Maybe (Pt a)Source
Do two Ln
s intersect, and if so at which Pt
.
ln_intersection (ln' (0,0) (5,5)) (ln' (5,0) (0,5)) == Just (Pt 2.5 2.5) ln_intersection (ln' (1,3) (9,3)) (ln' (0,1) (2,1)) == Nothing ln_intersection (ln' (1,5) (6,8)) (ln' (0.5,3) (6,4)) == Nothing ln_intersection (ln' (1,2) (3,6)) (ln' (2,4) (4,8)) == Nothing ln_intersection (ln' (2,3) (7,9)) (ln' (1,2) (5,7)) == Nothing ln_intersection (ln' (0,0) (1,1)) (ln' (0,0) (1,0)) == Just (Pt 0 0)
ln_intersection_ :: (Ord a, Fractional a) => Ln a -> Ln a -> Maybe (Pt a)Source
Variant definition of ln_intersection
, using algorithm at
http://paulbourke.net/geometry/lineline2d/.
ln_intersection_ (ln' (1,2) (3,6)) (ln' (2,4) (4,8)) == Nothing ln_intersection_ (ln' (0,0) (1,1)) (ln' (0,0) (1,0)) == Just (Pt 0 0)
ln_intersect_p :: (Ord a, Fractional a) => Ln a -> Ln a -> BoolSource
Predicate variant of ln_intersection
.
ln_intersect_p (ln' (1,1) (3,8)) (ln' (0.5,2) (4,7)) == True ln_intersect_p (ln' (3.5,9) (3.5,0.5)) (ln' (3,1) (9,1)) == True
Line slope
ln_parallel :: (Ord a, Fractional a) => Ln a -> Ln a -> BoolSource
Are Ln
s parallel, ie. have equal ln_slope
. Note that the
direction of the Ln
is not relevant, ie. this is not equal to
ln_same_direction
.
ln_parallel (ln' (0,0) (1,1)) (ln' (2,2) (1,1)) == True ln_parallel (ln' (0,0) (1,1)) (ln' (2,0) (1,1)) == False ln_parallel (ln' (1,2) (3,6)) (ln' (2,4) (4,8)) == True map ln_slope [ln' (2,2) (1,1),ln' (2,0) (1,1)] == [Just 1,Just (-1)]
vc_same_direction :: (Ord a, Floating a) => Vc a -> Vc a -> BoolSource
Are two vectors are in the same direction (to within a small tolerance).
ln_same_direction :: (Ord a, Floating a) => Ln a -> Ln a -> BoolSource
Do Ln
s have same direction (within tolerance).
ln_same_direction (ln' (0,0) (1,1)) (ln' (0,0) (2,2)) == True ln_same_direction (ln' (0,0) (1,1)) (ln' (2,2) (0,0)) == False
ln_parallel__ :: Ln R -> Ln R -> BoolSource
Are Ln
s parallel, ie. does ln_vc
of each equal ln_same_direction
.
ln_parallel__ (ln' (0,0) (1,1)) (ln' (2,2) (1,1)) == True
ln_horizontal :: (Fractional a, Eq a) => Ln a -> BoolSource
ln_vertical :: (Fractional a, Eq a) => Ln a -> BoolSource
Ln sets
L(ine) s(egment) functions
ls_negate_y :: Num a => Ls a -> Ls aSource
Negate y elements.
ls_tolerate' :: (Ord a, Num a) => Maybe (Vc a) -> Ls a -> Ls aSource
Variant of ls_tolerate
where Vc
is optional, and Nothing
gives id
.
ls_pt_inside' :: Ls R -> Pt R -> BoolSource
Variant that counts points at vertices as inside.
ls_pt_inside' (ls' [(0,0),(1,0),(1,1),(0,1)]) (Pt 0 1) == True
ls_check_normalised :: (Ord a, Num a) => Ls a -> BoolSource
Check all Pt
at Ls
are pt_is_normal
.
Window
wn_extract :: Wn a -> ((a, a), (a, a))Source
Extract (x,y) and (dx,dy) pairs.
wn_extract (Wn (Pt 0 0) (Vc 1 1)) == ((0,0),(1,1))
wn_show :: Int -> Wn R -> StringSource
Show function for window with fixed precision of n
.
wn_show 1 (Wn (Pt 0 0) (Vc 1 1)) == "((0.0,0.0),(1.0,1.0))"
wn_from_extent :: (Num a, Ord a) => (Pt a, Pt a) -> Wn aSource
Wn
from (lower-left,upper-right) extent.
wn_intersect :: (Num a, Ord a) => Wn a -> Wn a -> BoolSource
Predictate to determine if two Wn
s intersect.
Matrix
Transformation matrix data type.
Matrix n n n n n n |
mx_row :: Num n => Matrix n -> Matrix_Index -> (n, n, n)Source
mx_col :: Num n => Matrix n -> Matrix_Index -> (n, n, n)Source
mx_translation :: Num n => n -> n -> Matrix nSource
A translation matrix with independent x and y offsets.
mx_scaling :: Num n => n -> n -> Matrix nSource
A scaling matrix with independent x and y scalars.
mx_rotation :: Floating n => n -> Matrix nSource
A rotation matrix through the indicated angle (in radians).
mx_identity :: Num n => Matrix nSource
The identity matrix.
mx_translate :: Num n => n -> n -> Matrix n -> Matrix nSource
mx_scalar_multiply :: Num n => n -> Matrix n -> Matrix nSource
mx_adjoint :: Num n => Matrix n -> Matrix nSource
mx_invert :: Fractional n => Matrix n -> Matrix nSource
Bezier functions.
bezier4 :: Num n => Pt n -> Pt n -> Pt n -> Pt n -> n -> Pt nSource
Four-point bezier curve interpolation. The index mu is in the range zero to one.
Ord
in_range :: Ord a => a -> a -> a -> BoolSource
Given left and right, is x in range (inclusive).
map (in_range 0 1) [-1,0,1,2] == [False,True,True,False]
List
split_f :: (a -> a -> Bool) -> [a] -> ([a], [a])Source
Split list at element where predicate f over adjacent elements first holds.
split_f (\p q -> q - p < 3) [1,2,4,7,11] == ([1,2,4],[7,11])
segment_f :: (a -> a -> Bool) -> [a] -> [[a]]Source
Variant on split_f
that segments input.
segment_f (\p q -> abs (q - p) < 3) [1,3,7,9,15] == [[1,3],[7,9],[15]]