L'exécutable

Le source: Gloss.cpp

Les fichiers texture Tile.rgb et Reflect.rgb

/* $Id: gloss.c,v 1.4.4.1 2000/08/29 21:17:25 brianp Exp $ */

/*
 * Specular reflection demo.  The specular highlight is modulated by
 * a sphere-mapped texture.  The result is a high-gloss surface.
 * NOTE: you really need hardware acceleration for this.
 * Also note, this technique can't be implemented with multi-texture
 * and separate specular color interpolation because there's no way
 * to indicate that the second texture unit (the reflection map)
 * should modulate the specular color and not the base color.
 * A future multi-texture extension could fix that.
 *
 * Command line options:
 *    -info      print GL implementation information
 *
 *
 * Brian Paul  October 22, 1999  This program is in the public domain.
 */


#include <assert.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <math.h>

#include <GL/glut.h>
#include <GL/gl.h>
#include <GL/glu.h>

#include "ReadTex2.h"   /* I know, this is a hack. */
#include "ModuleManipulateur.h"
#include "ModuleReshape.h"

#define SPECULAR_TEXTURE_FILE "reflect.rgb"
#define BASE_TEXTURE_FILE "tile.rgb"

/* Menu items */
#define DO_SPEC_TEXTURE 1
#define OBJECT 2
#define ANIMATE 3
#define QUIT 100

static GLuint CylinderObj = 0;
static GLuint TeapotObj = 0;
static GLuint Object = 0;
static GLboolean Animate = GL_TRUE;

static GLfloat Xrot = 0.0, Yrot = 0.0, Zrot = 0.0;
static GLfloat DXrot = 1.0, DYrot = 2.5;

static GLfloat Black[4] = { 0, 0, 0, 0 };
static GLfloat White[4] = { 1, 1, 1, 1 };
static GLfloat Diffuse[4] = { .3F, .3F, 1.0F, 1.0F };  /* blue */
static GLfloat Shininess = 6;

static GLuint BaseTexture, SpecularTexture;
static GLboolean DoSpecTexture = GL_TRUE;

/* performance info */
static GLint T0 = 0;
static GLint Frames = 0;

static void Idle( void )
{
   if (Animate) {
      Xrot += DXrot;
      Yrot += DYrot;
      glutPostRedisplay();
   }
}

static void Display( void )
{
   glClearGL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );

   glPushMatrix();
   glRotatef(Xrot, 1.0, 0.0, 0.0);
   glRotatef(Yrot, 0.0, 1.0, 0.0);
   glRotatef(Zrot, 0.0, 0.0, 1.0);
   manipulateurSouris();
   manipulateurClavier();

   /* First pass: diffuse lighting with base texture */
   glMaterialfv(GL_FRONTGL_DIFFUSE, Diffuse);
   glMaterialfv(GL_FRONTGL_SPECULAR, Black);
   glEnable(GL_TEXTURE_2D);
   glBindTexture(GL_TEXTURE_2D, BaseTexture);
   glCallList(Object);

   /* Second pass: specular lighting with reflection texture */
   glBlendFunc(GL_ONEGL_ONE);  /* add */
   glEnable(GL_BLEND);
   glDepthFunc(GL_LEQUAL);
   glMaterialfv(GL_FRONTGL_DIFFUSE, Black);
   glMaterialfv(GL_FRONTGL_SPECULAR, White);
   if (DoSpecTexture) {
      glBindTexture(GL_TEXTURE_2D, SpecularTexture);
      glEnable(GL_TEXTURE_GEN_S);
      glEnable(GL_TEXTURE_GEN_T);
   }
   else {
      glDisable(GL_TEXTURE_2D);
   }
   glCallList(Object);
   glDisable(GL_TEXTURE_GEN_S);
   glDisable(GL_TEXTURE_GEN_T);
   glDisable(GL_BLEND);

   glPopMatrix();

   glutSwapBuffers();

   if (Animate) {
      GLint t = glutGet(GLUT_ELAPSED_TIME);
      Frames++;
      if (t - T0 >= 5000) {
         GLfloat seconds = (t - T0) / 1000.0;
         GLfloat fps = Frames / seconds;
         printf("%d frames in %g seconds = %g FPS\n", Frames, seconds, fps);
         T0 = t;
         Frames = 0;
      }
   }
}

static void ToggleAnimate(void)
{
   Animate = !Animate;
   if (Animate) {
      glutIdleFunc( Idle );
      T0 = glutGet(GLUT_ELAPSED_TIME);
      Frames = 0;
   }
   else {
      glutIdleFunc( NULL );
   }
}


static void ModeMenu(int entry)
{
   if (entry==ANIMATE) {
      ToggleAnimate();
   }
   else if (entry==DO_SPEC_TEXTURE) {
      DoSpecTexture = !DoSpecTexture;
   }
   else if (entry==OBJECT) {
      if (Object == TeapotObj)
         Object = CylinderObj;
      else
         Object = TeapotObj;
   }
   else if (entry==QUIT) {
      exit(0);
   }
   glutPostRedisplay();
}


void key(unsigned char key,int x,int y) {
  if ( keyManipulateur(key,x,y) )
    glutPostRedisplay();
    else {
    (void) x;
    (void) y;
    switch (key) {
      case 's':
         Shininess--;
         if (Shininess < 0.0)
            Shininess = 0.0;
         glMaterialf(GL_FRONTGL_SHININESS, Shininess);
         printf("Shininess = %g\n", Shininess);
         break;
      case 'S':
         Shininess++;
         if (Shininess > 128.0)
            Shininess = 128.0;
         glMaterialf(GL_FRONTGL_SHININESS, Shininess);
         printf("Shininess = %g\n", Shininess);
         break;
      case ' ':
         ToggleAnimate();
         break;
      case 27:
         exit(0);
         break; }
    glutPostRedisplay(); }
}


static void myinit(void)
{
   /* Cylinder object */
   {
      static GLfloat height = 100.0;
      static GLfloat radius = 40.0;
      static GLint slices = 24;  /* pie slices around Z axis */
      static GLint stacks = 10;  /* subdivisions along length of cylinder */
      static GLint rings = 4;    /* rings in the end disks */
      glEnable(GL_AUTO_NORMAL);
      glEnable(GL_NORMALIZE);
      GLUquadricObj *q = gluNewQuadric();
      assert(q);
      gluQuadricTexture(q, GL_TRUE);

      CylinderObj = glGenLists(1);
      glNewList(CylinderObj, GL_COMPILE);

      glPushMatrix();
      glTranslatef(0.0, 0.0, -0.5 * height);

      glMatrixMode(GL_TEXTURE);
      glLoadIdentity();
      /*glScalef(8.0, 4.0, 2.0);*/
      glMatrixMode(GL_MODELVIEW);

      /* cylinder */
      gluQuadricNormals(q, GL_SMOOTH);
      gluQuadricTexture(q, GL_TRUE);
      gluCylinder(q, radius, radius, height, slices, stacks);

      /* end cap */
      glMatrixMode(GL_TEXTURE);
      glLoadIdentity();
      glScalef(3.0, 3.0, 1.0);
      glMatrixMode(GL_MODELVIEW);

      glTranslatef(0.0, 0.0, height);
      gluDisk(q, 0.0, radius, slices, rings);

      /* other end cap */
      glTranslatef(0.0, 0.0, -height);
      gluQuadricOrientation(q, GLU_INSIDE);
      gluDisk(q, 0.0, radius, slices, rings);

      glPopMatrix();

      glMatrixMode(GL_TEXTURE);
      glLoadIdentity();
      glMatrixMode(GL_MODELVIEW);

      glEndList();
      gluDeleteQuadric(q);
   }

   /* Teapot */
   {
      TeapotObj = glGenLists(1);
      glNewList(TeapotObj, GL_COMPILE);

      glFrontFace(GL_CW);
      glutSolidTeapot(40.0);
      glFrontFace(GL_CCW);

      glEndList();
   }

   /* show cylinder by default */
   Object = CylinderObj;


   /* lighting */
   glEnable(GL_LIGHTING);
   {
      GLfloat pos[4] = { 3, 3, 3, 1 };
      glLightfv(GL_LIGHT0GL_AMBIENT, Black);
      glLightfv(GL_LIGHT0GL_DIFFUSE, White);
      glLightfv(GL_LIGHT0GL_SPECULAR, White);
      glLightfv(GL_LIGHT0GL_POSITION, pos);
      glEnable(GL_LIGHT0);
      glMaterialfv(GL_FRONTGL_AMBIENT, Black);
      glMaterialf(GL_FRONTGL_SHININESS, Shininess);
      glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, 1);
   }

   /* Base texture */
   glGenTextures(1, &BaseTexture);
   glBindTexture(GL_TEXTURE_2D, BaseTexture);
   glTexParameteri(GL_TEXTURE_2DGL_TEXTURE_MIN_FILTERGL_LINEAR);
   glTexParameteri(GL_TEXTURE_2DGL_TEXTURE_MAG_FILTERGL_LINEAR);
   if (!LoadRGBMipmaps(BASE_TEXTURE_FILE, GL_RGB)) {
      printf("Error: couldn't load texture image file %s\n", BASE_TEXTURE_FILE);
      exit(1);
   }

   /* Specular texture */
   glGenTextures(1, &SpecularTexture);
   glBindTexture(GL_TEXTURE_2D, SpecularTexture);
   glTexParameteri(GL_TEXTURE_2DGL_TEXTURE_MIN_FILTERGL_LINEAR);
   glTexParameteri(GL_TEXTURE_2DGL_TEXTURE_MAG_FILTERGL_LINEAR);
#if 1
   glTexGeni(GL_SGL_TEXTURE_GEN_MODEGL_SPHERE_MAP);
   glTexGeni(GL_TGL_TEXTURE_GEN_MODEGL_SPHERE_MAP);
#else
   glTexGeni(GL_SGL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
   glTexGeni(GL_TGL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
   glTexGeni(GL_RGL_TEXTURE_GEN_MODE, GL_NORMAL_MAP_NV);
#endif
   if (!LoadRGBMipmaps(SPECULAR_TEXTURE_FILE, GL_RGB)) {
      printf("Error: couldn't load texture image file %s\n", SPECULAR_TEXTURE_FILE);
      exit(1);
   }

   /* misc */
   glEnable(GL_CULL_FACE);
   glEnable(GL_TEXTURE_2D);
   glEnable(GL_DEPTH_TEST);
   glEnable(GL_NORMALIZE);

}

void creationMenus(void) {
  glutCreateMenu(ModeMenu);
  glutAddMenuEntry("Toggle Highlight",DO_SPEC_TEXTURE);
  glutAddMenuEntry("Toggle Object",OBJECT);
  glutAddMenuEntry("Toggle Animate",ANIMATE);
  glutAddMenuEntry("Quit",QUIT);
  glutAttachMenu(GLUT_RIGHT_BUTTON);
}

int main(int argc,char **argv) {
  glutInit(&argc,argv);
  glutInitWindowSize(250,250);
  glutInitDisplayMode(GLUT_RGBA|GLUT_DOUBLE|GLUT_DEPTH );
  glutCreateWindow("Des objets mirroirs");
  myinit();
  creationMenus();
  setParametresFrustumBasique(-30.0F,30.0F,-30.0,30.0F,150.0F,500.0F,0.0F,0.0F,-380.0F);
  setManipulateurDistance(380.0F);
  glutReshapeFunc(reshapeFrustumBasique);
  glutKeyboardFunc(key);
  glutSpecialFunc(specialBasique);
  glutMotionFunc(motionBasique);
  glutMouseFunc(sourisBasique);
  glutDisplayFunc(Display);
  glutIdleFunc(Idle);
  glutMainLoop();
  return(0);
}

Les modules utilitaires : Modules.zip

RETOUR