diff --git a/ArcFormats/AudioWMA.cs b/ArcFormats/AudioWMA.cs
index 1d33e783..dca846a3 100644
--- a/ArcFormats/AudioWMA.cs
+++ b/ArcFormats/AudioWMA.cs
@@ -112,43 +112,25 @@ namespace GameRes.Formats
}
///
- /// Custom implementation of MediaFoundationReader.
- /// NAudio uses MFCreateMFByteStreamOnStreamEx API call which is not available in Windows 7.
+ /// Custom implementation of StreamMediaFoundationReader.
+ /// Extends it with Duration property.
///
- internal class CustomMediaFoundationReader : MediaFoundationReader
+ internal class CustomMediaFoundationReader : StreamMediaFoundationReader
{
- private readonly Stream m_stream;
-
///
/// Specifies the duration of a presentation, in 100-nanosecond units.
///
public long Duration { get; private set; }
public CustomMediaFoundationReader (Stream stream, MediaFoundationReaderSettings settings = null)
+ : base (stream, settings)
{
- m_stream = stream;
- Init (settings);
}
protected override IMFSourceReader CreateReader (MediaFoundationReaderSettings settings)
{
- const int MF_SOURCE_READER_ALL_STREAMS = -2;
- const int MF_SOURCE_READER_FIRST_AUDIO_STREAM = -3;
-
- IMFByteStream byteStream;
- MFCreateMFByteStreamOnStream (new ComStream (m_stream), out byteStream);
- var source_reader = MediaFoundationApi.CreateSourceReaderFromByteStream (byteStream);
-
- source_reader.SetStreamSelection (MF_SOURCE_READER_ALL_STREAMS, false);
- source_reader.SetStreamSelection (MF_SOURCE_READER_FIRST_AUDIO_STREAM, true);
- source_reader.SetCurrentMediaType (MF_SOURCE_READER_FIRST_AUDIO_STREAM, IntPtr.Zero, new MediaType
- {
- MajorType = MediaTypes.MFMediaType_Audio,
- SubType = settings.RequestFloatOutput ? AudioSubtypes.MFAudioFormat_Float : AudioSubtypes.MFAudioFormat_PCM
- }.MediaFoundationObject);
-
+ var source_reader = base.CreateReader (settings);
Duration = GetDuration (source_reader);
-
return source_reader;
}
@@ -173,96 +155,5 @@ namespace GameRes.Formats
Marshal.FreeHGlobal (variantPtr);
}
}
-
- [DllImport("mfplat.dll", ExactSpelling = true, PreserveSig = false)]
- static extern void MFCreateMFByteStreamOnStream (IStream pStream, out IMFByteStream ppByteStream);
- }
-
- ///
- /// Implementation of Com IStream.
- /// NAudio implementation is inaccessible (private).
- ///
- internal class ComStream : ProxyStream, IStream
- {
- public ComStream (Stream stream) : base (Synchronized (stream))
- {
- }
-
- void IStream.Clone (out IStream ppstm)
- {
- ppstm = null;
- }
-
- void IStream.Commit (int grfCommitFlags)
- {
- Flush();
- }
-
- void IStream.CopyTo (IStream pstm, long cb, IntPtr pcbRead, IntPtr pcbWritten)
- {
- }
-
- void IStream.LockRegion (long libOffset, long cb, int dwLockType)
- {
- }
-
- void IStream.Read (byte[] pv, int cb, IntPtr pcbRead)
- {
- if (!CanRead)
- throw new InvalidOperationException ("Stream is not readable.");
- int read = Read (pv, 0, cb);
- if (pcbRead != IntPtr.Zero)
- Marshal.WriteInt32 (pcbRead, read);
- }
-
- void IStream.Revert()
- {
- }
-
- void IStream.Seek (long dlibMove, int dwOrigin, IntPtr plibNewPosition)
- {
- SeekOrigin origin = (SeekOrigin) dwOrigin;
- long val = Seek (dlibMove, origin);
- if (plibNewPosition != IntPtr.Zero)
- Marshal.WriteInt64 (plibNewPosition, val);
- }
-
- void IStream.SetSize (long libNewSize)
- {
- SetLength (libNewSize);
- }
-
- void IStream.Stat (out System.Runtime.InteropServices.ComTypes.STATSTG pstatstg, int grfStatFlag)
- {
- const int STGM_READ = 0x00000000;
- const int STGM_WRITE = 0x00000001;
- const int STGM_READWRITE = 0x00000002;
-
- var tmp = new System.Runtime.InteropServices.ComTypes.STATSTG { type = 2, cbSize = Length, grfMode = 0 };
-
- if (CanWrite && CanRead)
- tmp.grfMode |= STGM_READWRITE;
- else if (CanRead)
- tmp.grfMode |= STGM_READ;
- else if (CanWrite)
- tmp.grfMode |= STGM_WRITE;
- else
- throw new ObjectDisposedException ("Stream");
-
- pstatstg = tmp;
- }
-
- void IStream.UnlockRegion (long libOffset, long cb, int dwLockType)
- {
- }
-
- void IStream.Write (byte[] pv, int cb, IntPtr pcbWritten)
- {
- if (!CanWrite)
- throw new InvalidOperationException ("Stream is not writeable.");
- Write (pv, 0, cb);
- if (pcbWritten != IntPtr.Zero)
- Marshal.WriteInt32 (pcbWritten, cb);
- }
}
}