Exemple #1
0
        protected virtual void InsertAudioFilter(IBaseFilter sourceFilter, string audioDecoder)
        {
            if (string.IsNullOrEmpty(audioDecoder))
            {
                return;
            }

            // Set Audio Codec
            // Remove Pin
            var  audioPinFrom = DirectShowLib.DsFindPin.ByName(sourceFilter, "Audio");
            IPin audioPinTo;

            if (audioPinFrom != null)
            {
                int hr = audioPinFrom.ConnectedTo(out audioPinTo);
                if (hr >= 0 && audioPinTo != null)
                {
                    PinInfo pInfo;
                    audioPinTo.QueryPinInfo(out pInfo);
                    FilterInfo fInfo;
                    pInfo.filter.QueryFilterInfo(out fInfo);

                    DirectShowUtil.DisconnectAllPins(m_graph, pInfo.filter);
                    m_graph.RemoveFilter(pInfo.filter);

                    DsUtils.FreePinInfo(pInfo);
                    Marshal.ReleaseComObject(fInfo.pGraph);
                    Marshal.ReleaseComObject(audioPinTo);
                    audioPinTo = null;
                }
                Marshal.ReleaseComObject(audioPinFrom);
                audioPinFrom = null;
            }

            DirectShowUtil.AddFilterToGraph(m_graph, audioDecoder, Guid.Empty);
        }
        /// <summary>
        /// Opens the media by initializing the DirectShow graph
        /// </summary>
        protected virtual void OpenSource()
        {
            /* Make sure we clean up any remaining mess */
            FreeResources();

            if (m_sourceUri == null)
            {
                return;
            }

            string fileSource = m_sourceUri.OriginalString;

            if (string.IsNullOrEmpty(fileSource))
            {
                return;
            }

            try
            {
                /* Creates the GraphBuilder COM object */
                m_graph = new FilterGraphNoThread() as IGraphBuilder;

                if (m_graph == null)
                {
                    throw new Exception("Could not create a graph");
                }

                var filterGraph = m_graph as IFilterGraph2;

                if (filterGraph == null)
                {
                    throw new Exception("Could not QueryInterface for the IFilterGraph2");
                }

                IBaseFilter sourceFilter;
                int         hr;

                //var file = System.IO.File.CreateText(@"M:\DirectShowLog.txt");
                //filterGraph.SetLogFile((file.BaseStream as System.IO.FileStream).SafeFileHandle.DangerousGetHandle());


                // Set LAV Splitter
                LAVSplitterSource reader = new LAVSplitterSource();
                sourceFilter = reader as IBaseFilter;
                var objectWithSite = reader as IObjectWithSite;
                if (objectWithSite != null)
                {
                    objectWithSite.SetSite(this);
                }

                hr = m_graph.AddFilter(sourceFilter, SplitterSource);
                DsError.ThrowExceptionForHR(hr);


                IFileSourceFilter interfaceFile = (IFileSourceFilter)sourceFilter;
                hr = interfaceFile.Load(fileSource, null);
                DsError.ThrowExceptionForHR(hr);


                // Set Video Codec
                // Remove Pin
                var  videoPinFrom = DirectShowLib.DsFindPin.ByName(sourceFilter, "Video");
                IPin videoPinTo;
                if (videoPinFrom != null)
                {
                    hr = videoPinFrom.ConnectedTo(out videoPinTo);
                    if (hr >= 0 && videoPinTo != null)
                    {
                        PinInfo pInfo;
                        videoPinTo.QueryPinInfo(out pInfo);
                        FilterInfo fInfo;
                        pInfo.filter.QueryFilterInfo(out fInfo);

                        DirectShowUtil.DisconnectAllPins(m_graph, pInfo.filter);
                        m_graph.RemoveFilter(pInfo.filter);

                        DsUtils.FreePinInfo(pInfo);
                        Marshal.ReleaseComObject(fInfo.pGraph);
                        Marshal.ReleaseComObject(videoPinTo);
                        videoPinTo = null;
                    }
                    Marshal.ReleaseComObject(videoPinFrom);
                    videoPinFrom = null;
                }

                DirectShowUtil.AddFilterToGraph(m_graph, VideoDecoder, Guid.Empty);

                // Set Audio Codec
                // Remove Pin
                var  audioPinFrom = DirectShowLib.DsFindPin.ByName(sourceFilter, "Audio");
                IPin audioPinTo;
                if (audioPinFrom != null)
                {
                    hr = audioPinFrom.ConnectedTo(out audioPinTo);
                    if (hr >= 0 && audioPinTo != null)
                    {
                        PinInfo pInfo;
                        audioPinTo.QueryPinInfo(out pInfo);
                        FilterInfo fInfo;
                        pInfo.filter.QueryFilterInfo(out fInfo);

                        DirectShowUtil.DisconnectAllPins(m_graph, pInfo.filter);
                        m_graph.RemoveFilter(pInfo.filter);

                        DsUtils.FreePinInfo(pInfo);
                        Marshal.ReleaseComObject(fInfo.pGraph);
                        Marshal.ReleaseComObject(audioPinTo);
                        audioPinTo = null;
                    }
                    Marshal.ReleaseComObject(audioPinFrom);
                    audioPinFrom = null;
                }

                DirectShowUtil.AddFilterToGraph(m_graph, AudioDecoder, Guid.Empty);


                /* Add our prefered audio renderer */
                InsertAudioRenderer(AudioRenderer);

                IBaseFilter renderer = CreateVideoRenderer(VideoRenderer, m_graph, 2);



                /* We will want to enum all the pins on the source filter */
                IEnumPins pinEnum;

                hr = sourceFilter.EnumPins(out pinEnum);
                DsError.ThrowExceptionForHR(hr);

                IntPtr fetched = IntPtr.Zero;
                IPin[] pins    = { null };

                /* Counter for how many pins successfully rendered */
                int pinsRendered = 0;

                if (VideoRenderer == VideoRendererType.VideoMixingRenderer9)
                {
                    var mixer = renderer as IVMRMixerControl9;

                    if (mixer != null)
                    {
                        VMR9MixerPrefs dwPrefs;
                        mixer.GetMixingPrefs(out dwPrefs);
                        dwPrefs &= ~VMR9MixerPrefs.RenderTargetMask;
                        dwPrefs |= VMR9MixerPrefs.RenderTargetRGB;
                        //mixer.SetMixingPrefs(dwPrefs);
                    }
                }

                /* Test using FFDShow Video Decoder Filter
                 * var ffdshow = new FFDShow() as IBaseFilter;
                 *
                 * if (ffdshow != null)
                 *  m_graph.AddFilter(ffdshow, "ffdshow");
                 */


                /* Loop over each pin of the source filter */
                while (pinEnum.Next(pins.Length, pins, fetched) == 0)
                {
                    if (filterGraph.RenderEx(pins[0],
                                             AMRenderExFlags.RenderToExistingRenderers,
                                             IntPtr.Zero) >= 0)
                    {
                        pinsRendered++;
                    }


                    Marshal.ReleaseComObject(pins[0]);
                }


                Marshal.ReleaseComObject(pinEnum);
                Marshal.ReleaseComObject(sourceFilter);

                if (pinsRendered == 0)
                {
                    throw new Exception("Could not render any streams from the source Uri");
                }

#if DEBUG
                /* Adds the GB to the ROT so we can view
                 * it in graphedit */
                m_dsRotEntry = new DsROTEntry(m_graph);
#endif
                /* Configure the graph in the base class */
                SetupFilterGraph(m_graph);

                HasVideo = true;
                /* Sets the NaturalVideoWidth/Height */
                //SetNativePixelSizes(renderer);
            }
            catch (Exception ex)
            {
                /* This exection will happen usually if the media does
                 * not exist or could not open due to not having the
                 * proper filters installed */
                FreeResources();

                /* Fire our failed event */
                InvokeMediaFailed(new MediaFailedEventArgs(ex.Message, ex));
            }

            InvokeMediaOpened();
        }
        private bool DoesItHaveVideo(string filename)
        {
            if (string.IsNullOrEmpty(filename))
            {
                return(false);
            }
            bool          result;
            IGraphBuilder temp_graph = new FilterGraphNoThread() as IGraphBuilder;

            try
            {
                if (temp_graph == null)
                {
                    throw new WPFMediaKitException("Could not create a graph");
                }

                var filterGraph = temp_graph as IFilterGraph2;

                if (filterGraph == null)
                {
                    throw new WPFMediaKitException("Could not QueryInterface for the IFilterGraph2");
                }

                IBaseFilter sourceFilter;
                int         hr;

                sourceFilter = DirectShowUtil.AddFilterToGraph(temp_graph, SplitterSource, LAVFilterDirectory, Guid.Empty);
                if (sourceFilter == null)
                {
                    throw new WPFMediaKitException("Could not add SplitterSource to graph.");
                }



                IFileSourceFilter interfaceFile = (IFileSourceFilter)sourceFilter;
                hr = interfaceFile.Load(filename, null);
                DsError.ThrowExceptionForHR(hr);



                // Set Video Codec
                // Remove Pin
                var  videoPinFrom = DirectShowLib.DsFindPin.ByName(sourceFilter, "Video");
                IPin videoPinTo;
                if (videoPinFrom != null)
                {
                    hr = videoPinFrom.ConnectedTo(out videoPinTo);
                    if (hr >= 0 && videoPinTo != null)
                    {
                        PinInfo pInfo;
                        videoPinTo.QueryPinInfo(out pInfo);
                        FilterInfo fInfo;
                        pInfo.filter.QueryFilterInfo(out fInfo);

                        DirectShowUtil.DisconnectAllPins(temp_graph, pInfo.filter);
                        temp_graph.RemoveFilter(pInfo.filter);

                        DsUtils.FreePinInfo(pInfo);
                        Marshal.ReleaseComObject(fInfo.pGraph);
                        Marshal.ReleaseComObject(videoPinTo);
                        videoPinTo = null;
                    }
                    Marshal.ReleaseComObject(videoPinFrom);
                    videoPinFrom = null;

                    result = true;
                }
                else
                {
                    result = false;
                }

                DirectShowUtil.RemoveFilters(temp_graph, SplitterSource.Name);
                Marshal.FinalReleaseComObject(sourceFilter);
            }
            catch
            { result = false; }
            finally
            {
                Marshal.ReleaseComObject(temp_graph);
            }
            return(result);
        }
Exemple #4
0
        /// <summary>
        /// Opens the media by initializing the DirectShow graph
        /// </summary>
        protected virtual void OpenSource()
        {
            /* Make sure we clean up any remaining mess */
            FreeResources();

            string fileSource = FileSource;

            if (string.IsNullOrEmpty(fileSource))
            {
                return;
            }

            try
            {
                /* Creates the GraphBuilder COM object */
                m_graph = new FilterGraphNoThread() as IGraphBuilder;

                if (m_graph == null)
                {
                    throw new WPFMediaKitException("Could not create a graph");
                }

                var filterGraph = m_graph as IFilterGraph2;

                if (filterGraph == null)
                {
                    throw new WPFMediaKitException("Could not QueryInterface for the IFilterGraph2");
                }

                IBaseFilter sourceFilter;
                int         hr;


                // Set LAV Splitter

                /* LAVSplitterSource reader = new LAVSplitterSource();
                 * sourceFilter = reader as IBaseFilter;
                 * var objectWithSite = reader as IObjectWithSite;
                 * if (objectWithSite != null)
                 * {
                 *   objectWithSite.SetSite(this);
                 * }
                 *
                 *
                 * hr = m_graph.AddFilter(sourceFilter, SplitterSource);
                 * DsError.ThrowExceptionForHR(hr);*/

                sourceFilter = DirectShowUtil.AddFilterToGraph(m_graph, SplitterSource, Guid.Empty);
                if (sourceFilter == null)
                {
                    throw new WPFMediaKitException("Could not add SplitterSource to graph.");
                }

                IFileSourceFilter interfaceFile = (IFileSourceFilter)sourceFilter;
                hr = interfaceFile.Load(fileSource, null);
                DsError.ThrowExceptionForHR(hr);


                // Set Video Codec
                // Remove Pin
                var  videoPinFrom = DirectShowLib.DsFindPin.ByName(sourceFilter, "Video");
                IPin videoPinTo;
                if (videoPinFrom != null)
                {
                    hr = videoPinFrom.ConnectedTo(out videoPinTo);
                    if (hr >= 0 && videoPinTo != null)
                    {
                        PinInfo pInfo;
                        videoPinTo.QueryPinInfo(out pInfo);
                        FilterInfo fInfo;
                        pInfo.filter.QueryFilterInfo(out fInfo);

                        DirectShowUtil.DisconnectAllPins(m_graph, pInfo.filter);
                        m_graph.RemoveFilter(pInfo.filter);

                        DsUtils.FreePinInfo(pInfo);
                        Marshal.ReleaseComObject(fInfo.pGraph);
                        Marshal.ReleaseComObject(videoPinTo);
                        videoPinTo = null;
                    }
                    Marshal.ReleaseComObject(videoPinFrom);
                    videoPinFrom = null;

                    HasVideo = true;
                }
                else
                {
                    HasVideo = false;
                }

                DirectShowUtil.AddFilterToGraph(m_graph, VideoDecoder, Guid.Empty);

                try
                {
                    // use preffered audio filter
                    InsertAudioFilter(sourceFilter, AudioDecoder);
                }
                catch (Exception ex)
                {
                    // codecs misconfigured
                    log.Error(ex, "Cannot add audio decoder: {0}", AudioDecoder);
                }

                // use prefered audio renderer
                try
                {
                    InsertAudioRenderer(AudioRenderer);
                }
                catch (Exception ex)
                {
                    log.Error(ex, "Cannot add audio render: {0}", AudioRenderer);
                }

                IBaseFilter renderer = CreateVideoRenderer(VideoRenderer, m_graph, 2);

                /* We will want to enum all the pins on the source filter */
                IEnumPins pinEnum;

                hr = sourceFilter.EnumPins(out pinEnum);
                DsError.ThrowExceptionForHR(hr);

                IntPtr fetched = IntPtr.Zero;
                IPin[] pins    = { null };

                /* Counter for how many pins successfully rendered */
                int pinsRendered = 0;

                if (VideoRenderer == VideoRendererType.VideoMixingRenderer9)
                {
                    var mixer = renderer as IVMRMixerControl9;

                    if (mixer != null)
                    {
                        VMR9MixerPrefs dwPrefs;
                        mixer.GetMixingPrefs(out dwPrefs);
                        dwPrefs &= ~VMR9MixerPrefs.RenderTargetMask;
                        dwPrefs |= VMR9MixerPrefs.RenderTargetRGB;
                        //mixer.SetMixingPrefs(dwPrefs);
                    }
                }

                /* Loop over each pin of the source filter */
                while (pinEnum.Next(pins.Length, pins, fetched) == 0)
                {
                    if (filterGraph.RenderEx(pins[0],
                                             AMRenderExFlags.RenderToExistingRenderers,
                                             IntPtr.Zero) >= 0)
                    {
                        pinsRendered++;
                    }


                    Marshal.ReleaseComObject(pins[0]);
                }


                Marshal.ReleaseComObject(pinEnum);
                Marshal.ReleaseComObject(sourceFilter);

                if (pinsRendered == 0)
                {
                    throw new WPFMediaKitException("Could not render any streams from the source Uri");
                }

#if DEBUG
                /* Adds the GB to the ROT so we can view
                 * it in graphedit */
                m_dsRotEntry = new DsROTEntry(m_graph);
#endif
                /* Configure the graph in the base class */
                SetupFilterGraph(m_graph);
            }
            catch (Exception ex)
            {
                /* This exection will happen usually if the media does
                 * not exist or could not open due to not having the
                 * proper filters installed */


                // Fallback try auto graph:
                var result = oldOpenSource();

                if (!result)
                {
                    FreeResources();

                    HasVideo = false;

                    /* Fire our failed event */
                    InvokeMediaFailed(new MediaFailedEventArgs(ex.Message, ex));

                    return;
                }
            }

            InvokeMediaOpened();
        }
        protected virtual void OpenSource()
        {
            /* Make sure we clean up any remaining mess */
            FreeResources();

            string fileSource = FileSource;

            if (string.IsNullOrEmpty(fileSource))
            {
                return;
            }

            try
            {
                //lets get over with it right here
                HasVideo = DoesItHaveVideo(FileSource);
                GC.Collect();
                GC.WaitForPendingFinalizers();

                /* Creates the GraphBuilder COM object */
                m_graph = new FilterGraphNoThread() as IGraphBuilder;

                if (m_graph == null)
                {
                    throw new WPFMediaKitException("Could not create a graph");
                }

                var filterGraph = m_graph as IFilterGraph2;

                if (filterGraph == null)
                {
                    throw new WPFMediaKitException("Could not QueryInterface for the IFilterGraph2");
                }

                IBaseFilter sourceFilter;
                int         hr;


                // Set LAV Splitter

                /* LAVSplitterSource reader = new LAVSplitterSource();
                 * sourceFilter = reader as IBaseFilter;
                 * var objectWithSite = reader as IObjectWithSite;
                 * if (objectWithSite != null)
                 * {
                 *   objectWithSite.SetSite(this);
                 * }
                 *
                 *
                 * hr = m_graph.AddFilter(sourceFilter, SplitterSource);
                 * DsError.ThrowExceptionForHR(hr);*/



                //we are using AsyncFileSource here, so that file will not be locked during preview
                sourceFilter = DirectShowUtil.AddFilterToGraph(m_graph, AsyncFileSource, LAVFilterDirectory, Guid.Empty);
                if (sourceFilter == null)
                {
                    throw new WPFMediaKitException("Could not add SplitterSource to graph.");
                }


                IFileSourceFilter interfaceFile = (IFileSourceFilter)sourceFilter;
                hr = interfaceFile.Load(fileSource, null);
                DsError.ThrowExceptionForHR(hr);

                // we are going to need LavSpltter here, to connect AsyncFileSource with VideoDecoder
                DirectShowUtil.AddFilterToGraph(m_graph, Splitter, LAVFilterDirectory, Guid.Empty);

                DirectShowUtil.AddFilterToGraph(m_graph, VideoDecoder, LAVFilterDirectory, Guid.Empty);

                try
                {
                    // use preffered audio filter
                    InsertAudioFilter(sourceFilter, AudioDecoder);
                }
                catch (Exception ex)
                {
                    // codecs misconfigured
                    log.Error(ex, "Cannot add audio decoder: {0}", AudioDecoder);
                }

                // use prefered audio renderer
                try
                {
                    InsertAudioRenderer(AudioRenderer);
                }
                catch (Exception ex)
                {
                    log.Error(ex, "Cannot add audio render: {0}", AudioRenderer);
                }

                IBaseFilter renderer = CreateVideoRenderer(VideoRenderer, m_graph, 2);

                /* We will want to enum all the pins on the source filter */
                IEnumPins pinEnum;

                hr = sourceFilter.EnumPins(out pinEnum);
                DsError.ThrowExceptionForHR(hr);

                IntPtr fetched = IntPtr.Zero;
                IPin[] pins    = { null };

                /* Counter for how many pins successfully rendered */
                int pinsRendered = 0;

                if (VideoRenderer == VideoRendererType.VideoMixingRenderer9)
                {
                    var mixer = renderer as IVMRMixerControl9;

                    if (mixer != null)
                    {
                        VMR9MixerPrefs dwPrefs;
                        mixer.GetMixingPrefs(out dwPrefs);
                        dwPrefs &= ~VMR9MixerPrefs.RenderTargetMask;
                        dwPrefs |= VMR9MixerPrefs.RenderTargetRGB;
                        //mixer.SetMixingPrefs(dwPrefs);
                    }
                }

                /* Loop over each pin of the source filter */
                while (pinEnum.Next(pins.Length, pins, fetched) == 0)
                {
                    if (filterGraph.RenderEx(pins[0],
                                             AMRenderExFlags.RenderToExistingRenderers,
                                             IntPtr.Zero) >= 0)
                    {
                        pinsRendered++;
                    }


                    Marshal.ReleaseComObject(pins[0]);
                }


                Marshal.ReleaseComObject(pinEnum);
                Marshal.ReleaseComObject(sourceFilter);

                if (pinsRendered == 0)
                {
                    throw new WPFMediaKitException("Could not render any streams from the source Uri");
                }

#if DEBUG
                /* Adds the GB to the ROT so we can view
                 * it in graphedit */
                m_dsRotEntry = new DsROTEntry(m_graph);
#endif
                /* Configure the graph in the base class */
                SetupFilterGraph(m_graph);

                GetFrameStepInterface();
            }
            catch (Exception ex)
            {
                /* This exection will happen usually if the media does
                 * not exist or could not open due to not having the
                 * proper filters installed */


                // Fallback try auto graph:
                var result = oldOpenSource();

                if (!result)
                {
                    FreeResources();

                    HasVideo = false;

                    /* Fire our failed event */
                    InvokeMediaFailed(new MediaFailedEventArgs(ex.Message, ex));

                    return;
                }
            }

            InvokeMediaOpened();
        }