试试这个好用不:
用directshow 的ISampleGrabber接口GetCurrentBuffer方法捕获帧
例子:
SampleGrabber: ISampleGrabber;
procedure TMainForm.OpenFile(const FileName: string);
var
PFileName: array [0..255] of WideChar;
Filter: IBaseFilter;
MediaType: TAM_MEDIA_TYPE;
begin
CoCreateInstance(CLSID_FilterGraph, nil, CLSCTX_INPROC_SERVER,
IID_IGraphBuilder, GraphBuilder);
CoCreateInstance(CLSID_SampleGrabber, nil, CLSCTX_INPROC_SERVER,
IID_IBaseFilter, Filter);
Filter.QueryInterface(IID_ISampleGrabber, SampleGrabber);
GraphBuilder.AddFilter(Filter, 'Grabber');
Filter:=nil;
ZeroMemory(@MediaType, SizeOf(TAM_MEDIA_TYPE));
MediaType.majortype:=MEDIATYPE_Video;
MediaType.subtype:=MEDIASUBTYPE_RGB24;
MediaType.formattype:=FORMAT_VideoInfo;
SampleGrabber.SetMediaType(MediaType);
SampleGrabber.SetBufferSamples(True);
StringToWideChar(FileName, PFileName, 255);
GraphBuilder.RenderFile(PFileName, nil);
GraphBuilder.QueryInterface(IID_IVideoWindow, VideoWindow);
VideoWindow.put_Owner(DisplayPanel.Handle);
VideoWindow.put_WindowStyle(WS_CHILD or WS_CLIPSIBLINGS);
VideoWindow.put_Visible(True);
DisplayPanelResize(nil);
GraphBuilder.QueryInterface(IID_IMediaSeeking, MediaSeek);
MediaSeek.SetTimeFormat(Time_Format_Frame);
GraphBuilder.QueryInterface(IID_IMediaControl, MediaControl);
GraphBuilder.QueryInterface(IID_IMediaEventEx, MediaEvent);
MediaEvent.SetNotifyWindow(Handle, WM_GraphNotify, 0);
end;
procedure TMainForm.SpeedButton7Click(Sender: TObject);
var
MediaType: TAM_MEDIA_TYPE;
VideoInfoHeader: TVideoInfoHeader;
BitmapInfo: TBitmapInfo;
Bitmap: HBitmap;
Buffer: Pointer;
BufferSize: Integer;
begin
SampleGrabber.GetConnectedMediaType(MediaType);
ZeroMemory(@VideoInfoHeader, SizeOf(TVideoInfoHeader));
CopyMemory(@VideoInfoHeader, MediaType.pbFormat, SizeOf(VideoInfoHeader));
ZeroMemory(@BitmapInfo, SizeOf(TBitmapInfo));
CopyMemory(@BitmapInfo, @VideoInfoHeader.bmiHeader, SizeOf(VideoInfoHeader.bmiHeader));
Bitmap:=CreateDIBSection(0, BitmapInfo, DIB_RGB_COLORS, Buffer, 0, 0);
SampleGrabber.GetCurrentBuffer(BufferSize, Buffer);
Image1.Picture.Bitmap.Handle:=Bitmap
end;