/// <summary> /// Loads IWaveProvider. /// </summary> /// <param name="waveProvider">The waveProvider to be loaded.</param> public void Init(IWaveProvider waveProvider) { MediaFoundationApi.Startup(); m_sourcewave = waveProvider; int readcount; MemoryStream msByteStrem = new MemoryStream(); byte[] _data; do { readcount = 0; _data = new byte[32767]; readcount = waveProvider.Read(_data, 0, _data.Length); if (readcount < 0) { continue; } msByteStrem.Write(_data, 0, readcount); } while (readcount >= _data.Length | readcount < 0);//Creates a IMFByteStream and fills it with the data in waveProvider. ComStream csByteStream = new ComStream(msByteStrem); IMFByteStream mfByteStream = MediaFoundationApi.CreateByteStream(csByteStream); MediaFoundationInterop.MFCreateSourceResolver(out IMFSourceResolver resolver); IMFAttributes streamattributes = mfByteStream as IMFAttributes; mfByteStream.GetLength(out long _length); resolver.CreateObjectFromByteStream(mfByteStream, null, SourceResolverFlags.MF_RESOLUTION_MEDIASOURCE | SourceResolverFlags.MF_RESOLUTION_CONTENT_DOES_NOT_HAVE_TO_MATCH_EXTENSION_OR_MIME_TYPE, null, out _, out object _source);//Turns the stream to IMFMediaSource IMFMediaSource source = _source as IMFMediaSource; source.CreatePresentationDescriptor(out IMFPresentationDescriptor descriptor); MediaFoundationInterop.MFCreateTopology(out IMFTopology topo); descriptor.GetStreamDescriptorCount(out uint sdcount); for (uint i = 0; i < sdcount; i++)//For each stream in the source,creates renderer and adds to the topology. { descriptor.GetStreamDescriptorByIndex(i, out bool IsSelected, out IMFStreamDescriptor sd); if (!IsSelected) { if (SelectAllStream) { descriptor.SelectStream(i); } else { continue; } } sd.GetMediaTypeHandler(out IMFMediaTypeHandler typeHandler); typeHandler.GetMajorType(out Guid streamtype); IMFActivate renderer; if (streamtype == MediaTypes.MFMediaType_Audio) { MediaFoundationInterop.MFCreateAudioRendererActivate(out renderer);//Creates renderer for audio streams } else { continue; } //Creats and equips the topology nodes of the certain stream MediaFoundationInterop.MFCreateTopologyNode(MF_TOPOLOGY_TYPE.MF_TOPOLOGY_SOURCESTREAM_NODE, out IMFTopologyNode sourcenode); sourcenode.SetUnknown(MediaFoundationAttributes.MF_TOPONODE_SOURCE, source); sourcenode.SetUnknown(MediaFoundationAttributes.MF_TOPONODE_PRESENTATION_DESCRIPTOR, descriptor); sourcenode.SetUnknown(MediaFoundationAttributes.MF_TOPONODE_STREAM_DESCRIPTOR, sd); topo.AddNode(sourcenode); MediaFoundationInterop.MFCreateTopologyNode(MF_TOPOLOGY_TYPE.MF_TOPOLOGY_OUTPUT_NODE, out IMFTopologyNode outputnode); outputnode.SetObject(renderer); topo.AddNode(outputnode); sourcenode.ConnectOutput(0, outputnode, 0); } MediaFoundationInterop.MFCreateMediaSession(IntPtr.Zero, out m_Session); m_Session.SetTopology(0, topo); m_eventthread = new Thread(ProcessEvent); m_eventthread.Start(); }
private void Load() { MediaFoundationInterop.MFCreateSourceResolver(out IMFSourceResolver resolver); object unknown; try { resolver.CreateObjectFromURL(URL, SourceResolverFlags.MF_RESOLUTION_MEDIASOURCE | SourceResolverFlags.MF_RESOLUTION_CONTENT_DOES_NOT_HAVE_TO_MATCH_EXTENSION_OR_MIME_TYPE, null, out _, out unknown); } catch { throw new ArgumentException("Unsupported type."); } MediaFoundationInterop.MFCreateMediaSession(IntPtr.Zero, out m_Session); MediaFoundationInterop.MFCreateTopology(out IMFTopology topo); IMFMediaSource source = unknown as IMFMediaSource; source.CreatePresentationDescriptor(out m_pDescriptor); m_pDescriptor.GetUINT64(MediaFoundationAttributes.MF_PD_DURATION, out long dur); m_Duration = dur / 10000000; m_pDescriptor.GetStreamDescriptorCount(out uint sdcount); m_streamcount = (int)sdcount; for (uint i = 0; i < m_streamcount; i++) { m_pDescriptor.GetStreamDescriptorByIndex(i, out bool IsSelected, out IMFStreamDescriptor sd); m_DefaultStreamSelect.Add(IsSelected); switch (StreamSelectFlag) { case StreamSelectFlags.SelectAllStream: if (!IsSelected) { m_pDescriptor.SelectStream(i); } break; case StreamSelectFlags.SelectNone: if (IsSelected) { m_pDescriptor.DeselectStream(i); } break; } sd.GetMediaTypeHandler(out IMFMediaTypeHandler typeHandler); typeHandler.GetMediaTypeByIndex(0, out IMFMediaType mediaType); mediaType.GetMajorType(out Guid streamtype); IMFActivate renderer; if (streamtype == MediaTypes.MFMediaType_Audio) { MediaFoundationInterop.MFCreateAudioRendererActivate(out renderer); mediaType.GetUINT32(MediaFoundationAttributes.MF_MT_AUDIO_SAMPLES_PER_SECOND, out int rate);//SampleRate mediaType.GetUINT32(MediaFoundationAttributes.MF_MT_AUDIO_NUM_CHANNELS, out int channelcount); int samplesize; try { mediaType.GetUINT32(MediaFoundationAttributes.MF_MT_AUDIO_BITS_PER_SAMPLE, out samplesize); } catch (COMException e) { if ((uint)e.HResult != 0xC00D36E6) { throw e; } else { samplesize = 8; } } m_format.Add(new WaveFormat(rate, samplesize, channelcount)); } else { continue; } MediaFoundationInterop.MFCreateTopologyNode(MF_TOPOLOGY_TYPE.MF_TOPOLOGY_SOURCESTREAM_NODE, out IMFTopologyNode sourcenode); sourcenode.SetUnknown(MediaFoundationAttributes.MF_TOPONODE_SOURCE, source); sourcenode.SetUnknown(MediaFoundationAttributes.MF_TOPONODE_PRESENTATION_DESCRIPTOR, m_pDescriptor); sourcenode.SetUnknown(MediaFoundationAttributes.MF_TOPONODE_STREAM_DESCRIPTOR, sd); topo.AddNode(sourcenode); MediaFoundationInterop.MFCreateTopologyNode(MF_TOPOLOGY_TYPE.MF_TOPOLOGY_OUTPUT_NODE, out IMFTopologyNode outputnode); outputnode.SetObject(renderer); topo.AddNode(outputnode); sourcenode.ConnectOutput(0, outputnode, 0); } m_Session.SetTopology(0, topo); m_Eventthread = new Thread(ProcessEvent); m_Eventthread.Start(); }