在寫mfc程序時如果用到opencv,肯定會用到這兩個之間的轉化。在網上找了好多,幾乎都一樣,我的情況稍微特殊,找了半天也沒合適的,MD,一氣之下,自己跟蹤進去CvvImage::DrawToHDC,
void IplImage2CBitmap(Iplimage* ipg_src)
{
CBitmap* m_pBitmap=new CBitmap;
if (ipg_src->depth==IPL_DEPTH_8U)
{
uchar buffer[sizeof(BITMAPINFOHEADER) + 1024];
BITMAPINFO* bmi = (BITMAPINFO*)buffer;
int bmp_w = ipg_src->width, bmp_h = ipg_src->height;
//FillBitmapInfo( bmi, bmp_w, bmp_h, Bpp(), pImage->origin );
int width=bmp_w;
int height=bmp_h;
int bpp=ipg_src ? (ipg_src->depth & 255)*ipg_src->nChannels : 0;
int origin=ipg_src->origin;
HBITMAP hBitmap;
BITMAPINFOHEADER* bmih = &(bmi->bmiHeader);
memset( bmih, 0, sizeof(*bmih));
bmih->biSize = sizeof(BITMAPINFOHEADER);
bmih->biWidth = width;
bmih->biHeight = origin ? abs(height) : -abs(height);
bmih->biPlanes = 1;
bmih->biBitCount = (unsigned short)bpp;
bmih->biCompression = BI_RGB;
if( bpp == 8 )
{
RGBQUAD* palette = bmi->bmiColors;
int i;
for( i = 0; i < 256; i++ )
{
palette[i].rgbBlue = palette[i].rgbGreen = palette[i].rgbRed = (BYTE)i;
palette[i].rgbReserved = 0;
}
}
}
以上代碼改裝自opencv。到了這個時候就可以
HBITMAP hbmp=CreateDIBitmap(pdc->GetSafeHdc(),bmih,CBM_INIT,ipg_src->imageData,bmi,DIB_RGB_COLORS);
這裡千萬萬千要注意的是第一個參數,一定是要將圖片顯示的設備的句柄,null表示內存。
最後:m_pBitmap->Attach(hBitmap);完事大吉,當然如果加一個
if(m_pBitmap->m_hObject!=NULL)
{
m_pBitmap->Detach();
}更好。
opencv裡面是用的是 ::StretchDIBits(設備句柄,……),如果用pdc->StretchBlt()的話是無法顯示的,至於為什麼,由於水平有限!
網上的只是參考,一定要有自己的思考。寫一些自己理解的轉化,雖然也是抄的,但加了自己的東西。
CBitmap m_bitmap;
HBITMAP h_bmp;
h_bmp=m_bitmap.m_hObject; CBitmap ==>HBITMAP
m_bitmap=CBitmap::FromHandle(h_bmp); HBITMAP==>CBitmap
我曾試著把IplImage直接轉化為CBitmap就是用網上的這段代碼,可在顯示的時候卻沒成功,也不知道轉化是否成功。下面是代碼
IplImage ->CBitmap , Cbitmap ->IplImage
CDC *pdc = this ->GetDC() ;
IplImage *img = cvCreateImage( cvSize( 100,100 ) , 8 , 3 );
CBitmap m_bitmap ;
m_bitmap.CreateCompatibleBitmap( pdc , 100 ,100 ) ;
CDC memdc ;
memdc.CreateCompatibleDC( pdc ) ;
CBitmap *pold = memdc .SelectObject( &m_bitmap) ;
CvvImage cvimg ;
Rect rect(0 , 0 , 100,100 ) ;
cvimg.CopyOf( img , -1 ) ;
cvimg.DrawToHDC( memdc.m_hDC , &rect ) ;
ReleaseDC( pdc) ;
IplImage *tempimg = cvCloneImage( img ) ;
m_bitmap.GetBitmapBits( img ->widthStep * img ->height , img ->imageData) ;
我曾試著把m_bitmap顯示出來以驗證是否轉化成功,用了這樣的函數
memdc.StretchBlt(0,0,rect.Width(),rect.Height(),&memdc,0,0,w,h,SRCCOPY);
可是沒有奏效!至今還不明!