home *** CD-ROM | disk | FTP | other *** search
/ Aminet 10 / aminetcdnumber101996.iso / Aminet / gfx / x11 / Mesa_Amiwin.lha / Mesa-Amiwin / samples / star.c < prev    next >
C/C++ Source or Header  |  1995-10-03  |  7KB  |  332 lines

  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 <stdlib.h>
  28. #include <math.h>
  29. #include <time.h>
  30. #include "GL/gl.h"
  31. #include "GL/glu.h"
  32. #include "gltk.h"
  33.  
  34.  
  35. #define PI 3.141592657
  36.  
  37. enum {
  38.     NORMAL = 0,
  39.     WEIRD = 1
  40. };
  41.  
  42. enum {
  43.     STREAK = 0,
  44.     CIRCLE = 1
  45. };
  46.  
  47. #define MAXSTARS 400
  48. #define MAXPOS 10000
  49. #define MAXWARP 10
  50. #define MAXANGLES 6000
  51.  
  52.  
  53. typedef struct _starRec {
  54.     GLint type;
  55.     float x[2], y[2], z[2];
  56.     float offsetX, offsetY, offsetR, rotation;
  57. } starRec;
  58.  
  59.  
  60. GLenum doubleBuffer, directRender;
  61. GLint windW, windH;
  62.  
  63. GLenum flag = NORMAL;
  64. GLint starCount = MAXSTARS / 2;
  65. float speed = 1.0;
  66. GLint nitro = 0;
  67. starRec stars[MAXSTARS];
  68. float sinTable[MAXANGLES];
  69.  
  70.  
  71. float Sin(float angle)
  72. {
  73.  
  74.     return (sinTable[(GLint)angle]);
  75. }
  76.  
  77. float Cos(float angle)
  78. {
  79.  
  80.     return (sinTable[((GLint)angle+(MAXANGLES/4))%MAXANGLES]);
  81. }
  82.  
  83. void NewStar(GLint n, GLint d)
  84. {
  85.  
  86.     if (rand()%4 == 0) {
  87.     stars[n].type = CIRCLE;
  88.     } else {
  89.     stars[n].type = STREAK;
  90.     }
  91.     stars[n].x[0] = (float)(rand() % MAXPOS - MAXPOS / 2);
  92.     stars[n].y[0] = (float)(rand() % MAXPOS - MAXPOS / 2);
  93.     stars[n].z[0] = (float)(rand() % MAXPOS + d);
  94.     if (rand()%4 == 0 && flag == WEIRD) {
  95.     stars[n].offsetX = (float)(rand() % 100 - 100 / 2);
  96.     stars[n].offsetY = (float)(rand() % 100 - 100 / 2);
  97.     stars[n].offsetR = (float)(rand() % 25 - 25 / 2);
  98.     } else {
  99.     stars[n].offsetX = 0.0;
  100.     stars[n].offsetY = 0.0;
  101.     stars[n].offsetR = 0.0;
  102.     }
  103. }
  104.  
  105. void RotatePoint(float *x, float *y, float rotation)
  106. {
  107.     float tmpX, tmpY;
  108.  
  109.     tmpX = *x * Cos(rotation) - *y * Sin(rotation);
  110.     tmpY = *y * Cos(rotation) + *x * Sin(rotation);
  111.     *x = tmpX;
  112.     *y = tmpY;
  113. }
  114.  
  115. void MoveStars(void)
  116. {
  117.     float offset;
  118.     GLint n;
  119.  
  120.     offset = speed * 60.0;
  121.  
  122.     for (n = 0; n < starCount; n++) {
  123.     stars[n].x[1] = stars[n].x[0];
  124.     stars[n].y[1] = stars[n].y[0];
  125.     stars[n].z[1] = stars[n].z[0];
  126.     stars[n].x[0] += stars[n].offsetX;
  127.     stars[n].y[0] += stars[n].offsetY;
  128.     stars[n].z[0] -= offset;
  129.         stars[n].rotation += stars[n].offsetR;
  130.         if (stars[n].rotation > MAXANGLES) {
  131.             stars[n].rotation = 0.0;
  132.     }
  133.     }
  134. }
  135.  
  136. GLenum StarPoint(GLint n)
  137. {
  138.     float x0, y0, x1, y1, width;
  139.     GLint i;
  140.  
  141.     x0 = stars[n].x[0] * windW / stars[n].z[0];
  142.     y0 = stars[n].y[0] * windH / stars[n].z[0];
  143.     RotatePoint(&x0, &y0, stars[n].rotation);
  144.     x0 += windW / 2.0;
  145.     y0 += windH / 2.0;
  146.  
  147.     if (x0 >= 0.0 && x0 < windW && y0 >= 0.0 && y0 < windH) {
  148.     if (stars[n].type == STREAK) {
  149.         x1 = stars[n].x[1] * windW / stars[n].z[1];
  150.         y1 = stars[n].y[1] * windH / stars[n].z[1];
  151.         RotatePoint(&x1, &y1, stars[n].rotation);
  152.         x1 += windW / 2.0;
  153.         y1 += windH / 2.0;
  154.  
  155.         glLineWidth(MAXPOS/100.0/stars[n].z[0]+1.0);
  156.         glColor3f(1.0, (MAXWARP-speed)/MAXWARP, (MAXWARP-speed)/MAXWARP);
  157.         if (fabs(x0-x1) < 1.0 && fabs(y0-y1) < 1.0) {
  158.         glBegin(GL_POINTS);
  159.             glVertex2f(x0, y0);
  160.         glEnd();
  161.         } else {
  162.         glBegin(GL_LINES);
  163.             glVertex2f(x0, y0);
  164.             glVertex2f(x1, y1);
  165.         glEnd();
  166.         }
  167.     } else {
  168.         width = MAXPOS / 10.0 / stars[n].z[0] + 1.0;
  169.         glColor3f(1.0, 0.0, 0.0);
  170.         glBegin(GL_POLYGON);
  171.         for (i = 0; i < 8; i++) {
  172.             float x = x0 + width * Cos((float)i*MAXANGLES/8.0);
  173.             float y = y0 + width * Sin((float)i*MAXANGLES/8.0);
  174.             glVertex2f(x, y);
  175.         };
  176.         glEnd();
  177.     }
  178.     return GL_TRUE;
  179.     } else {
  180.     return GL_FALSE;
  181.     }
  182. }
  183.  
  184. void ShowStars(void)
  185. {
  186.     GLint n;
  187.  
  188.     glClear(GL_COLOR_BUFFER_BIT);
  189.  
  190.     for (n = 0; n < starCount; n++) {
  191.     if (stars[n].z[0] > speed || (stars[n].z[0] > 0.0 && speed < MAXWARP)) {
  192.         if (StarPoint(n) == GL_FALSE) {
  193.         NewStar(n, MAXPOS);
  194.         }
  195.     } else {
  196.         NewStar(n, MAXPOS);
  197.     }
  198.     }
  199. }
  200.  
  201. static void Init(void)
  202. {
  203.     float angle;
  204.     GLint n;
  205.  
  206.     srand((unsigned int)time(NULL));
  207.  
  208.     for (n = 0; n < MAXSTARS; n++) {
  209.     NewStar(n, 100);
  210.     }
  211.  
  212.     angle = 0.0;
  213.     for (n = 0; n < MAXANGLES ; n++) {
  214.     sinTable[n] = sin(angle);
  215.         angle += PI / (MAXANGLES / 2.0);
  216.     }
  217.  
  218.     glClearColor(0.0, 0.0, 0.0, 0.0);
  219.  
  220.     glDisable(GL_DITHER);
  221. }
  222.  
  223. void Reshape(int width, int height)
  224. {
  225.  
  226.     windW = (GLint)width;
  227.     windH = (GLint)height;
  228.  
  229.     glViewport(0, 0, windW, windH);
  230.  
  231.     glMatrixMode(GL_PROJECTION);
  232.     glLoadIdentity();
  233.     gluOrtho2D(-0.5, windW+0.5, -0.5, windH+0.5);
  234.     glMatrixMode(GL_MODELVIEW);
  235. }
  236.  
  237. static GLenum Key(int key, GLenum mask)
  238. {
  239.  
  240.     switch (key) {
  241.       case TK_ESCAPE:
  242.     tkQuit();
  243.       case TK_SPACE:
  244.     flag = (flag == NORMAL) ? WEIRD : NORMAL;
  245.     break;
  246.       case TK_t:
  247.     nitro = 1;
  248.     break;
  249.       default:
  250.     return GL_FALSE;
  251.     }
  252.     return GL_TRUE;
  253. }
  254.  
  255. void Idle(void)
  256. {
  257.  
  258.     MoveStars();
  259.     ShowStars();
  260.     if (nitro > 0) {
  261.     speed = (float)(nitro / 10) + 1.0;
  262.     if (speed > MAXWARP) {
  263.         speed = MAXWARP;
  264.     }
  265.     if (++nitro > MAXWARP*10) {
  266.         nitro = -nitro;
  267.     }
  268.     } else if (nitro < 0) {
  269.     nitro++;
  270.     speed = (float)(-nitro / 10) + 1.0;
  271.     if (speed > MAXWARP) {
  272.         speed = MAXWARP;
  273.     }
  274.     }
  275.  
  276.     glFlush();
  277.     if (doubleBuffer) {
  278.     tkSwapBuffers();
  279.     }
  280. }
  281.  
  282. static GLenum Args(int argc, char **argv)
  283. {
  284.     GLint i;
  285.  
  286.     doubleBuffer = GL_FALSE;
  287.     directRender = GL_TRUE;
  288.  
  289.     for (i = 1; i < argc; i++) {
  290.     if (strcmp(argv[i], "-sb") == 0) {
  291.         doubleBuffer = GL_FALSE;
  292.     } else if (strcmp(argv[i], "-db") == 0) {
  293.         doubleBuffer = GL_TRUE;
  294.     } else if (strcmp(argv[i], "-dr") == 0) {
  295.         directRender = GL_TRUE;
  296.     } else if (strcmp(argv[i], "-ir") == 0) {
  297.         directRender = GL_FALSE;
  298.     }
  299.     }
  300.     return GL_TRUE;
  301. }
  302.  
  303. void main(int argc, char **argv)
  304. {
  305.     GLenum type;
  306.  
  307.     if (Args(argc, argv) == GL_FALSE) {
  308.     tkQuit();
  309.     }
  310.  
  311.     windW = 300;
  312.     windH = 300;
  313.     tkInitPosition(0, 0, 300, 300);
  314.  
  315.     type = TK_RGB;
  316.     type |= (doubleBuffer) ? TK_DOUBLE : TK_SINGLE;
  317.     type |= (directRender) ? TK_DIRECT : TK_INDIRECT;
  318.     tkInitDisplayMode(type);
  319.  
  320.     if (tkInitWindow("Stars") == GL_FALSE) {
  321.     tkQuit();
  322.     }
  323.  
  324.     Init();
  325.  
  326.     tkExposeFunc(Reshape);
  327.     tkReshapeFunc(Reshape);
  328.     tkKeyDownFunc(Key);
  329.     tkIdleFunc(Idle);
  330.     tkExec();
  331. }
  332.