TextureDibImage.cpp
资源名称:gloop.zip [点击查看]
上传用户:shxiangxiu
上传日期:2007-01-03
资源大小:1101k
文件大小:9k
源码类别:
OpenGL
开发平台:
Visual C++
- /////////////////////////////////////////////////////////////////////////////
- // TextureDibImage.cpp : implementation file
- //
- // glOOP (OpenGL Object Oriented Programming library)
- // Copyright (c) Craig Fahrnbach 1997, 1998
- //
- // OpenGL is a registered trademark of Silicon Graphics
- //
- //
- // This program is provided for educational and personal use only and
- // is provided without guarantee or warrantee expressed or implied.
- //
- // Commercial use is strickly prohibited without written permission
- // from ImageWare Development.
- //
- // This program is -not- in the public domain.
- //
- // This source code has been adapted from the Microsoft Knowledge Base
- // for Visual C++ ( GLTEXTUR.EXE )
- //
- /////////////////////////////////////////////////////////////////////////////
- #include "stdafx.h"
- #include "glOOP.h"
- #include <math.h>
- #include "DIBUtil.h"
- #ifdef _DEBUG
- #define new DEBUG_NEW
- #undef THIS_FILE
- static char THIS_FILE[] = __FILE__;
- #endif
- /////////////////////////////////////////////////////////////////////////////
- // CTextureDibImage
- IMPLEMENT_DYNAMIC(CTextureDibImage, CTexture)
- /////////////////////////////////////////////////////////////////////////////
- // CTextureDibImage construction
- CTextureDibImage::CTextureDibImage()
- {
- // TODO: ADD ANY CONSTRUCTION CODE HERE
- }
- /////////////////////////////////////////////////////////////////////////////
- // CTextureDibImage Destructor
- CTextureDibImage::~CTextureDibImage()
- {
- // TODO: ADD ANY DE-CONSTRUCTION CODE HERE
- }
- /////////////////////////////////////////////////////////////////////////////
- // CTextureDibImage virtual overrides
- BOOL CTextureDibImage::OpenTexture(char* pFileName, HPALETTE hPalette)
- {
- // Get a pointer to our TextureMap
- m_pBits = (GLubyte*)OpenDIBFile(pFileName, hPalette);
- if(m_pBits)
- {
- // Now we have a square 32bpp DIB, use it as the texture.
- m_bApplyImage = TRUE;
- // Save the file name of the texture map
- m_szFileName.Format("%s", pFileName);
- return TRUE;
- }
- return FALSE;
- }
- void CTextureDibImage::Serialize(CArchive& ar, int iVersion)
- {
- CString szBuffer;
- if (ar.IsStoring())
- {
- // Save the Object Class header...
- szBuffer.Format("%sCTextureDibImage {n", szIndent);
- ar.WriteString(szBuffer);
- // Save the this objects' specific data...
- // szBuffer.Format("%stSolid < %d >n", szIndent, m_bSolid);
- // ar.WriteString(szBuffer);
- // Save the base class CTexture data...
- CTexture::Serialize(ar, iVersion);
- szBuffer.Format("%s}n", szIndent); // end of texture map def
- ar.WriteString(szBuffer);
- }
- else
- {
- // Read the derived class data..
- ar.ReadString(szBuffer); // Read the class header
- // ar.ReadString(szBuffer);
- // szBuffer.TrimLeft(); // Remove leading white spaces
- // sscanf(szBuffer, "Solid < %d >n", &m_bSolid);
- // Read the base class CTexture data...
- CTexture::Serialize(ar, iVersion);
- }
- }
- /////////////////////////////////////////////////////////////////////////////
- // CTextureDibImage function implementation
- /////////////////////////////////////////////////////////////////////////////
- //
- // FUNCTION : SaveDIBFile(LPSTR pszFileName, BITMAPINFO *pInfo, void *pBits
- //
- // PURPOSE : Save the DIB in a Windows Bitmap (*.bmp) compatable file.
- //
- // INPUTS : pszFileName - a 32-bit char pointer to the file to open
- // pInfo - The BITMAPINFO structure of the DIB to save
- // pBits - A GLubyte pointer to the DIB bits
- //
- // RETURNS : 0 - if successful.
- // NonZero - otherwise
- //
- int CTextureDibImage::SaveDIBFile(LPSTR pszFileName, BITMAPINFO *pInfo, void *pBits)
- {
- FILE *fp; // Open file pointer
- long size, // Size of file
- infosize, // Size of bitmap info
- bitsize; // Size of bitmap pixels
- BITMAPFILEHEADER header; // File header
- // Try opening the file; use "wb" mode to write this
- // *binary* file.
- if ((fp = fopen(pszFileName, "wb")) == NULL)
- return (-1);
- if (pInfo->bmiHeader.biSizeImage == 0) // Figure out the bitmap size
- bitsize = (pInfo->bmiHeader.biWidth *
- pInfo->bmiHeader.biBitCount + 7) / 8 *
- abs(pInfo->bmiHeader.biHeight);
- else
- bitsize = pInfo->bmiHeader.biSizeImage;
- infosize = sizeof(BITMAPINFOHEADER);
- switch (pInfo->bmiHeader.biCompression)
- {
- case BI_BITFIELDS :
- infosize += 12; // Add 3 RGB doubleword masks
- if (pInfo->bmiHeader.biClrUsed == 0)
- break;
- case BI_RGB :
- if (pInfo->bmiHeader.biBitCount > 8 &&
- pInfo->bmiHeader.biClrUsed == 0)
- break;
- case BI_RLE8 :
- case BI_RLE4 :
- if (pInfo->bmiHeader.biClrUsed == 0)
- infosize += (1 << pInfo->bmiHeader.biBitCount) * 4;
- else
- infosize += pInfo->bmiHeader.biClrUsed * 4;
- break;
- }
- size = sizeof(BITMAPFILEHEADER) + infosize + bitsize;
- // Write the file header, bitmap information, and
- // bitmap pixel data...
- header.bfType = 'MB'; // Non-portable... sigh
- header.bfSize = size;
- header.bfReserved1 = 0;
- header.bfReserved2 = 0;
- header.bfOffBits = sizeof(BITMAPFILEHEADER) + infosize;
- if (fwrite(&header, 1, sizeof(BITMAPFILEHEADER), fp) < sizeof(BITMAPFILEHEADER))
- {
- // Couldn't write the file header - return...
- fclose(fp);
- return (-1);
- }
- if (fwrite(pInfo, 1, infosize, fp) < (UINT)infosize)
- {
- // Couldn't write the bitmap header - return...
- fclose(fp);
- return (-1);
- }
- if (fwrite(pBits, 1, bitsize, fp) < (UINT)bitsize)
- {
- // Couldn't write the bitmap - return...
- fclose(fp);
- return (-1);
- }
- // OK, everything went fine - return...
- fclose(fp);
- return (0);
- }
- /////////////////////////////////////////////////////////////////////////////
- //
- // FUNCTION : OpenDIBFile(LPSTR pszFileName, HPALETTE hPalette)
- //
- // PURPOSE : Open a Windows DIB (*.bmp or *.dib) file and convert the file
- // to an OpenGL compatable format.
- //
- // INPUTS : filename - a char pointer to the file to open
- // hPalette - a HANDLE to the palette for mapping our DIB colors
- //
- // RETURNS : NULL if unsuccessful, otherwise
- // Pointer (GLubyte*) to our bits
- //
- void* CTextureDibImage::OpenDIBFile(LPSTR pszFileName, HPALETTE hPalette)
- {
- HANDLE hDibOriginal; // Handle to original-format memory DIB
- void* pScaledBits = NULL; // Pointer to our scaled DIB bits
- if (!pszFileName)
- return NULL; // No file to open!
- // Load the DIB
- hDibOriginal = OpenDIB(pszFileName);
- if(hDibOriginal)
- {
- // Convert DIB to a square 32bpp DIB.
- pScaledBits = ScaleDIB(hPalette, hDibOriginal); //(HANDLE)m_pBitmapInfo);
- if(!pScaledBits)
- {
- if(the3dEngine.m_bDisplayErrorMessages)
- AfxMessageBox("CTextureDibImage::FileOpen - ScaleDIB failed", MB_OK);
- return NULL;
- }
- return pScaledBits;
- }
- return NULL;
- }
- /////////////////////////////////////////////////////////////////////////////
- //
- // FUNCTION : ReadDIBitmap(BITMAPINFO **info)
- //
- // PURPOSE : Read the current OpenGL viewport into a 24-bit RGB bitmap
- //
- // RETURNS : A pointer to the bitmap if successful, otherwise
- // NULL
- //
- // AUTHOR : This code sample originated from the OpenGL Super Bible
- // chapter 11, page 358
- //
- void* CTextureDibImage::ReadDIBitmap(BITMAPINFO **info)
- {
- long i, j, // Looping var
- bitsize, // Total size of bitmap
- width; // Aligned width of a scanline
- GLint viewport[4];// Current viewport
- void *bits; // RGB bits
- GLubyte *rgb, // RGB looping var
- temp; // Temporary var for swapping
- // Grab the current viewport...
- glGetIntegerv(GL_VIEWPORT, viewport);
- // Allocate memory for the header and bitmap...
- if ((*info = (BITMAPINFO *)malloc(sizeof(BITMAPINFOHEADER))) == NULL)
- {
- // Couldn't allocate memory for bitmap info - return NULL...
- return (NULL);
- }
- width = viewport[2] * 3; /* Real width of scanline */
- width = (width + 3) & ~3; /* Aligned to 4 bytes */
- bitsize = width * viewport[3]; /* Size of bitmap, aligned */
- if ((bits = calloc(bitsize, 1)) == NULL)
- {
- // Couldn't allocate memory for bitmap pixels - return NULL...
- free(*info);
- return (NULL);
- }
- // Read pixels from the framebuffer...
- glFinish(); // Finish all OpenGL commands
- glPixelStorei(GL_PACK_ALIGNMENT, 4); // Force 4-byte alignment
- glPixelStorei(GL_PACK_ROW_LENGTH, 0);
- glPixelStorei(GL_PACK_SKIP_ROWS, 0);
- glPixelStorei(GL_PACK_SKIP_PIXELS, 0);
- glReadPixels(0, 0, viewport[2], viewport[3], GL_RGB, GL_UNSIGNED_BYTE,
- bits);
- // Swap red and blue for the bitmap...
- for (i = 0; i < viewport[3]; i ++)
- {
- for (j = 0, rgb = ((GLubyte *)bits) + i * width;
- j < viewport[2]; j ++, rgb += 3)
- {
- temp = rgb[0];
- rgb[0] = rgb[2];
- rgb[2] = temp;
- }
- }
- // Finally, initialize the bitmap header information...
- (*info)->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
- (*info)->bmiHeader.biWidth = viewport[2];
- (*info)->bmiHeader.biHeight = viewport[3];
- (*info)->bmiHeader.biPlanes = 1;
- (*info)->bmiHeader.biBitCount = 24;
- (*info)->bmiHeader.biCompression = BI_RGB;
- (*info)->bmiHeader.biSizeImage = bitsize;
- (*info)->bmiHeader.biXPelsPerMeter = 2952; // 75 DPI
- (*info)->bmiHeader.biYPelsPerMeter = 2952; // 75 DPI
- (*info)->bmiHeader.biClrUsed = 0;
- (*info)->bmiHeader.biClrImportant = 0;
- return (bits);
- }