Re: Grab a frame from cpature device
From: Ron Green (rgreen_at_titan.com)
Date: 03/31/04
- Next message: Ron Green: "Re: IAMPushSource for Capture Filter"
- Previous message: Feras: "Re: Should Pin 0 of the Overlay Mixer accept connections with RGBxx"
- Messages sorted by: [ date ] [ thread ]
Date: Tue, 30 Mar 2004 21:48:58 -0800
Andreas,
I think it is great that once a person gets a solution or some
help towards a solution, that it gets posted for the benefit of others
Many kudos!
--Ron Green
"Andreas Pfeuti" <andreas.pfeuti@switzerland.org> wrote in message
news:69717c26.0403182332.e2f76a3@posting.google.com...
> "The March Hare \(MVP\)" <phil@ndsm.maps> wrote in message
news:<#HMA9$2CEHA.2308@tk2msftngp13.phx.gbl>...
> > > Are there filters which can store a frame in a bmp-file? Or how could
> > > I solve my requirement?
> >
> > Look at the Grabber sample and the ISampleGrabber interface in the docs.
>
> Thanks for the hint.
>
> I post here my code-snipets. It shows how to grabb a frame triggered
> by the application and save the the frame into a bmp file.
> May somebody can use it.
>
>
> //first, add the Sample-Grabber-Filter to the graph
> //remark m_pGrabber is a member variable containing the
> ISampleGrabber-Interface
>
> // create a sample grabber
> //
> hr = CoCreateInstance(CLSID_SampleGrabber, NULL,
> CLSCTX_INPROC,IID_IBaseFilter, (void **)&pSampleGrabberFilter);
> if( FAILED(hr) )
> {
> Msg( TEXT("Could not create SampleGrabber (is qedit.dll
> registered?)"));
> return hr;
> }
> pSampleGrabberFilter->QueryInterface(IID_ISampleGrabber,
> (void**)&m_pGrabber);
> if( FAILED(hr) )
> {
> Msg( TEXT("Could not get ISampleGrabber - Interface"));
> return hr;
> }
>
>
> // force it to connect to video, 24 bit
> //
> AM_MEDIA_TYPE mt;
> ZeroMemory(&mt, sizeof(AM_MEDIA_TYPE));
> mt.majortype = MEDIATYPE_Video;
> mt.subtype = MEDIASUBTYPE_RGB24;
> hr = m_pGrabber->SetMediaType(&mt);
> if( FAILED( hr ) )
> {
> Msg( TEXT("Could not set media type"));
> return hr;
> }
>
> // add the grabber to the graph
> //
> hr = m_pGraph->AddFilter( pSampleGrabberFilter, L"Grabber" );
> if( FAILED( hr ) )
> {
> Msg( TEXT("Could not put sample grabber in graph"));
> return hr;
> }
>
> //set buffering mode
> hr = m_pGrabber->SetBufferSamples(TRUE);
>
> -------------------------------------------------------------------------
>
>
> //the GetStillImage - method is called by the application
> //this method uses the ISampleGrabber-Interface to grabb a frame an
> converts
> //the frame into a MFC CBitmap - object
>
> CBitmap* TVideoCapture::GetStillImage()
> {
> // The video header contains the bitmap information.
> // Copy it into a BITMAPINFO structure.
> BITMAPINFO bitmapInfo;
> ZeroMemory(&bitmapInfo, sizeof(bitmapInfo));
>
> VIDEOINFOHEADER* pVih = NULL;
> pVih = this->GetVideoInfoHeader();
> if (!pVih)
> {
> return NULL;
> }
>
> CopyMemory(&bitmapInfo.bmiHeader, &(pVih->bmiHeader),
> sizeof(BITMAPINFOHEADER));
>
> // Create a DIB from the bitmap header, and get a pointer to the
> buffer.
> char *buffer = NULL;
> HBITMAP hBitmap = ::CreateDIBSection(0, &bitmapInfo, DIB_RGB_COLORS,
> (void**)&buffer,
> NULL, 0);
>
> // Copy the image into the buffer.
> long size = 0;
>
> //determine the required size of the buffer
> HRESULT hr = m_pGrabber->GetCurrentBuffer(&size, NULL);
>
> //grab the frame
> hr = m_pGrabber->GetCurrentBuffer(&size,(long *)buffer);
> if (FAILED(hr))
> {
>
Msg(TEXT(TLanguageInterface::instance()->getString(EXTRACT_STILL_IMAGE_FAILE
D)));
> return NULL;
> }
>
> //make a CBitmap object and return it
> CBitmap* image = CBitmap::FromHandle(hBitmap);
>
> return image;
> }
>
> VIDEOINFOHEADER* TVideoCapture::GetVideoInfoHeader()
> {
> AM_MEDIA_TYPE mt;
> HRESULT hr = m_pGrabber->GetConnectedMediaType(&mt);
> if (FAILED(hr))
> {
> // Return error code.
> }
> // Examine the format block.
> VIDEOINFOHEADER *pVih = NULL;
> if ((mt.formattype == FORMAT_VideoInfo) &&
> (mt.cbFormat >= sizeof(VIDEOINFOHEADER)) &&
> (mt.pbFormat != NULL) )
> {
> pVih = (VIDEOINFOHEADER*)mt.pbFormat;
> }
> else
> {
> // Wrong format. Free the format block and return an error.
> MyFreeMediaType(mt);
>
Msg(TEXT(TLanguageInterface::instance()->getString(VIDEOINFOHEADER_WRONG_FOR
MAT)));
> }
> return pVih;
> }
>
> void TVideoCapture::MyFreeMediaType(AM_MEDIA_TYPE& mt)
> {
> if (mt.cbFormat != 0)
> {
> CoTaskMemFree((PVOID)mt.pbFormat);
> mt.cbFormat = 0;
> mt.pbFormat = NULL;
> }
> if (mt.pUnk != NULL)
> {
> // Unecessary because pUnk should not be used, but safest.
> mt.pUnk->Release();
> mt.pUnk = NULL;
> }
> }
>
> --------------------------------------------------------------------------
--
>
> //save the received CBitmap into a file
> //note: m_pImage is a pointer to the CBitmap-object received by
> GetStillImage()
>
> BOOL TStillImageDialog::saveImage()
> {
>
> BOOL success;
>
> CString fileName = "MyStillImage.bmp";
>
> HANDLE hf = CreateFile(
> fileName, GENERIC_WRITE, FILE_SHARE_READ, NULL,
> CREATE_ALWAYS, NULL, NULL );
>
> if( hf == INVALID_HANDLE_VALUE )
> return FALSE;
>
> // write out the file header
> //
>
> BITMAP bitmap;
> m_pImage->GetBitmap(&bitmap);
>
> long imageSize = bitmap.bmWidthBytes * bitmap.bmHeight;
>
> BITMAPFILEHEADER bfh;
> memset( &bfh, 0, sizeof( bfh ) );
> bfh.bfType = 'MB';
> bfh.bfSize = sizeof( bfh ) + imageSize + sizeof( BITMAPINFOHEADER );
> bfh.bfOffBits = sizeof( BITMAPINFOHEADER ) + sizeof(
> BITMAPFILEHEADER );
>
> DWORD dwWritten = 0;
> success = WriteFile( hf, &bfh, sizeof( bfh ), &dwWritten, NULL );
> if (!success)
> {
> CloseHandle( hf );
> return success;
> }
>
> // and the bitmap format
> //
> BITMAPINFOHEADER bih;
> memset( &bih, 0, sizeof( bih ) );
> bih.biSize = sizeof( bih );
> bih.biWidth = bitmap.bmWidth;
> bih.biHeight = bitmap.bmHeight;
> bih.biPlanes = bitmap.bmPlanes;
> bih.biSizeImage = imageSize;
> bih.biBitCount = bitmap.bmBitsPixel;
>
>
> dwWritten = 0;
> success = WriteFile( hf, &bih, sizeof( bih ), &dwWritten, NULL );
> if (!success)
> {
> CloseHandle( hf );
> return success;
> }
>
>
> // and the bits themselves
> //
> dwWritten = 0;
> success = WriteFile( hf, bitmap.bmBits, imageSize, &dwWritten, NULL
> );
> if (!success)
> {
> CloseHandle( hf );
> return success;
> }
>
> success = CloseHandle( hf );
> return success;
> }
>
> ---- E N
D -----------------------------------------------------------------
- Next message: Ron Green: "Re: IAMPushSource for Capture Filter"
- Previous message: Feras: "Re: Should Pin 0 of the Overlay Mixer accept connections with RGBxx"
- Messages sorted by: [ date ] [ thread ]
Relevant Pages
|