progs/redbook: Fix array out-of-bounds access.
[mesa.git] / progs / redbook / combiner.c
1 /*
2 * Copyright (c) 1993-2003, Silicon Graphics, Inc.
3 * All Rights Reserved
4 *
5 * Permission to use, copy, modify, and distribute this software for any
6 * purpose and without fee is hereby granted, provided that the above
7 * copyright notice appear in all copies and that both the copyright
8 * notice and this permission notice appear in supporting documentation,
9 * and that the name of Silicon Graphics, Inc. not be used in
10 * advertising or publicity pertaining to distribution of the software
11 * without specific, written prior permission.
12 *
13 * THE MATERIAL EMBODIED ON THIS SOFTWARE IS PROVIDED TO YOU "AS-IS" AND
14 * WITHOUT WARRANTY OF ANY KIND, EXPRESS, IMPLIED OR OTHERWISE,
15 * INCLUDING WITHOUT LIMITATION, ANY WARRANTY OF MERCHANTABILITY OR
16 * FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SILICON
17 * GRAPHICS, INC. BE LIABLE TO YOU OR ANYONE ELSE FOR ANY DIRECT,
18 * SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND,
19 * OR ANY DAMAGES WHATSOEVER, INCLUDING WITHOUT LIMITATION, LOSS OF
20 * PROFIT, LOSS OF USE, SAVINGS OR REVENUE, OR THE CLAIMS OF THIRD
21 * PARTIES, WHETHER OR NOT SILICON GRAPHICS, INC. HAS BEEN ADVISED OF
22 * THE POSSIBILITY OF SUCH LOSS, HOWEVER CAUSED AND ON ANY THEORY OF
23 * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE POSSESSION, USE
24 * OR PERFORMANCE OF THIS SOFTWARE.
25 *
26 * US Government Users Restricted Rights
27 * Use, duplication, or disclosure by the Government is subject to
28 * restrictions set forth in FAR 52.227.19(c)(2) or subparagraph
29 * (c)(1)(ii) of the Rights in Technical Data and Computer Software
30 * clause at DFARS 252.227-7013 and/or in similar or successor clauses
31 * in the FAR or the DOD or NASA FAR Supplement. Unpublished - rights
32 * reserved under the copyright laws of the United States.
33 *
34 * Contractor/manufacturer is:
35 * Silicon Graphics, Inc.
36 * 1500 Crittenden Lane
37 * Mountain View, CA 94043
38 * United State of America
39 *
40 * OpenGL(R) is a registered trademark of Silicon Graphics, Inc.
41 */
42
43 /* combiner.c
44 * This program renders a variety of quads showing different
45 * effects of texture combiner functions.
46 *
47 * The first row renders an untextured polygon (so you can
48 * compare the fragment colors) and then the 2 textures.
49 * The second row shows several different combiner functions
50 * on a single texture: replace, modulate, add, add-signed,
51 * and subtract.
52 * The third row shows the interpolate combiner function
53 * on a single texture with a constant color/alpha value,
54 * varying the amount of interpolation.
55 * The fourth row uses multitexturing with two textures
56 * and different combiner functions.
57 * The fifth row are some combiner experiments: using the
58 * scaling factor and reversing the order of subtraction
59 * for a combination function.
60 */
61 #include <GL/glew.h>
62 #include <GL/glut.h>
63 #include <stdlib.h>
64 #include <stdio.h>
65
66 #define imageWidth 8
67 #define imageHeight 8
68 /* arrays for two textures */
69 static GLubyte image0[imageHeight][imageWidth][4];
70 static GLubyte image1[imageHeight][imageWidth][4];
71
72 static GLuint texName[4];
73
74 static void makeImages(void)
75 {
76 int i, j, c;
77 for (i = 0; i < imageHeight; i++) {
78 for (j = 0; j < imageWidth; j++) {
79 c = ((i&2)==0)*255; /* horiz b & w stripes */
80 image0[i][j][0] = (GLubyte) c;
81 image0[i][j][1] = (GLubyte) c;
82 image0[i][j][2] = (GLubyte) c;
83 image0[i][j][3] = (GLubyte) 255;
84 c = ((j&4)!=0)*128; /* wider vertical 50% cyan and black stripes */
85 image1[i][j][0] = (GLubyte) 0;
86 image1[i][j][1] = (GLubyte) c;
87 image1[i][j][2] = (GLubyte) c;
88 image1[i][j][3] = (GLubyte) 255;
89 }
90 }
91 }
92
93 static void init(void)
94 {
95 glClearColor (0.0, 0.0, 0.0, 0.0);
96 glShadeModel(GL_SMOOTH);
97
98 makeImages();
99 glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
100
101 glGenTextures(4, texName);
102
103 glBindTexture(GL_TEXTURE_2D, texName[0]);
104 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
105 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
106 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
107 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
108 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, imageWidth, imageHeight,
109 0, GL_RGBA, GL_UNSIGNED_BYTE, image0);
110
111 glBindTexture(GL_TEXTURE_2D, texName[1]);
112 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
113 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
114 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
115 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
116 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, imageWidth, imageHeight,
117 0, GL_RGBA, GL_UNSIGNED_BYTE, image1);
118
119 /* smooth-shaded polygon with multiple texture coordinates */
120 glNewList (1, GL_COMPILE);
121 glBegin(GL_QUADS);
122 glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 0.0, 0.0);
123 glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 0.0, 0.0);
124 glColor3f (0.5, 1.0, 0.25);
125 glVertex3f(0.0, 0.0, 0.0);
126 glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 0.0, 2.0);
127 glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 0.0, 2.0);
128 glColor3f (1.0, 1.0, 1.0);
129 glVertex3f(0.0, 1.0, 0.0);
130 glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 2.0, 2.0);
131 glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 2.0, 2.0);
132 glColor3f (1.0, 1.0, 1.0);
133 glVertex3f(1.0, 1.0, 0.0);
134 glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 2.0, 0.0);
135 glMultiTexCoord2fARB(GL_TEXTURE1_ARB, 2.0, 0.0);
136 glColor3f (1.0, 0.5, 0.25);
137 glVertex3f(1.0, 0.0, 0.0);
138 glEnd();
139 glEndList ();
140 }
141
142 static void display(void)
143 {
144 static GLfloat constColor[4] = {0.0, 0.0, 0.0, 0.0}; /* for use as constant texture color */
145
146 glClear(GL_COLOR_BUFFER_BIT);
147
148 glDisable(GL_TEXTURE_2D); /* untextured polygon--see the "fragment" colors */
149 glPushMatrix();
150 glTranslatef(0.0, 5.0, 0.0);
151 glCallList(1);
152 glPopMatrix();
153
154 glEnable(GL_TEXTURE_2D);
155 /* draw ordinary textured polys; 1 texture unit; combine mode disabled */
156 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
157 glPushMatrix();
158 glBindTexture(GL_TEXTURE_2D, texName[0]);
159 glTranslatef(1.0, 5.0, 0.0);
160 glCallList(1);
161 glPopMatrix();
162
163 glPushMatrix();
164 glBindTexture(GL_TEXTURE_2D, texName[1]);
165 glTranslatef(2.0, 5.0, 0.0);
166 glCallList(1);
167 glPopMatrix();
168
169 /* different combine modes enabled; 1 texture unit
170 * defaults are:
171 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE);
172 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR);
173 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB);
174 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR);
175 */
176 glBindTexture(GL_TEXTURE_2D, texName[0]);
177 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB);
178 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE);
179 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE);
180 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR);
181 glPushMatrix();
182 glTranslatef(1.0, 4.0, 0.0);
183 glCallList(1);
184 glPopMatrix();
185
186 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE);
187 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB);
188 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR);
189 glPushMatrix();
190 glTranslatef(2.0, 4.0, 0.0);
191 glCallList(1);
192 glPopMatrix();
193
194 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_ADD);
195 glPushMatrix();
196 glTranslatef(3.0, 4.0, 0.0);
197 glCallList(1);
198 glPopMatrix();
199
200 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_ADD_SIGNED_ARB);
201 glPushMatrix();
202 glTranslatef(4.0, 4.0, 0.0);
203 glCallList(1);
204 glPopMatrix();
205
206 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_SUBTRACT_ARB);
207 glPushMatrix();
208 glTranslatef(5.0, 4.0, 0.0);
209 glCallList(1);
210 glPopMatrix();
211
212 /* interpolate combine with constant color; 1 texture unit
213 * use different alpha values for constant color
214 * defaults are:
215 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE);
216 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR);
217 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB);
218 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR);
219 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_CONSTANT_ARB);
220 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_ALPHA);
221 */
222 constColor[3] = 0.2;
223 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constColor);
224 glBindTexture(GL_TEXTURE_2D, texName[0]);
225 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB);
226 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_INTERPOLATE_ARB);
227 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE);
228 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR);
229 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB);
230 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR);
231 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE2_RGB_ARB, GL_CONSTANT_ARB);
232 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND2_RGB_ARB, GL_SRC_ALPHA);
233 glPushMatrix();
234 glTranslatef(1.0, 3.0, 0.0);
235 glCallList(1);
236 glPopMatrix();
237
238 constColor[3] = 0.4;
239 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constColor);
240 glPushMatrix();
241 glTranslatef(2.0, 3.0, 0.0);
242 glCallList(1);
243 glPopMatrix();
244
245 constColor[3] = 0.6;
246 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constColor);
247 glPushMatrix();
248 glTranslatef(3.0, 3.0, 0.0);
249 glCallList(1);
250 glPopMatrix();
251
252 constColor[3] = 0.8;
253 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, constColor);
254 glPushMatrix();
255 glTranslatef(4.0, 3.0, 0.0);
256 glCallList(1);
257 glPopMatrix();
258
259 /* combine textures 0 & 1
260 * defaults are:
261 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_TEXTURE);
262 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR);
263 * glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_PREVIOUS_ARB);
264 * glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR);
265 */
266
267 glActiveTextureARB (GL_TEXTURE0_ARB);
268 glEnable (GL_TEXTURE_2D);
269 glBindTexture(GL_TEXTURE_2D, texName[0]);
270 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
271
272 glActiveTextureARB (GL_TEXTURE1_ARB);
273 glEnable (GL_TEXTURE_2D);
274 glBindTexture(GL_TEXTURE_2D, texName[1]);
275 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB);
276 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE);
277 glPushMatrix();
278 glTranslatef(1.0, 2.0, 0.0);
279 glCallList(1);
280 glPopMatrix();
281
282 /* try different combiner modes of texture unit 1 */
283 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE);
284 glPushMatrix();
285 glTranslatef(2.0, 2.0, 0.0);
286 glCallList(1);
287 glPopMatrix();
288
289 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_ADD);
290 glPushMatrix();
291 glTranslatef(3.0, 2.0, 0.0);
292 glCallList(1);
293 glPopMatrix();
294
295 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_ADD_SIGNED_ARB);
296 glPushMatrix();
297 glTranslatef(4.0, 2.0, 0.0);
298 glCallList(1);
299 glPopMatrix();
300
301 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_SUBTRACT_ARB);
302 glPushMatrix();
303 glTranslatef(5.0, 2.0, 0.0);
304 glCallList(1);
305 glPopMatrix();
306
307 /* some experiments */
308
309 /* see the effect of RGB_SCALE */
310 glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_ARB, 2.0);
311 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_REPLACE);
312 glPushMatrix();
313 glTranslatef(1.0, 1.0, 0.0);
314 glCallList(1);
315 glPopMatrix();
316
317 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_MODULATE);
318 glPushMatrix();
319 glTranslatef(2.0, 1.0, 0.0);
320 glCallList(1);
321 glPopMatrix();
322 glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_ARB, 1.0);
323
324 /* using SOURCE0 and SOURCE1, reverse the order of subtraction Arg1-Arg0 */
325
326 glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_ARB);
327 glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_ARB, GL_SUBTRACT_ARB);
328 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_ARB, GL_PREVIOUS_ARB);
329 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND0_RGB_ARB, GL_SRC_COLOR);
330 glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_ARB, GL_TEXTURE);
331 glTexEnvf(GL_TEXTURE_ENV, GL_OPERAND1_RGB_ARB, GL_SRC_COLOR);
332 glPushMatrix();
333 glTranslatef(5.0, 1.0, 0.0);
334 glCallList(1);
335 glPopMatrix();
336
337 glActiveTextureARB (GL_TEXTURE1_ARB); /* deactivate multitexturing */
338 glDisable (GL_TEXTURE_2D);
339 glActiveTextureARB (GL_TEXTURE0_ARB); /* activate single texture unit */
340
341 glFlush();
342 }
343
344 static void reshape(int w, int h)
345 {
346 glViewport(0, 0, (GLsizei) w, (GLsizei) h);
347 glMatrixMode(GL_PROJECTION);
348 glLoadIdentity();
349 gluOrtho2D(0.0, 7.0, 0.0, 7.0);
350 glMatrixMode(GL_MODELVIEW);
351 glLoadIdentity();
352 }
353
354 static void keyboard (unsigned char key, int x, int y)
355 {
356 switch (key) {
357 case 27:
358 exit(0);
359 break;
360 default:
361 break;
362 }
363 }
364
365 int main(int argc, char** argv)
366 {
367 glutInit(&argc, argv);
368 glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB);
369 glutInitWindowSize(400, 400);
370 glutInitWindowPosition(100, 100);
371 glutCreateWindow(argv[0]);
372 glewInit();
373 init();
374 glutDisplayFunc(display);
375 glutReshapeFunc(reshape);
376 glutKeyboardFunc(keyboard);
377 glutMainLoop();
378 return 0;
379 }