diff options
author | Joe Crayne <joe@jerkface.net> | 2019-04-07 10:03:53 -0400 |
---|---|---|
committer | Joe Crayne <joe@jerkface.net> | 2019-04-07 10:03:53 -0400 |
commit | c155a1d9b8ca4b2cc5f327580847ad8f6249c1b6 (patch) | |
tree | 10d9011fe319a7691ae8e9c4022307d37416971c /GtkHello.hs | |
parent | 31b12994b0f5273282271ff3ed04596f49bc8003 (diff) |
Non-working experiment.
Diffstat (limited to 'GtkHello.hs')
-rw-r--r-- | GtkHello.hs | 184 |
1 files changed, 174 insertions, 10 deletions
diff --git a/GtkHello.hs b/GtkHello.hs index 43de1d2..0084d87 100644 --- a/GtkHello.hs +++ b/GtkHello.hs | |||
@@ -1,12 +1,25 @@ | |||
1 | {-# LANGUAGE OverloadedLabels #-} | 1 | {-# LANGUAGE OverloadedLabels #-} |
2 | {-# LANGUAGE OverloadedLists #-} | 2 | {-# LANGUAGE OverloadedLists #-} |
3 | {-# LANGUAGE OverloadedStrings #-} | 3 | {-# LANGUAGE OverloadedStrings #-} |
4 | {-# LANGUAGE TypeApplications #-} | ||
5 | {-# LANGUAGE DataKinds #-} | ||
4 | module Main where | 6 | module Main where |
5 | 7 | ||
8 | import GHC.OverloadedLabels | ||
9 | |||
6 | import qualified GI.Gtk as Gtk | 10 | import qualified GI.Gtk as Gtk |
7 | import GI.Gtk.Declarative | 11 | import GI.Gtk.Declarative |
8 | import GI.Gtk.Declarative.App.Simple | 12 | import GI.Gtk.Declarative.App.Simple |
9 | import GI.Gdk.Objects.GLContext | 13 | import GI.Gdk.Objects.GLContext |
14 | import GI.Gdk.Objects.Window | ||
15 | import Data.Bits | ||
16 | |||
17 | import Graphics.GL.Compatibility33 as GL33 | ||
18 | {- | ||
19 | import qualified Graphics.Rendering.OpenGL.GL.Framebuffer as GL | ||
20 | import Graphics.Rendering.OpenGL.GL.VertexSpec | ||
21 | import Data.StateVar | ||
22 | -} | ||
10 | 23 | ||
11 | import qualified Data.Map as Map | 24 | import qualified Data.Map as Map |
12 | import qualified Data.Vector as V | 25 | import qualified Data.Vector as V |
@@ -20,17 +33,100 @@ import Codec.Picture as Juicy | |||
20 | import Data.Aeson | 33 | import Data.Aeson |
21 | import qualified Data.ByteString as SB | 34 | import qualified Data.ByteString as SB |
22 | 35 | ||
36 | import System.Exit | ||
37 | |||
23 | type State = () | 38 | type State = () |
24 | 39 | ||
25 | data Event = Closed | Ignored | 40 | data Event = Closed | Ignored |
26 | 41 | ||
27 | view' :: Constants -> State -> AppView Gtk.Window Event | 42 | view' :: Constants -> State -> AppView Gtk.Window Event |
28 | view' storage _ = bin | 43 | view' c _ = bin |
29 | Gtk.Window | 44 | Gtk.Window |
30 | [ #title := "LambdaCube 3D DSL Hello World" | 45 | [ #title := "LambdaCube 3D DSL Hello World" |
31 | , on #deleteEvent $ {- GI.Gdk.Unions.Event.Event -> (Bool, Event) -} \_ -> (True,Closed) | 46 | , on #deleteEvent $ {- GI.Gdk.Unions.Event.Event -> (Bool, Event) -} \_ -> (True,Closed) |
32 | ] | 47 | ] |
33 | $ widget Gtk.GLArea [onM #render $ render storage] | 48 | $ widget Gtk.GLArea |
49 | [ onM #realize $ realize c | ||
50 | -- , onM #unrealize $ unrealize c | ||
51 | -- , onM #render $ render c | ||
52 | -- , on #createContext $ _todo -- createContext | ||
53 | ] | ||
54 | -- type instance SignalList GLArea = GLAreaSignalList | ||
55 | -- type GLAreaSignalList = ('[ '("accel-closures-changed" , WidgetAccelClosuresChangedSignalInfo) | ||
56 | -- , '("button-press-event" , WidgetButtonPressEventSignalInfo) | ||
57 | -- , '("button-release-event" , WidgetButtonReleaseEventSignalInfo) | ||
58 | -- , '("can-activate-accel" , WidgetCanActivateAccelSignalInfo) | ||
59 | -- , '("child-notify" , WidgetChildNotifySignalInfo) | ||
60 | -- , '("composited-changed" , WidgetCompositedChangedSignalInfo) | ||
61 | -- , '("configure-event" , WidgetConfigureEventSignalInfo) | ||
62 | -- , '("create-context" , GLAreaCreateContextSignalInfo) | ||
63 | -- , '("damage-event" , WidgetDamageEventSignalInfo) | ||
64 | -- , '("delete-event" , WidgetDeleteEventSignalInfo) | ||
65 | -- , '("destroy" , WidgetDestroySignalInfo) | ||
66 | -- , '("destroy-event" , WidgetDestroyEventSignalInfo) | ||
67 | -- , '("direction-changed" , WidgetDirectionChangedSignalInfo) | ||
68 | -- , '("drag-begin" , WidgetDragBeginSignalInfo) | ||
69 | -- , '("drag-data-delete" , WidgetDragDataDeleteSignalInfo) | ||
70 | -- , '("drag-data-get" , WidgetDragDataGetSignalInfo) | ||
71 | -- , '("drag-data-received" , WidgetDragDataReceivedSignalInfo) | ||
72 | -- , '("drag-drop" , WidgetDragDropSignalInfo) | ||
73 | -- , '("drag-end" , WidgetDragEndSignalInfo) | ||
74 | -- , '("drag-failed" , WidgetDragFailedSignalInfo) | ||
75 | -- , '("drag-leave" , WidgetDragLeaveSignalInfo) | ||
76 | -- , '("drag-motion" , WidgetDragMotionSignalInfo) | ||
77 | -- , '("draw" , WidgetDrawSignalInfo) | ||
78 | -- , '("enter-notify-event" , WidgetEnterNotifyEventSignalInfo) | ||
79 | -- , '("event" , WidgetEventSignalInfo) | ||
80 | -- , '("event-after" , WidgetEventAfterSignalInfo) | ||
81 | -- , '("focus" , WidgetFocusSignalInfo) | ||
82 | -- , '("focus-in-event" , WidgetFocusInEventSignalInfo) | ||
83 | -- , '("focus-out-event" , WidgetFocusOutEventSignalInfo) | ||
84 | -- , '("grab-broken-event" , WidgetGrabBrokenEventSignalInfo) | ||
85 | -- , '("grab-focus" , WidgetGrabFocusSignalInfo) | ||
86 | -- , '("grab-notify" , WidgetGrabNotifySignalInfo) | ||
87 | -- , '("hide" , WidgetHideSignalInfo) | ||
88 | -- , '("hierarchy-changed" , WidgetHierarchyChangedSignalInfo) | ||
89 | -- , '("key-press-event" , WidgetKeyPressEventSignalInfo) | ||
90 | -- , '("key-release-event" , WidgetKeyReleaseEventSignalInfo) | ||
91 | -- , '("keynav-failed" , WidgetKeynavFailedSignalInfo) | ||
92 | -- , '("leave-notify-event" , WidgetLeaveNotifyEventSignalInfo) | ||
93 | -- , '("map" , WidgetMapSignalInfo) | ||
94 | -- , '("map-event" , WidgetMapEventSignalInfo) | ||
95 | -- , '("mnemonic-activate" , WidgetMnemonicActivateSignalInfo) | ||
96 | -- , '("motion-notify-event" , WidgetMotionNotifyEventSignalInfo) | ||
97 | -- , '("move-focus" , WidgetMoveFocusSignalInfo) | ||
98 | -- , '("notify" , GObject.ObjectNotifySignalInfo) | ||
99 | -- , '("parent-set" , WidgetParentSetSignalInfo) | ||
100 | -- , '("popup-menu" , WidgetPopupMenuSignalInfo) | ||
101 | -- , '("property-notify-event" , WidgetPropertyNotifyEventSignalInfo) | ||
102 | -- , '("proximity-in-event" , WidgetProximityInEventSignalInfo) | ||
103 | -- , '("proximity-out-event" , WidgetProximityOutEventSignalInfo) | ||
104 | -- , '("query-tooltip" , WidgetQueryTooltipSignalInfo) | ||
105 | -- , '("realize" , WidgetRealizeSignalInfo) | ||
106 | -- , '("render" , GLAreaRenderSignalInfo) | ||
107 | -- , '("resize" , GLAreaResizeSignalInfo) | ||
108 | -- , '("screen-changed" , WidgetScreenChangedSignalInfo) | ||
109 | -- , '("scroll-event" , WidgetScrollEventSignalInfo) | ||
110 | -- , '("selection-clear-event" , WidgetSelectionClearEventSignalInfo) | ||
111 | -- , '("selection-get" , WidgetSelectionGetSignalInfo) | ||
112 | -- , '("selection-notify-event" , WidgetSelectionNotifyEventSignalInfo) | ||
113 | -- , '("selection-received" , WidgetSelectionReceivedSignalInfo) | ||
114 | -- , '("selection-request-event" , WidgetSelectionRequestEventSignalInfo) | ||
115 | -- , '("show" , WidgetShowSignalInfo) | ||
116 | -- , '("show-help" , WidgetShowHelpSignalInfo) | ||
117 | -- , '("size-allocate" , WidgetSizeAllocateSignalInfo) | ||
118 | -- , '("state-changed" , WidgetStateChangedSignalInfo) | ||
119 | -- , '("state-flags-changed" , WidgetStateFlagsChangedSignalInfo) | ||
120 | -- , '("style-set" , WidgetStyleSetSignalInfo) | ||
121 | -- , '("style-updated" , WidgetStyleUpdatedSignalInfo) | ||
122 | -- , '("touch-event" , WidgetTouchEventSignalInfo) | ||
123 | -- , '("unmap" , WidgetUnmapSignalInfo) | ||
124 | -- , '("unmap-event" , WidgetUnmapEventSignalInfo) | ||
125 | -- , '("unrealize" , WidgetUnrealizeSignalInfo) | ||
126 | -- , '("visibility-notify-event" , WidgetVisibilityNotifyEventSignalInfo) | ||
127 | -- , '("window-state-event" , WidgetWindowStateEventSignalInfo) | ||
128 | -- , '("notify::[property]" , GObjectNotifySignalInfo)] :: [(Symbol, *)]) | ||
129 | |||
34 | 130 | ||
35 | 131 | ||
36 | update' :: State -> Event -> Transition State Event | 132 | update' :: State -> Event -> Transition State Event |
@@ -58,24 +154,85 @@ triangleB = Mesh | |||
58 | 154 | ||
59 | data Constants = Constants | 155 | data Constants = Constants |
60 | { cStorage :: GLStorage | 156 | { cStorage :: GLStorage |
157 | , cSchema :: PipelineSchema | ||
61 | , cPipeline :: Pipeline | 158 | , cPipeline :: Pipeline |
159 | , cTextures :: TextureData | ||
160 | , cLogo :: DynamicImage | ||
62 | } | 161 | } |
63 | 162 | ||
64 | 163 | ||
65 | render :: Constants -> GLContext -> Gtk.GLArea -> IO (Bool, Event) | 164 | render :: Constants -> GLContext -> Gtk.GLArea -> IO (Bool, Event) |
66 | render c _ _ = do | 165 | render c0 gl area = do |
67 | putStrLn "render!" | 166 | e <- Gtk.gLAreaGetError area |
167 | putStrLn $ "render! " ++ show e | ||
68 | 168 | ||
69 | renderer <- LambdaCubeGL.allocRenderer (cPipeline c) | ||
70 | 169 | ||
71 | {- | 170 | storage <- LambdaCubeGL.allocStorage (cSchema c0) |
171 | |||
72 | -- upload geometry to GPU and add to pipeline input | 172 | -- upload geometry to GPU and add to pipeline input |
73 | LambdaCubeGL.uploadMeshToGPU triangleA >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] | 173 | LambdaCubeGL.uploadMeshToGPU triangleA >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] |
74 | LambdaCubeGL.uploadMeshToGPU triangleB >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] | 174 | LambdaCubeGL.uploadMeshToGPU triangleB >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] |
75 | -} | ||
76 | 175 | ||
176 | -- load image and upload texture | ||
177 | textureData <- LambdaCubeGL.uploadTexture2DToGPU (cLogo c0) | ||
178 | |||
179 | let c = c0 { cStorage = storage, cTextures = textureData } | ||
180 | |||
181 | renderer <- LambdaCubeGL.allocRenderer (cPipeline c) | ||
182 | |||
183 | compat <- LambdaCubeGL.setStorage renderer (cStorage c) -- check schema compatibility | ||
184 | |||
185 | maybe id (\e _ -> putStrLn e) compat $ do | ||
186 | |||
187 | -- Load input to pipeline. | ||
188 | -- GLFW.getWindowSize win >>= \(w,h) -> LambdaCubeGL.setScreenSize storage (fromIntegral w) (fromIntegral h) | ||
189 | return (500,500) >>= \(w,h) -> LambdaCubeGL.setScreenSize (cStorage c) (fromIntegral w) (fromIntegral h) | ||
190 | LambdaCubeGL.updateUniforms (cStorage c) $ do | ||
191 | "diffuseTexture" @= return (cTextures c) | ||
192 | "time" @= do | ||
193 | -- Just t <- GLFW.getTime | ||
194 | let t = 1.0 :: Double | ||
195 | return (realToFrac t :: Float) | ||
196 | |||
197 | -- GL33.glClearColor 0 255 0 128 | ||
198 | -- GL33.glClear $ GL_COLOR_BUFFER_BIT .|. GL_DEPTH_BUFFER_BIT | ||
199 | -- | ||
200 | -- -- GL33.glDrawArrays GL_TRIANGLES 0 3 | ||
201 | |||
202 | -- Run pipeline. | ||
203 | LambdaCubeGL.renderFrame renderer | ||
204 | -- GL33.glDrawArrays GL_TRIANGLES 0 3 | ||
205 | -- GL33.glEnd | ||
206 | GL33.glFlush | ||
207 | {- | ||
208 | w <- getGLContextWindow gl | ||
209 | mapM_ windowEndPaint w | ||
210 | -} | ||
211 | return () | ||
212 | |||
213 | LambdaCubeGL.disposeRenderer renderer | ||
214 | -- LambdaCubeGL.disposeStorage storage -- Not implemented? | ||
77 | return (True,Ignored) | 215 | return (True,Ignored) |
78 | 216 | ||
217 | realize :: Constants -> Gtk.GLArea -> IO Event | ||
218 | realize c _ = do | ||
219 | putStrLn "realize!" | ||
220 | exitSuccess | ||
221 | return Closed -- Ignored | ||
222 | |||
223 | unrealize :: Constants -> Gtk.GLArea -> IO Event | ||
224 | unrealize c _ = do | ||
225 | putStrLn "unrealize!" | ||
226 | return Ignored | ||
227 | |||
228 | |||
229 | -- createContext :: GI.Gtk.Declarative.Attributes.Internal.EventHandler.UserEventHandler Gtk.GLAreaCreateContextCallback Gtk.GLArea 'GI.Gtk.Declarative.Attributes.Internal.EventHandler.Impure Event | ||
230 | {- | ||
231 | createContext :: Gtk.GLArea -> IO (GLContext,Event) | ||
232 | createContext _ = do | ||
233 | return (error "todo",Ignored) | ||
234 | -} | ||
235 | |||
79 | main :: IO () | 236 | main :: IO () |
80 | main = do | 237 | main = do |
81 | Just pipelineDesc <- decodeStrict <$> SB.readFile "hello.json" | 238 | Just pipelineDesc <- decodeStrict <$> SB.readFile "hello.json" |
@@ -89,14 +246,17 @@ main = do | |||
89 | "time" @: Float | 246 | "time" @: Float |
90 | "diffuseTexture" @: FTexture2D | 247 | "diffuseTexture" @: FTexture2D |
91 | 248 | ||
249 | -- load image | ||
250 | Right img <- Juicy.readImage "logo.png" | ||
251 | |||
252 | {- | ||
92 | storage <- LambdaCubeGL.allocStorage inputSchema | 253 | storage <- LambdaCubeGL.allocStorage inputSchema |
93 | 254 | ||
94 | -- upload geometry to GPU and add to pipeline input | 255 | -- upload geometry to GPU and add to pipeline input |
95 | LambdaCubeGL.uploadMeshToGPU triangleA >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] | 256 | LambdaCubeGL.uploadMeshToGPU triangleA >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] |
96 | LambdaCubeGL.uploadMeshToGPU triangleB >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] | 257 | LambdaCubeGL.uploadMeshToGPU triangleB >>= LambdaCubeGL.addMeshToObjectArray storage "objects" [] |
97 | 258 | ||
98 | -- load image and upload texture | 259 | -- upload texture |
99 | Right img <- Juicy.readImage "logo.png" | ||
100 | textureData <- LambdaCubeGL.uploadTexture2DToGPU img | 260 | textureData <- LambdaCubeGL.uploadTexture2DToGPU img |
101 | 261 | ||
102 | -- Disabled, triggers shader compilation. | 262 | -- Disabled, triggers shader compilation. |
@@ -106,12 +266,16 @@ main = do | |||
106 | -- allocate GL pipeline | 266 | -- allocate GL pipeline |
107 | renderer <- LambdaCubeGL.allocRenderer pipelineDesc | 267 | renderer <- LambdaCubeGL.allocRenderer pipelineDesc |
108 | return () | 268 | return () |
269 | -} | ||
270 | let storage = error "storage" | ||
271 | textureData = error "textureData" | ||
109 | 272 | ||
110 | putStrLn "Starting Gtk window!" | 273 | putStrLn "Starting Gtk window!" |
111 | run App | 274 | run App |
112 | -- :: App Gtk.Window State Event | 275 | -- :: App Gtk.Window State Event |
113 | { view = view' Constants { cStorage = storage, cPipeline = pipelineDesc } | 276 | { view = view' Constants { cStorage = storage, cPipeline = pipelineDesc, cTextures = textureData, cLogo = img, cSchema = inputSchema } |
114 | , update = update' | 277 | , update = update' |
115 | , inputs = [] | 278 | , inputs = [] |
116 | , initialState = () | 279 | , initialState = () |
117 | } | 280 | } |
281 | LambdaCubeGL.disposeStorage storage | ||