linear 1.15.1 → 1.15.2
raw patch · 3 files changed
+128/−25 lines, 3 filesPVP ok
version bump matches the API change (PVP)
API changes (from Hackage documentation)
+ Linear.Projection: frustum :: Floating a => a -> a -> a -> a -> a -> a -> M44 a
+ Linear.Projection: inverseFrustum :: Floating a => a -> a -> a -> a -> a -> a -> M44 a
+ Linear.Projection: inverseInfinitePerspective :: Floating a => a -> a -> a -> M44 a
+ Linear.Projection: inverseOrtho :: Floating a => a -> a -> a -> a -> a -> a -> M44 a
Files
- CHANGELOG.markdown +5/−0
- linear.cabal +1/−1
- src/Linear/Projection.hs +122/−24
CHANGELOG.markdown view
@@ -1,3 +1,8 @@+1.15.2+------+* Added `frustum`, analogous to the old `glFrustum` call.+* Added `inverseInfinitePerspective`, `inverseOrtho`, `inverseFrustum`.+ 1.15.1 ------ * Added `inversePerspective`. It is much more accurate to compute it directly than to compute an inverse.
linear.cabal view
@@ -1,6 +1,6 @@ name: linear category: Math, Algebra-version: 1.15.1+version: 1.15.2 license: BSD3 cabal-version: >= 1.8 license-file: LICENSE
src/Linear/Projection.hs view
@@ -9,13 +9,17 @@ -- -- Common projection matrices: e.g. perspective/orthographic transformation -- matrices.+--+-- Analytically derived inverses are also supplied, because they can be+-- much more accurate in practice than computing them through general+-- purpose means --------------------------------------------------------------------------- module Linear.Projection ( lookAt- , perspective- , inversePerspective- , infinitePerspective- , ortho+ , perspective, inversePerspective+ , infinitePerspective, inverseInfinitePerspective+ , frustum, inverseFrustum+ , ortho, inverseOrtho ) where import Control.Lens hiding (index)@@ -47,7 +51,7 @@ -- | Build a matrix for a symmetric perspective-view frustum perspective :: Floating a- => a -- ^ FOV+ => a -- ^ FOV (y direction, in radians) -> a -- ^ Aspect ratio -> a -- ^ Near plane -> a -- ^ Far plane@@ -66,7 +70,7 @@ -- | Build an inverse perspective matrix inversePerspective :: Floating a- => a -- ^ FOV+ => a -- ^ FOV (y direction, in radians) -> a -- ^ Aspect ratio -> a -- ^ Near plane -> a -- ^ Far plane@@ -82,27 +86,99 @@ c = -(far - near) / (2 * far * near) d = (far + near) / (2 * far * near) ++-- | Build a perspective matrix per the classic @glFrustum@ arguments.+frustum+ :: Floating a+ => a -- ^ Left+ -> a -- ^ Right+ -> a -- ^ Bottom+ -> a -- ^ Top+ -> a -- ^ Near+ -> a -- ^ Far+ -> M44 a+frustum l r b t n f = + V4 (V4 x 0 a 0)+ (V4 0 y e 0)+ (V4 0 0 c d)+ (V4 0 0 (-1) 0)+ where+ rml = r-l + tmb = t-b+ fmn = f-n+ x = 2*n/rml+ y = 2*n/tmb+ a = (r+l)/rml+ e = (t+b)/tmb+ c = negate (f+n)/fmn+ d = (-2*f*n)/fmn++inverseFrustum+ :: Floating a+ => a -- ^ Left+ -> a -- ^ Right+ -> a -- ^ Bottom+ -> a -- ^ Top+ -> a -- ^ Near+ -> a -- ^ Far+ -> M44 a+inverseFrustum l r b t n f = + V4 (V4 rx 0 0 ax)+ (V4 0 ry 0 by)+ (V4 0 0 0 (-1))+ (V4 0 0 rd cd)+ where+ hrn = 0.5/n+ hrnf = 0.5/(n*f)+ rx = (r-l)*hrn+ ry = (t-b)*hrn+ ax = (r+l)*hrn+ by = (t+b)*hrn+ cd = (f+n)*hrnf+ rd = (n-f)*hrnf+ -- | Build a matrix for a symmetric perspective-view frustum with a far plane at infinite infinitePerspective :: Floating a- => a -- ^ FOV+ => a -- ^ FOV (y direction, in radians) -> a -- ^ Aspect Ratio -> a -- ^ Near plane -> M44 a-infinitePerspective fovy aspect near =+infinitePerspective fovy a n = V4 (V4 x 0 0 0) (V4 0 y 0 0) (V4 0 0 (-1) w) (V4 0 0 (-1) 0)- where range = tan (fovy / 2) * near- left = -range * aspect- right = range * aspect- bottom = -range- top = range- x = (2 * near) / (right - left)- y = (2 * near) / (top - bottom)- w = -2 * near+ where+ t = n*tan(fovy/2)+ b = -t+ l = b*a+ r = t*a+ x = (2*n)/(r-l)+ y = (2*n)/(t-b)+ w = -2*n +inverseInfinitePerspective+ :: Floating a+ => a -- ^ FOV (y direction, in radians)+ -> a -- ^ Aspect Ratio+ -> a -- ^ Near plane+ -> M44 a+inverseInfinitePerspective fovy a n =+ V4 (V4 rx 0 0 0)+ (V4 0 ry 0 0)+ (V4 0 0 0 (-1))+ (V4 0 0 rw (-rw))+ where+ t = n*tan(fovy/2)+ b = -t+ l = b*a+ r = t*a+ hrn = 0.5/n+ rx = (r-l)*hrn+ ry = (t-b)*hrn+ rw = -hrn+ -- | Build an orthographic perspective matrix from 6 clipping planes ortho :: Floating a@@ -113,11 +189,33 @@ -> a -- ^ Near -> a -- ^ Far -> M44 a-ortho left right bottom top near far =- V4 (V4 (2 / a) 0 0 (negate (right + left) / a))- (V4 0 (2 / b) 0 (negate (top + bottom) / b))- (V4 0 0 (-2 / c) (negate (far + near) / c))- (V4 0 0 0 1)- where a = right - left- b = top - bottom- c = far - near+ortho l r b t n f =+ V4 (V4 (-2*x) 0 0 ((r+l)*x))+ (V4 0 (-2*y) 0 ((t+b)*y))+ (V4 0 0 (2*z) ((f+n)*z))+ (V4 0 0 0 1)+ where x = recip(l-r)+ y = recip(b-t)+ z = recip(n-f)++-- | Build an inverse orthographic perspective matrix from 6 clipping planes+inverseOrtho+ :: Floating a+ => a -- ^ Left+ -> a -- ^ Right+ -> a -- ^ Bottom+ -> a -- ^ Top+ -> a -- ^ Near+ -> a -- ^ Far+ -> M44 a+inverseOrtho l r b t n f =+ V4 (V4 x 0 0 c)+ (V4 0 y 0 d)+ (V4 0 0 z e)+ (V4 0 0 0 1)+ where x = 0.5*(r-l)+ y = 0.5*(t-b)+ z = 0.5*(n-f)+ c = 0.5*(l+r)+ d = 0.5*(b+t)+ e = -0.5*(n+f)