本帖最后由 qf230zhj 于 2010-08-07 17:20:21 编辑

解决方案 »

  1.   

    SaveBitmapToFile(bitmap,(LPSTR)(LPCTSTR)str);
    是网上的标准公共代码
      

  2.   

    SaveBitmapToFile(bitmap,(LPSTR)(LPCTSTR)str.MakeReverse());//
      

  3.   

    楼主试试CXImage类,这个可以把buffer中的图像保存成图片的,你看看memmove(pBits,bm.bmBits,bm.bmWidthBytes*bm.bmHeight)之后,pBits里的图像是不是反的。有一个效率低一些的办法,再把图像反过来:
             DWORD dwRGB24BufLen = iWidth * iHeight * 3;
    BYTE *pTempBuf = new BYTE[dwRGB24BufLen];
    if(NULL == pTempBuf) 
    {
    return;
    }
    memset(pTempBuf, 0, dwRGB24BufLen * sizeof(BYTE)); DWORD dwLineData = (iWidth * 24) >> 3;
    for(DWORD dwLoop = 0; dwLoop < iHeight; dwLoop++)
    {
    memcpy(pTempBuf + dwLoop * dwLineData, pBits + dwRGB24BufLen - (dwLoop + 1) * dwLineData, dwLineData * sizeof(BYTE));
    }
    memcpy(pBits, pTempBuf, dwRGB24BufLen);
    delete[] pTempBuf;
    pTempBuf = NULL;
      

  4.   

    见4楼。
    原因:DDB的图素位是从上到下的,DIB的图素位是从下到上的。
    你把SaveBitmapToFile函数里的biHeight字段改称相反的值就行了。
      

  5.   

    DIB数据在内存中就是底朝上放的。
    你要是想自己控制缓冲区pBits中的数据,自己颠倒过来,可以这样:
    BYTE *buf=new BYTE[bm.bmWidthBytes*bm.bmHeight];
    for(int i=0; i<bm.bmHeight; i++)
    {
        memcpy(buf+i*bm.bmWidthBytes ,pBits+(bm.bmHeight-i-1)*bm.bmWidthBytes),bm.bmWidthBytes);
    }
      

  6.   

    int CDemoView::SaveDCToBitmap(CDC *pDC, LPRECT pRect, const char *pFileName)
    {
         int nRet;
         int w,h;
         if ( pDC == NULL )
         {
             return -1;
         }
         if ( pRect == NULL )
         {
             return -1;
         }
         if ( pFileName == NULL )
         {
             return -1;
         }
     
         w = pRect->right - pRect->left;
         h = pRect->bottom - pRect->top;
         CBitmap bm; 
         bm.CreateCompatibleBitmap(pDC,w,h); 
         CDC memdc; 
         memdc.CreateCompatibleDC(pDC); 
         CBitmap*pOld=memdc.SelectObject(&bm);
         memdc.BitBlt( 0, 0, w, h, pDC, pRect->left, pRect->top, SRCCOPY );
         BITMAP btm; 
         bm.GetBitmap(&btm); 
         DWORD size=btm.bmWidthBytes*btm.bmHeight; 
         LPSTR lpData=(LPSTR)::GlobalAlloc(GPTR,size); 
         ///////////////////////////////////////////// 
         BITMAPINFOHEADER bih; 
         bih.biBitCount=btm.bmBitsPixel; 
         bih.biClrImportant=0; 
         bih.biClrUsed=0; 
         bih.biCompression=0; 
         bih.biHeight=btm.bmHeight; 
         bih.biPlanes=1; 
         bih.biSize=sizeof(BITMAPINFOHEADER); 
         bih.biSizeImage=size; 
         bih.biWidth=btm.bmWidth; 
         bih.biXPelsPerMeter=0; 
         bih.biYPelsPerMeter=0; 
         GetDIBits(memdc,bm,0,bih.biHeight,lpData,(BITMAPINFO*)&bih,DIB_RGB_COLORS); 
         CString name; 
         name = pFileName;//保存文件名
         BITMAPFILEHEADER bfh; 
         bfh.bfReserved1=bfh.bfReserved2=0; 
         bfh.bfType=((WORD)('M'<< 8)|'B'); 
         bfh.bfSize=54+size; 
         bfh.bfOffBits=54; 
         CFile bf; 
         if(bf.Open(name,CFile::modeCreate|CFile::modeWrite))
         { 
             bf.WriteHuge(&bfh,sizeof(BITMAPFILEHEADER)); 
             bf.WriteHuge(&bih,sizeof(BITMAPINFOHEADER)); 
             bf.WriteHuge(lpData,size); 
             bf.Close(); 
             nRet = 0;
         }else
         {
           nRet = 1;
         }
         memdc.SelectObject( pOld );
         bm.DeleteObject( );
         memdc.DeleteDC( );
         ::GlobalFree(lpData); 
         return nRet;
    }改biheight是那一个,我两个分别改了无效!!!!!!!
      

  7.   

    bool CDemoView::SaveBitmapToFile(CBitmap *bitmap, LPSTR lpFileName)
    {
     HBITMAP   hBitmap;  
     HDC hDC; //设备描述表  
     int iBits; //当前显示分辨率下每个像素所占字节数  
     WORD                         wBitCount; //位图中每个像素所占字节数  
     DWORD                       dwPaletteSize=0, //定义调色板大小,   位图中像素字节大小   ,位图文件大小   ,   写入文件字节数  
      dwBmBitsSize,  
      dwDIBSize,   dwWritten;  
     BITMAP                     Bitmap; //位图属性结构  
     BITMAPFILEHEADER       bmfHdr; //位图文件头结构  
     BITMAPINFOHEADER       bi; //位图信息头结构    
     LPBITMAPINFOHEADER   lpbi; //指向位图信息头结构  
     HANDLE                     fh,   hDib,   hPal,hOldPal=NULL; //定义文件,分配内存句柄,调色板句柄    //计算位图文件每个像素所占字节数  
     hBitmap   =   (HBITMAP)*bitmap;  
     hDC   =   CreateDC("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   if   (iBits   <=   24)  
      wBitCount   =   24;  
     else if ( iBits <= 32 )
      wBitCount = 32;  //计算调色板大小  
     if   (wBitCount   <=   8)  
      dwPaletteSize   =   (1   <<     wBitCount)   *   sizeof(RGBQUAD);    //设置位图信息头结构  
     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.biClrUsed                   =   0;  
     bi.biClrImportant             =   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,  
      (LPBITMAPINFO   )  
      lpbi,   DIB_RGB_COLORS);    //恢复调色板        
     if   (hOldPal)  
     {  
      SelectPalette(hDC,   (HPALETTE)hOldPal,   TRUE);  
      RealizePalette(hDC);  
      ::ReleaseDC(NULL,   hDC);  
     }    //创建位图文件          
     fh   =   CreateFile(lpFileName,   GENERIC_WRITE,    
      0,   NULL,   CREATE_ALWAYS,  
      FILE_ATTRIBUTE_NORMAL   |   FILE_FLAG_SEQUENTIAL_SCAN,   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;  
    }楼上代码贴错了,这个是正确的请问改biheight是那一个,我两个分别改了无效!!!!!!!
      

  8.   

    //设置位图信息头结构  
    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.biClrUsed = 0;  
    bi.biClrImportant = 0;   注意:改称负的只能是用看图软件打开时不颠倒,里面的数据其实仍是倒得。
      

  9.   

    DIBSECTION跟bmp文件一样是倒置的。
    SetBitmapBits是用填充DDB位,但是你用DIB位区填充式什么意思呢?
    此处应该用memmove(bm.bmBits,pBits,bm.bmWidthBytes*bm.bmHeight);