/******************************Module*Header*******************************\ * Module Name: texture.c * * Handles texture initialization * * Copyright (c) 1994-1995 Microsoft Corporation * \**************************************************************************/ #include #include #include #include #include #include #include #include #include #include "pipes.h" #include "texture.h" mfPoint2di texRep; // texture repetition factors // creates a texture from a BMP file int InitBMPTexture( char *bmpfile, int wflag ) { AUX_RGBImageRec *image = (AUX_RGBImageRec *) NULL; double xPow2, yPow2; int ixPow2, iyPow2; int xSize2, ySize2; BYTE *pData; float fxFact, fyFact; GLint glMaxTexDim; // load the bmp file if( wflag ) image = auxDIBImageLoadW( (LPCWSTR) bmpfile); else image = auxDIBImageLoadA( bmpfile ); if( !image ) return 0; // failure glEnable(GL_TEXTURE_2D); glPixelStorei(GL_UNPACK_ALIGNMENT, 1); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); switch( textureQuality ) { case TEX_HIGH: glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST); break; case TEX_MID: glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); break; case TEX_LOW: default: glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); break; } glGetIntegerv(GL_MAX_TEXTURE_SIZE, &glMaxTexDim); glMaxTexDim = min(256, glMaxTexDim); if (image->sizeX <= glMaxTexDim) xPow2 = log((double)image->sizeX) / log((double)2.0); else xPow2 = log((double)glMaxTexDim) / log((double)2.0); if (image->sizeY <= glMaxTexDim) yPow2 = log((double)image->sizeY) / log((double)2.0); else yPow2 = log((double)glMaxTexDim) / log((double)2.0); ixPow2 = (int)xPow2; iyPow2 = (int)yPow2; if (xPow2 != (double)ixPow2) ixPow2++; if (yPow2 != (double)iyPow2) iyPow2++; xSize2 = 1 << ixPow2; ySize2 = 1 << iyPow2; pData = LocalAlloc(LMEM_FIXED, xSize2 * ySize2 * 3 * sizeof(BYTE)); if (!pData) return 0; gluScaleImage(GL_RGB, image->sizeX, image->sizeY, GL_UNSIGNED_BYTE, image->data, xSize2, ySize2, GL_UNSIGNED_BYTE, pData); if( textureQuality == TEX_HIGH ) { gluBuild2DMipmaps(GL_TEXTURE_2D, 3, image->sizeX, image->sizeY, GL_RGB, GL_UNSIGNED_BYTE, image->data); } else { glTexImage2D(GL_TEXTURE_2D, 0, 3, xSize2, ySize2, 0, GL_RGB, GL_UNSIGNED_BYTE, pData); } // Figure out repetition factor of texture, based on bitmap size and // screen size. // // We arbitrarily decide to repeat textures that are smaller than // 1/8th of screen width or height. texRep.x = texRep.y = 1; if( (fxFact = vc.winSize.width / xSize2 / 8.0f) >= 1.0f) texRep.x = (int) (fxFact+0.5f); if( (fyFact = vc.winSize.height / ySize2 / 8.0f) >= 1.0f) texRep.y = (int) (fyFact+0.5f); LocalFree(image->data); image->data = pData; return 1; // success }