How to use EZrgb24 filter

对着背影说爱祢 提交于 2019-12-25 03:59:27

问题


Context

I'm trying to apply filter such as contrast, color change, brightness on every frame of a .avi video.

The video is playing just fine with directshow.net and c#.

after a couple hours of research, I found out that buffercb was not the way to go to do the job.

Apparantly, EZrgb24 is a filter I can add to my graph that does exactly what I want.

However, I can't get it to work.

Added in the beggining of my class

[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);

Here is relevant code that works

        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.

Code that doesnt work

            /*

            // { 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

            }

My diagnostic

I found out that the int value returned in hr1, is the hexadecimal value for dll not registred. Which means to me that EZRGB is not registred on my computer.

How I tryed to solve the problem

Found and downloaded EZRGB.ax on some obscure web site.

executed the command : cd \windows\syswow64 regsvr32 c:\ezrgb24.ax

A message box appeared with DllRegisterServer in c:\ezrgb24.ax succeeded.

Still doesn't work.

I am using directshow.net, however, this is also tagged both directshow as I feel the solution will work for either c# or c++.


回答1:


  1. Use can use SampleCB instead of BufferCB; the former provides you access to data which is streamed further, so you can modify it
  2. The typical problem with registration is that you build 32-bit DLL and you are trying to use it from 64-bit code. The bitnesses have to match.
  3. You need CLSCTX_ALL or CLSCTX_INPROC_SERVER


来源:https://stackoverflow.com/questions/25797025/how-to-use-ezrgb24-filter

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