CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 3 of 3
  1. #1
    Join Date
    May 2012
    Posts
    22

    Raster operations. Exchange between windows.

    Hi!
    In my MFC doc/view programm I have two classes with their windows. The first one is view, the second is a dialog. The view is constantly displaying image form camera. I want the second window, dialog, to show the image that has been in view when some event happens, in picture control actually.

    I know how to show picture from program resources or from disk, and my code does it fine.
    And I have some functions in view. Some of them get picture from view and can save it at disk.

    But when I try to pass somehow image from view to dialog, even if no errors occure - nothing happens, nothing is drawn. I tried to pass pointer of CBitmap of actual DC of the view. I tried to pass BITMAP structures. By the way every part of this structures like some information goes fine, but no image itself. It seems to me there are some problems with "passing" pixelsbits.

    so, I'll be glad to any help: ideas, examples, concepts)
    Thanks in advance!

  2. #2
    VictorN's Avatar
    VictorN is offline Super Moderator Power Poster
    Join Date
    Jan 2003
    Location
    Hanover Germany
    Posts
    20,430

    Re: Raster operations. Exchange between windows.

    Quote Originally Posted by 330xi View Post
    ...
    But when I try to pass somehow image from view to dialog, even if no errors occure - nothing happens, nothing is drawn. I tried to pass pointer of CBitmap of actual DC of the view. I tried to pass BITMAP structures. By the way every part of this structures like some information goes fine, but no image itself. It seems to me there are some problems with "passing" pixelsbits.
    How did you implemented it? Show your code.

    PS: don't forget to use Code tags around code snippets!
    Victor Nijegorodov

  3. #3
    Join Date
    May 2012
    Posts
    22

    Re: Raster operations. Exchange between windows.

    One of my variants was like this.

    The view class has a variable of some custom class with many methods of processing image - RXPicture. With next methods I save picture to disk, and one of them return HANDLE.

    Code:
    HANDLE RXPicture::pDCtoDIB24() 
    {
    	CBitmap * bitmap;
    	bitmap = pDC->GetCurrentBitmap();
    	BITMAP			bm;
    	BITMAPINFOHEADER	bi;
    	LPBITMAPINFOHEADER 	lpbi;
    	DWORD			dwLen;
    	HANDLE			hDIB;
    	HANDLE			handle;
    	HDC 			hDC;	
    
    	ASSERT( bitmap->GetSafeHandle() );	
    	bitmap->GetObject(sizeof(bm),(LPSTR)&bm);
    	
    	bi.biSize		= sizeof(BITMAPINFOHEADER);
    	bi.biWidth		= bm.bmWidth;
    	bi.biHeight 		= bm.bmHeight;
    	bi.biPlanes 		= 1;
    	bi.biBitCount		= bm.bmPlanes * bm.bmBitsPixel;
    	bi.biCompression	= BI_RGB;
    	bi.biSizeImage		= 0;
    	bi.biXPelsPerMeter	= 0;
    	bi.biYPelsPerMeter	= 0;
    	bi.biClrUsed		= 0;
    	bi.biClrImportant	= 0;
    	
    	dwLen  = bi.biSize;
    	
    	hDC = GetDC(NULL);	
    	hDIB = GlobalAlloc(GMEM_FIXED,dwLen);
    
    	if (!hDIB){		
    		ReleaseDC(NULL,hDC);
    		bitmap->DeleteObject();		
    		return NULL;
    	}
    
    	lpbi = (LPBITMAPINFOHEADER)hDIB;
    
    	*lpbi = bi;
    
    	GetDIBits(hDC, (HBITMAP)bitmap->GetSafeHandle(), 0L, (DWORD)bi.biHeight,
    			(LPBYTE)NULL, (LPBITMAPINFO)lpbi, (DWORD)DIB_RGB_COLORS);
    
    	bi = *lpbi;
    
    	if (bi.biSizeImage == 0){
    		bi.biSizeImage = ((((bi.biWidth * bi.biBitCount) + 31) & ~31) / 8) 
    						* bi.biHeight;
    	}
    	
    	dwLen += bi.biSizeImage;
    	if (handle = GlobalReAlloc(hDIB, dwLen, GMEM_MOVEABLE))
    		hDIB = handle;
    	else{
    		GlobalFree(hDIB);		
    		ReleaseDC(NULL,hDC);
    		bitmap->DeleteObject();		
    		return NULL;
    	}
    	
    	lpbi = (LPBITMAPINFOHEADER)hDIB;
    
    	BOOL bGotBits = GetDIBits( hDC, (HBITMAP)bitmap->GetSafeHandle(),
    				0L,				// Start scan line
    				(DWORD)bi.biHeight,		// # of scan lines
    				(LPBYTE)lpbi 			// address for bitmap bits
    				+ bi.biSize,
    				(LPBITMAPINFO)lpbi,		// address of bitmapinfo
    				(DWORD)DIB_RGB_COLORS);		// Use RGB for color table
    
    	if( !bGotBits )
    	{
    		GlobalFree(hDIB);		
    		ReleaseDC(NULL,hDC);
    		bitmap->DeleteObject();		
    		return NULL;
    	}	
    	ReleaseDC(NULL,hDC);
    	bitmap->DeleteObject();	
    	return hDIB;
    }
    and the method that writes to disk that uses this handle

    Code:
    BOOL RXPicture::WriteDIB( LPTSTR szFile, HANDLE hDIB, BOOL havepalette, CWnd * wnd)
    {
    	BITMAPFILEHEADER	hdr;
    	LPBITMAPINFOHEADER	lpbi;
    	
    	if (!hDIB)
    		return FALSE;
    
    	CFile file;
    	if( !file.Open( szFile, CFile::modeWrite|CFile::modeCreate) )
    	{
    		wnd->MessageBox ((CString("Could't create or write ") + CString(szFile)),
    	            "Can't write image to file", MB_OK|MB_ICONERROR);
    		return FALSE;
    	}
    
    	lpbi = (LPBITMAPINFOHEADER)hDIB;
    	int nColors = 1 << lpbi->biBitCount;
    
    	hdr.bfType		= ((WORD) ('M' << 8) | 'B');	// is always "BM"
    	hdr.bfSize		= GlobalSize (hDIB) + sizeof( hdr );
    	hdr.bfReserved1 	= 0;
    	hdr.bfReserved2 	= 0;
    	if (havepalette)
    		hdr.bfOffBits		= (DWORD) (sizeof( hdr ) + lpbi->biSize +
    							nColors * sizeof(RGBQUAD));
    	else hdr.bfOffBits		= (DWORD) (sizeof( hdr ) + lpbi->biSize);
    
    	file.Write( &hdr, sizeof(hdr) );
    	file.Write( lpbi, GlobalSize(hDIB) );
    
    	return TRUE;
    }
    they work together fine.

    In dialoge class I have a class connected with picture control. It draws pictures from disk by:

    Code:
    void myStaric::OnPaint()
    {		
    	CClientDC dc(this);	
    	GetClientRect(&rc);	 	
    
    switch (ext)
    {
    case 2:
    	m_jpgBack.Destroy();
    	m_jpgBack.Load(name);	
    	m_jpgBack.StretchBlt(dc,0,0,rc.right,rc.bottom,SRCCOPY);
    	break;
    case 1:
    	dcMem.DeleteDC();
    	hBmp = NULL;
    	m_bmpBack.DeleteObject();
    	hBmp = LoadImage(NULL,name,IMAGE_BITMAP,0,0,LR_LOADFROMFILE);	
    	GetObject ( hBmp, sizeof(bm), &bm );	
    	m_bmpBack.Attach(hBmp);		
    	dcMem.CreateCompatibleDC(&dc);
    	hbmpOld = (HBITMAP)dcMem.SelectObject(m_bmpBack);	
    	dc.StretchBlt(rc.left, rc.top, rc.right, rc.bottom,&dcMem, 0, 0, (int)bm.bmWidth, (int)bm.bmHeight, SRCCOPY);		
    	break;
    case 3:
    	dcMem.DeleteDC();
    	hBmp = NULL;
    	GlobalFree(hBmp);
    	m_bmpBack.DeleteObject();
    	hBmp = sp->pDCtoDIB24();
    	GetObject ( hBmp, sizeof(bm), &bm );	
    	m_bmpBack.Attach(hBmp);		
    	dcMem.CreateCompatibleDC(&dc);
    	hbmpOld = (HBITMAP)dcMem.SelectObject(m_bmpBack);	
    	dc.StretchBlt(rc.left, rc.top, rc.right, rc.bottom,&dcMem, 0, 0, (int)bm.bmWidth, (int)bm.bmHeight, SRCCOPY);		
    	break;
    }			
    }
    very well. So I tried to pass a pointer to RXPicture variable from the view, and choice variable as "3" and tried to use my working method pDCtoDIB24() that returns handle. I followed code line by line so "switch 3" works, but nothing appears in picture control.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured