游戏开发—乱dib

Posted on 2010-03-15 18:48  625747  阅读(285)  评论(0)    收藏  举报

 

代码
#include "DibBMP.h"
#include
<fstream>
#define WIDTHBYTES(i) ((i+31)/32*4)

CDibBMP::CDibBMP(
void)
{
}

CDibBMP::
~CDibBMP(void)
{
}

BOOL CDibBMP::LoadBitmap(
char *filename)
{

std::ifstream fileBmp;
//(filename);


fileBmp.open(filename,std::ios::binary);

if (!fileBmp)
{
MessageBox(NULL,
"无法打开喔", "XinXin's WinMain", MB_OK | MB_ICONINFORMATION);
fileBmp.close();
return false;
}
fileBmp.read ((
char*)&bitmap.bitmapfileheader,sizeof(BITMAPFILEHEADER)) ;

if (bitmap.bitmapfileheader.bfType != ((WORD) ('M'<<8)|'B'))// 判断是否是DIB对象
{
fileBmp.close();
MessageBox(NULL,
"不是0x4D42-BMP", "XinXin's WinMain", MB_OK | MB_ICONINFORMATION);
return NULL;// 如果不是则返回NULL。
}

numQuad
=0;
if (bitmap.bitmapinfoheader.biBitCount<24)
numQuad
=1<<bitmap.bitmapinfoheader.biBitCount;


fileBmp.read( (
char*)&bitmap.bitmapinfoheader, sizeof(BITMAPINFOHEADER));
Info
= (BITMAPINFO*)HeapAlloc(GetProcessHeap(),0,sizeof(BITMAPINFOHEADER) + 24*sizeof(RGBQUAD));
memcpy(Info,
&bitmap.bitmapinfoheader,sizeof(bitmap.bitmapinfoheader));

quad
=(RGBQUAD*)(BYTE*)Info+sizeof(BITMAPINFOHEADER);
fileBmp.read ((
char*)quad,sizeof(RGBQUAD)*numQuad);


bitmap.bitmapinfoheader .biSizeImage
=bitmap.bitmapfileheader.bfSize -bitmap .bitmapfileheader.bfOffBits;
lpBuf
=(BYTE*)HeapAlloc(GetProcessHeap(),0,bitmap.bitmapinfoheader .biSizeImage);

fileBmp.read ((
char*)lpBuf,bitmap.bitmapinfoheader .biSizeImage);





// BmpBit = bitmap.bitmapinfoheader.biBitCount;
//
//
// int BmpDataSize = 0;
//
// if(bitmap.bitmapinfoheader.biSizeImage > 0)
// BmpDataSize = bitmap.bitmapinfoheader.biSizeImage;
// else
// BmpDataSize = bitmap.bitmapinfoheader.biWidth * bitmap.bitmapinfoheader.biBitCount * bitmap.bitmapinfoheader.biHeight;
//
//
//
// fileBmp.seekg((BmpDataSize)*(-1), std::ios::end);
// bitmap.Buffer = new UCHAR[BmpDataSize];
// memset(bitmap.Buffer,1,BmpDataSize);
//
//
//int dataline;
//
// if(bitmap.bitmapinfoheader.biHeight >= 0)
// {
// IMAGE_Width = bitmap.bitmapinfoheader.biWidth;
// IMAGE_Height = bitmap.bitmapinfoheader.biHeight;
//
// //biHeight >= 0, 图像数据上下倒置(如图片左上角的像素颜色值在图像数据的左下角),因此翻转图像
// UCHAR *temp;
// temp = new UCHAR[BmpDataSize];
// memcpy(temp, bitmap.Buffer, BmpDataSize);
//
// // Windows规定一个扫描行所占的字节数必须是4的倍数(即以long为单位),不足的以0填充
// dataline=(IMAGE_Width * bitmap.bitmapinfoheader.biBitCount+31)/32*4;
// //int del;
// //int dataline = bitmap->bitmapinfoheader.biWidth * bitmap->bitmapinfoheader.biBitCount /8;
// //if( (del = dataline%4) != 0 )dataline += 4 - del;
//
// //翻转
// for(int i = 0; i < IMAGE_Height; i++)
// memcpy(&bitmap.Buffer[(IMAGE_Height-1 -i)*(long)dataline], &temp[i*(long)dataline], dataline);//memcpy单位:字节,扫描线必须为4BYTES倍数
//
// delete []temp;
// }
// else
// {
// IMAGE_Width = bitmap.bitmapinfoheader.biWidth;
// IMAGE_Height = -bitmap.bitmapinfoheader.biHeight;
// }
//
//
//
//
// //BmpDC = CreateCompatibleDC(DrawDeviceHandler);
// // if(bitmap.Buffer != NULL)bitmap.Buffer = NULL;
// // mBMP = CreateDIBSection(dc, (BITMAPINFO *)&bitmap.bitmapinfoheader,
// // DIB_RGB_COLORS, (void **)&bitmap.Buffer, NULL, 0);
// fileBmp.read( (char*)bitmap.Buffer, bitmap.bitmapinfoheader.biSizeImage );
//
//
// ::SetDIBitsToDevice (dc,0,0,0,0,0,0,dataline,dataline,bitmap.Buffer,(BITMAPINFO*)&(bitmap.bitmapinfoheader) ,DIB_RGB_COLORS);
fileBmp.close();//关闭ifstream对像
return TRUE;
}


void CDibBMP::ShowBmp(HDC hdc,int oriXpos, int OriYpos, int width, int height)
{
long bitsAlloc = 32 * 480;
long headerSize = sizeof(BITMAPINFOHEADER); if ((hGlobal = ::GlobalAlloc(GMEM_MOVEABLE, bitsAlloc + headerSize)) == 0)
// return FALSE;
Info = (BITMAPINFO *)::GlobalLock(hGlobal);
//Bits = (void *)((char *)Info + headerSize);

//Info->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
//Info->bmiHeader.biWidth = width;
//Info->bmiHeader.biHeight = height;
//Info->bmiHeader.biBitCount = (unsigned short)24;
//Info->bmiHeader.biPlanes = 1;
//Info->bmiHeader.biXPelsPerMeter = 0;
//Info->bmiHeader.biYPelsPerMeter = 0;
//Info->bmiHeader.biClrUsed = 0;
//Info->bmiHeader.biClrImportant = 0;
//Info->bmiHeader.biCompression = BI_RGB;
//Info->bmiHeader.biSizeImage = bitsAlloc;

int n = 119 * ((640 * 480 + 31) / 32)* 4 + (24 + 7) / 8;
SetDIBitsToDevice(hdc,
0, 0,
640, 480,
0, 0, 0, 640,
(
char*)n,
Info,
DIB_RGB_COLORS);


//ViewImage.GetBits() = (char *)(640 -480 - 1) * (640 * 480 + 31) / 32) * 4; + (24 + 7) / 8);
//ViewImage.GetInfo(),

//::SetDIBitsToDevice(dc, 0, 0,
// ViewImage.Width(), ViewImage.Height(),
// 0, 0, 0, ViewImage.Height(),
// ViewImage.GetBits(),
// ViewImage.GetInfo(),
// DIB_RGB_COLORS);

}


void CDibBMP::Show(char *filename)
{
BITMAPFILEHEADER m_bmfh;
//BMP文件头变量
BITMAPINFOHEADER m_bmih;//BMP文件信息变量

std::ifstream fileBmp;
//(filename);

char *m_pImgData=NULL;
/* CFile file;
CFileDialog dlg(TRUE);
if(dlg.DoModal()==IDCANCEL)
return;

file.Open(dlg.GetPathName(),CFile::modeRead);
file.Read(&m_bmfh,sizeof(m_bmfh));
file.Read(&m_bmih,sizeof(m_bmih));
*/

fileBmp.read ((
char*)&m_bmfh,sizeof(m_bmfh)) ;
fileBmp.read ((
char*)&m_bmfh,sizeof(m_bmfh)) ;

m_pImgData
=new char[m_bmih.biSizeImage];
fileBmp.seekg(m_bmfh.bfOffBits,
0);
fileBmp.read (m_pImgData,m_bmih.biSizeImage);
fileBmp.close ();
// CClientDC dc(this);
//SetDIBitsToDevice(dc.m_hDC,
//0,0,
//m_bmih.biWidth,m_bmih.biHeight,
//0,0,
//0,m_bmih.biHeight,
//m_pImgData,
//(BITMAPINFO*)&m_bmih,
//DIB_RGB_COLORS);
delete m_pImgData;
}


BOOL CDibBMP::Show1(HWND hWnd,
char *filename)
{
// HFILE hf;
HANDLE hf;

LPBITMAPINFOHEADER lpImgData;


LPSTR lpPtr;

LPBITMAPINFOHEADER lpTempImgData;

LPSTR lpNewPtr;


LOGPALETTE
*pPal;

LPRGBQUAD lpRGB;

HPALETTE hPrevPalette;

HDC hDc;

HLOCAL hPal;

DWORD ImgSize;

DWORD i;
char temp[100];
DWORD bytesread;

//BITMAPFILEHEADER bf,bfNew;
//BITMAPINFOHEADER bi;

std::ifstream fileBmp;
//(filename);


fileBmp.open(filename,std::ios::binary);

if (!fileBmp)
{
MessageBox(NULL,
"无法打开喔", "XinXin's WinMain", MB_OK | MB_ICONINFORMATION);
fileBmp.close();
return false;
}



fileBmp.read ((
char*)&bf,sizeof(BITMAPFILEHEADER)) ;
fileBmp.read( (
char*)&bi, sizeof(BITMAPINFOHEADER));
if (bf.bfType != ((WORD) ('M'<<8)|'B'))// 判断是否是DIB对象
{
fileBmp.close();
MessageBox(NULL,
"不是0x4D42-BMP", "XinXin's WinMain", MB_OK | MB_ICONINFORMATION);
return NULL;// 如果不是则返回NULL。
}
//hf = file.GetFileTitle(0);
// hf = CreateFile(BmpFileName,GENERIC_READ|GENERIC_WRITE,FILE_SHARE_READ,NULL,
// OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);

//if((hf=_lopen(BmpFileName,OF_READ))==HFILE_ERROR)
//if( hf == NULL){

// MessageBox(hWnd,"file can not open","Error Message",MB_OK|MB_ICONEXCLAMATION);

// return FALSE;

//}

//ReadFile(hf,&bf,sizeof(BITMAPFILEHEADER),&bytesread,NULL);
//ReadFile(hf,&bi,sizeof(BITMAPINFOHEADER),&bytesread,NULL);

memcpy(
&bfNew,&bf,sizeof(BITMAPFILEHEADER));
// _lread(hf,(LPSTR)&bf,sizeof(BITMAPFILEHEADER));

// _lread(hf,(LPSTR)&bi,sizeof(BITMAPINFOHEADER));

ImgWidth
=bi.biWidth;

ImgHeight
=bi.biHeight;

LineBytes
=(DWORD)WIDTHBYTES(bi.biWidth*bi.biBitCount);

ImgSize
=(DWORD)LineBytes*bi.biHeight;
switch(bi.biBitCount){

case 1:

NumColors
=2;
// SetWindowText(hWnd,"2");
// _sleep(1000);
break;

case 4:

NumColors
=16;
// SetWindowText(hWnd,"4");
// _sleep(1000);
break;

case 8:

NumColors
=256;
// SetWindowText(hWnd,"8");
// _sleep(1000);
break;

case 24:

NumColors
=0;//真彩色不用调色板
// SetWindowText(hWnd,"24");
// _sleep(1000);
break;

default:

MessageBox(hWnd,
"Invalid color numbers!","Error Message",MB_OK|MB_ICONEXCLAMATION);

// _lclose(hf);
CloseHandle(hf);

return FALSE;

}

if(bf.bfOffBits!=(DWORD)(NumColors*sizeof(RGBQUAD)+sizeof(BITMAPFILEHEADER)

+sizeof(BITMAPINFOHEADER)))

{
//偏移有误:即颜色数有误

MessageBox(hWnd,
"Invalid color numbers!","Error Message" ,MB_OK|

MB_ICONEXCLAMATION);

// _lclose(hf);
CloseHandle(hf);

return FALSE;

}

bf.bfSize
=sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER)+NumColors*sizeof(RGBQUAD)+ImgSize;

if((hImgData=GlobalAlloc(GHND,(DWORD)(sizeof(BITMAPINFOHEADER)+

NumColors
*sizeof(RGBQUAD)+ImgSize)))==NULL)

{
//分配内存

MessageBox(hWnd,
"Error alloc memory!","ErrorMessage",MB_OK|

MB_ICONEXCLAMATION);

// _lclose(hf);
CloseHandle(hf);

return FALSE;

}

if((hTempImgData=GlobalAlloc(GHND,(DWORD)(sizeof(BITMAPINFOHEADER)+

NumColors
*sizeof(RGBQUAD)+ImgSize)))==NULL)

{
//分配内存

MessageBox(hWnd,
"Error alloc memory!","ErrorMessage",MB_OK|

MB_ICONEXCLAMATION);

// _lclose(hf);
if(hf != NULL)
CloseHandle(hf);

return FALSE;

}

lpImgData
=(LPBITMAPINFOHEADER)GlobalLock(hImgData);

lpTempImgData
= (LPBITMAPINFOHEADER)GlobalLock(hTempImgData);


fileBmp.seekg(
sizeof(BITMAPFILEHEADER), std::ios::beg);
fileBmp.read ((
char*)lpImgData,sizeof(BITMAPINFOHEADER) + NumColors*sizeof(RGBQUAD) + ImgSize);

HDC dc;
dc
= GetDC(hWnd);
SetDIBitsToDevice(dc,
0,0,640,480,0,0,640,480,(void*)4220,(BITMAPINFO*)lpImgData,DIB_RGB_COLORS);

//SetFilePointer(hf,sizeof(BITMAPFILEHEADER),NULL,FILE_BEGIN);
//fileBmp.seekg (
//ReadFile(hf,(char *)lpImgData,sizeof(BITMAPINFOHEADER) + NumColors*sizeof(RGBQUAD) + ImgSize,&bytesread,NULL);

//CloseHandle(hf);


//lpPtr = (char*)lpImgData;
//lpNewPtr = (char*)lpTempImgData;

//memcpy(lpNewPtr,lpPtr,bf.bfSize - sizeof(BITMAPFILEHEADER));

// if(NumColors!=0)//用到了调色板

//{

// hPal=LocalAlloc(LHND,sizeof(LOGPALETTE) + NumColors* sizeof(PALETTEENTRY));

// pPal =(LOGPALETTE *)LocalLock(hPal);

// pPal->palNumEntries =(WORD) NumColors;

// pPal->palVersion = 0x300;
// //移到调色板的开始处
// lpRGB = (LPRGBQUAD)((LPSTR)lpImgData + (DWORD)sizeof(BITMAPINFOHEADER));

// for (i = 0; i < NumColors; i++) {

// pPal->palPalEntry[i].peRed=lpRGB->rgbRed;

// pPal->palPalEntry[i].peGreen=lpRGB->rgbGreen;

// pPal->palPalEntry[i].peBlue=lpRGB->rgbBlue;

// pPal->palPalEntry[i].peFlags=(BYTE)0;

// lpRGB++;

// }

// hPalette=CreatePalette(pPal);//创建逻辑调色板

// LocalUnlock(hPal);

// LocalFree(hPal);

//}

//hDc=GetDC(hWnd);

//if(hPalette){

// hPrevPalette=SelectPalette(hDc,hPalette,FALSE);

// RealizePalette(hDc);

//}
////如果有调色板先将调色板调入内存中
//hBitmap=CreateDIBitmap(hDc, (LPBITMAPINFOHEADER)lpImgData, (LONG)CBM_INIT,

// (LPSTR)lpImgData+sizeof(BITMAPINFOHEADER) +NumColors*sizeof(RGBQUAD),

// (LPBITMAPINFO)lpImgData, DIB_RGB_COLORS);
////再把原调色板调入内存
//if(hPalette && hPrevPalette){

// SelectPalette(hDc,hPrevPalette,FALSE);

// RealizePalette(hDc);

//}



//ReleaseDC(hWnd,hDc);

GlobalUnlock(hTempImgData);

GlobalUnlock(hImgData);

return TRUE;


}