private static WaveFormat GetOutputFormat(IWMSyncReader reader, uint outputNumber, uint formatNumber) { IWMOutputMediaProps Props = null; int size = 0; WaveFormat fmt = null; reader.GetOutputFormat(outputNumber, formatNumber, out Props); Props.GetMediaType(IntPtr.Zero, ref size); IntPtr buffer = Marshal.AllocCoTaskMem(Math.Max(size, Marshal.SizeOf(typeof(WM_MEDIA_TYPE)) + Marshal.SizeOf(typeof(WaveFormat)))); try { Props.GetMediaType(buffer, ref size); var mt = (WM_MEDIA_TYPE)Marshal.PtrToStructure(buffer, typeof(WM_MEDIA_TYPE)); if ((mt.majortype == MediaTypes.WMMEDIATYPE_Audio) && (mt.subtype == MediaTypes.WMMEDIASUBTYPE_PCM) && (mt.formattype == MediaTypes.WMFORMAT_WaveFormatEx) && (mt.cbFormat >= WAVE_FORMAT_EX_SIZE)) { fmt = new WaveFormat(44100, 16, 2); Marshal.PtrToStructure(mt.pbFormat, fmt); } else { throw new ArgumentException(string.Format("The format {0} of the output {1} is not a valid PCM format", formatNumber, outputNumber)); } } finally { Marshal.FreeCoTaskMem(buffer); } return(fmt); }
private static uint GetAudioOutputNumber(IWMSyncReader Reader) { uint res = InvalidOuput; uint OutCounts = 0; Reader.GetOutputCount(out OutCounts); for (uint i = 0; i < OutCounts; i++) { IWMOutputMediaProps Props = null; Reader.GetOutputProps(i, out Props); Guid mt; Props.GetType(out mt); if (mt == MediaTypes.WMMEDIATYPE_Audio) { res = i; break; } } return(res); }
private static int[] GetPCMOutputNumbers(IWMSyncReader Reader, uint OutputNumber) { var result = new List <int>(); uint FormatCount = 0; Reader.GetOutputFormatCount(OutputNumber, out FormatCount); int BufferSize = Marshal.SizeOf(typeof(WM_MEDIA_TYPE)) + Marshal.SizeOf(typeof(WaveFormat)); IntPtr buffer = Marshal.AllocCoTaskMem(BufferSize); try { for (int i = 0; i < FormatCount; i++) { IWMOutputMediaProps Props = null; int size = 0; WM_MEDIA_TYPE mt; Reader.GetOutputFormat(OutputNumber, (uint)i, out Props); Props.GetMediaType(IntPtr.Zero, ref size); if (size > BufferSize) { BufferSize = size; Marshal.FreeCoTaskMem(buffer); buffer = Marshal.AllocCoTaskMem(BufferSize); } Props.GetMediaType(buffer, ref size); mt = (WM_MEDIA_TYPE)Marshal.PtrToStructure(buffer, typeof(WM_MEDIA_TYPE)); if ((mt.majortype == MediaTypes.WMMEDIATYPE_Audio) && (mt.subtype == MediaTypes.WMMEDIASUBTYPE_PCM) && (mt.formattype == MediaTypes.WMFORMAT_WaveFormatEx) && (mt.cbFormat >= WAVE_FORMAT_EX_SIZE)) { result.Add(i); } } } finally { Marshal.FreeCoTaskMem(buffer); } return(result.ToArray()); }
private void GetAudioOutput() { int cOutputs = 0; short i; IWMOutputMediaProps pProps = null; AMMediaType pMediaType = null; int cbType = 0; // // Sanity check // if (IsDisposed()) { throw new COMException("Instance has been Disposed", E_Unexpected); } // // Find out the output count // m_pReader.GetOutputCount(out cOutputs); // // Find one audio output. // Note: This sample only shows how to handle one audio output. // If there is more than one audio output, the first one will be picked. // StringBuilder sName = null; for (i = 0; i < cOutputs; i++) { m_pReader.GetOutputProps(i, out pProps); try { // // Find out the space needed for pMediaType // cbType = 0; pMediaType = null; pProps.GetMediaType(pMediaType, ref cbType); // Get the name of the output we'll be using sName = null; short iName = 0; pProps.GetConnectionName(sName, ref iName); sName = new StringBuilder(iName); pProps.GetConnectionName(sName, ref iName); pMediaType = new AMMediaType(); pMediaType.formatSize = cbType - Marshal.SizeOf(typeof(AMMediaType)); // // Get the value for MediaType // pProps.GetMediaType(pMediaType, ref cbType); try { if (MediaType.Audio == pMediaType.majorType) { m_pWfx = new WaveFormatEx(); Marshal.PtrToStructure(pMediaType.formatPtr, m_pWfx); break; } } finally { WMUtils.FreeWMMediaType(pMediaType); } } finally { Marshal.ReleaseComObject(pProps); } } if (i == cOutputs) { throw new COMException("Could not find an audio stream in the specified file", E_Unexpected); } m_dwAudioOutputNum = i; // Only deliver samples for the single output SetStreams(sName.ToString()); }
private void Init(WaveFormat OutputFormat) { m_outputNumber = GetAudioOutputNumber(m_reader); if (m_outputNumber == InvalidOuput) { throw new ArgumentException("An audio stream was not found"); } int[] FormatIndexes = GetPCMOutputNumbers(m_reader, (uint)m_outputNumber); if (FormatIndexes.Length == 0) { throw new ArgumentException("An audio stream was not found"); } if (OutputFormat != null) { m_outputFormatNumber = -1; for (int i = 0; i < FormatIndexes.Length; i++) { WaveFormat fmt = GetOutputFormat(m_reader, (uint)m_outputNumber, (uint)FormatIndexes[i]); if (// (fmt.wFormatTag == OutputFormat.wFormatTag) && (fmt.AverageBytesPerSecond == OutputFormat.AverageBytesPerSecond) && (fmt.BlockAlign == OutputFormat.BlockAlign) && (fmt.Channels == OutputFormat.Channels) && (fmt.SampleRate == OutputFormat.SampleRate) && (fmt.BitsPerSample == OutputFormat.BitsPerSample)) { m_outputFormatNumber = FormatIndexes[i]; m_outputFormat = fmt; break; } } if (m_outputFormatNumber < 0) { throw new ArgumentException("No PCM output found"); } } else { m_outputFormatNumber = FormatIndexes[0]; m_outputFormat = GetOutputFormat(m_reader, (uint)m_outputNumber, (uint)FormatIndexes[0]); } uint OutputCtns = 0; m_reader.GetOutputCount(out OutputCtns); ushort[] StreamNumbers = new ushort[OutputCtns]; WMT_STREAM_SELECTION[] StreamSelections = new WMT_STREAM_SELECTION[OutputCtns]; for (uint i = 0; i < OutputCtns; i++) { m_reader.GetStreamNumberForOutput(i, out StreamNumbers[i]); if (i == m_outputNumber) { StreamSelections[i] = WMT_STREAM_SELECTION.WMT_ON; m_outputStream = StreamNumbers[i]; m_reader.SetReadStreamSamples(m_outputStream, false); } else { StreamSelections[i] = WMT_STREAM_SELECTION.WMT_OFF; } } m_reader.SetStreamsSelected((ushort)OutputCtns, StreamNumbers, StreamSelections); IWMOutputMediaProps Props = null; m_reader.GetOutputFormat((uint)m_outputNumber, (uint)m_outputFormatNumber, out Props); m_reader.SetOutputProps((uint)m_outputNumber, Props); int size = 0; Props.GetMediaType(IntPtr.Zero, ref size); IntPtr buffer = Marshal.AllocCoTaskMem(size); try { WM_MEDIA_TYPE mt; Props.GetMediaType(buffer, ref size); mt = (WM_MEDIA_TYPE)Marshal.PtrToStructure(buffer, typeof(WM_MEDIA_TYPE)); m_sampleSize = mt.lSampleSize; } finally { Marshal.FreeCoTaskMem(buffer); Props = null; } m_seekable = false; m_length = -1; WMHeaderInfo head = new WMHeaderInfo(HeaderInfo); try { m_seekable = (bool)head[WM.g_wszWMSeekable]; // Yuval Naveh ulong nanoDuration = (ulong)head[WM.g_wszWMDuration]; m_duration = new TimeSpan((long)nanoDuration); m_length = SampleTime2BytePosition(nanoDuration); } catch (COMException e) { if (e.ErrorCode != WM.ASF_E_NOTFOUND) { throw (e); } } }
public Metadata GetMetadata(object target) { if (target == null || !(target is string)) { return(null); } string filename = target.ToString(); IWMMetadataEditor2 metadataEditor = null; IWMSyncReader syncReader = null; WMMetadata metadata = new WMMetadata(); try { WMFSDKFunctions.WMCreateEditor(out metadataEditor); metadataEditor.OpenEx(filename, FILE_ACCESS.GENERIC_READ, FILE_SHARE.FILE_SHARE_NONE); IWMHeaderInfo3 header = (IWMHeaderInfo3)metadataEditor; ushort attributeCount; header.GetAttributeCountEx(StreamNumber, out attributeCount); for (int i = 0; i < attributeCount; i++) { MetadataField metadataField = GetAttributeByIndex(header, i); metadata.AddMetadataField(metadataField); } } catch (COMException ex) { // TODO: Logging } finally { if (metadataEditor != null) { metadataEditor.Close(); Marshal.FinalReleaseComObject(metadataEditor); metadataEditor = null; } } try { WMFSDKFunctions.WMCreateSyncReader(IntPtr.Zero, WMT_RIGHTS.WMT_RIGHT_PLAYBACK, out syncReader); syncReader.Open(filename); int outputCount; syncReader.GetOutputCount(out outputCount); IWMOutputMediaProps outputMediaProps = null; for (uint i = 0; i < outputCount; i++) { IWMOutputMediaProps innerOutputMediaProps; syncReader.GetOutputProps(i, out innerOutputMediaProps); Guid type; innerOutputMediaProps.GetType(out type); if (type == WMFSDKFunctions.WMMEDIATYPE_Video) { outputMediaProps = innerOutputMediaProps; break; } } if (outputMediaProps != null) { int pcbType = 0; outputMediaProps.GetMediaType(IntPtr.Zero, ref pcbType); IntPtr mediaTypeBufferPtr = Marshal.AllocHGlobal(pcbType); outputMediaProps.GetMediaType(mediaTypeBufferPtr, ref pcbType); WM_MEDIA_TYPE mediaType = new WM_MEDIA_TYPE(); WMVIDEOINFOHEADER videoInfoHeader = new WMVIDEOINFOHEADER(); Marshal.PtrToStructure(mediaTypeBufferPtr, mediaType); Marshal.FreeHGlobal(mediaTypeBufferPtr); Marshal.PtrToStructure(mediaType.pbFormat, videoInfoHeader); double frameRate = Math.Round((double)10000000 / videoInfoHeader.AvgTimePerFrame, 2); metadata.AddMetadataField(new MetadataField("FrameRate", frameRate)); } } catch (COMException ex) { // TODO: Logging } finally { if (syncReader != null) { syncReader.Close(); Marshal.FinalReleaseComObject(syncReader); syncReader = null; } } return(metadata); }
public void FindAudioOutputFormat(uint outputNum, ref WM_MEDIA_TYPE mediaType, ref Guid subtype, ref WaveFormat waveFormat) { IWMOutputMediaProps readerOutputProps = null; uint bufferSize = (uint)(Marshal.SizeOf(typeof(WM_MEDIA_TYPE)) + Marshal.SizeOf(typeof(WaveFormat))); uint formatCount; Logger.WriteLogMessage("Finding audio output formats for reader, output [" + outputNum + "]."); _reader.GetOutputFormatCount(outputNum, out formatCount); Logger.WriteLogMessage("Reader can produce " + formatCount + " possible audio output formats."); IntPtr buffer = Marshal.AllocCoTaskMem((int)bufferSize); try { for (uint j = 0; j < formatCount; j++) { uint size = 0; _reader.GetOutputFormat(outputNum, j, out readerOutputProps); readerOutputProps.GetMediaType(IntPtr.Zero, ref size); if (size > bufferSize) { bufferSize = size; Marshal.FreeCoTaskMem(buffer); buffer = Marshal.AllocCoTaskMem((int)bufferSize); } readerOutputProps.GetMediaType(buffer, ref size); mediaType = (WM_MEDIA_TYPE)Marshal.PtrToStructure(buffer, typeof(WM_MEDIA_TYPE)); if (mediaType.formattype == FormatTypes.WMFORMAT_WaveFormatEx) { Logger.WriteLogMessage("Walking output format [" + j + "], format type [" + GetFormatTypeName(mediaType.formattype) + "], subtype [" + GetSubTypeName(mediaType.subtype) + "], sample size [" + mediaType.lSampleSize + "]."); // // NOTE: only look for PCM subtypes // if (mediaType.subtype == MediaSubTypes.WMMEDIASUBTYPE_PCM) { subtype = mediaType.subtype; Logger.WriteLogMessage("- Found PCM sub type, grabbing WaveFormat."); waveFormat = (WaveFormat)Marshal.PtrToStructure(mediaType.pbFormat, typeof(WaveFormat)); WaveFormats format = (WaveFormats)waveFormat.wFormatTag; Logger.WriteLogMessage("- format [" + format + "], sample rate [" + waveFormat.nSamplesPerSec + "], bits per sample [" + waveFormat.wBitsPerSample + "], bytes/sec [" + waveFormat.nAvgBytesPerSec + "], channels [" + waveFormat.nChannels + "]."); _reader.SetOutputProps(outputNum, readerOutputProps); break; } } } } finally { Marshal.FreeCoTaskMem(buffer); } Marshal.ReleaseComObject(readerOutputProps); }
public void FindVideoOutputFormat(uint outputNum, ref WM_MEDIA_TYPE mediaType, ref Guid subtype, ref VideoInfoHeader outputVideoInfoHeader) { IWMOutputMediaProps readerOutputProps = null; uint bufferSize = (uint)(Marshal.SizeOf(typeof(WM_MEDIA_TYPE)) + Marshal.SizeOf(typeof(VideoInfoHeader))); uint formatCount; Logger.WriteLogMessage("Finding video output formats for reader, output [" + outputNum + "]."); _reader.GetOutputFormatCount(outputNum, out formatCount); Logger.WriteLogMessage("Reader can produce " + formatCount + " possible video output formats."); IntPtr buffer = Marshal.AllocCoTaskMem((int)bufferSize); try { for (uint j = 0; j < formatCount; j++) { uint size = 0; _reader.GetOutputFormat(outputNum, j, out readerOutputProps); readerOutputProps.GetMediaType(IntPtr.Zero, ref size); if (size > bufferSize) { bufferSize = size; Marshal.FreeCoTaskMem(buffer); buffer = Marshal.AllocCoTaskMem((int)bufferSize); } readerOutputProps.GetMediaType(buffer, ref size); mediaType = (WM_MEDIA_TYPE)Marshal.PtrToStructure(buffer, typeof(WM_MEDIA_TYPE)); if (mediaType.formattype == FormatTypes.WMFORMAT_VideoInfo) { Logger.WriteLogMessage("Walking output format [" + j + "], format type [" + GetFormatTypeName(mediaType.formattype) + "], subtype [" + GetSubTypeName(mediaType.subtype) + "], sample size [" + mediaType.lSampleSize + "]."); // // NOTE: only look for RGB subtypes // if ((mediaType.subtype == MediaSubTypes.WMMEDIASUBTYPE_RGB555) || (mediaType.subtype == MediaSubTypes.WMMEDIASUBTYPE_RGB24) || (mediaType.subtype == MediaSubTypes.WMMEDIASUBTYPE_RGB32)) { Logger.WriteLogMessage("- Found RGB555, RGB24 or RGB32 sub type, grabbing VideoInfoHeader."); subtype = mediaType.subtype; outputVideoInfoHeader = (VideoInfoHeader)Marshal.PtrToStructure(mediaType.pbFormat, typeof(VideoInfoHeader)); Logger.WriteLogMessage("- width [" + outputVideoInfoHeader.bmiHeader.biWidth + "], height [" + outputVideoInfoHeader.bmiHeader.biHeight + "], dwBitrate [" + outputVideoInfoHeader.dwBitRate + "], dwBitErrorRate [" + outputVideoInfoHeader.dwBitErrorRate + "]."); _reader.SetOutputProps(outputNum, readerOutputProps); break; } } } } finally { Marshal.FreeCoTaskMem(buffer); } Marshal.ReleaseComObject(readerOutputProps); }
private void Init(WaveFormat outputFormat) { m_OutputNumber = GetAudioOutputNumber(m_Reader); if (m_OutputNumber == InvalidOuput) { throw new ArgumentException("An audio stream was not found"); } int[] formatIndexes = GetPCMOutputNumbers(m_Reader, (uint)m_OutputNumber); if (formatIndexes.Length == 0) { throw new ArgumentException("An audio stream was not found"); } if (outputFormat != null) { m_OutputFormatNumber = -1; for (int i = 0; i < formatIndexes.Length; i++) { WaveFormat fmt = GetOutputFormat(m_Reader, (uint)m_OutputNumber, (uint)formatIndexes[i]); if ((fmt.wFormatTag == outputFormat.wFormatTag) && (fmt.nAvgBytesPerSec == outputFormat.nAvgBytesPerSec) && (fmt.nBlockAlign == outputFormat.nBlockAlign) && (fmt.nChannels == outputFormat.nChannels) && (fmt.nSamplesPerSec == outputFormat.nSamplesPerSec) && (fmt.wBitsPerSample == outputFormat.wBitsPerSample)) { m_OutputFormatNumber = formatIndexes[i]; m_OutputFormat = fmt; break; } } if (m_OutputFormatNumber < 0) { throw new ArgumentException("No PCM output found"); } } else { m_OutputFormatNumber = formatIndexes[0]; m_OutputFormat = GetOutputFormat(m_Reader, (uint)m_OutputNumber, (uint)formatIndexes[0]); } uint outputCtns = 0; m_Reader.GetOutputCount(out outputCtns); var streamNumbers = new ushort[outputCtns]; var streamSelections = new WMT_STREAM_SELECTION[outputCtns]; for (uint i = 0; i < outputCtns; i++) { m_Reader.GetStreamNumberForOutput(i, out streamNumbers[i]); if (i == m_OutputNumber) { streamSelections[i] = WMT_STREAM_SELECTION.WMT_ON; m_OuputStream = streamNumbers[i]; m_Reader.SetReadStreamSamples(m_OuputStream, false); } else { streamSelections[i] = WMT_STREAM_SELECTION.WMT_OFF; } } m_Reader.SetStreamsSelected((ushort)outputCtns, streamNumbers, streamSelections); IWMOutputMediaProps props = null; m_Reader.GetOutputFormat((uint)m_OutputNumber, (uint)m_OutputFormatNumber, out props); m_Reader.SetOutputProps((uint)m_OutputNumber, props); uint size = 0; props.GetMediaType(IntPtr.Zero, ref size); IntPtr buffer = Marshal.AllocCoTaskMem((int)size); try { props.GetMediaType(buffer, ref size); var mt = (WM_MEDIA_TYPE)Marshal.PtrToStructure(buffer, typeof(WM_MEDIA_TYPE)); m_SampleSize = mt.lSampleSize; } finally { Marshal.FreeCoTaskMem(buffer); props = null; } m_Seekable = false; m_Length = -1; var head = new WMHeaderInfo(HeaderInfo); try { m_Seekable = (bool)head[WM.g_wszWMSeekable]; m_Length = SampleTime2BytePosition((ulong)head[WM.g_wszWMDuration]); } catch (COMException e) { if (e.ErrorCode != WM.ASF_E_NOTFOUND) { throw; } } }