Exemplo n.º 1
0
// ==================================================================
// DESTRUCTOR
// ==================================================================
Material::~Material() {
  if (hasTextureMap()) {
    glDeleteTextures(1,&texture_id);
    assert (image != NULL);
    delete image;
  }
}
Exemplo n.º 2
0
// ==================================================================
// OpenGL setup for textures
// ==================================================================
GLuint Material::getTextureID() { 
  assert (hasTextureMap()); 

  // if this is the first time the texture is being used, we must
  // initialize it
  if (texture_id == 0)  {
    glGenTextures(1,&texture_id);
    assert (texture_id != 0);
    glBindTexture(GL_TEXTURE_2D, texture_id);
    // select modulate to mix texture with color for shading
    glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
    // or decal to not mix local shading
    //glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
    // when texture area is small, bilinear filter the closest mipmap
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
		     GL_LINEAR_MIPMAP_NEAREST );
    // when texture area is large, bilinear filter the original
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
    // the texture wraps over at the edges (repeat)
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT );
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );
    // to be most compatible, textures should be square and a power of 2
    assert (image->Width() == image->Height());
    assert (image->Width() == 256);
    // build our texture mipmaps
    gluBuild2DMipmaps( GL_TEXTURE_2D, 3, image->Width(), image->Height(),
		       GL_RGB, GL_UNSIGNED_BYTE, image->getGLPixelData());
  }
  
  return texture_id;
}
Exemplo n.º 3
0
// ==================================================================
// An average texture color, a hack for use in radiosity
// ==================================================================
void Material::ComputeAverageTextureColor() {
  assert (hasTextureMap());
  double r = 0;
  double g = 0;
  double b = 0;
  for (int i = 0; i < image->Width(); i++) {
    for (int j = 0; j < image->Height(); j++) {
      Color c = image->GetPixel(i,j);
       r += srgb_to_linear(c.r/255.0);
       g += srgb_to_linear(c.g/255.0);
       b += srgb_to_linear(c.b/255.0);
    }
  }
  int count = image->Width() * image->Height();
  r /= double(count);
  g /= double(count);
  b /= double(count);
  diffuseColor = Vec3f(r,g,b);
}
Exemplo n.º 4
0
// ==================================================================
// TEXTURE LOOKUP FOR DIFFUSE COLOR
// ==================================================================
const Vec3f Material::getDiffuseColor(double s, double t) const {
  if (!hasTextureMap()) return diffuseColor; 

  assert (image != NULL);

  // simple biliear interpolation on the closest 4 pixels in the texture
  double i_ = (s * image->Width());
  double j_ = (t * image->Height());
  int i1 = int(s * image->Width());
  int j1 = int(t * image->Height());
  double dx = i_-i1;
  double dy = j_-j1;
  i1 %= image->Width();
  j1 %= image->Height();
  if (i1 < 0) i1 += image->Width();
  if (j1 < 0) j1 += image->Height();
  assert (i1 >= 0 && i1 < image->Width());
  assert (j1 >= 0 && j1 < image->Height());
  int i2 = i1+1;  if (i2 == image->Width()) i2-=1;
  int j2 = j1+1;  if (j2 == image->Height()) j2-=1;
  assert (i2 >= 0 && i2 < image->Width());
  assert (j2 >= 0 && j2 < image->Height());

  // average the 4 colors
  Color c1 = image->GetPixel(i1,j1);
  Color c2 = image->GetPixel(i1,j2);
  Color c3 = image->GetPixel(i2,j1);
  Color c4 = image->GetPixel(i2,j2);

  // we assume the texture is stored in sRGB and convert to linear for
  // computation.  It will be converted back to sRGB before display.
  Vec3f c1v(srgb_to_linear(c1.r/255.0),srgb_to_linear(c1.g/255.0),srgb_to_linear(c1.b/255.0));
  Vec3f c2v(srgb_to_linear(c2.r/255.0),srgb_to_linear(c2.g/255.0),srgb_to_linear(c2.b/255.0));
  Vec3f c3v(srgb_to_linear(c3.r/255.0),srgb_to_linear(c3.g/255.0),srgb_to_linear(c3.b/255.0));
  Vec3f c4v(srgb_to_linear(c4.r/255.0),srgb_to_linear(c4.g/255.0),srgb_to_linear(c4.b/255.0));

  return c1v*(1-dx)*(1-dy) + c2v*(1-dx)*dy + c3v*dx*(1-dy) + c4v*dx*dy;
}
Exemplo n.º 5
0
// ==================================================================
// TEXTURE LOOKUP FOR DIFFUSE COLOR
// ==================================================================
const Vec3f Material::getDiffuseColor(double s, double t) const {
  if (!hasTextureMap()) return diffuseColor; 

  assert (image != NULL);

  // this is just using nearest neighbor and could be improved to
  // bilinear interpolation, etc.
  int i = int(s * image->Width()) % image->Width();
  int j = int(t * image->Height()) % image->Height();
  if (i < 0) i += image->Width();
  if (j < 0) j += image->Height();
  assert (i >= 0 && i < image->Width());
  assert (j >= 0 && j < image->Height());
  Color c = image->GetPixel(i,j);

  // we assume the texture is stored in sRGB and convert to linear for
  // computation.  It will be converted back to sRGB before display.
  double r = srgb_to_linear(c.r/255.0);
  double g = srgb_to_linear(c.g/255.0);
  double b = srgb_to_linear(c.b/255.0);

  return Vec3f(r,g,b);
}