progs/tests: compile with SCons and glew
[mesa.git] / progs / tests / arraytexture.c
1 /*
2 * (C) Copyright IBM Corporation 2007
3 * All Rights Reserved.
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * on the rights to use, copy, modify, merge, publish, distribute, sub
9 * license, and/or sell copies of the Software, and to permit persons to whom
10 * the Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice (including the next
13 * paragraph) shall be included in all copies or substantial portions of the
14 * Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
19 * IBM AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22 * IN THE SOFTWARE.
23 */
24
25 /**
26 * \file arraytexture.c
27 *
28 *
29 * \author Ian Romanick <idr@us.ibm.com>
30 */
31
32 #include <assert.h>
33 #include <stdlib.h>
34 #include <stdio.h>
35 #include <string.h>
36 #include <math.h>
37 #include <GL/glew.h>
38 #include <GL/glut.h>
39 #include <GL/glext.h>
40
41 #if !defined(GL_EXT_texture_array) && !defined(GL_MESA_texture_array)
42 # error "This demo requires enums for either GL_EXT_texture_array or GL_MESA_texture_array to build."
43 #endif
44
45 #include "readtex.h"
46
47 #define GL_CHECK_ERROR() \
48 do { \
49 GLenum err = glGetError(); \
50 if (err) { \
51 printf("%s:%u: %s (0x%04x)\n", __FILE__, __LINE__, \
52 gluErrorString(err), err); \
53 } \
54 } while (0)
55
56 static const char *const textures[] = {
57 "../images/girl.rgb",
58 "../images/girl2.rgb",
59 "../images/arch.rgb",
60 "../images/s128.rgb",
61
62 "../images/tree3.rgb",
63 "../images/bw.rgb",
64 "../images/reflect.rgb",
65 "../images/wrs_logo.rgb",
66 NULL
67 };
68
69 static const char frag_prog[] =
70 "!!ARBfp1.0\n"
71 "OPTION MESA_texture_array;\n"
72 "TEX result.color, fragment.texcoord[0], texture[0], ARRAY2D;\n"
73 "END\n";
74
75 static GLfloat Xrot = 0, Yrot = -30, Zrot = 0;
76 static GLfloat texZ = 0.0;
77 static GLfloat texZ_dir = 0.01;
78 static GLint num_layers;
79
80 static PFNGLBINDPROGRAMARBPROC bind_program;
81 static PFNGLPROGRAMSTRINGARBPROC program_string;
82 static PFNGLGENPROGRAMSARBPROC gen_programs;
83
84
85 static void
86 PrintString(const char *s)
87 {
88 while (*s) {
89 glutBitmapCharacter(GLUT_BITMAP_8_BY_13, (int) *s);
90 s++;
91 }
92 }
93
94
95 static void Idle(void)
96 {
97 static int lastTime = 0;
98 int t = glutGet(GLUT_ELAPSED_TIME);
99
100 if (lastTime == 0)
101 lastTime = t;
102 else if (t - lastTime < 10)
103 return;
104
105 lastTime = t;
106
107 texZ += texZ_dir;
108 if ((texZ < 0.0) || ((GLint) texZ > num_layers)) {
109 texZ_dir = -texZ_dir;
110 }
111
112 glutPostRedisplay();
113 }
114
115
116 static void Display(void)
117 {
118 char str[100];
119
120 glClear(GL_COLOR_BUFFER_BIT);
121
122 glMatrixMode(GL_PROJECTION);
123 glLoadIdentity();
124 glOrtho(-1, 1, -1, 1, -1, 1);
125 glMatrixMode(GL_MODELVIEW);
126 glLoadIdentity();
127
128 (*bind_program)(GL_FRAGMENT_PROGRAM_ARB, 0);
129 glColor3f(1,1,1);
130 glRasterPos3f(-0.9, -0.9, 0.0);
131 sprintf(str, "Texture Z coordinate = %4.1f", texZ);
132 PrintString(str);
133
134 (*bind_program)(GL_FRAGMENT_PROGRAM_ARB, 1);
135 GL_CHECK_ERROR();
136 glEnable(GL_TEXTURE_2D_ARRAY_EXT);
137 GL_CHECK_ERROR();
138
139 glMatrixMode(GL_PROJECTION);
140 glLoadIdentity();
141 glFrustum(-1.0, 1.0, -1.0, 1.0, 5.0, 25.0);
142 glMatrixMode(GL_MODELVIEW);
143 glLoadIdentity();
144 glTranslatef(0.0, 0.0, -8.0);
145
146 glPushMatrix();
147 glRotatef(Xrot, 1, 0, 0);
148 glRotatef(Yrot, 0, 1, 0);
149 glRotatef(Zrot, 0, 0, 1);
150
151 glBegin(GL_QUADS);
152 glTexCoord3f(0.0, 0.0, texZ); glVertex2f(-1.0, -1.0);
153 glTexCoord3f(2.0, 0.0, texZ); glVertex2f(1.0, -1.0);
154 glTexCoord3f(2.0, 2.0, texZ); glVertex2f(1.0, 1.0);
155 glTexCoord3f(0.0, 2.0, texZ); glVertex2f(-1.0, 1.0);
156 glEnd();
157
158 glPopMatrix();
159
160 glDisable(GL_TEXTURE_2D_ARRAY_EXT);
161 GL_CHECK_ERROR();
162 (*bind_program)(GL_FRAGMENT_PROGRAM_ARB, 0);
163 GL_CHECK_ERROR();
164
165 glutSwapBuffers();
166 }
167
168
169 static void Reshape(int width, int height)
170 {
171 glViewport(0, 0, width, height);
172 }
173
174
175 static void Key(unsigned char key, int x, int y)
176 {
177 (void) x;
178 (void) y;
179 switch (key) {
180 case 27:
181 exit(0);
182 break;
183 }
184 glutPostRedisplay();
185 }
186
187
188 static void SpecialKey(int key, int x, int y)
189 {
190 const GLfloat step = 3.0;
191 (void) x;
192 (void) y;
193 switch (key) {
194 case GLUT_KEY_UP:
195 Xrot -= step;
196 break;
197 case GLUT_KEY_DOWN:
198 Xrot += step;
199 break;
200 case GLUT_KEY_LEFT:
201 Yrot -= step;
202 break;
203 case GLUT_KEY_RIGHT:
204 Yrot += step;
205 break;
206 }
207 glutPostRedisplay();
208 }
209
210
211 static int FindLine(const char *program, int position)
212 {
213 int i, line = 1;
214 for (i = 0; i < position; i++) {
215 if (program[i] == '\n')
216 line++;
217 }
218 return line;
219 }
220
221
222 static void
223 compile_fragment_program(GLuint id, const char *prog)
224 {
225 int errorPos;
226 int err;
227
228 err = glGetError();
229 (*bind_program)(GL_FRAGMENT_PROGRAM_ARB, id);
230 (*program_string)(GL_FRAGMENT_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB,
231 strlen(prog), (const GLubyte *) prog);
232
233 glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &errorPos);
234 err = glGetError();
235 if (err != GL_NO_ERROR || errorPos != -1) {
236 int l = FindLine(prog, errorPos);
237
238 printf("Fragment Program Error (err=%d, pos=%d line=%d): %s\n",
239 err, errorPos, l,
240 (char *) glGetString(GL_PROGRAM_ERROR_STRING_ARB));
241 exit(0);
242 }
243 }
244
245
246 static void require_extension(const char *ext)
247 {
248 if (!glutExtensionSupported(ext)) {
249 printf("Sorry, %s not supported by this renderer.\n", ext);
250 exit(1);
251 }
252 }
253
254
255 static void Init(void)
256 {
257 const char *const ver_string = (const char *const) glGetString(GL_VERSION);
258 unsigned i;
259
260 printf("GL_RENDERER = %s\n", (char *) glGetString(GL_RENDERER));
261 printf("GL_VERSION = %s\n", ver_string);
262
263 require_extension("GL_ARB_fragment_program");
264 require_extension("GL_MESA_texture_array");
265 require_extension("GL_SGIS_generate_mipmap");
266
267 bind_program = glutGetProcAddress("glBindProgramARB");
268 program_string = glutGetProcAddress("glProgramStringARB");
269 gen_programs = glutGetProcAddress("glGenProgramsARB");
270
271
272 for (num_layers = 0; textures[num_layers] != NULL; num_layers++)
273 /* empty */ ;
274
275 glBindTexture(GL_TEXTURE_2D_ARRAY_EXT, 1);
276 glTexImage3D(GL_TEXTURE_2D_ARRAY_EXT, 0, GL_RGB8,
277 256, 256, num_layers, 0, GL_RGB, GL_UNSIGNED_BYTE, NULL);
278 GL_CHECK_ERROR();
279
280 glTexParameteri(GL_TEXTURE_2D_ARRAY_EXT, GL_GENERATE_MIPMAP_SGIS,
281 GL_TRUE);
282
283 for (i = 0; textures[i] != NULL; i++) {
284 GLint width, height;
285 GLenum format;
286
287 GLubyte *image = LoadRGBImage(textures[i], &width, &height, &format);
288 if (!image) {
289 printf("Error: could not load texture image %s\n", textures[i]);
290 exit(1);
291 }
292
293 /* resize to 256 x 256 */
294 if (width != 256 || height != 256) {
295 GLubyte *newImage = malloc(256 * 256 * 4);
296 gluScaleImage(format, width, height, GL_UNSIGNED_BYTE, image,
297 256, 256, GL_UNSIGNED_BYTE, newImage);
298 free(image);
299 image = newImage;
300 }
301
302 glTexSubImage3D(GL_TEXTURE_2D_ARRAY_EXT, 0,
303 0, 0, i, 256, 256, 1,
304 format, GL_UNSIGNED_BYTE, image);
305 free(image);
306 }
307 GL_CHECK_ERROR();
308
309 glTexParameteri(GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_WRAP_S, GL_REPEAT);
310 glTexParameteri(GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_WRAP_T, GL_REPEAT);
311 glTexParameteri(GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
312
313 glTexParameteri(GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
314 GL_CHECK_ERROR();
315 glTexParameteri(GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
316 GL_CHECK_ERROR();
317
318 compile_fragment_program(1, frag_prog);
319 GL_CHECK_ERROR();
320 }
321
322
323 int main(int argc, char *argv[])
324 {
325 glutInit(&argc, argv);
326 glutInitWindowPosition(0, 0);
327 glutInitWindowSize(350, 350);
328 glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
329 glutCreateWindow("Array texture test");
330 glewInit();
331 glutReshapeFunc(Reshape);
332 glutKeyboardFunc(Key);
333 glutSpecialFunc(SpecialKey);
334 glutDisplayFunc(Display);
335 glutIdleFunc(Idle);
336 Init();
337 glutMainLoop();
338 return 0;
339 }