1/* 2 * Copyright (c) 1991, 1992, 1993 Silicon Graphics, Inc. 3 * 4 * Permission to use, copy, modify, distribute, and sell this software and 5 * its documentation for any purpose is hereby granted without fee, provided 6 * that (i) the above copyright notices and this permission notice appear in 7 * all copies of the software and related documentation, and (ii) the name of 8 * Silicon Graphics may not be used in any advertising or 9 * publicity relating to the software without the specific, prior written 10 * permission of Silicon Graphics. 11 * 12 * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF 13 * ANY KIND, 14 * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY 15 * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. 16 * 17 * IN NO EVENT SHALL SILICON GRAPHICS BE LIABLE FOR 18 * ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, 19 * OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, 20 * WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF 21 * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE 22 * OF THIS SOFTWARE. 23 */ 24 25#include <stdio.h> 26#include <string.h> 27#include <math.h> 28#include <stdlib.h> 29#include "glut_wrap.h" 30 31 32#include "loadppm.c" 33 34GLenum doubleBuffer; 35 36char *texFileName = 0; 37PPMImage *image; 38 39float *minFilter, *magFilter, *sWrapMode, *tWrapMode; 40float decal[] = {GL_DECAL}; 41float modulate[] = {GL_MODULATE}; 42float repeat[] = {GL_REPEAT}; 43float clamp[] = {GL_CLAMP}; 44float nr[] = {GL_NEAREST}; 45float ln[] = {GL_LINEAR}; 46float nr_mipmap_nr[] = {GL_NEAREST_MIPMAP_NEAREST}; 47float nr_mipmap_ln[] = {GL_NEAREST_MIPMAP_LINEAR}; 48float ln_mipmap_nr[] = {GL_LINEAR_MIPMAP_NEAREST}; 49float ln_mipmap_ln[] = {GL_LINEAR_MIPMAP_LINEAR}; 50GLint sphereMap[] = {GL_SPHERE_MAP}; 51 52GLenum doSphere = GL_FALSE; 53float xRotation = 0.0, yRotation = 0.0, zTranslate = -3.125; 54 55GLint cube; 56float c[6][4][3] = { 57 { 58 { 59 1.0, 1.0, -1.0 60 }, 61 { 62 -1.0, 1.0, -1.0 63 }, 64 { 65 -1.0, -1.0, -1.0 66 }, 67 { 68 1.0, -1.0, -1.0 69 } 70 }, 71 { 72 { 73 1.0, 1.0, 1.0 74 }, 75 { 76 1.0, 1.0, -1.0 77 }, 78 { 79 1.0, -1.0, -1.0 80 }, 81 { 82 1.0, -1.0, 1.0 83 } 84 }, 85 { 86 { 87 -1.0, 1.0, 1.0 88 }, 89 { 90 1.0, 1.0, 1.0 91 }, 92 { 93 1.0, -1.0, 1.0 94 }, 95 { 96 -1.0, -1.0, 1.0 97 } 98 }, 99 { 100 { 101 -1.0, 1.0, -1.0 102 }, 103 { 104 -1.0, 1.0, 1.0 105 }, 106 { 107 -1.0, -1.0, 1.0 108 }, 109 { 110 -1.0, -1.0, -1.0 111 } 112 }, 113 { 114 { 115 -1.0, 1.0, 1.0 116 }, 117 { 118 -1.0, 1.0, -1.0 119 }, 120 { 121 1.0, 1.0, -1.0 122 }, 123 { 124 1.0, 1.0, 1.0 125 } 126 }, 127 { 128 { 129 -1.0, -1.0, -1.0 130 }, 131 { 132 -1.0, -1.0, 1.0 133 }, 134 { 135 1.0, -1.0, 1.0 136 }, 137 { 138 1.0, -1.0, -1.0 139 } 140 } 141}; 142static float n[6][3] = { 143 { 144 0.0, 0.0, -1.0 145 }, 146 { 147 1.0, 0.0, 0.0 148 }, 149 { 150 0.0, 0.0, 1.0 151 }, 152 { 153 -1.0, 0.0, 0.0 154 }, 155 { 156 0.0, 1.0, 0.0 157 }, 158 { 159 0.0, -1.0, 0.0 160 } 161}; 162static float t[6][4][2] = { 163 { 164 { 165 1.1, 1.1 166 }, 167 { 168 -0.1, 1.1 169 }, 170 { 171 -0.1, -0.1 172 }, 173 { 174 1.1, -0.1 175 } 176 }, 177 { 178 { 179 1.1, 1.1 180 }, 181 { 182 -0.1, 1.1 183 }, 184 { 185 -0.1, -0.1 186 }, 187 { 188 1.1, -0.1 189 } 190 }, 191 { 192 { 193 -0.1, 1.1 194 }, 195 { 196 1.1, 1.1 197 }, 198 { 199 1.1, -0.1 200 }, 201 { 202 -0.1, -0.1 203 } 204 }, 205 { 206 { 207 1.1, 1.1 208 }, 209 { 210 -0.1, 1.1 211 }, 212 { 213 -0.1, -0.1 214 }, 215 { 216 1.1, -0.1 217 } 218 }, 219 { 220 { 221 1.1, 1.1 222 }, 223 { 224 -0.1, 1.1 225 }, 226 { 227 -0.1, -0.1 228 }, 229 { 230 1.1, -0.1 231 } 232 }, 233 { 234 { 235 1.1, 1.1 236 }, 237 { 238 -0.1, 1.1 239 }, 240 { 241 -0.1, -0.1 242 }, 243 { 244 1.1, -0.1 245 } 246 }, 247}; 248 249static void BuildCube(void) 250{ 251 GLint i; 252 253 glNewList(cube, GL_COMPILE); 254 for (i = 0; i < 6; i++) { 255 glBegin(GL_POLYGON); 256 glNormal3fv(n[i]); glTexCoord2fv(t[i][0]); glVertex3fv(c[i][0]); 257 glNormal3fv(n[i]); glTexCoord2fv(t[i][1]); glVertex3fv(c[i][1]); 258 glNormal3fv(n[i]); glTexCoord2fv(t[i][2]); glVertex3fv(c[i][2]); 259 glNormal3fv(n[i]); glTexCoord2fv(t[i][3]); glVertex3fv(c[i][3]); 260 glEnd(); 261 } 262 glEndList(); 263} 264 265static void BuildLists(void) 266{ 267 268 cube = glGenLists(1); 269 BuildCube(); 270} 271 272static void Init(void) 273{ 274 275 glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 276 gluBuild2DMipmaps(GL_TEXTURE_2D, 3, image->sizeX, image->sizeY, 277 GL_RGB, GL_UNSIGNED_BYTE, image->data); 278 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, decal); 279 glEnable(GL_TEXTURE_2D); 280 281 glFrontFace(GL_CCW); 282 glCullFace(GL_FRONT); 283 glEnable(GL_CULL_FACE); 284 285 BuildLists(); 286 287 glClearColor(0.0, 0.0, 0.0, 0.0); 288 289 magFilter = nr; 290 minFilter = nr; 291 sWrapMode = repeat; 292 tWrapMode = repeat; 293} 294 295static void Reshape(int width, int height) 296{ 297 298 glViewport(0, 0, (GLint)width, (GLint)height); 299 300 glMatrixMode(GL_PROJECTION); 301 glLoadIdentity(); 302 gluPerspective(145.0, 1.0, 0.01, 1000); 303 glMatrixMode(GL_MODELVIEW); 304} 305 306static void Key2(int key, int x, int y) 307{ 308 309 switch (key) { 310 case GLUT_KEY_LEFT: 311 yRotation -= 0.5; 312 break; 313 case GLUT_KEY_RIGHT: 314 yRotation += 0.5; 315 break; 316 case GLUT_KEY_UP: 317 xRotation -= 0.5; 318 break; 319 case GLUT_KEY_DOWN: 320 xRotation += 0.5; 321 break; 322 default: 323 return; 324 } 325 326 glutPostRedisplay(); 327} 328 329static void Key(unsigned char key, int x, int y) 330{ 331 332 switch (key) { 333 case 27: 334 exit(1); 335 336 case 'T': 337 zTranslate += 0.25; 338 break; 339 case 't': 340 zTranslate -= 0.25; 341 break; 342 343 case 's': 344 doSphere = !doSphere; 345 if (doSphere) { 346 glTexGeniv(GL_S, GL_TEXTURE_GEN_MODE, sphereMap); 347 glTexGeniv(GL_T, GL_TEXTURE_GEN_MODE, sphereMap); 348 glEnable(GL_TEXTURE_GEN_S); 349 glEnable(GL_TEXTURE_GEN_T); 350 } else { 351 glDisable(GL_TEXTURE_GEN_S); 352 glDisable(GL_TEXTURE_GEN_T); 353 } 354 break; 355 356 case '0': 357 magFilter = nr; 358 break; 359 case '1': 360 magFilter = ln; 361 break; 362 case '2': 363 minFilter = nr; 364 break; 365 case '3': 366 minFilter = ln; 367 break; 368 case '4': 369 minFilter = nr_mipmap_nr; 370 break; 371 case '5': 372 minFilter = nr_mipmap_ln; 373 break; 374 case '6': 375 minFilter = ln_mipmap_nr; 376 break; 377 case '7': 378 minFilter = ln_mipmap_ln; 379 break; 380 default: 381 return; 382 } 383 384 glutPostRedisplay(); 385} 386 387static void Draw(void) 388{ 389 390 glClear(GL_COLOR_BUFFER_BIT); 391 392 glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, sWrapMode); 393 glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, tWrapMode); 394 glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, magFilter); 395 glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, minFilter); 396 397 glPushMatrix(); 398 399 glTranslatef(0.0, 0.0, zTranslate); 400 glRotatef(xRotation, 1, 0, 0); 401 glRotatef(yRotation, 0, 1, 0); 402 glCallList(cube); 403 404 glPopMatrix(); 405 406 glFlush(); 407 408 if (doubleBuffer) { 409 glutSwapBuffers(); 410 } 411} 412 413static GLenum Args(int argc, char **argv) 414{ 415 GLint i; 416 417 doubleBuffer = GL_FALSE; 418 419 for (i = 1; i < argc; i++) { 420 if (strcmp(argv[i], "-sb") == 0) { 421 doubleBuffer = GL_FALSE; 422 } else if (strcmp(argv[i], "-db") == 0) { 423 doubleBuffer = GL_TRUE; 424 } else if (strcmp(argv[i], "-f") == 0) { 425 if (i+1 >= argc || argv[i+1][0] == '-') { 426 printf("-f (No file name).\n"); 427 return GL_FALSE; 428 } else { 429 texFileName = argv[++i]; 430 } 431 } else { 432 printf("%s (Bad option).\n", argv[i]); 433 return GL_FALSE; 434 } 435 } 436 return GL_TRUE; 437} 438 439int main(int argc, char **argv) 440{ 441 GLenum type; 442 443 glutInit(&argc, argv); 444 445 if (Args(argc, argv) == GL_FALSE) { 446 exit(1); 447 } 448 449 if (texFileName == 0) { 450 printf("No image file.\n"); 451 exit(1); 452 } 453 454 image = LoadPPM(texFileName); 455 456 glutInitWindowPosition(0, 0); glutInitWindowSize( 300, 300); 457 458 type = GLUT_RGB; 459 type |= (doubleBuffer) ? GLUT_DOUBLE : GLUT_SINGLE; 460 glutInitDisplayMode(type); 461 462 if (glutCreateWindow("Texture Test") == GL_FALSE) { 463 exit(1); 464 } 465 466 Init(); 467 468 glutReshapeFunc(Reshape); 469 glutKeyboardFunc(Key); 470 glutSpecialFunc(Key2); 471 glutDisplayFunc(Draw); 472 glutMainLoop(); 473 return 0; 474} 475