天天看點

儲存HBITMAP圖像到檔案中

BOOL CShape::SaveBmp(HBITMAP hBitmap, const char *FileName)      

{      

 HDC     hDC;      

 //目前分辨率下每象素所占位元組數      

 int     iBits;      

 //位圖中每象素所占位元組數      

 WORD     wBitCount;      

 //定義調色闆大小,     位圖中像素位元組大小     ,位圖檔案大小     ,     寫入檔案位元組數          

 DWORD     dwPaletteSize=0,     dwBmBitsSize=0,     dwDIBSize=0,     dwWritten=0;          

 //位圖屬性結構          

 BITMAP     Bitmap;              

 //位圖檔案頭結構      

 BITMAPFILEHEADER     bmfHdr;              

 //位圖資訊頭結構          

 BITMAPINFOHEADER     bi;              

 //指向位圖資訊頭結構              

 LPBITMAPINFOHEADER     lpbi;              

 //定義檔案,配置設定記憶體句柄,調色闆句柄          

 HANDLE     fh,     hDib,     hPal,hOldPal=NULL;          

 //計算位圖檔案每個像素所占位元組數          

 hDC     =     CreateDC(_T("DISPLAY"),     NULL,     NULL,     NULL);      

 iBits     =     GetDeviceCaps(hDC,     BITSPIXEL) *GetDeviceCaps(hDC,     PLANES);          

 DeleteDC(hDC);          

 if (iBits <= 1)

 {

  wBitCount = 1;

 }

 else if (iBits <= 4)  

 {

  wBitCount = 4;        

 }

 else if (iBits <= 8) 

 {

  wBitCount = 8; 

 }

 else

 {

  wBitCount = 24;

 }

 GetObject(hBitmap, sizeof(Bitmap), (LPSTR)&Bitmap);      

 bi.biSize = sizeof(BITMAPINFOHEADER);      

 bi.biWidth =  Bitmap.bmWidth;      

 bi.biHeight = Bitmap.bmHeight;      

 bi.biPlanes = 1;      

 bi.biBitCount = wBitCount;      

 bi.biCompression =  BI_RGB;      

 bi.biSizeImage  =  0;      

 bi.biXPelsPerMeter = 0;      

 bi.biYPelsPerMeter   =   0;      

 bi.biClrImportant = 0;      

 bi.biClrUsed   = 0;      

 dwBmBitsSize  = ((Bitmap.bmWidth     *     wBitCount     +     31)     /     32)     *     4     *     Bitmap.bmHeight;      

 //為位圖内容配置設定記憶體          

 hDib     =     GlobalAlloc(GHND,dwBmBitsSize     +     dwPaletteSize     +     sizeof(BITMAPINFOHEADER));          

 lpbi     =     (LPBITMAPINFOHEADER)GlobalLock(hDib);          

 *lpbi     =     bi;          

 //     處理調色闆              

 hPal     =     GetStockObject(DEFAULT_PALETTE);          

 if     (hPal)          

 {          

  hDC     =     ::GetDC(NULL);          

  hOldPal     =     ::SelectPalette(hDC,     (HPALETTE)hPal,     FALSE);          

  RealizePalette(hDC);          

 }      

 //     擷取該調色闆下新的像素值          

 GetDIBits(hDC,

  hBitmap,

  0,  

  (UINT)Bitmap.bmHeight,

  (LPSTR)lpbi+sizeof(BITMAPINFOHEADER)+dwPaletteSize,

  (BITMAPINFO *)lpbi,

  DIB_RGB_COLORS);          

 //恢複調色闆              

 if (hOldPal)          

 {          

  ::SelectPalette(hDC,     (HPALETTE)hOldPal,     TRUE);          

  RealizePalette(hDC);          

  ::ReleaseDC(NULL,     hDC);          

 }          

 //建立位圖檔案              

 fh  =  CreateFile((LPCWSTR)FileName,

           GENERIC_WRITE,

     0,    

     NULL,   

     CREATE_ALWAYS,          

     FILE_ATTRIBUTE_NORMAL,

     NULL);        

 if     (fh == INVALID_HANDLE_VALUE)

 {

  return     FALSE; 

 }

 //     設定位圖檔案頭          

 bmfHdr.bfType     =     0x4D42;     //     "BM"          

 dwDIBSize     =     sizeof(BITMAPFILEHEADER)     +     sizeof(BITMAPINFOHEADER)     +     dwPaletteSize     +     dwBmBitsSize;              

 bmfHdr.bfSize     =     dwDIBSize;          

 bmfHdr.bfReserved1     =     0;          

 bmfHdr.bfReserved2     =     0;          

 bmfHdr.bfOffBits     =     (DWORD)sizeof(BITMAPFILEHEADER)     +     (DWORD)sizeof(BITMAPINFOHEADER)     +     dwPaletteSize;          

 //     寫入位圖檔案頭          

 WriteFile(fh,     (LPSTR)&bmfHdr,     sizeof(BITMAPFILEHEADER),     &dwWritten,     NULL);          

 //     寫入位圖檔案其餘内容          

 WriteFile(fh,     (LPSTR)lpbi,     dwDIBSize,     &dwWritten,     NULL);          

 //清除              

 GlobalUnlock(hDib);          

 GlobalFree(hDib);          

 CloseHandle(fh);          

 return     TRUE;      

}