如何使用EZrgb24过滤器

时间:2014-09-11 21:12:07

标签: c# directshow directshow.net

上下文

我正在尝试在.avi视频的每一帧上应用滤镜,例如对比度,颜色变化,亮度。

使用directshow.net和c#播放视频时很好。

经过几个小时的研究,我发现buffercb不适合做这项工作。

显然,EZrgb24是我可以添加到我的图表中的过滤器,它完全符合我的要求。

然而,我无法让它发挥作用。

在班级的开头

中添加
[DllImport("ole32.dll", EntryPoint = "CoCreateInstance", CallingConvention = CallingConvention.StdCall)]
    static extern UInt32 CoCreateInstance([In, MarshalAs(UnmanagedType.LPStruct)] Guid rclsid,
       IntPtr pUnkOuter, UInt32 dwClsContext, [In, MarshalAs(UnmanagedType.LPStruct)] Guid riid,
       [MarshalAs(UnmanagedType.IUnknown)] out object rReturnedComObject);

以下是相关的代码

        int hr = 0;

        IBaseFilter ibfRenderer = null;
        ISampleGrabber sampGrabber = null;
        IBaseFilter capFilter = null;
        IPin iPinInFilter = null;
        IPin iPinOutFilter = null;
        IPin iPinInDest = null;



        Type comType = null;
        object comObj = null;

        m_FilterGraph = new FilterGraph() as IFilterGraph2;

        try
        {
            // Get the SampleGrabber interface
            sampGrabber = new SampleGrabber() as ISampleGrabber;

            // Add the video source
            hr = m_FilterGraph.AddSourceFilter(_videoPath, "Ds.NET FileFilter", out capFilter);
            DsError.ThrowExceptionForHR(hr);

            // Hopefully this will be the video pin
            IPin iPinOutSource = DsFindPin.ByDirection(capFilter, PinDirection.Output, 0);

            IBaseFilter baseGrabFlt = sampGrabber as IBaseFilter;
            ConfigureSampleGrabber(sampGrabber);

            iPinInFilter = DsFindPin.ByDirection(baseGrabFlt, PinDirection.Input, 0);
            iPinOutFilter = DsFindPin.ByDirection(baseGrabFlt, PinDirection.Output, 0);

            // Add the frame grabber to the graph
            hr = m_FilterGraph.AddFilter(baseGrabFlt, "Ds.NET Grabber");
            DsError.ThrowExceptionForHR(hr);

            hr = m_FilterGraph.Connect(iPinOutSource, iPinInFilter);
            DsError.ThrowExceptionForHR(hr);

            // Get the default video renderer
            ibfRenderer = (IBaseFilter)new VideoRendererDefault();

            // Add it to the graph
            hr = m_FilterGraph.AddFilter(ibfRenderer, "Ds.NET VideoRendererDefault");
            DsError.ThrowExceptionForHR(hr);
            iPinInDest = DsFindPin.ByDirection(ibfRenderer, PinDirection.Input, 0);

            // Connect the graph.  Many other filters automatically get added here
            hr = m_FilterGraph.Connect(iPinOutFilter, iPinInDest);
            DsError.ThrowExceptionForHR(hr);


            SaveSizeInfo(sampGrabber);

            HERE WE WANT TO ADD THE EZRGB FILTER.

无效的代码

            /*

            // { 8B498501-1218-11cf-ADC4-00A0D100041B }
            DEFINE_GUID(CLSID_EZrgb24,
            0x8b498501, 0x1218, 0x11cf, 0xad, 0xc4, 0x0, 0xa0, 0xd1, 0x0, 0x4, 0x1b);
             */
            unsafe
            {
                Guid IUnknownGuid = new Guid("00000000-0000-0000-C000-000000000046"); //Can it be written in more pretty style?

                Guid ezrgbclsid = new Guid(0x8b498501, 0x1218, 0x11cf, 0xad, 0xc4, 0x0, 0xa0, 0xd1, 0x0, 0x4, 0x1b);
                uint hr1 = CoCreateInstance(ezrgbclsid, IntPtr.Zero, (uint)(CLSCTX.CLSCTX_INPROC_HANDLER), ezrgbclsid, out x);//CLSCTX_LOCAL_SERVER

                IIPEffect myEffect = (IIPEffect)x;// as IIPEffect;

                if (hr1 != 0)
                {
                    int iError = Marshal.GetLastWin32Error();
                    Console.Write("CoCreateInstance Error = {0}, LastWin32Error = {1}", hr1, iError);

                }

                myEffect.put_IPEffect(1004, 0, 100); //for this filter, look at resource.h for what the int should be, in this case 1002 is the emboss effect

            }

我的诊断

我发现hr1中返回的int值是dll未注册的十六进制值。 这对我来说意味着EZRGB没有在我的电脑上注册。

我是如何尝试解决问题的

在一些不起眼的网站上找到并下载了EZRGB.ax。

执行命令:     cd \ windows \ syswow64     regsvr32 c:\ ezrgb24.ax

在c:\ ezrgb24.ax中,DllRegisterServer出现了一个消息框。

仍然无效。

我正在使用directshow.net,但是,这也被标记为directshow,因为我觉得该解决方案适用于c#或c ++。

1 个答案:

答案 0 :(得分:2)

  1. 使用可以使用SampleCB代替BufferCB;前者允许您访问进一步流式传输的数据,因此您可以对其进行修改
  2. 注册的典型问题是您构建了32位DLL,并且您尝试使用64位代码。比特必须匹配。
  3. 您需要CLSCTX_ALLCLSCTX_INPROC_SERVER