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

GIS编程

开发平台:

Visual C++

  1. #include <math.h>
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <GL/glut.h>
  5. #include "texture.h"
  6. #ifndef __sgi
  7. /* Most math.h's do not define float versions of the trig functions. */
  8. #define sinf sin
  9. #define cosf cos
  10. #define atan2f atan2
  11. #endif
  12. /* Some <math.h> files do not define M_PI... */
  13. #ifndef M_PI
  14. #define M_PI 3.14159265358979323846
  15. #endif
  16. static int texture = 1;
  17. static float rot = 0;
  18. static float opacity = 1.0;
  19. static float intensity = 1.0;
  20. static float size = .001, delta = 0;
  21. static float scale = 1.;
  22. static float transx, transy, rotx, roty;
  23. static int ox = -1, oy = -1;
  24. static int mot = 0;
  25. #define PAN 1
  26. #define ROT 2
  27. void
  28. pan(int x, int y) {
  29.     transx +=  (x-ox)/500.;
  30.     transy -= (y-oy)/500.;
  31.     ox = x; oy = y;
  32.     glutPostRedisplay();
  33. }
  34. void
  35. rotate(int x, int y) {
  36.     rotx += x-ox;
  37.     if (rotx > 360.) rotx -= 360.;
  38.     else if (rotx < -360.) rotx += 360.;
  39.     roty += y-oy;
  40.     if (roty > 360.) roty -= 360.;
  41.     else if (roty < -360.) roty += 360.;
  42.     ox = x; oy = y;
  43.     glutPostRedisplay();
  44. }
  45. void
  46. motion(int x, int y) {
  47.     if (mot == PAN) pan(x, y);
  48.     else if (mot == ROT) rotate(x,y);
  49. }
  50. void
  51. mouse(int button, int state, int x, int y) {
  52.     if(state == GLUT_DOWN) {
  53. switch(button) {
  54. case GLUT_LEFT_BUTTON:
  55.     mot = PAN;
  56.     motion(ox = x, oy = y);
  57.     break;
  58. case GLUT_RIGHT_BUTTON:
  59.     mot = ROT;
  60.     motion(ox = x, oy = y);
  61.     break;
  62. case GLUT_MIDDLE_BUTTON:
  63.     break;
  64. }
  65.     } else if (state == GLUT_UP) {
  66. mot = 0;
  67.     }
  68. }
  69. void afunc(void) {
  70.     static int state;
  71.     if (state ^= 1) {
  72. glAlphaFunc(GL_GREATER, .01);
  73. glEnable(GL_ALPHA_TEST);
  74.     } else {
  75. glDisable(GL_ALPHA_TEST);
  76.     }
  77. }
  78. void bfunc(void) {
  79.     static int state;
  80.     if (state ^= 1) {
  81. glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
  82. glEnable(GL_BLEND);
  83.     } else {
  84. glDisable(GL_BLEND);
  85.     }
  86. }
  87. void tfunc(void) {
  88.     texture ^= 1;
  89. }
  90. void up(void) { scale += .1; }
  91. void down(void) { scale -= .1; }
  92. void left(void) { intensity -= .05f; if (intensity < 0.f) intensity = 0.0f; }
  93. void right(void) { intensity += .05f; if (intensity > 1.f) intensity = 1.0f; }
  94. void help(void) {
  95.     printf("Usage: explode [image]n");
  96.     printf("'h'            - helpn");
  97.     printf("'a'            - toggle alpha testn");
  98.     printf("'b'            - toggle blendn");
  99.     printf("'t'            - toggle texturingn");
  100.     printf("'UP'           - scale upn");
  101.     printf("'DOWN'         - scale downn");
  102.     printf("'LEFT'    - darkenn");
  103.     printf("'RIGHT'    - brightenn");
  104.     printf("left mouse     - pann");
  105.     printf("right mouse    - rotaten");
  106. }
  107. void init(char *filename) {
  108.     static unsigned *image;
  109.     static int width, height, components;
  110.     if (filename) {
  111. image = read_texture(filename, &width, &height, &components);
  112. if (image == NULL) {
  113.     fprintf(stderr, "Error: Can't load image file "%s".n",
  114.     filename);
  115.     exit(EXIT_FAILURE);
  116. } else {
  117.     printf("%d x %d image loadedn", width, height);
  118. }
  119. if (components != 2 && components != 4) {
  120.     printf("must be an RGBA or LA imagen");
  121.     exit(EXIT_FAILURE);
  122. }
  123.     } else {
  124. int i, j;
  125. unsigned char *img;
  126. components = 4; width = height = 512;
  127. image = (unsigned *) malloc(width*height*sizeof(unsigned));
  128. img = (unsigned char *)image;
  129. for (j = 0; j < height; j++)
  130.     for (i = 0; i < width; i++) {
  131. int w2 = width/2, h2 = height/2;
  132. if (i & 32)
  133.     img[4*(i+j*width)+0] = 0xff;
  134. else
  135.     img[4*(i+j*width)+1] = 0xff;
  136. if (j&32)
  137.     img[4*(i+j*width)+2] = 0xff;
  138. if ((i-w2)*(i-w2) + (j-h2)*(j-h2) > 64*64 &&
  139.     (i-w2)*(i-w2) + (j-h2)*(j-h2) < 300*300) img[4*(i+j*width)+3] = 0xff;
  140.     }
  141.     }
  142.     glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
  143.     glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
  144.     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
  145.     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  146.     glTexImage2D(GL_TEXTURE_2D, 0, components, width,
  147.                  height, 0, GL_RGBA, GL_UNSIGNED_BYTE,
  148.                  image);
  149.     glEnable(GL_TEXTURE_2D);
  150.     glMatrixMode(GL_PROJECTION);
  151.     glLoadIdentity();
  152.     gluPerspective(50.,1.,.1,20.);
  153.     glMatrixMode(GL_MODELVIEW);
  154.     glLoadIdentity();
  155.     glTranslatef(0.,0.,-5.5);
  156.     glClearColor(.25f, .25f, .75f, .25f);
  157.     glAlphaFunc(GL_GREATER, 0.016);
  158.     glEnable(GL_ALPHA_TEST);
  159.     glEnable(GL_BLEND);
  160.     glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
  161.     glEnable(GL_DEPTH_TEST);
  162.     glEnable(GL_LIGHT0);
  163.     glEnable(GL_COLOR_MATERIAL);
  164.     glEnable(GL_NORMALIZE);
  165. }
  166. void
  167. animate(void) {
  168.     if (delta > 10) {
  169. delta = 0.f;
  170. size = 0.f;
  171.         opacity = 1.f;
  172. rot = 0.f;
  173.     }
  174.     size += .08f;
  175.     delta += .07f;
  176.     rot += .9f;
  177.     opacity -= .005f;
  178.     glutPostRedisplay();
  179. }
  180. void
  181. cube(void) {
  182.     glBegin(GL_QUADS);
  183. glNormal3f(0.f, 0.f, -1.f);
  184. glTexCoord2f(0.0, 0.0); glVertex3f(-1.0, -1.0, -1.0);
  185. glTexCoord2f(1.0, 0.0); glVertex3f( 1.0, -1.0, -1.0);
  186. glTexCoord2f(1.0, 1.0); glVertex3f( 1.0,  1.0, -1.0);
  187. glTexCoord2f(0.0, 1.0); glVertex3f(-1.0,  1.0, -1.0);
  188. glNormal3f(0.f, 0.f, 1.f);
  189. glTexCoord2f(0.0, 0.0); glVertex3f(-1.0, -1.0,  1.0);
  190. glTexCoord2f(1.0, 0.0); glVertex3f( 1.0, -1.0,  1.0);
  191. glTexCoord2f(1.0, 1.0); glVertex3f( 1.0,  1.0,  1.0);
  192. glTexCoord2f(0.0, 1.0); glVertex3f(-1.0,  1.0,  1.0);
  193. glNormal3f(0.f, 1.f, 0.f);
  194. glTexCoord2f(0.0, 0.0); glVertex3f(-1.0,  1.0, -1.0);
  195. glTexCoord2f(1.0, 0.0); glVertex3f( 1.0,  1.0, -1.0);
  196. glTexCoord2f(1.0, 1.0); glVertex3f( 1.0,  1.0,  1.0);
  197. glTexCoord2f(0.0, 1.0); glVertex3f(-1.0,  1.0,  1.0);
  198. glNormal3f(0.f, -1.f, 0.f);
  199. glTexCoord2f(0.0, 0.0); glVertex3f(-1.0, -1.0, -1.0);
  200. glTexCoord2f(1.0, 0.0); glVertex3f( 1.0, -1.0, -1.0);
  201. glTexCoord2f(1.0, 1.0); glVertex3f( 1.0, -1.0,  1.0);
  202. glTexCoord2f(0.0, 1.0); glVertex3f(-1.0, -1.0,  1.0);
  203. glNormal3f( 1.f, 0.f, 0.f);
  204. glTexCoord2f(0.0, 0.0); glVertex3f( 1.0, -1.0, -1.0);
  205. glTexCoord2f(1.0, 0.0); glVertex3f( 1.0,  1.0, -1.0);
  206. glTexCoord2f(1.0, 1.0); glVertex3f( 1.0,  1.0,  1.0);
  207. glTexCoord2f(0.0, 1.0); glVertex3f( 1.0, -1.0,  1.0);
  208. glNormal3f(-1.f, 0.f, 0.f);
  209. glTexCoord2f(0.0, 0.0); glVertex3f(-1.0, -1.0, -1.0);
  210. glTexCoord2f(1.0, 0.0); glVertex3f(-1.0,  1.0, -1.0);
  211. glTexCoord2f(1.0, 1.0); glVertex3f(-1.0,  1.0,  1.0);
  212. glTexCoord2f(0.0, 1.0); glVertex3f(-1.0, -1.0,  1.0);
  213.     glEnd();
  214. }
  215. static void calcMatrix(void);
  216. void display(void) {
  217.     glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
  218.     glLoadIdentity();
  219. #define RAD(x) (((x)*M_PI)/180.)
  220.     gluLookAt(-sinf(RAD(rotx))*5.5,transy,cosf(RAD(rotx))*5.5, 0.,0.,0., 0.,1.,0.);
  221.     /* floor */
  222.     glColor4f(0.f,.2f,0.f,1.f);
  223.     glBegin(GL_POLYGON);
  224. glVertex3f(-4.0, -1.0, -4.0);
  225. glVertex3f( 4.0, -1.0, -4.0);
  226. glVertex3f( 4.0, -1.0,  4.0);
  227. glVertex3f(-4.0, -1.0,  4.0);
  228.     glEnd();
  229.     glEnable(GL_LIGHTING);
  230.     glPushMatrix();
  231.     glColor3f(.3f,.3f,.3f);
  232.     glPushMatrix();
  233.     glTranslatef(-1.f, -1.+.2f, -1.5f);
  234.     glScalef(.2f,.2f, .2f);
  235.     cube();
  236.     glPopMatrix();
  237.     glDisable(GL_LIGHTING);
  238.     glTranslatef(-1.f, -1.f, -1.5f);
  239.     calcMatrix();
  240.     glScalef(size,size,1.);
  241.     if (texture) glEnable(GL_TEXTURE_2D);
  242.     glColor4f(intensity, intensity, intensity, opacity);
  243.     glDepthMask(0);
  244.     glBegin(GL_POLYGON);
  245. glTexCoord2f(0.0, 0.0); glVertex2f(-1.0, -1.0);
  246. glTexCoord2f(1.0, 0.0); glVertex2f(1.0, -1.0);
  247. glTexCoord2f(1.0, 1.0); glVertex2f(1.0, 1.0);
  248. glTexCoord2f(0.0, 1.0); glVertex2f(-1.0, 1.0);
  249.     glEnd();
  250.     glDepthMask(1);
  251.     glPopMatrix();
  252.     glDisable(GL_TEXTURE_2D);
  253.     glutSwapBuffers();
  254. }
  255. void reshape(int w, int h) {
  256.     glViewport(0, 0, w, h);
  257. }
  258. /* ARGSUSED1 */
  259. void
  260. key(unsigned char key, int x, int y) {
  261.     switch(key) {
  262.     case 'a': afunc(); break;
  263.     case 'b': bfunc(); break;
  264.     case 'h': help(); break;
  265.     case 't': tfunc(); break;
  266.     case '33': exit(EXIT_SUCCESS); break;
  267.     default: break;
  268.     }
  269.     glutPostRedisplay();
  270. }
  271. /* ARGSUSED1 */
  272. void
  273. special(int key, int x, int y) {
  274.     switch(key) {
  275.     case GLUT_KEY_UP: up(); break;
  276.     case GLUT_KEY_DOWN: down(); break;
  277.     case GLUT_KEY_LEFT: left(); break;
  278.     case GLUT_KEY_RIGHT:right(); break;
  279.     }
  280. }
  281. int main(int argc, char** argv) {
  282.     glutInitWindowSize(512, 512);
  283.     glutInit(&argc, argv);
  284.     glutInitDisplayMode(GLUT_RGBA|GLUT_DOUBLE|GLUT_DEPTH);
  285.     (void)glutCreateWindow(argv[0]);
  286.     init(argc == 1 ? "../data/explosion.rgba" : argv[1]);
  287.     glutDisplayFunc(display);
  288.     glutKeyboardFunc(key);
  289.     glutSpecialFunc(special);
  290.     glutReshapeFunc(reshape);
  291.     glutMouseFunc(mouse);
  292.     glutMotionFunc(motion);
  293.     glutIdleFunc(animate);
  294.     glutMainLoop();
  295.     return 0;
  296. }
  297. void
  298. printmat(float *m) {
  299.     int i;
  300.     for(i = 0; i < 4; i++) {
  301. printf("%f %f %f %fn", m[4*i+0], m[4*i+1], m[4*i+2], m[4*i+3]);
  302.     }
  303. }
  304. void
  305. buildRot(float theta, float x, float y, float z, float m[16]) {
  306.     float d = x*x + y*y + z*z;
  307.     float ct = cosf(RAD(theta)), st = sinf(RAD(theta));
  308.     /* normalize */
  309.     if (d > 0) {
  310. d = 1/d;
  311. x *= d;
  312. y *= d;
  313. z *= d;
  314.     }
  315.     m[ 0] = 1; m[ 1] = 0; m[ 2] = 0; m[ 3] = 0;
  316.     m[ 4] = 0; m[ 5] = 1; m[ 6] = 0; m[ 7] = 0;
  317.     m[ 8] = 0; m[ 9] = 0; m[10] = 1; m[11] = 0;
  318.     m[12] = 0; m[13] = 0; m[14] = 0; m[15] = 1;
  319.     /* R = uu' + cos(theta)*(I-uu') + sin(theta)*S
  320.      *
  321.      * S =  0  -z   y    u' = (x, y, z)
  322.      *     z   0  -x
  323.      *    -y   x   0
  324.      */
  325.      m[0] = x*x + ct*(1-x*x) + st*0;
  326.      m[4] = x*y + ct*(0-x*y) + st*-z;
  327.      m[8] = x*z + ct*(0-x*z) + st*y;
  328.      m[1] = y*x + ct*(0-y*x) + st*z;
  329.      m[5] = y*y + ct*(1-y*y) + st*0;
  330.      m[9] = y*z + ct*(0-y*z) + st*-x;
  331.      m[2] = z*x + ct*(0-z*x) + st*-y;
  332.      m[6] = z*y + ct*(0-z*y) + st*x;
  333.      m[10]= z*z + ct*(1-z*z) + st*0;
  334. }
  335. static void
  336. calcMatrix(void) {
  337.     float mat[16];
  338.     glGetFloatv(GL_MODELVIEW_MATRIX, mat);
  339.     buildRot(-180*atan2f(mat[8], mat[10])/M_PI, 0, 1, 0, mat);
  340.     glMultMatrixf(mat);
  341. }