handa-opengl 0.1.11.2 → 0.1.12.1
raw patch · 3 files changed
+144/−47 lines, 3 filesdep +splitPVP: major bump suggested
API removals or changes: PVP suggests a major version bump
Dependencies added: split
API changes (from Hackage documentation)
- Foreign.C.Types.Instances: instance Data.Aeson.Types.Class.FromJSON Foreign.C.Types.CDouble
- Foreign.C.Types.Instances: instance Data.Aeson.Types.Class.FromJSON Foreign.C.Types.CFloat
- Foreign.C.Types.Instances: instance GHC.Generics.Constructor Foreign.C.Types.Instances.C1_0CDouble
- Foreign.C.Types.Instances: instance GHC.Generics.Constructor Foreign.C.Types.Instances.C1_0CFloat
- Foreign.C.Types.Instances: instance GHC.Generics.Datatype Foreign.C.Types.Instances.D1CDouble
- Foreign.C.Types.Instances: instance GHC.Generics.Datatype Foreign.C.Types.Instances.D1CFloat
- Graphics.Rendering.Handa.Projection: instance (GHC.Generics.Generic a, Data.Aeson.Types.Class.FromJSON a) => Data.Aeson.Types.Class.FromJSON (Graphics.Rendering.Handa.Projection.Screen a)
- Graphics.Rendering.Handa.Projection: instance GHC.Generics.Constructor Graphics.Rendering.Handa.Projection.C1_0Screen
- Graphics.Rendering.Handa.Projection: instance GHC.Generics.Datatype Graphics.Rendering.Handa.Projection.D1Screen
- Graphics.Rendering.Handa.Projection: instance GHC.Generics.Selector Graphics.Rendering.Handa.Projection.S1_0_0Screen
- Graphics.Rendering.Handa.Projection: instance GHC.Generics.Selector Graphics.Rendering.Handa.Projection.S1_0_1Screen
- Graphics.Rendering.Handa.Projection: instance GHC.Generics.Selector Graphics.Rendering.Handa.Projection.S1_0_2Screen
- Graphics.Rendering.Handa.Viewer: instance (GHC.Generics.Generic a, Data.Aeson.Types.Class.FromJSON a) => Data.Aeson.Types.Class.FromJSON (Graphics.Rendering.Handa.Viewer.ViewerParameters a)
- Graphics.Rendering.Handa.Viewer: instance (GHC.Generics.Generic a, Data.Binary.Class.Binary a) => Data.Binary.Class.Binary (Graphics.Rendering.Handa.Viewer.ViewerParameters a)
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Constructor Graphics.Rendering.Handa.Viewer.C1_0ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Datatype Graphics.Rendering.Handa.Viewer.D1ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_0ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_1ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_2ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_3ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_4ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_5ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_6ViewerParameters
- Graphics.Rendering.Handa.Viewer: instance GHC.Generics.Selector Graphics.Rendering.Handa.Viewer.S1_0_7ViewerParameters
- Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance (Data.Aeson.Types.Class.FromJSON a, GHC.Generics.Generic a) => Data.Aeson.Types.Class.FromJSON (Graphics.Rendering.OpenGL.GL.Tensor.Vector3 a)
- Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance (Data.Aeson.Types.Class.FromJSON a, GHC.Generics.Generic a) => Data.Aeson.Types.Class.FromJSON (Graphics.Rendering.OpenGL.GL.Tensor.Vertex3 a)
- Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance GHC.Generics.Constructor Graphics.Rendering.OpenGL.GL.Tensor.Instances.C1_0Vector3
- Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance GHC.Generics.Constructor Graphics.Rendering.OpenGL.GL.Tensor.Instances.C1_0Vertex3
- Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance GHC.Generics.Datatype Graphics.Rendering.OpenGL.GL.Tensor.Instances.D1Vector3
- Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance GHC.Generics.Datatype Graphics.Rendering.OpenGL.GL.Tensor.Instances.D1Vertex3
- Graphics.UI.Handa.Setup: instance (GHC.Generics.Generic a, Data.Aeson.Types.Class.FromJSON a) => Data.Aeson.Types.Class.FromJSON (Graphics.UI.Handa.Setup.Setup a)
- Graphics.UI.Handa.Setup: instance Data.Aeson.Types.Class.FromJSON Graphics.UI.Handa.Setup.Stereo
- Graphics.UI.Handa.Setup: instance Data.Aeson.Types.Class.FromJSON Graphics.UI.Handa.Setup.Viewer
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_0Setup
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_0Stereo
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_0Viewer
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_1Stereo
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_1Viewer
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_2Stereo
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_2Viewer
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_3Stereo
- Graphics.UI.Handa.Setup: instance GHC.Generics.Constructor Graphics.UI.Handa.Setup.C1_3Viewer
- Graphics.UI.Handa.Setup: instance GHC.Generics.Datatype Graphics.UI.Handa.Setup.D1Setup
- Graphics.UI.Handa.Setup: instance GHC.Generics.Datatype Graphics.UI.Handa.Setup.D1Stereo
- Graphics.UI.Handa.Setup: instance GHC.Generics.Datatype Graphics.UI.Handa.Setup.D1Viewer
- Graphics.UI.Handa.Setup: instance GHC.Generics.Selector Graphics.UI.Handa.Setup.S1_0_0Setup
- Graphics.UI.Handa.Setup: instance GHC.Generics.Selector Graphics.UI.Handa.Setup.S1_0_1Setup
- Graphics.UI.Handa.Setup: instance GHC.Generics.Selector Graphics.UI.Handa.Setup.S1_0_2Setup
- Graphics.UI.Handa.Setup: instance GHC.Generics.Selector Graphics.UI.Handa.Setup.S1_0_3Setup
+ Foreign.C.Types.Instances: instance Data.Aeson.Types.FromJSON.FromJSON Foreign.C.Types.CDouble
+ Foreign.C.Types.Instances: instance Data.Aeson.Types.FromJSON.FromJSON Foreign.C.Types.CFloat
+ Graphics.Rendering.Handa.Projection: KooimaOffAxis :: OffAxisProjection
+ Graphics.Rendering.Handa.Projection: VTKOffAxis :: OffAxisProjection
+ Graphics.Rendering.Handa.Projection: data OffAxisProjection
+ Graphics.Rendering.Handa.Projection: fetchProjection :: forall a. (MatrixComponent a, RealFloat a) => IO [[a]]
+ Graphics.Rendering.Handa.Projection: instance (GHC.Generics.Generic a, Data.Aeson.Types.FromJSON.FromJSON a) => Data.Aeson.Types.FromJSON.FromJSON (Graphics.Rendering.Handa.Projection.Screen a)
+ Graphics.Rendering.Handa.Projection: instance GHC.Classes.Eq Graphics.Rendering.Handa.Projection.OffAxisProjection
+ Graphics.Rendering.Handa.Projection: instance GHC.Read.Read Graphics.Rendering.Handa.Projection.OffAxisProjection
+ Graphics.Rendering.Handa.Projection: instance GHC.Show.Show Graphics.Rendering.Handa.Projection.OffAxisProjection
+ Graphics.Rendering.Handa.Projection: upperRight :: (Num a) => Screen a -> Vertex3 a
+ Graphics.Rendering.Handa.Viewer: dlpViewerDisplay' :: (AdditiveGroup a, MatrixComponent a, RealFloat a, Storable a) => Bool -> DlpEncoding -> IORef (ViewerParameters a) -> DisplayCallback -> DlpDisplay
+ Graphics.Rendering.Handa.Viewer: instance (Data.Aeson.Types.FromJSON.FromJSON a, GHC.Generics.Generic a) => Data.Aeson.Types.FromJSON.FromJSON (Graphics.Rendering.Handa.Viewer.ViewerParameters a)
+ Graphics.Rendering.Handa.Viewer: instance (Data.Binary.Class.Binary a, GHC.Generics.Generic a) => Data.Binary.Class.Binary (Graphics.Rendering.Handa.Viewer.ViewerParameters a)
+ Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance (Data.Aeson.Types.FromJSON.FromJSON a, GHC.Generics.Generic a) => Data.Aeson.Types.FromJSON.FromJSON (Graphics.Rendering.OpenGL.GL.Tensor.Vector3 a)
+ Graphics.Rendering.OpenGL.GL.Tensor.Instances: instance (Data.Aeson.Types.FromJSON.FromJSON a, GHC.Generics.Generic a) => Data.Aeson.Types.FromJSON.FromJSON (Graphics.Rendering.OpenGL.GL.Tensor.Vertex3 a)
+ Graphics.UI.Handa.Setup: instance (GHC.Generics.Generic a, Data.Aeson.Types.FromJSON.FromJSON a) => Data.Aeson.Types.FromJSON.FromJSON (Graphics.UI.Handa.Setup.Setup a)
+ Graphics.UI.Handa.Setup: instance Data.Aeson.Types.FromJSON.FromJSON Graphics.UI.Handa.Setup.Stereo
+ Graphics.UI.Handa.Setup: instance Data.Aeson.Types.FromJSON.FromJSON Graphics.UI.Handa.Setup.Viewer
- Graphics.Rendering.Handa.Projection: projection :: (AdditiveGroup a, MatrixComponent a, RealFloat a) => Screen a -> Vertex3 a -> a -> a -> IO ()
+ Graphics.Rendering.Handa.Projection: projection :: forall a. (AdditiveGroup a, MatrixComponent a, RealFloat a) => OffAxisProjection -> Screen a -> Vertex3 a -> a -> a -> IO ()
- Graphics.Rendering.Handa.Viewer: dlpViewerDisplay :: (RealFloat a, Storable a) => DlpEncoding -> ViewerParameters a -> DisplayCallback -> DlpDisplay
+ Graphics.Rendering.Handa.Viewer: dlpViewerDisplay :: (AdditiveGroup a, MatrixComponent a, RealFloat a, Storable a) => Bool -> DlpEncoding -> ViewerParameters a -> DisplayCallback -> DlpDisplay
- Graphics.Rendering.Handa.Viewer: loadViewer :: (RealFloat a, Storable a) => ViewerParameters a -> DlpEye -> IO ()
+ Graphics.Rendering.Handa.Viewer: loadViewer :: (AdditiveGroup a, MatrixComponent a, RealFloat a, Storable a) => Bool -> ViewerParameters a -> DlpEye -> IO ()
Files
- handa-opengl.cabal +3/−2
- src/Graphics/Rendering/Handa/Projection.hs +77/−13
- src/Graphics/Rendering/Handa/Viewer.hs +64/−32
handa-opengl.cabal view
@@ -1,5 +1,5 @@ name: handa-opengl-version: 0.1.11.2+version: 0.1.12.1 synopsis: Utility functions for OpenGL and GLUT description: This is a collection of miscellaneous utility functions for OpenGL and GLUT. @@ -14,7 +14,7 @@ stability: Stable homepage: https://bitbucket.org/bwbush/handa-opengl bug-reports: https://bwbush.atlassian.net/projects/HOGL/issues/-package-url: https://bitbucket.org/bwbush/handa-opengl/downloads/handa-opengl-0.1.11.2.tar.gz+package-url: https://bitbucket.org/bwbush/handa-opengl/downloads/handa-opengl-0.1.12.1.tar.gz extra-source-files: ReadMe.md @@ -31,6 +31,7 @@ , GLUT >= 2.7.0.1 , opengl-dlp-stereo >= 0.1.5.1 , OpenGL >= 2.12.0.1+ , split >= 0.2.2 , vector-space >= 0.10.2 exposed-modules: Foreign.C.Types.Instances Graphics.Rendering.Handa.Face
src/Graphics/Rendering/Handa/Projection.hs view
@@ -14,6 +14,7 @@ {-# LANGUAGE DeriveDataTypeable #-} {-# LANGUAGE DeriveGeneric #-} {-# LANGUAGE ExplicitForAll #-}+{-# LANGUAGE FlexibleContexts #-} {-# LANGUAGE RecordWildCards #-} {-# LANGUAGE ScopedTypeVariables #-} @@ -21,22 +22,26 @@ module Graphics.Rendering.Handa.Projection ( -- * Screens. Screen(..)+, upperRight , aspectRatio , throwRatio -- * Projections.+, OffAxisProjection(..) , projection+, fetchProjection ) where import Data.AdditiveGroup (AdditiveGroup) import Data.Aeson (FromJSON)-import Data.AffineSpace ((.-.))-import Data.Binary (Binary(..))+import Data.AffineSpace ((.+^), (.-.))+import Data.Binary (Binary) import Data.Cross (cross3) import Data.Data (Data)-import Data.VectorSpace ((<.>), magnitude, normalized)+import Data.List.Split (chunksOf)+import Data.VectorSpace ((*^), (<.>), magnitude, normalized) import GHC.Generics (Generic)-import Graphics.Rendering.OpenGL (GLmatrix, MatrixComponent, MatrixOrder(RowMajor), Vector3(..), Vertex3(..), frustum, multMatrix, newMatrix, translate)+import Graphics.Rendering.OpenGL (GLmatrix, MatrixComponent, MatrixOrder(RowMajor), Vector3(..), Vertex3(..), frustum, get, getMatrixComponents, matrix, multMatrix, newMatrix, translate) import Graphics.Rendering.OpenGL.GL.Tensor.Instances (origin) @@ -60,6 +65,13 @@ } +-- | The upper right corner.+upperRight :: (Num a)+ => Screen a+ -> Vertex3 a+upperRight Screen{..} = lowerRight .+^ (upperLeft .-. lowerLeft)++ -- | The aspect ratio. aspectRatio :: (AdditiveGroup a, RealFloat a) => Screen a -- ^ The screen geometry.@@ -86,20 +98,30 @@ throw / width --- | Make an off-axis projection for a screen. This projection is based on the equations in \<<http://csc.lsu.edu/~kooima/pdfs/gen-perspective.pdf>\> .+-- | The equations to use for off-axis projection.+data OffAxisProjection =+ KooimaOffAxis -- ^ Based on Kooima 2009, \<<http://csc.lsu.edu/~kooima/pdfs/gen-perspective.pdf>\>, which assumes a rectangular screen.+ | VTKOffAxis -- ^ Based on VTK 6.3.0, \<<https://gitlab.kitware.com/vtk/vtk/blob/v6.3.0/Rendering/Core/vtkCamera.cxx#L414>\>, which does not assume a rectangular screen.+ deriving (Eq, Read, Show)+++-- | Make an off-axis projection for a screen. projection :: forall a . (AdditiveGroup a, MatrixComponent a, RealFloat a)- => Screen a -- ^ The screen geometry.- -> Vertex3 a -- ^ The eye position.- -> a -- ^ The distance to the near culling plane.- -> a -- ^ The distance to the far culling plane.- -> IO () -- ^ An action for performing the off-axis projection.-projection Screen{..} eye near far =+ => OffAxisProjection -- ^ The off-axis equations to use.+ -> Screen a -- ^ The screen geometry.+ -> Vertex3 a -- ^ The eye position.+ -> a -- ^ The distance to the near culling plane.+ -> a -- ^ The distance to the far culling plane.+ -> IO () -- ^ An action for performing the off-axis projection.++-- Based on Kooima 2009, \<<http://csc.lsu.edu/~kooima/pdfs/gen-perspective.pdf>\>, which assumes a rectangular screen .+projection KooimaOffAxis Screen{..} eye near far = do let -- Orthonomal basis for screen. vr = normalized $ lowerRight .-. lowerLeft vu = normalized $ upperLeft .-. lowerLeft- vn = vr `cross3` vu+ vn = normalized $ vr `cross3` vu -- Screen corners relative to eye. va = lowerLeft .-. eye vb = lowerRight .-. eye@@ -114,9 +136,51 @@ top = realToFrac $ (vu <.> vc) * scaling -- Matrix transforming world to screen. m = [[x, y, z, 0] | Vector3 x y z <- [vr, vu, vn]] ++ [[0, 0, 0, 1]]- -- Perpendicator projection+ -- Perpendicator projection. frustum left right bottom top (realToFrac near) (realToFrac far) -- Rotate to non-perpendicular. multMatrix =<< (newMatrix RowMajor $ concat m :: IO (GLmatrix a)) -- Move apex of frustum. translate $ origin .-. eye++-- Rewrite of VTK 6.3.0, \<<https://gitlab.kitware.com/vtk/vtk/blob/v6.3.0/Rendering/Core/vtkCamera.cxx#L414>\>, which does not assume a rectangular screen, in cleaner notation and using vector algebra.+projection VTKOffAxis s@Screen{..} eye near far =+ do+ let+ -- Orthonomal basis for screen.+ vr = normalized $ lowerRight .-. lowerLeft+ vu = normalized $ upperRight s .-. lowerRight+ vn = normalized $ vr `cross3` vu+ -- Basis for inverse.+ idet = 1 / (vr <.> vu `cross3` vn)+ ur = idet *^ vu `cross3` vn+ uu = idet *^ vn `cross3` vr+ un = idet *^ vr `cross3` vu+ -- Screen corners relative to eye.+ va = lowerLeft .-. eye+ vd = upperRight s .-. eye+ -- Distance from eye to screen.+ throw = - va <.> un+ -- Extent on near clipping plane.+ scaling = near / throw+ left = realToFrac $ (ur <.> va) * scaling+ right = realToFrac $ (ur <.> vd) * scaling+ bottom = realToFrac $ (uu <.> va) * scaling+ top = realToFrac $ (uu <.> vd) * scaling+ -- Matrix transforming world to screen.+ m = [[x, y, z, 0] | Vector3 x y z <- [ur, uu, un]] ++ [[0, 0, 0, 1]]+ -- Perpendicator projection.+ frustum left right bottom top (realToFrac near) (realToFrac far)+ -- Rotate to non-perpendicular.+ multMatrix =<< (newMatrix RowMajor $ concat m :: IO (GLmatrix a))+ -- Move apex of frustum.+ translate $ origin .-. eye+++-- | Retrieve the current projection matrix.+fetchProjection :: forall a . (MatrixComponent a, RealFloat a)+ => IO [[a]] -- ^ An action to retrieve the projection matrix, in row-major order.+fetchProjection =+ do+ m <- get $ matrix Nothing :: IO (GLmatrix a)+ chunksOf 4 <$> getMatrixComponents RowMajor m
src/Graphics/Rendering/Handa/Viewer.hs view
@@ -32,21 +32,25 @@ , reshape , loadViewer , dlpViewerDisplay+, dlpViewerDisplay' ) where import Data.AdditiveGroup (AdditiveGroup)+import Data.AffineSpace ((.+^)) import Data.Aeson (FromJSON)-import Data.Binary (Binary(..))+import Data.Binary (Binary) import Data.Data (Data)+import Data.VectorSpace ((*^)) import Data.Default (Default, def)+import Data.IORef (IORef) import Foreign.Storable (Storable) import GHC.Generics (Generic) import Graphics.Rendering.DLP (DlpEncoding, DlpEye(..)) import Graphics.Rendering.DLP.Callbacks (DlpDisplay(..))-import Graphics.Rendering.Handa.Projection (Screen(..), aspectRatio, projection, throwRatio)+import Graphics.Rendering.Handa.Projection (OffAxisProjection(VTKOffAxis), Screen(..), aspectRatio, projection, throwRatio) import Graphics.Rendering.Handa.Util (degree)-import Graphics.Rendering.OpenGL (GLdouble, MatrixComponent, MatrixMode(..), Position(..), Vector3(..), Vertex3(..), ($=!), loadIdentity, lookAt, matrixMode, scale, viewport)+import Graphics.Rendering.OpenGL (GLdouble, MatrixComponent, MatrixMode(..), Position(..), Vector3(..), Vertex3(..), ($=!), get, loadIdentity, lookAt, matrixMode, scale, viewport) import Graphics.Rendering.OpenGL.GL.Tensor.Instances () import Graphics.UI.GLUT (DisplayCallback, ReshapeCallback) @@ -93,11 +97,11 @@ } , nearPlane = 0.1 , farPlane = 100- , eyePosition = Vertex3 0 0 1- , eyeSeparation = Vector3 0.2 0 0- , eyeUpward = Vector3 0 1 0- , sceneCenter = Vertex3 0 0 0- , sceneScale = Vector3 1 1 1+ , eyePosition = Vertex3 0 0 1+ , eyeSeparation = Vector3 0.02 0 0+ , eyeUpward = Vector3 0 1 0+ , sceneCenter = Vertex3 0 0 0+ , sceneScale = Vector3 1 1 1 } @@ -118,7 +122,7 @@ , upperLeft = Vertex3 (- 1 / 2) ( height / width / 2) 0 } , eyePosition = Vertex3 0 0 (throw / width)- , sceneScale = Vector3 1 (height / width) 1+ , sceneScale = 0.5 *^ Vector3 1 (height / width) 1 } @@ -172,42 +176,70 @@ viewport $=! (Position 0 0, wh) matrixMode $=! Projection loadIdentity- projection screen eyePosition nearPlane farPlane+ projection VTKOffAxis screen eyePosition nearPlane farPlane matrixMode $=! Modelview 0 -- | Create an action look at the scene according to the viewer parameters.-loadViewer :: (RealFloat a, Storable a)- => ViewerParameters a -- ^ The viewer parameters.+loadViewer :: (AdditiveGroup a, MatrixComponent a, RealFloat a, Storable a)+ => Bool -- ^ Whether to use an on-axis projection.+ -> ViewerParameters a -- ^ The viewer parameters. -> DlpEye -- ^ The eye from which to view. -> IO () -- ^ An action for looking at the scene using the specified eye and viewer parameters.-loadViewer ViewerParameters{..} eye =- do- let- offset =- case eye of- LeftDlp -> -0.5- RightDlp -> 0.5- Vertex3 xEye yEye zEye = eyePosition- Vector3 dxEye dyEye dzEye = eyeSeparation- Vector3 sx sy sz = realToFrac <$> sceneScale :: Vector3 GLdouble- loadIdentity- scale sx sy sz- lookAt- (realToFrac <$> Vertex3 (xEye + offset * dxEye) (yEye + offset * dyEye) (zEye + offset * dzEye))- (realToFrac <$> sceneCenter)- (realToFrac <$> eyeUpward)+loadViewer onAxis ViewerParameters{..} eye =+ let+ offset =+ case eye of+ LeftDlp -> -0.5+ RightDlp -> 0.5+ eyePosition' = eyePosition .+^ offset *^ eyeSeparation+ Vector3 sx sy sz = realToFrac <$> sceneScale :: Vector3 GLdouble+ in+ if onAxis+ then do+ loadIdentity+ lookAt+ (realToFrac <$> eyePosition')+ (realToFrac <$> sceneCenter)+ (realToFrac <$> eyeUpward)+ scale sx sy sz+ else do+ matrixMode $=! Projection+ loadIdentity+ projection VTKOffAxis screen eyePosition' nearPlane farPlane+ matrixMode $=! Modelview 0+ loadIdentity+ scale sx sy sz -- | Construct a DLP display from a display callback.-dlpViewerDisplay :: (RealFloat a, Storable a)- => DlpEncoding -- ^ The DLP encoding.+dlpViewerDisplay :: (AdditiveGroup a, MatrixComponent a, RealFloat a, Storable a)+ => Bool -- ^ Whether to use on-axis projection.+ -> DlpEncoding -- ^ The DLP encoding. -> ViewerParameters a -- ^ The viewer parameters. -> DisplayCallback -- ^ The display callback. -> DlpDisplay -- ^ The DLP display data for using the specified encoding, viewer parameters, and display callback.-dlpViewerDisplay encoding viewerParameters display =+dlpViewerDisplay onAxis encoding viewerParameters display = def { dlpEncoding = encoding- , doDisplay = \eye -> loadViewer viewerParameters eye >> display+ , doDisplay = \eye -> loadViewer onAxis viewerParameters eye >> display+ }+++-- | Construct a DLP display from a display callback.+dlpViewerDisplay' :: (AdditiveGroup a, MatrixComponent a, RealFloat a, Storable a)+ => Bool -- ^ Whether to use on-axis projection.+ -> DlpEncoding -- ^ The DLP encoding.+ -> IORef (ViewerParameters a) -- ^ A reference to the viewer parameters.+ -> DisplayCallback -- ^ The display callback.+ -> DlpDisplay -- ^ The DLP display data for using the specified encoding, viewer parameters, and display callback.+dlpViewerDisplay' onAxis encoding viewerParameters display =+ def + {+ dlpEncoding = encoding+ , doDisplay = \eye -> do+ viewerParameters' <- get viewerParameters+ loadViewer onAxis viewerParameters' eye+ display }