Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Last modification | View Log | RSS feed

  1. #include <math.h>
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <string.h>
  5. #include "GL/osmesa.h"
  6. #include "GL/glu.h"
  7.  
  8. #define XK_Left      176
  9. #define XK_Right    179
  10. #define XK_Up        178
  11. #define XK_Down    177
  12.  
  13. extern GLfloat view_rotx, view_roty, view_rotz;
  14. GLint gear1, gear2, gear3;
  15. extern GLfloat angle;
  16.  
  17. static void gear(GLfloat inner_radius, GLfloat outer_radius, GLfloat width,
  18.      GLint teeth, GLfloat tooth_depth)
  19. {
  20.    GLint i;
  21.    GLfloat r0, r1, r2;
  22.    GLfloat angle, da;
  23.    GLfloat u, v, len;
  24.  
  25.    r0 = inner_radius;
  26.    r1 = outer_radius - tooth_depth / 2.0;
  27.    r2 = outer_radius + tooth_depth / 2.0;
  28.  
  29.    da = 2.0 * M_PI / teeth / 4.0;
  30.  
  31.    glShadeModel(GL_FLAT);
  32.  
  33.    glNormal3f(0.0, 0.0, 1.0);
  34.  
  35.    /* draw front face */
  36.    glBegin(GL_QUAD_STRIP);
  37.    for (i = 0; i <= teeth; i++) {
  38.       angle = i * 2.0 * M_PI / teeth;
  39.       glVertex3f(r0 * cos(angle), r0 * sin(angle), width * 0.5);
  40.       glVertex3f(r1 * cos(angle), r1 * sin(angle), width * 0.5);
  41.       if (i < teeth) {
  42.          glVertex3f(r0 * cos(angle), r0 * sin(angle), width * 0.5);
  43.          glVertex3f(r1 * cos(angle + 3 * da), r1 * sin(angle + 3 * da),
  44.                     width * 0.5);
  45.       }
  46.    }
  47.    glEnd();
  48.  
  49.    /* draw front sides of teeth */
  50.    glBegin(GL_QUADS);
  51.    da = 2.0 * M_PI / teeth / 4.0;
  52.    for (i = 0; i < teeth; i++) {
  53.       angle = i * 2.0 * M_PI / teeth;
  54.  
  55.       glVertex3f(r1 * cos(angle), r1 * sin(angle), width * 0.5);
  56.       glVertex3f(r2 * cos(angle + da), r2 * sin(angle + da), width * 0.5);
  57.       glVertex3f(r2 * cos(angle + 2 * da), r2 * sin(angle + 2 * da),
  58.                  width * 0.5);
  59.       glVertex3f(r1 * cos(angle + 3 * da), r1 * sin(angle + 3 * da),
  60.                  width * 0.5);
  61.    }
  62.    glEnd();
  63.  
  64.    glNormal3f(0.0, 0.0, -1.0);
  65.  
  66.    /* draw back face */
  67.    glBegin(GL_QUAD_STRIP);
  68.    for (i = 0; i <= teeth; i++) {
  69.       angle = i * 2.0 * M_PI / teeth;
  70.       glVertex3f(r1 * cos(angle), r1 * sin(angle), -width * 0.5);
  71.       glVertex3f(r0 * cos(angle), r0 * sin(angle), -width * 0.5);
  72.       if (i < teeth) {
  73.          glVertex3f(r1 * cos(angle + 3 * da), r1 * sin(angle + 3 * da),
  74.                     -width * 0.5);
  75.          glVertex3f(r0 * cos(angle), r0 * sin(angle), -width * 0.5);
  76.       }
  77.    }
  78.    glEnd();
  79.  
  80.    /* draw back sides of teeth */
  81.    glBegin(GL_QUADS);
  82.    da = 2.0 * M_PI / teeth / 4.0;
  83.    for (i = 0; i < teeth; i++) {
  84.       angle = i * 2.0 * M_PI / teeth;
  85.  
  86.       glVertex3f(r1 * cos(angle + 3 * da), r1 * sin(angle + 3 * da),
  87.                  -width * 0.5);
  88.       glVertex3f(r2 * cos(angle + 2 * da), r2 * sin(angle + 2 * da),
  89.                  -width * 0.5);
  90.       glVertex3f(r2 * cos(angle + da), r2 * sin(angle + da), -width * 0.5);
  91.       glVertex3f(r1 * cos(angle), r1 * sin(angle), -width * 0.5);
  92.    }
  93.    glEnd();
  94.  
  95.    /* draw outward faces of teeth */
  96.    glBegin(GL_QUAD_STRIP);
  97.    for (i = 0; i < teeth; i++) {
  98.       angle = i * 2.0 * M_PI / teeth;
  99.  
  100.       glVertex3f(r1 * cos(angle), r1 * sin(angle), width * 0.5);
  101.       glVertex3f(r1 * cos(angle), r1 * sin(angle), -width * 0.5);
  102.       u = r2 * cos(angle + da) - r1 * cos(angle);
  103.       v = r2 * sin(angle + da) - r1 * sin(angle);
  104.       len = sqrt(u * u + v * v);
  105.       u /= len;
  106.       v /= len;
  107.       glNormal3f(v, -u, 0.0);
  108.       glVertex3f(r2 * cos(angle + da), r2 * sin(angle + da), width * 0.5);
  109.       glVertex3f(r2 * cos(angle + da), r2 * sin(angle + da), -width * 0.5);
  110.       glNormal3f(cos(angle), sin(angle), 0.0);
  111.       glVertex3f(r2 * cos(angle + 2 * da), r2 * sin(angle + 2 * da),
  112.                  width * 0.5);
  113.       glVertex3f(r2 * cos(angle + 2 * da), r2 * sin(angle + 2 * da),
  114.                  -width * 0.5);
  115.       u = r1 * cos(angle + 3 * da) - r2 * cos(angle + 2 * da);
  116.       v = r1 * sin(angle + 3 * da) - r2 * sin(angle + 2 * da);
  117.       glNormal3f(v, -u, 0.0);
  118.       glVertex3f(r1 * cos(angle + 3 * da), r1 * sin(angle + 3 * da),
  119.                  width * 0.5);
  120.       glVertex3f(r1 * cos(angle + 3 * da), r1 * sin(angle + 3 * da),
  121.                  -width * 0.5);
  122.       glNormal3f(cos(angle), sin(angle), 0.0);
  123.    }
  124.  
  125.    glVertex3f(r1 * cos(0), r1 * sin(0), width * 0.5);
  126.    glVertex3f(r1 * cos(0), r1 * sin(0), -width * 0.5);
  127.  
  128.    glEnd();
  129.  
  130.    glShadeModel(GL_SMOOTH);
  131.  
  132.    /* draw inside radius cylinder */
  133.    glBegin(GL_QUAD_STRIP);
  134.    for (i = 0; i <= teeth; i++) {
  135.       angle = i * 2.0 * M_PI / teeth;
  136.       glNormal3f(-cos(angle), -sin(angle), 0.0);
  137.       glVertex3f(r0 * cos(angle), r0 * sin(angle), -width * 0.5);
  138.       glVertex3f(r0 * cos(angle), r0 * sin(angle), width * 0.5);
  139.    }
  140.    glEnd();
  141. }
  142.  
  143. void Draw(void)
  144. {
  145.    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  146.  
  147.    glPushMatrix();
  148.    glRotatef(view_rotx, 1.0, 0.0, 0.0);
  149.    glRotatef(view_roty, 0.0, 1.0, 0.0);
  150.    glRotatef(view_rotz, 0.0, 0.0, 1.0);
  151.  
  152.    glPushMatrix();
  153.    glTranslatef(-3.0, -2.0, 0.0);
  154.    glRotatef(angle, 0.0, 0.0, 1.0);
  155.    glCallList(gear1);
  156.    glPopMatrix();
  157.  
  158.    glPushMatrix();
  159.    glTranslatef(3.1, -2.0, 0.0);
  160.    glRotatef(-2.0 * angle - 9.0, 0.0, 0.0, 1.0);
  161.    glCallList(gear2);
  162.    glPopMatrix();
  163.  
  164.    glPushMatrix();
  165.    glTranslatef(-3.1, 4.2, 0.0);
  166.    glRotatef(-2.0 * angle - 25.0, 0.0, 0.0, 1.0);
  167.    glCallList(gear3);
  168.    glPopMatrix();
  169.  
  170.    glPopMatrix();
  171. }
  172.  
  173.  
  174. /* new window size or exposure */
  175. void Reshape(int width, int height)
  176. {
  177.    glViewport(0, 0, (GLint) width, (GLint) height);
  178.  
  179.       GLfloat h = (GLfloat) height / (GLfloat) width;
  180.  
  181.       glMatrixMode(GL_PROJECTION);
  182.       glLoadIdentity();
  183.       glFrustum(-1.0, 1.0, -h, h, 5.0, 60.0);
  184.  
  185.  
  186.    glMatrixMode(GL_MODELVIEW);
  187.    glLoadIdentity();
  188.    glTranslatef(0.0, 0.0, -40.0);
  189. }
  190.  
  191.  
  192. void Init(void)
  193. {
  194.    static GLfloat pos[4] = { 5.0, 5.0, 10.0, 0.0 };
  195.    static GLfloat red[4] = { 0.8, 0.1, 0.0, 1.0 };
  196.    static GLfloat green[4] = { 0.0, 0.8, 0.2, 1.0 };
  197.    static GLfloat blue[4] = { 0.2, 0.2, 1.0, 1.0 };
  198.  
  199.    glLightfv(GL_LIGHT0, GL_POSITION, pos);
  200.    glEnable(GL_CULL_FACE);
  201.    glEnable(GL_LIGHTING);
  202.    glEnable(GL_LIGHT0);
  203.    glEnable(GL_DEPTH_TEST);
  204.  
  205.    /* make the gears */
  206.    gear1 = glGenLists(1);
  207.    glNewList(gear1, GL_COMPILE);
  208.    glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, red);
  209.    gear(1.0, 4.0, 1.0, 20, 0.7);
  210.    glEndList();
  211.  
  212.    gear2 = glGenLists(1);
  213.    glNewList(gear2, GL_COMPILE);
  214.    glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, green);
  215.    gear(0.5, 2.0, 2.0, 10, 0.7);
  216.    glEndList();
  217.  
  218.    gear3 = glGenLists(1);
  219.    glNewList(gear3, GL_COMPILE);
  220.    glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, blue);
  221.    gear(1.3, 2.0, 0.5, 10, 0.7);
  222.    glEndList();
  223.  
  224.    glEnable(GL_NORMALIZE);
  225. }
  226.  
  227. void Key(unsigned char code, int x, int y)
  228. {
  229.     int i;
  230.     (void) x; (void) y;
  231.  
  232.     if (code == XK_Left) {
  233.         view_roty += 5.0;
  234.     }
  235.     else if (code == XK_Right) {
  236.         view_roty -= 5.0;
  237.     }
  238.     else if (code == XK_Up) {
  239.         view_rotx += 5.0;
  240.     }
  241.     else if (code == XK_Down) {
  242.         view_rotx -= 5.0;
  243.     }
  244. };
  245.  
  246. void Idle(void)
  247. {
  248.     angle += 70.0 * 0.05;  /* 70 degrees per second */
  249.     if (angle > 3600.0)
  250.         angle -= 3600.0;
  251. }
  252.  
  253.  
  254.