mipmap_lines.c
上传用户:xk288cn
上传日期:2007-05-28
资源大小:4876k
文件大小:7k
源码类别:

GIS编程

开发平台:

Visual C++

  1. /* mipmap_lines.c - by David Blythe, SGI */
  2. /* Different mipmap filters. */
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <string.h>
  6. #include <GL/glut.h>
  7. #include "texture.h"
  8. #include "izoom.h"
  9. static int w = 1024, h = 512;
  10. void 
  11. reshape(int w, int h)
  12. {
  13.   glViewport(0, 0, w, h);
  14.   glMatrixMode(GL_PROJECTION);
  15.   glLoadIdentity();
  16.   gluPerspective(40.0, (GLfloat) w / (GLfloat) h, 1.0, 20.0);
  17.   gluLookAt(0, 1, 3,
  18.     0, 0, 0,
  19.     0, 1, 0);
  20.   glMatrixMode(GL_MODELVIEW);
  21.   glLoadIdentity();
  22. }
  23. int original_width, reduced_width, global_comp;
  24. unsigned *original, *reduced;
  25. void 
  26. getimgrow(short *buf, int y)
  27. {
  28.   int i;
  29.   unsigned *p = &original[y * original_width];
  30.   int shift = global_comp * 8;
  31.   unsigned int mask = 0xff << shift;
  32.   for (i = 0; i < original_width; i++) {
  33.     buf[i] = (p[i] & mask) >> shift;
  34.   }
  35. }
  36. void 
  37. putimgrow(short *buf, int y)
  38. {
  39.   int i;
  40.   unsigned *p = &reduced[y * reduced_width];
  41.   int shift = global_comp * 8;
  42.   unsigned int mask = 0xff << shift;
  43.   for (i = 0; i < reduced_width; i++) {
  44.     p[i] = (p[i] & ~mask) | (buf[i] << shift);
  45.   }
  46. }
  47. void 
  48. buildMitchellMipmaps(int components, int width, int height, unsigned
  49.   *buf)
  50. {
  51.   int level = 0;
  52.   original_width = width;
  53.   original = buf;
  54.   glTexImage2D(GL_TEXTURE_2D, level, components, width,
  55.     height, 0, GL_RGBA, GL_UNSIGNED_BYTE,
  56.     original);
  57.   while (width) {
  58.     reduced_width = width / 2;
  59.     for (global_comp = 0; global_comp < 4; global_comp++) {
  60.       filterzoom(getimgrow, putimgrow, width, height, width / 2,
  61.         height / 2, MITCHELL, 1.);
  62.     }
  63.     glTexImage2D(GL_TEXTURE_2D, ++level, components, width / 2,
  64.       height / 2, 0, GL_RGBA, GL_UNSIGNED_BYTE,
  65.       reduced);
  66.     width /= 2, height /= 2;
  67.     memcpy(original, reduced, width * height * sizeof(unsigned));
  68.     original_width = width;
  69.     printf("build level %dn", level);
  70.   }
  71. }
  72. int width = 256, height = 256;
  73. int grid_space = 4;
  74. void 
  75. init_textures(char *filename)
  76. {
  77.   unsigned *buf;
  78.   int components;
  79.   if (filename) {
  80.     buf = read_texture(filename, &width, &height, &components);
  81.     if (buf == NULL) {
  82.       fprintf(stderr, "Error: Can't load image file "%s".n",
  83.         filename);
  84.       exit(1);
  85.     } else {
  86.       printf("%d x %d texture loadedn", width, height);
  87.     }
  88.   } else {
  89.     int i, j;
  90.     components = 4;
  91.     buf = (unsigned *) malloc(width * height * sizeof(unsigned));
  92.     for (i = 0; i < height; i++)
  93.       for (j = 0; j < width; j++)
  94.         if ((i % grid_space) && (j % grid_space))
  95.           buf[i * width + j] = 0xffffffff;
  96.         else
  97.           buf[i * width + j] = 0;
  98.   }
  99. #ifdef GL_EXT_texture_object
  100.   glBindTextureEXT(GL_TEXTURE_2D, 1);
  101. #else
  102.   glNewList(1001, GL_COMPILE);
  103. #endif
  104.   glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
  105.   glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
  106.   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
  107.     GL_LINEAR_MIPMAP_LINEAR);
  108.   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  109.   gluBuild2DMipmaps(GL_TEXTURE_2D, components, width, height, GL_RGBA,
  110.     GL_UNSIGNED_BYTE, buf);
  111. #ifndef GL_EXT_texture_object
  112.   glEndList();
  113. #endif
  114. #ifdef GL_EXT_texture_object
  115.   glBindTextureEXT(GL_TEXTURE_2D, 2);
  116. #else
  117.   glNewList(1002, GL_COMPILE);
  118. #endif
  119.   glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
  120.   glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
  121.   reduced = (unsigned *) malloc(width * height * sizeof(unsigned));
  122.   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
  123.     GL_LINEAR_MIPMAP_LINEAR);
  124.   glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  125.   buildMitchellMipmaps(components, width, height, buf);
  126. #ifndef GL_EXT_texture_object
  127.   glEndList();
  128. #endif
  129.   free(buf);
  130.   free(reduced);
  131. }
  132. void 
  133. init(char *filename)
  134. {
  135.   glEnable(GL_TEXTURE_2D);
  136.   init_textures(filename);
  137.   glNewList(1, GL_COMPILE);
  138.   glColor3f(1., 1., 1.);
  139.   glBegin(GL_QUADS);
  140.   glTexCoord2f(0, 1);
  141.   glVertex3f(-4, 0, -10);
  142.   glTexCoord2f(1, 1);
  143.   glVertex3f(4, 0, -10);
  144.   glTexCoord2f(1, 0);
  145.   glVertex3f(4, 0, 3);
  146.   glTexCoord2f(0, 0);
  147.   glVertex3f(-4, 0, 3);
  148.   glEnd();
  149.   glEndList();
  150.   glClearColor(.2, 0, .9, 0);
  151. }
  152. void 
  153. display(void)
  154. {
  155.   glClear(GL_COLOR_BUFFER_BIT);
  156.   glViewport(0, 0, w / 2, h);
  157. #ifdef GL_EXT_texture_object
  158.   glBindTextureEXT(GL_TEXTURE_2D, 1);
  159. #else
  160.   glCallList(1001);
  161. #endif
  162.   glCallList(1);
  163.   glViewport(w / 2, 0, w / 2, h);
  164. #ifdef GL_EXT_texture_object
  165.   glBindTextureEXT(GL_TEXTURE_2D, 2);
  166. #else
  167.   glCallList(1002);
  168. #endif
  169.   glCallList(1);
  170.   glutSwapBuffers();
  171. }
  172. void 
  173. idle(void)
  174. {
  175.   glRotatef(.1, 1, 0, 0);
  176.   glutPostRedisplay();
  177. }
  178. void 
  179. bidle(void)
  180. {
  181.   glRotatef(-.1, 1, 0, 0);
  182.   glutPostRedisplay();
  183. }
  184. /* ARGSUSED1 */
  185. void
  186. mouse(int button, int state, int x, int y)
  187. {
  188.   if (state == GLUT_DOWN) {
  189.     switch (button) {
  190.     case GLUT_LEFT_BUTTON:
  191.       glutIdleFunc(idle);
  192.       break;
  193.     case GLUT_MIDDLE_BUTTON:
  194.       glutIdleFunc(bidle);
  195.       break;
  196.     case GLUT_RIGHT_BUTTON:
  197.       break;
  198.     }
  199.   } else {
  200.     glutIdleFunc(NULL);
  201.   }
  202. }
  203. void 
  204. help(void)
  205. {
  206.   printf("'h'   - helpn");
  207.   printf("'g'   - increase line spacingn");
  208.   printf("'G'   - decrease line spacingn");
  209.   printf("'s'   - double texture dimensionsn");
  210.   printf("'S'   - halve texture dimensionsn");
  211. }
  212. char *filename;
  213. /* ARGSUSED1 */
  214. void
  215. key(unsigned char key, int x, int y)
  216. {
  217.   switch (key) {
  218.   case 'h':
  219.     help();
  220.     break;
  221.   case 'g':
  222.     grid_space++;
  223.     init_textures(filename);
  224.     printf("grid spacing %dn", grid_space);
  225.     break;
  226.   case 'G':
  227.     grid_space--;
  228.     if (grid_space <= 0)
  229.       grid_space = 1;
  230.     init_textures(filename);
  231.     printf("grid spacing %dn", grid_space);
  232.     break;
  233.   case 's':
  234.     height = width *= 2;
  235.     if (height > 1024)
  236.       height = width = 1024;
  237.     init_textures(filename);
  238.     printf("texture size %dn", height);
  239.     break;
  240.   case 'S':
  241.     height = width /= 2;
  242.     init_textures(filename);
  243.     printf("texture size %dn", height);
  244.     break;
  245.   default:
  246.     return;
  247.   case '33':
  248.     exit(0);
  249.     break;
  250.   }
  251.   glutPostRedisplay();
  252. }
  253. int 
  254. main(int argc, char *argv[])
  255. {
  256.   glutInit(&argc, argv);
  257.   glutInitWindowSize(w, h);
  258.   glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE);
  259.   (void) glutCreateWindow("Left: GLU mipmaps, Right: Mitchell mipmaps");
  260.   if (argc > 1)
  261.     init(filename = argv[1]);
  262.   else
  263.     init(filename = 0);
  264.   glutDisplayFunc(display);
  265.   glutKeyboardFunc(key);
  266.   glutReshapeFunc(reshape);
  267.   glutMouseFunc(mouse);
  268.   glutMainLoop();
  269.   return 0;             /* ANSI C requires main to return int. */
  270. }