How to work with AMMediaType for video filters

和自甴很熟 提交于 2020-02-04 11:44:59

问题


I am using Video Resizer DSP Video Resizer DSP to resize my video. I work with Lazarus Free Pascal and DSPack.

This site explains how to use: http://alax.info/blog/1371

  • CoCreateInstance the DSP as DMO and add it to DMO Wrapper Filter
  • Use IWMResizerProps::SetFullCropRegion to initialize the DSP
  • Connect input pin
  • Set output type via IMediaObject::SetOutputType
  • IGraphBuilder::ConnectDirect output pin

I write this:

//Create Resizer DMO
hr := CoCreateInstance(CLSID_DMOWrapperFilter, NIL, CLSCTX_ALL,
IID_IBaseFilter, FResizerDMO);
if FAILED(hr) then EXIT;
//CLSID_CVideoResizerDMO = '{1ea1ea14-48f4-4054-ad1a-e8aee10ac805}'
Hr := (FResizerDMO as IDMOWrapperFilter).Init( CLSID_CVideoResizerDMO,  
DMOCATEGORY_VIDEO_EFFECT );
if FAILED(Hr) then EXIT;
//Add filter to graph
(fgRender as IGraphBuilder).AddFilter( FResizerDMO, 'Resizer' );
if FAILED(Hr) then EXIT; 
// end create FResizerDMO in my graph

// Set output type via IMediaObject::SetOutputType and create structure 
ZeroMemory(@mt, sizeof(DMO_MEDIA_TYPE));
mt.majortype := MEDIATYPE_Video;
mt.subtype := MEDIASUBTYPE_RGB32;
mt.formattype := FORMAT_VideoInfo; 
mt.lSampleSize := pVIH.bmiHeader.biSize;
FillChar(pVIH, SizeOf(TVideoInfoHeader), 0);
mt.pbFormat := CoTaskMemAlloc(sizeof(VIDEOINFOHEADER));
pVIH := TVideoInfoHeader(mt.pbFormat^);
pVIH.bmiHeader.biWidth := 720;
pVIH.bmiHeader.biHeight := 576;
pVIH.bmiHeader.biXPelsPerMeter:=9;
pVIH.bmiHeader.biYPelsPerMeter:=16;
pVIH.bmiHeader.biSize := SizeOf(TBitmapInfoHeader);
pVIH.bmiHeader.biSizeImage := 720 * 576 * 4;
//  connect pin and next
hr := (FResizerDMO as IMediaObject).SetOutputType
(0,@mt,DMO_SET_TYPEF_CLEAR);

in hr i receive DMO_E_TYPE_NOT_ACCEPTED. where I go wrong? can anyone help me? thank you.


回答1:


Cross-post of a thread on this topic: How to configure the Resizer DMO?.

I don't think your code around pbFormat is correct. Apparently, FillChar is to cause memory access vioaltion as you do it too early. Then it looks like you're modifying a copy of allocated data (pVIH declaration is not shown). Then biXPelsPerMeter/biYPelsPerMeter looks somewhat weird even though I think this can be accepted. Then you don't initilaize the rest of TVideoInfoHeader fields.

Just watch pVIH in debuger before the call and you will see the structure is not well-defined.

Start with initializing explicitly all fields of VIDEOINFOHEADER structure.




回答2:


thank you Roman R.

//Create Resizer DMO
hr := CoCreateInstance(CLSID_DMOWrapperFilter, NIL, CLSCTX_ALL,
IID_IBaseFilter, FResizerDMO);
if FAILED(hr) then EXIT;
//CLSID_CVideoResizerDMO = '{1ea1ea14-48f4-4054-ad1a-e8aee10ac805}'
Hr := (FResizerDMO as IDMOWrapperFilter).Init( CLSID_CVideoResizerDMO,  
DMOCATEGORY_VIDEO_EFFECT );
if FAILED(Hr) then EXIT;
//Add filter to graph
(fgRender as IGraphBuilder).AddFilter( FResizerDMO, 'Resizer' );
if FAILED(Hr) then EXIT; 
// end create FResizerDMO in my graph
//--------------------------------
// Use IWMResizerProps::SetFullCropRegion to initialize the DSP
// I have a hard time writing this. this must resize the canvas?
//-------------------------------
ZeroMemory(@mt, sizeof(DMO_MEDIA_TYPE));
mt.majortype := MEDIATYPE_Video;
mt.subtype := MEDIASUBTYPE_RGB32;
mt.formattype := FORMAT_VideoInfo; 
mt.lSampleSize := pVIH.bmiHeader.biSize;
FillChar(pVIH, SizeOf(TVideoInfoHeader), 0);
mt.pbFormat := CoTaskMemAlloc(sizeof(VIDEOINFOHEADER));
pVIH := TVideoInfoHeader(mt.pbFormat^);
source.Left:=0;  source.Top:=0; source.Right:=1920; source.Bottom:=1080;
// if source = ( 0,0,0,0) read size of the video source?
pVIH.rcSource := source;
target.Left:=0; target.Top:=0; target.Right:=576; target.Bottom:=720;
PVIH.rcTarget:= target;
pVIH.dwBitRate:= 0;
PVIH.dwBitErrorRate:= 0;
pVIH.AvgTimePerFrame:= 333667; //this is for 29 frames, I want 25 frames
 pVIH.bmiHeader.biWidth := 720;
pVIH.bmiHeader.biHeight := 576;
pVIH.bmiHeader.biXPelsPerMeter:=9;
pVIH.bmiHeader.biYPelsPerMeter:=16;
pVIH.bmiHeader.biSize := SizeOf(TBitmapInfoHeader);
pVIH.bmiHeader.biSizeImage := 720 * 576 * 4;
pVIH.bmiHeader.biPlanes := 1;
pVIH.bmiHeader.biBitCount := 4;
pVIH.bmiHeader.biCompression:= BI_RGB;
pVIH.bmiHeader.biClrUsed:=0;
pVIH.bmiHeader.biClrImportant:=0; 
//******* connect  pin input filter of FResizerDMO
Connect(SourceFilter,LAVSplitter);
Connect(LAVSplitter, ffdshowVideoDecoderV1);
Connect(ffdshowVideoDecoderV1,FResizerDMO);
//***************
hr := (FResizerDMO as IMediaObject).SetOutputType
(0,@mt,DMO_SET_TYPEF_CLEAR);

all that I have to correct for configure the Resizer DMO. maybe I'm doing it all wrong?




回答3:


sorry for my english. I write little to avoid errors. videowindow1 is component of pl_Win_DSPack for free pascal. videowindows1 = Video Mixing Renderer 9.

hr := CoCreateInstance(CLSID_CaptureGraphBuilder2, nil,
CLSCTX_INPROC_SERVER,IID_ICaptureGraphBuilder2, ICapGraph);
ICapGraph.SetFilterGraph(fgRender as IGraphBuilder);
                    //*****************
hr := ICapGraph.RenderStream(nil,nil, SourceFilter, nil, FResizerDMO);
hr := (FResizerDMO as IMediaObject).SetOutputType(0,@(pMT^),0);// or pMT 
DeleteMediaType(pMT);
hr := ICapGraph.RenderStream(nil, nil, FResizerDMO, nil, VideoWindow1 as 
IBaseFilter);
fgRender.Play;
mc.Run; 

1)with this code, video does not resize.I see in videowindow1, small square with video run, videowindow1 is bigger. 2)with GraphStudioNext i have established many combinations. Only ffdshow Video Decoder connects with ResizerDMO and in property filter ResizerDMO i change parameters but the video does not resize.

excuse me, and thanks for your help



来源:https://stackoverflow.com/questions/29386190/how-to-work-with-ammediatype-for-video-filters

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!