diff options
author | Csaba Hruska <csaba.hruska@gmail.com> | 2015-04-30 14:28:27 +0200 |
---|---|---|
committer | Csaba Hruska <csaba.hruska@gmail.com> | 2015-05-18 14:50:52 +0200 |
commit | 91f82aca82dc282d5630c1bddd8dc773c679cc76 (patch) | |
tree | 6060474da94e6fb8a1f46eebd0cba0c5a607cbd3 /Backend/GL/Util.hs | |
parent | 1d047c6fa195901dc149bdbe4b4d0497c9b5f9c6 (diff) |
split dsl compiler and ir backend
Diffstat (limited to 'Backend/GL/Util.hs')
-rw-r--r-- | Backend/GL/Util.hs | 717 |
1 files changed, 717 insertions, 0 deletions
diff --git a/Backend/GL/Util.hs b/Backend/GL/Util.hs new file mode 100644 index 0000000..7a36290 --- /dev/null +++ b/Backend/GL/Util.hs | |||
@@ -0,0 +1,717 @@ | |||
1 | {-# LANGUAGE OverloadedStrings #-} | ||
2 | module Backend.GL.Util ( | ||
3 | queryUniforms, | ||
4 | queryStreams, | ||
5 | mkUniformSetter, | ||
6 | setUniform, | ||
7 | setVertexAttrib, | ||
8 | compileShader, | ||
9 | printProgramLog, | ||
10 | glGetShaderiv1, | ||
11 | glGetProgramiv1, | ||
12 | Buffer(..), | ||
13 | ArrayDesc(..), | ||
14 | StreamSetter, | ||
15 | streamToInputType, | ||
16 | arrayTypeToGLType, | ||
17 | comparisonFunctionToGLType, | ||
18 | logicOperationToGLType, | ||
19 | blendEquationToGLType, | ||
20 | blendingFactorToGLType, | ||
21 | checkGL, | ||
22 | textureDataTypeToGLType, | ||
23 | textureDataTypeToGLArityType, | ||
24 | glGetIntegerv1, | ||
25 | setSampler, | ||
26 | checkFBO, | ||
27 | compileTexture, | ||
28 | primitiveToFetchPrimitive, | ||
29 | primitiveToGLType, | ||
30 | inputTypeToTextureTarget, | ||
31 | toTrie | ||
32 | ) where | ||
33 | |||
34 | import Control.Applicative | ||
35 | import Control.Exception | ||
36 | import Control.Monad | ||
37 | import Data.ByteString.Char8 (ByteString,pack,unpack) | ||
38 | import Data.IORef | ||
39 | import Data.List as L | ||
40 | import Data.Trie as T | ||
41 | import Foreign | ||
42 | import qualified Data.ByteString.Char8 as SB | ||
43 | import qualified Data.Vector as V | ||
44 | import Data.Vector.Unboxed.Mutable (IOVector) | ||
45 | import qualified Data.Vector.Unboxed.Mutable as MV | ||
46 | import Data.Map (Map) | ||
47 | import qualified Data.Map as Map | ||
48 | |||
49 | import Graphics.Rendering.OpenGL.Raw.Core33 | ||
50 | import IR | ||
51 | import Backend.GL.Type | ||
52 | |||
53 | toTrie :: Map String a -> Trie a | ||
54 | toTrie m = T.fromList [(pack k,v) | (k,v) <- Map.toList m] | ||
55 | |||
56 | setSampler :: GLint -> Int32 -> IO () | ||
57 | setSampler i v = glUniform1i i $ fromIntegral v | ||
58 | |||
59 | z2 = V2 0 0 :: V2F | ||
60 | z3 = V3 0 0 0 :: V3F | ||
61 | z4 = V4 0 0 0 0 :: V4F | ||
62 | |||
63 | -- uniform functions | ||
64 | queryUniforms :: GLuint -> IO (Trie GLint, Trie InputType) | ||
65 | queryUniforms po = do | ||
66 | ul <- getNameTypeSize po glGetActiveUniform glGetUniformLocation gl_ACTIVE_UNIFORMS gl_ACTIVE_UNIFORM_MAX_LENGTH | ||
67 | let uNames = [n | (n,_,_,_) <- ul] | ||
68 | uTypes = [fromGLType (e,s) | (_,_,e,s) <- ul] | ||
69 | uLocation = [i | (_,i,_,_) <- ul] | ||
70 | return $! (T.fromList $! zip uNames uLocation, T.fromList $! zip uNames uTypes) | ||
71 | |||
72 | b2w :: Bool -> GLuint | ||
73 | b2w True = 1 | ||
74 | b2w False = 0 | ||
75 | |||
76 | mkUniformSetter :: InputType -> IO (GLUniform, InputSetter) | ||
77 | mkUniformSetter t@Bool = do {r <- newIORef 0; return $! (GLUniform t r, SBool $! writeIORef r . b2w)} | ||
78 | mkUniformSetter t@V2B = do {r <- newIORef (V2 0 0); return $! (GLUniform t r, SV2B $! writeIORef r . fmap b2w)} | ||
79 | mkUniformSetter t@V3B = do {r <- newIORef (V3 0 0 0); return $! (GLUniform t r, SV3B $! writeIORef r . fmap b2w)} | ||
80 | mkUniformSetter t@V4B = do {r <- newIORef (V4 0 0 0 0); return $! (GLUniform t r, SV4B $! writeIORef r . fmap b2w)} | ||
81 | mkUniformSetter t@Word = do {r <- newIORef 0; return $! (GLUniform t r, SWord $! writeIORef r)} | ||
82 | mkUniformSetter t@V2U = do {r <- newIORef (V2 0 0); return $! (GLUniform t r, SV2U $! writeIORef r)} | ||
83 | mkUniformSetter t@V3U = do {r <- newIORef (V3 0 0 0); return $! (GLUniform t r, SV3U $! writeIORef r)} | ||
84 | mkUniformSetter t@V4U = do {r <- newIORef (V4 0 0 0 0); return $! (GLUniform t r, SV4U $! writeIORef r)} | ||
85 | mkUniformSetter t@Int = do {r <- newIORef 0; return $! (GLUniform t r, SInt $! writeIORef r)} | ||
86 | mkUniformSetter t@V2I = do {r <- newIORef (V2 0 0); return $! (GLUniform t r, SV2I $! writeIORef r)} | ||
87 | mkUniformSetter t@V3I = do {r <- newIORef (V3 0 0 0); return $! (GLUniform t r, SV3I $! writeIORef r)} | ||
88 | mkUniformSetter t@V4I = do {r <- newIORef (V4 0 0 0 0); return $! (GLUniform t r, SV4I $! writeIORef r)} | ||
89 | mkUniformSetter t@Float = do {r <- newIORef 0; return $! (GLUniform t r, SFloat $! writeIORef r)} | ||
90 | mkUniformSetter t@V2F = do {r <- newIORef (V2 0 0); return $! (GLUniform t r, SV2F $! writeIORef r)} | ||
91 | mkUniformSetter t@V3F = do {r <- newIORef (V3 0 0 0); return $! (GLUniform t r, SV3F $! writeIORef r)} | ||
92 | mkUniformSetter t@V4F = do {r <- newIORef (V4 0 0 0 0); return $! (GLUniform t r, SV4F $! writeIORef r)} | ||
93 | mkUniformSetter t@M22F = do {r <- newIORef (V2 z2 z2); return $! (GLUniform t r, SM22F $! writeIORef r)} | ||
94 | mkUniformSetter t@M23F = do {r <- newIORef (V3 z2 z2 z2); return $! (GLUniform t r, SM23F $! writeIORef r)} | ||
95 | mkUniformSetter t@M24F = do {r <- newIORef (V4 z2 z2 z2 z2); return $! (GLUniform t r, SM24F $! writeIORef r)} | ||
96 | mkUniformSetter t@M32F = do {r <- newIORef (V2 z3 z3); return $! (GLUniform t r, SM32F $! writeIORef r)} | ||
97 | mkUniformSetter t@M33F = do {r <- newIORef (V3 z3 z3 z3); return $! (GLUniform t r, SM33F $! writeIORef r)} | ||
98 | mkUniformSetter t@M34F = do {r <- newIORef (V4 z3 z3 z3 z3); return $! (GLUniform t r, SM34F $! writeIORef r)} | ||
99 | mkUniformSetter t@M42F = do {r <- newIORef (V2 z4 z4); return $! (GLUniform t r, SM42F $! writeIORef r)} | ||
100 | mkUniformSetter t@M43F = do {r <- newIORef (V3 z4 z4 z4); return $! (GLUniform t r, SM43F $! writeIORef r)} | ||
101 | mkUniformSetter t@M44F = do {r <- newIORef (V4 z4 z4 z4 z4); return $! (GLUniform t r, SM44F $! writeIORef r)} | ||
102 | mkUniformSetter t@FTexture2D = do {r <- newIORef (TextureData 0); return $! (GLUniform t r, SFTexture2D $! writeIORef r)} | ||
103 | |||
104 | -- sets value based uniforms only (does not handle textures) | ||
105 | setUniform :: Storable a => GLint -> InputType -> IORef a -> IO () | ||
106 | setUniform i ty ref = do | ||
107 | v <- readIORef ref | ||
108 | let false = fromIntegral gl_FALSE | ||
109 | with v $ \p -> case ty of | ||
110 | Bool -> glUniform1uiv i 1 (castPtr p) | ||
111 | V2B -> glUniform2uiv i 1 (castPtr p) | ||
112 | V3B -> glUniform3uiv i 1 (castPtr p) | ||
113 | V4B -> glUniform4uiv i 1 (castPtr p) | ||
114 | Word -> glUniform1uiv i 1 (castPtr p) | ||
115 | V2U -> glUniform2uiv i 1 (castPtr p) | ||
116 | V3U -> glUniform3uiv i 1 (castPtr p) | ||
117 | V4U -> glUniform4uiv i 1 (castPtr p) | ||
118 | Int -> glUniform1iv i 1 (castPtr p) | ||
119 | V2I -> glUniform2iv i 1 (castPtr p) | ||
120 | V3I -> glUniform3iv i 1 (castPtr p) | ||
121 | V4I -> glUniform4iv i 1 (castPtr p) | ||
122 | Float -> glUniform1fv i 1 (castPtr p) | ||
123 | V2F -> glUniform2fv i 1 (castPtr p) | ||
124 | V3F -> glUniform3fv i 1 (castPtr p) | ||
125 | V4F -> glUniform4fv i 1 (castPtr p) | ||
126 | M22F -> glUniformMatrix2fv i 1 false (castPtr p) | ||
127 | M23F -> glUniformMatrix2x3fv i 1 false (castPtr p) | ||
128 | M24F -> glUniformMatrix2x4fv i 1 false (castPtr p) | ||
129 | M32F -> glUniformMatrix3x2fv i 1 false (castPtr p) | ||
130 | M33F -> glUniformMatrix3fv i 1 false (castPtr p) | ||
131 | M34F -> glUniformMatrix3x4fv i 1 false (castPtr p) | ||
132 | M42F -> glUniformMatrix4x2fv i 1 false (castPtr p) | ||
133 | M43F -> glUniformMatrix4x3fv i 1 false (castPtr p) | ||
134 | M44F -> glUniformMatrix4fv i 1 false (castPtr p) | ||
135 | _ -> fail "internal error (setUniform)!" | ||
136 | |||
137 | -- attribute functions | ||
138 | queryStreams :: GLuint -> IO (Trie GLuint, Trie InputType) | ||
139 | queryStreams po = do | ||
140 | al <- getNameTypeSize po glGetActiveAttrib glGetAttribLocation gl_ACTIVE_ATTRIBUTES gl_ACTIVE_ATTRIBUTE_MAX_LENGTH | ||
141 | let aNames = [n | (n,_,_,_) <- al] | ||
142 | aTypes = [fromGLType (e,s) | (_,_,e,s) <- al] | ||
143 | aLocation = [fromIntegral i | (_,i,_,_) <- al] | ||
144 | return $! (T.fromList $! zip aNames aLocation, T.fromList $! zip aNames aTypes) | ||
145 | |||
146 | arrayTypeToGLType :: ArrayType -> GLenum | ||
147 | arrayTypeToGLType a = case a of | ||
148 | ArrWord8 -> gl_UNSIGNED_BYTE | ||
149 | ArrWord16 -> gl_UNSIGNED_SHORT | ||
150 | ArrWord32 -> gl_UNSIGNED_INT | ||
151 | ArrInt8 -> gl_BYTE | ||
152 | ArrInt16 -> gl_SHORT | ||
153 | ArrInt32 -> gl_INT | ||
154 | ArrFloat -> gl_FLOAT | ||
155 | ArrHalf -> gl_HALF_FLOAT | ||
156 | |||
157 | setVertexAttrib :: GLuint -> Stream Buffer -> IO () | ||
158 | setVertexAttrib i val = case val of | ||
159 | ConstWord v -> with v $! \p -> glVertexAttribI1uiv i $! castPtr p | ||
160 | ConstV2U v -> with v $! \p -> glVertexAttribI2uiv i $! castPtr p | ||
161 | ConstV3U v -> with v $! \p -> glVertexAttribI3uiv i $! castPtr p | ||
162 | ConstV4U v -> with v $! \p -> glVertexAttribI4uiv i $! castPtr p | ||
163 | ConstInt v -> with v $! \p -> glVertexAttribI1iv i $! castPtr p | ||
164 | ConstV2I v -> with v $! \p -> glVertexAttribI2iv i $! castPtr p | ||
165 | ConstV3I v -> with v $! \p -> glVertexAttribI3iv i $! castPtr p | ||
166 | ConstV4I v -> with v $! \p -> glVertexAttribI4iv i $! castPtr p | ||
167 | ConstFloat v -> setAFloat i v | ||
168 | ConstV2F v -> setAV2F i v | ||
169 | ConstV3F v -> setAV3F i v | ||
170 | ConstV4F v -> setAV4F i v | ||
171 | ConstM22F (V2 x y) -> setAV2F i x >> setAV2F (i+1) y | ||
172 | ConstM23F (V3 x y z) -> setAV2F i x >> setAV2F (i+1) y >> setAV2F (i+2) z | ||
173 | ConstM24F (V4 x y z w) -> setAV2F i x >> setAV2F (i+1) y >> setAV2F (i+2) z >> setAV2F (i+3) w | ||
174 | ConstM32F (V2 x y) -> setAV3F i x >> setAV3F (i+1) y | ||
175 | ConstM33F (V3 x y z) -> setAV3F i x >> setAV3F (i+1) y >> setAV3F (i+2) z | ||
176 | ConstM34F (V4 x y z w) -> setAV3F i x >> setAV3F (i+1) y >> setAV3F (i+2) z >> setAV3F (i+3) w | ||
177 | ConstM42F (V2 x y) -> setAV4F i x >> setAV4F (i+1) y | ||
178 | ConstM43F (V3 x y z) -> setAV4F i x >> setAV4F (i+1) y >> setAV4F (i+2) z | ||
179 | ConstM44F (V4 x y z w) -> setAV4F i x >> setAV4F (i+1) y >> setAV4F (i+2) z >> setAV4F (i+3) w | ||
180 | _ -> fail "internal error (setVertexAttrib)!" | ||
181 | |||
182 | setAFloat :: GLuint -> Float -> IO () | ||
183 | setAV2F :: GLuint -> V2F -> IO () | ||
184 | setAV3F :: GLuint -> V3F -> IO () | ||
185 | setAV4F :: GLuint -> V4F -> IO () | ||
186 | setAFloat i v = with v $! \p -> glVertexAttrib1fv i $! castPtr p | ||
187 | setAV2F i v = with v $! \p -> glVertexAttrib2fv i $! castPtr p | ||
188 | setAV3F i v = with v $! \p -> glVertexAttrib3fv i $! castPtr p | ||
189 | setAV4F i v = with v $! \p -> glVertexAttrib4fv i $! castPtr p | ||
190 | |||
191 | -- result list: [(name string,location,gl type,component count)] | ||
192 | getNameTypeSize :: GLuint -> (GLuint -> GLuint -> GLsizei -> Ptr GLsizei -> Ptr GLint -> Ptr GLenum -> Ptr GLchar -> IO ()) | ||
193 | -> (GLuint -> Ptr GLchar -> IO GLint) -> GLenum -> GLenum -> IO [(ByteString,GLint,GLenum,GLint)] | ||
194 | getNameTypeSize o f g enum enumLen = do | ||
195 | nameLen <- glGetProgramiv1 enumLen o | ||
196 | allocaArray (fromIntegral nameLen) $! \namep -> alloca $! \sizep -> alloca $! \typep -> do | ||
197 | n <- glGetProgramiv1 enum o | ||
198 | forM [0..n-1] $! \i -> f o (fromIntegral i) (fromIntegral nameLen) nullPtr sizep typep namep >> | ||
199 | (,,,) <$> SB.packCString (castPtr namep) <*> g o namep <*> peek typep <*> peek sizep | ||
200 | |||
201 | fromGLType :: (GLenum,GLint) -> InputType | ||
202 | fromGLType (t,1) | ||
203 | | t == gl_BOOL = Bool | ||
204 | | t == gl_BOOL_VEC2 = V2B | ||
205 | | t == gl_BOOL_VEC3 = V3B | ||
206 | | t == gl_BOOL_VEC4 = V4B | ||
207 | | t == gl_UNSIGNED_INT = Word | ||
208 | | t == gl_UNSIGNED_INT_VEC2 = V2U | ||
209 | | t == gl_UNSIGNED_INT_VEC3 = V3U | ||
210 | | t == gl_UNSIGNED_INT_VEC4 = V4U | ||
211 | | t == gl_INT = Int | ||
212 | | t == gl_INT_VEC2 = V2I | ||
213 | | t == gl_INT_VEC3 = V3I | ||
214 | | t == gl_INT_VEC4 = V4I | ||
215 | | t == gl_FLOAT = Float | ||
216 | | t == gl_FLOAT_VEC2 = V2F | ||
217 | | t == gl_FLOAT_VEC3 = V3F | ||
218 | | t == gl_FLOAT_VEC4 = V4F | ||
219 | | t == gl_FLOAT_MAT2 = M22F | ||
220 | | t == gl_FLOAT_MAT2x3 = M23F | ||
221 | | t == gl_FLOAT_MAT2x4 = M24F | ||
222 | | t == gl_FLOAT_MAT3x2 = M32F | ||
223 | | t == gl_FLOAT_MAT3 = M33F | ||
224 | | t == gl_FLOAT_MAT3x4 = M34F | ||
225 | | t == gl_FLOAT_MAT4x2 = M42F | ||
226 | | t == gl_FLOAT_MAT4x3 = M43F | ||
227 | | t == gl_FLOAT_MAT4 = M44F | ||
228 | | t == gl_SAMPLER_1D_ARRAY_SHADOW = STexture1DArray | ||
229 | | t == gl_SAMPLER_1D_SHADOW = STexture1D | ||
230 | | t == gl_SAMPLER_2D_ARRAY_SHADOW = STexture2DArray | ||
231 | | t == gl_SAMPLER_2D_RECT_SHADOW = STexture2DRect | ||
232 | | t == gl_SAMPLER_2D_SHADOW = STexture2D | ||
233 | | t == gl_SAMPLER_CUBE_SHADOW = STextureCube | ||
234 | | t == gl_INT_SAMPLER_1D = ITexture1D | ||
235 | | t == gl_INT_SAMPLER_1D_ARRAY = ITexture1DArray | ||
236 | | t == gl_INT_SAMPLER_2D = ITexture2D | ||
237 | | t == gl_INT_SAMPLER_2D_ARRAY = ITexture2DArray | ||
238 | | t == gl_INT_SAMPLER_2D_MULTISAMPLE = ITexture2DMS | ||
239 | | t == gl_INT_SAMPLER_2D_MULTISAMPLE_ARRAY = ITexture2DMSArray | ||
240 | | t == gl_INT_SAMPLER_2D_RECT = ITexture2DRect | ||
241 | | t == gl_INT_SAMPLER_3D = ITexture3D | ||
242 | | t == gl_INT_SAMPLER_BUFFER = ITextureBuffer | ||
243 | | t == gl_INT_SAMPLER_CUBE = ITextureCube | ||
244 | | t == gl_SAMPLER_1D = FTexture1D | ||
245 | | t == gl_SAMPLER_1D_ARRAY = FTexture1DArray | ||
246 | | t == gl_SAMPLER_2D = FTexture2D | ||
247 | | t == gl_SAMPLER_2D_ARRAY = FTexture2DArray | ||
248 | | t == gl_SAMPLER_2D_MULTISAMPLE = FTexture2DMS | ||
249 | | t == gl_SAMPLER_2D_MULTISAMPLE_ARRAY = FTexture2DMSArray | ||
250 | | t == gl_SAMPLER_2D_RECT = FTexture2DRect | ||
251 | | t == gl_SAMPLER_3D = FTexture3D | ||
252 | | t == gl_SAMPLER_BUFFER = FTextureBuffer | ||
253 | | t == gl_SAMPLER_CUBE = FTextureCube | ||
254 | | t == gl_UNSIGNED_INT_SAMPLER_1D = UTexture1D | ||
255 | | t == gl_UNSIGNED_INT_SAMPLER_1D_ARRAY = UTexture1DArray | ||
256 | | t == gl_UNSIGNED_INT_SAMPLER_2D = UTexture2D | ||
257 | | t == gl_UNSIGNED_INT_SAMPLER_2D_ARRAY = UTexture2DArray | ||
258 | | t == gl_UNSIGNED_INT_SAMPLER_2D_MULTISAMPLE = UTexture2DMS | ||
259 | | t == gl_UNSIGNED_INT_SAMPLER_2D_MULTISAMPLE_ARRAY = UTexture2DMSArray | ||
260 | | t == gl_UNSIGNED_INT_SAMPLER_2D_RECT = UTexture2DRect | ||
261 | | t == gl_UNSIGNED_INT_SAMPLER_3D = UTexture3D | ||
262 | | t == gl_UNSIGNED_INT_SAMPLER_BUFFER = UTextureBuffer | ||
263 | | t == gl_UNSIGNED_INT_SAMPLER_CUBE = UTextureCube | ||
264 | | otherwise = error "Failed fromGLType" | ||
265 | fromGLUniformType _ = error "Failed fromGLType" | ||
266 | |||
267 | printShaderLog :: GLuint -> IO () | ||
268 | printShaderLog o = do | ||
269 | i <- glGetShaderiv1 gl_INFO_LOG_LENGTH o | ||
270 | when (i > 0) $ | ||
271 | alloca $ \sizePtr -> allocaArray (fromIntegral i) $! \ps -> do | ||
272 | glGetShaderInfoLog o (fromIntegral i) sizePtr ps | ||
273 | size <- peek sizePtr | ||
274 | log <- SB.packCStringLen (castPtr ps, fromIntegral size) | ||
275 | SB.putStrLn log | ||
276 | |||
277 | glGetShaderiv1 :: GLenum -> GLuint -> IO GLint | ||
278 | glGetShaderiv1 pname o = alloca $! \pi -> glGetShaderiv o pname pi >> peek pi | ||
279 | |||
280 | glGetProgramiv1 :: GLenum -> GLuint -> IO GLint | ||
281 | glGetProgramiv1 pname o = alloca $! \pi -> glGetProgramiv o pname pi >> peek pi | ||
282 | |||
283 | printProgramLog :: GLuint -> IO () | ||
284 | printProgramLog o = do | ||
285 | i <- glGetProgramiv1 gl_INFO_LOG_LENGTH o | ||
286 | when (i > 0) $ | ||
287 | alloca $ \sizePtr -> allocaArray (fromIntegral i) $! \ps -> do | ||
288 | glGetProgramInfoLog o (fromIntegral i) sizePtr ps | ||
289 | size <- peek sizePtr | ||
290 | log <- SB.packCStringLen (castPtr ps, fromIntegral size) | ||
291 | SB.putStrLn log | ||
292 | |||
293 | compileShader :: GLuint -> [ByteString] -> IO () | ||
294 | compileShader o srcl = withMany SB.useAsCString srcl $! \l -> withArray l $! \p -> do | ||
295 | glShaderSource o (fromIntegral $! length srcl) (castPtr p) nullPtr | ||
296 | glCompileShader o | ||
297 | printShaderLog o | ||
298 | status <- glGetShaderiv1 gl_COMPILE_STATUS o | ||
299 | when (status /= fromIntegral gl_TRUE) $ fail "compileShader failed!" | ||
300 | |||
301 | checkGL :: IO ByteString | ||
302 | checkGL = do | ||
303 | let f e | e == gl_INVALID_ENUM = "INVALID_ENUM" | ||
304 | | e == gl_INVALID_VALUE = "INVALID_VALUE" | ||
305 | | e == gl_INVALID_OPERATION = "INVALID_OPERATION" | ||
306 | | e == gl_INVALID_FRAMEBUFFER_OPERATION = "INVALID_FRAMEBUFFER_OPERATION" | ||
307 | | e == gl_OUT_OF_MEMORY = "OUT_OF_MEMORY" | ||
308 | | e == gl_NO_ERROR = "OK" | ||
309 | | otherwise = "Unknown error" | ||
310 | e <- glGetError | ||
311 | return $ f e | ||
312 | |||
313 | streamToInputType :: Stream Buffer -> InputType | ||
314 | streamToInputType s = case s of | ||
315 | ConstWord _ -> Word | ||
316 | ConstV2U _ -> V2U | ||
317 | ConstV3U _ -> V3U | ||
318 | ConstV4U _ -> V4U | ||
319 | ConstInt _ -> Int | ||
320 | ConstV2I _ -> V2I | ||
321 | ConstV3I _ -> V3I | ||
322 | ConstV4I _ -> V4I | ||
323 | ConstFloat _ -> Float | ||
324 | ConstV2F _ -> V2F | ||
325 | ConstV3F _ -> V3F | ||
326 | ConstV4F _ -> V4F | ||
327 | ConstM22F _ -> M22F | ||
328 | ConstM23F _ -> M23F | ||
329 | ConstM24F _ -> M24F | ||
330 | ConstM32F _ -> M32F | ||
331 | ConstM33F _ -> M33F | ||
332 | ConstM34F _ -> M34F | ||
333 | ConstM42F _ -> M42F | ||
334 | ConstM43F _ -> M43F | ||
335 | ConstM44F _ -> M44F | ||
336 | Stream t (Buffer a _) i _ _ | ||
337 | | 0 <= i && i < V.length a && | ||
338 | if elem t integralTypes then elem at integralArrTypes else True | ||
339 | -> fromStreamType t | ||
340 | | otherwise -> throw $ userError "streamToInputType failed" | ||
341 | where | ||
342 | at = arrType $! (a V.! i) | ||
343 | integralTypes = [TWord, TV2U, TV3U, TV4U, TInt, TV2I, TV3I, TV4I] | ||
344 | integralArrTypes = [ArrWord8, ArrWord16, ArrWord32, ArrInt8, ArrInt16, ArrInt32] | ||
345 | |||
346 | comparisonFunctionToGLType :: ComparisonFunction -> GLenum | ||
347 | comparisonFunctionToGLType a = case a of | ||
348 | Always -> gl_ALWAYS | ||
349 | Equal -> gl_EQUAL | ||
350 | Gequal -> gl_GEQUAL | ||
351 | Greater -> gl_GREATER | ||
352 | Lequal -> gl_LEQUAL | ||
353 | Less -> gl_LESS | ||
354 | Never -> gl_NEVER | ||
355 | Notequal -> gl_NOTEQUAL | ||
356 | |||
357 | logicOperationToGLType :: LogicOperation -> GLenum | ||
358 | logicOperationToGLType a = case a of | ||
359 | And -> gl_AND | ||
360 | AndInverted -> gl_AND_INVERTED | ||
361 | AndReverse -> gl_AND_REVERSE | ||
362 | Clear -> gl_CLEAR | ||
363 | Copy -> gl_COPY | ||
364 | CopyInverted -> gl_COPY_INVERTED | ||
365 | Equiv -> gl_EQUIV | ||
366 | Invert -> gl_INVERT | ||
367 | Nand -> gl_NAND | ||
368 | Noop -> gl_NOOP | ||
369 | Nor -> gl_NOR | ||
370 | Or -> gl_OR | ||
371 | OrInverted -> gl_OR_INVERTED | ||
372 | OrReverse -> gl_OR_REVERSE | ||
373 | Set -> gl_SET | ||
374 | Xor -> gl_XOR | ||
375 | |||
376 | blendEquationToGLType :: BlendEquation -> GLenum | ||
377 | blendEquationToGLType a = case a of | ||
378 | FuncAdd -> gl_FUNC_ADD | ||
379 | FuncReverseSubtract -> gl_FUNC_REVERSE_SUBTRACT | ||
380 | FuncSubtract -> gl_FUNC_SUBTRACT | ||
381 | Max -> gl_MAX | ||
382 | Min -> gl_MIN | ||
383 | |||
384 | blendingFactorToGLType :: BlendingFactor -> GLenum | ||
385 | blendingFactorToGLType a = case a of | ||
386 | ConstantAlpha -> gl_CONSTANT_ALPHA | ||
387 | ConstantColor -> gl_CONSTANT_COLOR | ||
388 | DstAlpha -> gl_DST_ALPHA | ||
389 | DstColor -> gl_DST_COLOR | ||
390 | One -> gl_ONE | ||
391 | OneMinusConstantAlpha -> gl_ONE_MINUS_CONSTANT_ALPHA | ||
392 | OneMinusConstantColor -> gl_ONE_MINUS_CONSTANT_COLOR | ||
393 | OneMinusDstAlpha -> gl_ONE_MINUS_DST_ALPHA | ||
394 | OneMinusDstColor -> gl_ONE_MINUS_DST_COLOR | ||
395 | OneMinusSrcAlpha -> gl_ONE_MINUS_SRC_ALPHA | ||
396 | OneMinusSrcColor -> gl_ONE_MINUS_SRC_COLOR | ||
397 | SrcAlpha -> gl_SRC_ALPHA | ||
398 | SrcAlphaSaturate -> gl_SRC_ALPHA_SATURATE | ||
399 | SrcColor -> gl_SRC_COLOR | ||
400 | Zero -> gl_ZERO | ||
401 | |||
402 | textureDataTypeToGLType :: ImageSemantic -> TextureDataType -> GLenum | ||
403 | textureDataTypeToGLType Color a = case a of | ||
404 | FloatT Red -> gl_R32F | ||
405 | IntT Red -> gl_R32I | ||
406 | WordT Red -> gl_R32UI | ||
407 | FloatT RG -> gl_RG32F | ||
408 | IntT RG -> gl_RG32I | ||
409 | WordT RG -> gl_RG32UI | ||
410 | FloatT RGBA -> gl_RGBA32F | ||
411 | IntT RGBA -> gl_RGBA32I | ||
412 | WordT RGBA -> gl_RGBA32UI | ||
413 | a -> error $ "FIXME: This texture format is not yet supported" ++ show a | ||
414 | textureDataTypeToGLType Depth a = case a of | ||
415 | FloatT Red -> gl_DEPTH_COMPONENT32F | ||
416 | WordT Red -> gl_DEPTH_COMPONENT32 | ||
417 | a -> error $ "FIXME: This texture format is not yet supported" ++ show a | ||
418 | textureDataTypeToGLType Stencil a = case a of | ||
419 | a -> error $ "FIXME: This texture format is not yet supported" ++ show a | ||
420 | |||
421 | textureDataTypeToGLArityType :: ImageSemantic -> TextureDataType -> GLenum | ||
422 | textureDataTypeToGLArityType Color a = case a of | ||
423 | FloatT Red -> gl_RED | ||
424 | IntT Red -> gl_RED | ||
425 | WordT Red -> gl_RED | ||
426 | FloatT RG -> gl_RG | ||
427 | IntT RG -> gl_RG | ||
428 | WordT RG -> gl_RG | ||
429 | FloatT RGBA -> gl_RGBA | ||
430 | IntT RGBA -> gl_RGBA | ||
431 | WordT RGBA -> gl_RGBA | ||
432 | a -> error $ "FIXME: This texture format is not yet supported" ++ show a | ||
433 | textureDataTypeToGLArityType Depth a = case a of | ||
434 | FloatT Red -> gl_DEPTH_COMPONENT | ||
435 | WordT Red -> gl_DEPTH_COMPONENT | ||
436 | a -> error $ "FIXME: This texture format is not yet supported" ++ show a | ||
437 | textureDataTypeToGLArityType Stencil a = case a of | ||
438 | a -> error $ "FIXME: This texture format is not yet supported" ++ show a | ||
439 | {- | ||
440 | Texture and renderbuffer color formats (R): | ||
441 | R11F_G11F_B10F | ||
442 | R16 | ||
443 | R16F | ||
444 | R16I | ||
445 | R16UI | ||
446 | R32F | ||
447 | R32I | ||
448 | R32UI | ||
449 | R8 | ||
450 | R8I | ||
451 | R8UI | ||
452 | RG16 | ||
453 | RG16F | ||
454 | RG16I | ||
455 | RG16UI | ||
456 | RG32F | ||
457 | RG32I | ||
458 | RG32UI | ||
459 | RG8 | ||
460 | RG8I | ||
461 | RG8UI | ||
462 | RGB10_A2 | ||
463 | RGB10_A2UI | ||
464 | RGBA16 | ||
465 | RGBA16F | ||
466 | RGBA16I | ||
467 | RGBA16UI | ||
468 | RGBA32F | ||
469 | RGBA32I | ||
470 | RGBA32UI | ||
471 | RGBA8 | ||
472 | RGBA8I | ||
473 | RGBA8UI | ||
474 | SRGB8_ALPHA8 | ||
475 | -} | ||
476 | |||
477 | glGetIntegerv1 :: GLenum -> IO GLint | ||
478 | glGetIntegerv1 e = alloca $ \pi -> glGetIntegerv e pi >> peek pi | ||
479 | |||
480 | checkFBO :: IO ByteString | ||
481 | checkFBO = do | ||
482 | let f e | e == gl_FRAMEBUFFER_UNDEFINED = "FRAMEBUFFER_UNDEFINED" | ||
483 | | e == gl_FRAMEBUFFER_INCOMPLETE_ATTACHMENT = "FRAMEBUFFER_INCOMPLETE_ATTACHMENT" | ||
484 | | e == gl_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER = "FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER" | ||
485 | | e == gl_FRAMEBUFFER_INCOMPLETE_READ_BUFFER = "FRAMEBUFFER_INCOMPLETE_READ_BUFFER" | ||
486 | | e == gl_FRAMEBUFFER_UNSUPPORTED = "FRAMEBUFFER_UNSUPPORTED" | ||
487 | | e == gl_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE = "FRAMEBUFFER_INCOMPLETE_MULTISAMPLE" | ||
488 | | e == gl_FRAMEBUFFER_INCOMPLETE_LAYER_TARGETS = "FRAMEBUFFER_INCOMPLETE_LAYER_TARGETS" | ||
489 | | e == gl_FRAMEBUFFER_COMPLETE = "FRAMEBUFFER_COMPLETE" | ||
490 | | otherwise = "Unknown error" | ||
491 | e <- glCheckFramebufferStatus gl_DRAW_FRAMEBUFFER | ||
492 | return $ f e | ||
493 | |||
494 | filterToGLType :: Filter -> GLenum | ||
495 | filterToGLType a = case a of | ||
496 | Nearest -> gl_NEAREST | ||
497 | Linear -> gl_LINEAR | ||
498 | NearestMipmapNearest -> gl_NEAREST_MIPMAP_NEAREST | ||
499 | NearestMipmapLinear -> gl_NEAREST_MIPMAP_LINEAR | ||
500 | LinearMipmapNearest -> gl_LINEAR_MIPMAP_NEAREST | ||
501 | LinearMipmapLinear -> gl_LINEAR_MIPMAP_LINEAR | ||
502 | |||
503 | edgeModeToGLType :: EdgeMode -> GLenum | ||
504 | edgeModeToGLType a = case a of | ||
505 | Repeat -> gl_REPEAT | ||
506 | MirroredRepeat -> gl_MIRRORED_REPEAT | ||
507 | ClampToEdge -> gl_CLAMP_TO_EDGE | ||
508 | ClampToBorder -> gl_CLAMP_TO_BORDER | ||
509 | |||
510 | setTextureSamplerParameters :: GLenum -> SamplerDescriptor -> IO () | ||
511 | setTextureSamplerParameters t s = do | ||
512 | glTexParameteri t gl_TEXTURE_WRAP_S $ fromIntegral $ edgeModeToGLType $ samplerWrapS s | ||
513 | case samplerWrapT s of | ||
514 | Nothing -> return () | ||
515 | Just a -> glTexParameteri t gl_TEXTURE_WRAP_T $ fromIntegral $ edgeModeToGLType a | ||
516 | case samplerWrapR s of | ||
517 | Nothing -> return () | ||
518 | Just a -> glTexParameteri t gl_TEXTURE_WRAP_R $ fromIntegral $ edgeModeToGLType a | ||
519 | glTexParameteri t gl_TEXTURE_MIN_FILTER $ fromIntegral $ filterToGLType $ samplerMinFilter s | ||
520 | glTexParameteri t gl_TEXTURE_MAG_FILTER $ fromIntegral $ filterToGLType $ samplerMagFilter s | ||
521 | |||
522 | let setBColorV4F a = with a $ \p -> glTexParameterfv t gl_TEXTURE_BORDER_COLOR $ castPtr p | ||
523 | setBColorV4I a = with a $ \p -> glTexParameterIiv t gl_TEXTURE_BORDER_COLOR $ castPtr p | ||
524 | setBColorV4U a = with a $ \p -> glTexParameterIuiv t gl_TEXTURE_BORDER_COLOR $ castPtr p | ||
525 | case samplerBorderColor s of | ||
526 | -- float, word, int, red, rg, rgb, rgba | ||
527 | VFloat a -> setBColorV4F $ V4 a 0 0 0 | ||
528 | VV2F (V2 a b) -> setBColorV4F $ V4 a b 0 0 | ||
529 | VV3F (V3 a b c) -> setBColorV4F $ V4 a b c 0 | ||
530 | VV4F a -> setBColorV4F a | ||
531 | |||
532 | VInt a -> setBColorV4I $ V4 a 0 0 0 | ||
533 | VV2I (V2 a b) -> setBColorV4I $ V4 a b 0 0 | ||
534 | VV3I (V3 a b c) -> setBColorV4I $ V4 a b c 0 | ||
535 | VV4I a -> setBColorV4I a | ||
536 | |||
537 | VWord a -> setBColorV4U $ V4 a 0 0 0 | ||
538 | VV2U (V2 a b) -> setBColorV4U $ V4 a b 0 0 | ||
539 | VV3U (V3 a b c) -> setBColorV4U $ V4 a b c 0 | ||
540 | VV4U a -> setBColorV4U a | ||
541 | _ -> fail "internal error (setTextureSamplerParameters)!" | ||
542 | |||
543 | case samplerMinLod s of | ||
544 | Nothing -> return () | ||
545 | Just a -> glTexParameterf t gl_TEXTURE_MIN_LOD $ realToFrac a | ||
546 | case samplerMaxLod s of | ||
547 | Nothing -> return () | ||
548 | Just a -> glTexParameterf t gl_TEXTURE_MAX_LOD $ realToFrac a | ||
549 | glTexParameterf t gl_TEXTURE_LOD_BIAS $ realToFrac $ samplerLodBias s | ||
550 | case samplerCompareFunc s of | ||
551 | Nothing -> glTexParameteri t gl_TEXTURE_COMPARE_MODE $ fromIntegral gl_NONE | ||
552 | Just a -> do | ||
553 | glTexParameteri t gl_TEXTURE_COMPARE_MODE $ fromIntegral gl_COMPARE_REF_TO_TEXTURE | ||
554 | glTexParameteri t gl_TEXTURE_COMPARE_FUNC $ fromIntegral $ comparisonFunctionToGLType a | ||
555 | |||
556 | compileTexture :: TextureDescriptor -> IO GLTexture | ||
557 | compileTexture txDescriptor = do | ||
558 | to <- alloca $! \pto -> glGenTextures 1 pto >> peek pto | ||
559 | let TextureDescriptor | ||
560 | { textureType = txType | ||
561 | , textureSize = txSize | ||
562 | , textureSemantic = txSemantic | ||
563 | , textureSampler = txSampler | ||
564 | , textureBaseLevel = txBaseLevel | ||
565 | , textureMaxLevel = txMaxLevel | ||
566 | } = txDescriptor | ||
567 | |||
568 | txSetup txTarget dTy = do | ||
569 | let internalFormat = fromIntegral $ textureDataTypeToGLType txSemantic dTy | ||
570 | dataFormat = fromIntegral $ textureDataTypeToGLArityType txSemantic dTy | ||
571 | glBindTexture txTarget to | ||
572 | glTexParameteri txTarget gl_TEXTURE_BASE_LEVEL $ fromIntegral txBaseLevel | ||
573 | glTexParameteri txTarget gl_TEXTURE_MAX_LEVEL $ fromIntegral txMaxLevel | ||
574 | setTextureSamplerParameters txTarget txSampler | ||
575 | return (internalFormat,dataFormat) | ||
576 | |||
577 | mipSize 0 x = [x] | ||
578 | mipSize n x = x : mipSize (n-1) (x `div` 2) | ||
579 | mipS = mipSize (txMaxLevel - txBaseLevel) | ||
580 | levels = [txBaseLevel..txMaxLevel] | ||
581 | target <- case txType of | ||
582 | Texture1D dTy layerCnt -> do | ||
583 | let VWord txW = txSize | ||
584 | txTarget = if layerCnt > 1 then gl_TEXTURE_1D_ARRAY else gl_TEXTURE_1D | ||
585 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
586 | forM_ (zip levels (mipS txW)) $ \(l,w) -> case layerCnt > 1 of | ||
587 | True -> glTexImage2D txTarget (fromIntegral l) internalFormat (fromIntegral w) (fromIntegral layerCnt) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
588 | False -> glTexImage1D txTarget (fromIntegral l) internalFormat (fromIntegral w) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
589 | return txTarget | ||
590 | Texture2D dTy layerCnt -> do | ||
591 | let VV2U (V2 txW txH) = txSize | ||
592 | txTarget = if layerCnt > 1 then gl_TEXTURE_2D_ARRAY else gl_TEXTURE_2D | ||
593 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
594 | forM_ (zip3 levels (mipS txW) (mipS txH)) $ \(l,w,h) -> case layerCnt > 1 of | ||
595 | True -> glTexImage3D txTarget (fromIntegral l) internalFormat (fromIntegral w) (fromIntegral h) (fromIntegral layerCnt) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
596 | False -> glTexImage2D txTarget (fromIntegral l) internalFormat (fromIntegral w) (fromIntegral h) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
597 | return txTarget | ||
598 | Texture3D dTy -> do | ||
599 | let VV3U (V3 txW txH txD) = txSize | ||
600 | txTarget = gl_TEXTURE_3D | ||
601 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
602 | forM_ (zip4 levels (mipS txW) (mipS txH) (mipS txD)) $ \(l,w,h,d) -> | ||
603 | glTexImage3D txTarget (fromIntegral l) internalFormat (fromIntegral w) (fromIntegral h) (fromIntegral d) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
604 | return txTarget | ||
605 | TextureCube dTy -> do | ||
606 | let VV2U (V2 txW txH) = txSize | ||
607 | txTarget = gl_TEXTURE_CUBE_MAP | ||
608 | targets = | ||
609 | [ gl_TEXTURE_CUBE_MAP_POSITIVE_X | ||
610 | , gl_TEXTURE_CUBE_MAP_NEGATIVE_X | ||
611 | , gl_TEXTURE_CUBE_MAP_POSITIVE_Y | ||
612 | , gl_TEXTURE_CUBE_MAP_NEGATIVE_Y | ||
613 | , gl_TEXTURE_CUBE_MAP_POSITIVE_Z | ||
614 | , gl_TEXTURE_CUBE_MAP_NEGATIVE_Z | ||
615 | ] | ||
616 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
617 | forM_ (zip3 levels (mipS txW) (mipS txH)) $ \(l,w,h) -> | ||
618 | forM_ targets $ \t -> glTexImage2D t (fromIntegral l) internalFormat (fromIntegral w) (fromIntegral h) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
619 | return txTarget | ||
620 | TextureRect dTy -> do | ||
621 | let VV2U (V2 txW txH) = txSize | ||
622 | txTarget = gl_TEXTURE_RECTANGLE | ||
623 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
624 | forM_ (zip3 levels (mipS txW) (mipS txH)) $ \(l,w,h) -> | ||
625 | glTexImage2D txTarget (fromIntegral l) internalFormat (fromIntegral w) (fromIntegral h) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
626 | return txTarget | ||
627 | Texture2DMS dTy layerCnt sampleCount isFixedLocations -> do | ||
628 | let VV2U (V2 w h) = txSize | ||
629 | txTarget = if layerCnt > 1 then gl_TEXTURE_2D_MULTISAMPLE_ARRAY else gl_TEXTURE_2D_MULTISAMPLE | ||
630 | isFixed = fromIntegral $ if isFixedLocations then gl_TRUE else gl_FALSE | ||
631 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
632 | case layerCnt > 1 of | ||
633 | True -> glTexImage3DMultisample txTarget (fromIntegral sampleCount) internalFormat (fromIntegral w) (fromIntegral h) (fromIntegral layerCnt) isFixed | ||
634 | False -> glTexImage2DMultisample txTarget (fromIntegral sampleCount) internalFormat (fromIntegral w) (fromIntegral h) isFixed | ||
635 | return txTarget | ||
636 | TextureBuffer dTy -> do | ||
637 | fail "internal error: buffer texture is not supported yet" | ||
638 | -- TODO | ||
639 | let VV2U (V2 w h) = txSize | ||
640 | txTarget = gl_TEXTURE_2D | ||
641 | (internalFormat,dataFormat) <- txSetup txTarget dTy | ||
642 | glTexImage2D gl_TEXTURE_2D 0 internalFormat (fromIntegral w) (fromIntegral h) 0 dataFormat gl_UNSIGNED_BYTE nullPtr | ||
643 | return txTarget | ||
644 | return $ GLTexture | ||
645 | { glTextureObject = to | ||
646 | , glTextureTarget = target | ||
647 | } | ||
648 | |||
649 | primitiveToFetchPrimitive :: Primitive -> FetchPrimitive | ||
650 | primitiveToFetchPrimitive prim = case prim of | ||
651 | TriangleStrip -> Triangles | ||
652 | TriangleList -> Triangles | ||
653 | TriangleFan -> Triangles | ||
654 | LineStrip -> Lines | ||
655 | LineList -> Lines | ||
656 | PointList -> Points | ||
657 | TriangleStripAdjacency -> TrianglesAdjacency | ||
658 | TriangleListAdjacency -> TrianglesAdjacency | ||
659 | LineStripAdjacency -> LinesAdjacency | ||
660 | LineListAdjacency -> LinesAdjacency | ||
661 | |||
662 | primitiveToGLType :: Primitive -> GLenum | ||
663 | primitiveToGLType p = case p of | ||
664 | TriangleStrip -> gl_TRIANGLE_STRIP | ||
665 | TriangleList -> gl_TRIANGLES | ||
666 | TriangleFan -> gl_TRIANGLE_FAN | ||
667 | LineStrip -> gl_LINE_STRIP | ||
668 | LineList -> gl_LINES | ||
669 | PointList -> gl_POINTS | ||
670 | TriangleStripAdjacency -> gl_TRIANGLE_STRIP_ADJACENCY | ||
671 | TriangleListAdjacency -> gl_TRIANGLES_ADJACENCY | ||
672 | LineStripAdjacency -> gl_LINE_STRIP_ADJACENCY | ||
673 | LineListAdjacency -> gl_LINES_ADJACENCY | ||
674 | |||
675 | inputTypeToTextureTarget :: InputType -> GLenum | ||
676 | inputTypeToTextureTarget ty = case ty of | ||
677 | STexture1D -> gl_TEXTURE_1D | ||
678 | STexture2D -> gl_TEXTURE_2D | ||
679 | STextureCube -> gl_TEXTURE_CUBE_MAP | ||
680 | STexture1DArray -> gl_TEXTURE_1D_ARRAY | ||
681 | STexture2DArray -> gl_TEXTURE_2D_ARRAY | ||
682 | STexture2DRect -> gl_TEXTURE_RECTANGLE | ||
683 | |||
684 | FTexture1D -> gl_TEXTURE_1D | ||
685 | FTexture2D -> gl_TEXTURE_2D | ||
686 | FTexture3D -> gl_TEXTURE_3D | ||
687 | FTextureCube -> gl_TEXTURE_CUBE_MAP | ||
688 | FTexture1DArray -> gl_TEXTURE_1D_ARRAY | ||
689 | FTexture2DArray -> gl_TEXTURE_2D_ARRAY | ||
690 | FTexture2DMS -> gl_TEXTURE_2D_MULTISAMPLE | ||
691 | FTexture2DMSArray -> gl_TEXTURE_2D_MULTISAMPLE_ARRAY | ||
692 | FTextureBuffer -> gl_TEXTURE_BUFFER | ||
693 | FTexture2DRect -> gl_TEXTURE_RECTANGLE | ||
694 | |||
695 | ITexture1D -> gl_TEXTURE_1D | ||
696 | ITexture2D -> gl_TEXTURE_2D | ||
697 | ITexture3D -> gl_TEXTURE_3D | ||
698 | ITextureCube -> gl_TEXTURE_CUBE_MAP | ||
699 | ITexture1DArray -> gl_TEXTURE_1D_ARRAY | ||
700 | ITexture2DArray -> gl_TEXTURE_2D_ARRAY | ||
701 | ITexture2DMS -> gl_TEXTURE_2D_MULTISAMPLE | ||
702 | ITexture2DMSArray -> gl_TEXTURE_2D_MULTISAMPLE_ARRAY | ||
703 | ITextureBuffer -> gl_TEXTURE_BUFFER | ||
704 | ITexture2DRect -> gl_TEXTURE_RECTANGLE | ||
705 | |||
706 | UTexture1D -> gl_TEXTURE_1D | ||
707 | UTexture2D -> gl_TEXTURE_2D | ||
708 | UTexture3D -> gl_TEXTURE_3D | ||
709 | UTextureCube -> gl_TEXTURE_CUBE_MAP | ||
710 | UTexture1DArray -> gl_TEXTURE_1D_ARRAY | ||
711 | UTexture2DArray -> gl_TEXTURE_2D_ARRAY | ||
712 | UTexture2DMS -> gl_TEXTURE_2D_MULTISAMPLE | ||
713 | UTexture2DMSArray -> gl_TEXTURE_2D_MULTISAMPLE_ARRAY | ||
714 | UTextureBuffer -> gl_TEXTURE_BUFFER | ||
715 | UTexture2DRect -> gl_TEXTURE_RECTANGLE | ||
716 | |||
717 | _ -> error "internal error (inputTypeToTextureTarget)!" | ||