Updated by Andrey Kamaev about 13 years ago

Hi everybody here,
I was developing one DLL involving in image processing for some Win32 applications. It was quite hard trying to display my images directly to a desired window or control. And I found a lot of people having the same troubles. Finally I decided to investigate a little bit through de Highgui code, and decided to write a modification for @cvShowImage@ cvShowImage based on the basic one, but passing to the function the @HWND@ HWND handler of the control you want to display your yor images rescaled. If it's for your interest, here is the code:

<pre><code class="cpp"> @
CV_IMPL void cvShowImage2( HWND w_hWnd, const CvArr* arr )
{
CV_FUNCNAME( "cvShowImage2" );

__BEGIN__;

SIZE size = { 0, 0 };
int channels = 0;
void* dst_ptr = 0;
const int channels0 = 3;
int origin = 0;
CvMat stub, dst, *image;
bool changed_size = false;
BITMAPINFO* tempbinfo = NULL;
HDC hdc = NULL;

// Ensure we have valid image & HWND
if( !arr )
return;
if( !w_hWnd )
return;

hdc = ::GetDC(w_hWnd);

if( CV_IS_IMAGE_HDR( arr ))
origin = ((IplImage*)arr)->origin;

CV_CALL( image = cvGetMat( arr, &stub ));

if ( hdc )
{
//GetBitmapData
BITMAP bmp;
GdiFlush();
HGDIOBJ h = GetCurrentObject( hdc, OBJ_BITMAP );

if (h == NULL)
return;
if (GetObject(h, sizeof(bmp), &bmp) == 0) //GetObject(): returns size of object, 0 if error
return;

channels = bmp.bmBitsPixel/8;
dst_ptr = bmp.bmBits;
}

if( size.cx != image->width || size.cy != image->height || channels != channels0)
{
changed_size = true;

uchar buffer[sizeof(BITMAPINFO) + 255*sizeof(RGBQUAD)];
BITMAPINFO* binfo = (BITMAPINFO*)buffer;

BOOL bDeleteObj = DeleteObject(GetCurrentObject( hdc, OBJ_BITMAP));
assert( FALSE != bDeleteObj );

size.cx = image->width;
size.cy = image->height;
channels = channels0;

FillBitmapInfo( binfo, size.cx, size.cy, channels*8, 1 );
tempbinfo = binfo;

HGDIOBJ tempImage = SelectObject( hdc, CreateDIBSection( hdc, binfo, DIB_RGB_COLORS, &dst_ptr, 0, 0));
}

cvInitMatHeader( &dst, size.cy, size.cx, CV_8UC3,dst_ptr, ( size.cx * channels + 3 ) & -4 );
cvConvertImage( image, &dst, origin == 0 ? CV_CVTIMG_FLIP : 0 );

// Image stretching to fit the window
RECT rect;
GetClientRect(w_hWnd, &rect);
int bSuccess = StretchDIBits( hdc,0, 0, rect.right, rect.bottom, 0, 0, image->width, image->height,
dst_ptr, tempbinfo, DIB_RGB_COLORS, SRCCOPY );

InvalidateRect(w_hWnd, 0, 0);

__END__;
}
</code></pre>


@

Back