** File:          extrude1.c
** Description:   Renders a 3D image of x, y, z axes.
** Rev:           1.0
** Created:       29 August 2001
** Last Update:   07 October 2002
** Author:        Fran Soddell
** Email:         F.Soddell@bendigo.latrobe.edu.au
**/
#include <GL/glut.h>
#include <stdio.h>
#include <math.h>

#define TRUE 1
#define FALSE 0
#define PI 3.14159
/*
** manage 3D
*/
enum {x,y,z};
/*
** manage window
*/
int width =400;
int height=400;
int xPosition=50;
int yPosition=70;
/*
** manage world projection
*/
enum {xLeft,xRight,yBottom,yTop,zNear,zFar};
GLdouble world[]={
   -5.0,5.0,-5.0,5.0,0.1,100
};
GLdouble fovy   =90.0;
GLdouble aspect =1.0;
int perspective =TRUE;
/*
** manage camera
*/
enum {camera1,camera2};
int camera=camera1;
GLdouble eye[][3]={
   {0.5,0.5,2.5},{0.0,1.0,3.0}
};
GLdouble centre[][3]={
   {0.0,1.0,0.0},{0.0,0.0,0.0}
};
GLdouble up[]={
   0.0,1.0,0.0
};
/*
** manage colour
*/
#define ALPHA 0.0
enum {red,green,blue,
      yellow,magenta,cyan,
      pink,
      white,black,colours};
typedef GLfloat colourType[3];
colourType colour[]={
   {1.0,0.0,0.0},{0.0,1.0,0.0},{0.0,0.0,1.0},
   {1.0,1.0,0.0},{1.0,0.0,1.0},{0.0,1.0,1.0},
   {1.0,0.65,0.65},
   {1.0,1.0,1.0},{0.0,0.0,0.0}
};
/*
** model management
*/
typedef GLdouble vertexType[3];
#define NGON_SIZE 8
vertexType nGon[NGON_SIZE];
vertexType duplicate[NGON_SIZE];
double radius=0.25;
GLint extrusionMode=GL_LINE_LOOP;
/*
**  ***********************************************************
*/
void renderImage(vertexType * image,
                 int start, int numVertices,
                 GLint primitive){
   int i;
   glBegin(primitive);
      for(i=start;i<numVertices;i++)
         glVertex3dv(image[i]);
   glEnd();
}
void extrude(vertexType * front,vertexType * back,
             int numVertices,GLint primitive){
   int i,j=0;
   for(i=0;i<numVertices;i++){
      glBegin(primitive);
         glVertex3dv(front[j]);
         glVertex3dv(back[j]);
         if(i==numVertices-1)
            j=0;
         else
            j++;
         glVertex3dv(back[j]);
         glVertex3dv(front[j]);
      glEnd();
   }
}
void renderAxis(double length){
   glPushMatrix();
   glBegin(GL_LINES);
      glVertex3d(0,0,0);
      glVertex3d(0,0,length);
   glEnd();
   glTranslated(0,0,length-0.2);
   glutWireCone(0.04,0.2,12,9);
   glPopMatrix();
}
void axes(){
   glLineWidth(1);
   glColor3fv(colour[red]);
   /* z-axis */
   renderAxis(1.5);
   glPushMatrix();
   /* y-axis */
   glRotated(90,0,1.0,0);
   glColor3fv(colour[green]);
   renderAxis(1.5);
   /* x-axis */
   glRotated(-90,1,0,0);
   glColor3fv(colour[blue]);
   renderAxis(1.5);
   glPopMatrix();
}
void setProjection(){
   glMatrixMode(GL_PROJECTION);
   glLoadIdentity();
   if(!perspective)
      glOrtho(world[xLeft],  world[xRight],
              world[yBottom],world[yTop],
              world[zNear],  world[zFar]);
   else
      gluPerspective(fovy,1,world[zNear],world[zFar]);
}
void setCamera(){
   glMatrixMode(GL_MODELVIEW);
   glLoadIdentity();
   gluLookAt(eye[camera][x], eye[camera][y],eye[camera][z],
             centre[camera][x],centre[camera][y],centre[camera][z],
             up[x],up[y],up[z]);
}
void display(){
   setCamera();
   /*
   ** Clear window with background colour before (re)rendering.
   */
   glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

   glPushMatrix();
   axes();
   glPopMatrix();

   glColor3fv(colour[magenta]);
   renderImage(nGon,0,NGON_SIZE,GL_POLYGON);
   glColor3fv(colour[pink]);
   renderImage(duplicate,0,NGON_SIZE,GL_POLYGON);

   if(extrusionMode==-999){
      glColor3fv(colour[black]);
      extrude(nGon,duplicate,NGON_SIZE,GL_LINE_LOOP);
      glColor3fv(colour[red]);
      extrude(nGon,duplicate,NGON_SIZE,GL_POLYGON);
   }
   else{
      if(extrusionMode==GL_POLYGON)
         glColor3fv(colour[red]);
      else
         glColor3fv(colour[black]);
      extrude(nGon,duplicate,NGON_SIZE,extrusionMode);
   }

   glPopMatrix();
   glutSwapBuffers();;
}
void keyboard(unsigned char key,int xMouse,int yMouse){
   static int depthEnabled=FALSE;
   static int cullEnabled=FALSE;
   switch(key){
      case 27 : exit(0);
      case 'p': perspective=!perspective;
                setProjection();
                break;
      case 'f': if(fovy<180) fovy+=0.5;
                setProjection();
                break;
      case 'F': if(fovy>0) fovy-=0.5;
                setProjection();
                break;
      case 'C': if(camera==camera1)
                   camera=camera2;
                else camera=camera1;
                break;
      case 'd': depthEnabled=!depthEnabled;
                if(depthEnabled) glEnable(GL_DEPTH_TEST);
                else glDisable(GL_DEPTH_TEST);
                break;
      case 'c': cullEnabled=!cullEnabled;
                if(cullEnabled) glEnable(GL_CULL_FACE);
                else glDisable(GL_CULL_FACE);
                break;
      case 'P': extrusionMode=GL_POLYGON; break;
      case 'L': extrusionMode=GL_LINE_LOOP; break;
      case 'M': extrusionMode=GL_LINES; break;
      case 'N': extrusionMode=-999; break;
   }
   glutPostRedisplay();
}
void reshapeWindow(int w, int h){
   int yOrigin=0, xOrigin=0;
   if(w>h){
      yOrigin=(h-w)/2;
      h=w;
   }
   else{
      xOrigin=(w-h)/2;
      w=h;
   }
   glViewport(xOrigin,yOrigin,(GLsizei)w,(GLsizei)h);
   setProjection();
}
void setUpGLUT(int argc,char ** argv){
   glutInit(&argc,argv);
   glutInitDisplayMode(GLUT_DEPTH|GLUT_DOUBLE|GLUT_RGB);
   glutInitWindowSize(width,height);
   glutInitWindowPosition(xPosition,yPosition);
   glutCreateWindow("Extruded nGon");
   /*
   ** Register callbacks.
   */
   glutDisplayFunc(display);
   glutReshapeFunc(reshapeWindow);
   glutKeyboardFunc(keyboard);
}
void initialiseGL(){
   glClearColor(1,1,1,ALPHA);
   glCullFace(GL_BACK);
}
void computeVertices(GLdouble centreX,GLdouble centreY,
                     GLdouble radius,GLint numVertices){
   int i;
   GLdouble angle=2*PI/numVertices;

   for(i=0;i<numVertices;i++){
      nGon[i][x]=centreX+radius*cos(i*angle);
      nGon[i][y]=centreY+radius*sin(i*angle);
   }
}
void initialise(){
   int i;
   computeVertices(0.0,0.0,radius,NGON_SIZE);
   for(i=0;i<NGON_SIZE;i++){
      duplicate[i][x]=nGon[i][x];
      duplicate[i][y]=nGon[i][y];
      duplicate[i][z]=nGon[i][z]-1.5;
   }
}
int main(int argc,char ** argv){
   initialise();
   setUpGLUT(argc,argv);
   initialiseGL();
   /*
    * Display window and enter the GLUT event
    * processing loop.
    */
   glutMainLoop();

   return 0;
}

&lt;/pre&gt;&lt;/body&gt;&lt;/html&gt;</pre></body></html>