// This method changed to work with Windows 7 // Under this OS, the MPEG-2 Demux now have dozens of outputs pins. // Rendering all of them is not a good solution. // The rendering process must be more smart... private void ConnectFilters() { int hr = 0; int pinNumber = 0; IPin pinOut, pinIn; // After the rendering process, our 4 downstream filters must be rendered bool bdaTIFRendered = false; bool bdaSecTabRendered = false; bool audioRendered = false; bool videoRendered = false; // for each output pins... while (true) { pinOut = DsFindPin.ByDirection(mpeg2Demux, PinDirection.Output, pinNumber); // Is the last pin reached ? if (pinOut == null) { break; } IEnumMediaTypes enumMediaTypes = null; AMMediaType[] mediaTypes = new AMMediaType[1]; try { // Get Pin's MediaType enumerator hr = pinOut.EnumMediaTypes(out enumMediaTypes); DsError.ThrowExceptionForHR(hr); // for each media types... while (enumMediaTypes.Next(mediaTypes.Length, mediaTypes, IntPtr.Zero) == 0) { // Store the majortype and the subtype and free the structure Guid majorType = mediaTypes[0].majorType; Guid subType = mediaTypes[0].subType; DsUtils.FreeAMMediaType(mediaTypes[0]); if (majorType == MediaType.Audio) { // Is the Audio already rendered ? if (!audioRendered) { // Get the first input pin pinIn = DsFindPin.ByDirection(audioRenderer, PinDirection.Input, 0); // Render it with IntelliConnect (a decoder should be added between the two filters. hr = graphBuilder.Connect(pinOut, pinIn); DsError.ThrowExceptionForHR(hr); // Release the Pin Marshal.ReleaseComObject(pinIn); pinIn = null; // Notify that the audio renderer is connected audioRendered = true; } } else if (majorType == MediaType.Video) { // Is the Video already rendered ? if (!videoRendered) { // Get the first input pin pinIn = DsFindPin.ByDirection(videoRenderer, PinDirection.Input, 0); // Render it with IntelliConnect (a decoder should be added between the two filters. hr = graphBuilder.Connect(pinOut, pinIn); DsError.ThrowExceptionForHR(hr); // Release the Pin Marshal.ReleaseComObject(pinIn); pinIn = null; // Notify that the video renderer is connected videoRendered = true; } } else if (majorType == MediaType.Mpeg2Sections) { if (subType == MediaSubType.Mpeg2Data) { // Is the MPEG-2 Sections and Tables Filter already rendered ? if (!bdaSecTabRendered) { // Get the first input pin pinIn = DsFindPin.ByDirection(bdaSecTab, PinDirection.Input, 0); // A direct connection is enough hr = graphBuilder.ConnectDirect(pinOut, pinIn, null); DsError.ThrowExceptionForHR(hr); // Release the Pin Marshal.ReleaseComObject(pinIn); pinIn = null; // Notify that the MPEG-2 Sections and Tables Filter is connected bdaSecTabRendered = true; } } // This sample only support DVB-T or DVB-S so only supporting this subtype is enough. // If you want to support ATSC or ISDB, don't forget to handle these network types. else if (subType == MediaSubType.DvbSI) { // Is the BDA MPEG-2 Transport Information Filter already rendered ? if (!bdaTIFRendered) { // Get the first input pin pinIn = DsFindPin.ByDirection(bdaTIF, PinDirection.Input, 0); // A direct connection is enough hr = graphBuilder.ConnectDirect(pinOut, pinIn, null); DsError.ThrowExceptionForHR(hr); // Release the Pin Marshal.ReleaseComObject(pinIn); pinIn = null; // Notify that the BDA MPEG-2 Transport Information Filter is connected bdaTIFRendered = true; } } } } } finally { // Free COM objects Marshal.ReleaseComObject(enumMediaTypes); enumMediaTypes = null; Marshal.ReleaseComObject(pinOut); pinOut = null; } // Next pin, please ! pinNumber++; } }
public void SetUpForTs(ISampleGrabberCB grabber, int methodToCall) { FilterGraphTools.DisconnectPins(mpeg2Demux); //FilterGraphTools.DisconnectPins(demodulator); FilterGraphTools.DisconnectPins(audioRenderer); FilterGraphTools.DisconnectPins(videoRenderer); //graphBuilder.RemoveFilter(audioRenderer); //graphBuilder.RemoveFilter(videoRenderer); sampleGrabber = (ISampleGrabber) new SampleGrabber(); AMMediaType media = new AMMediaType(); media.majorType = MediaType.Stream; media.subType = MediaSubType.Mpeg2Transport; media.formatType = FormatType.MpegStreams; sampleGrabber.SetOneShot(false); sampleGrabber.SetBufferSamples(true); int hr = sampleGrabber.SetMediaType(media); DsError.ThrowExceptionForHR(hr); graphBuilder.AddFilter((IBaseFilter)sampleGrabber, "Sample Grabber"); nullRenderer = (IBaseFilter) new NullRenderer(); graphBuilder.AddFilter(nullRenderer, "NULL Renderer"); IPin pinIn = DsFindPin.ByName((IBaseFilter)sampleGrabber, "Input"); IPin pinOut = DsFindPin.ByDirection(capture, PinDirection.Output, 0); IEnumMediaTypes eMedia; pinOut.EnumMediaTypes(out eMedia); AMMediaType[] mediaTypes = new AMMediaType[1]; eMedia.Next(mediaTypes.Length, mediaTypes, IntPtr.Zero); hr = sampleGrabber.SetMediaType(mediaTypes[0]); DsError.ThrowExceptionForHR(hr); pinOut.Disconnect(); PinInfo info; pinOut.QueryPinInfo(out info); hr = graphBuilder.ConnectDirect(pinOut, pinIn, mediaTypes[0]); //hr = graphBuilder.Connect(pinOut, pinIn); DsError.ThrowExceptionForHR(hr); // Release the Pin Marshal.ReleaseComObject(pinIn); pinIn = DsFindPin.ByName(nullRenderer, "In"); pinOut = DsFindPin.ByName((IBaseFilter)sampleGrabber, "Output"); hr = graphBuilder.Connect(pinOut, pinIn); DsError.ThrowExceptionForHR(hr); sampleGrabber.SetCallback(grabber, methodToCall); // Release the Pin Marshal.ReleaseComObject(pinIn); pinIn = null; }