示例#1
0
        public AudioInfo ReadAudioInfo(Stream stream)
        {
            Contract.Ensures(Contract.Result <AudioInfo>() != null);

            var buffer = new byte[4096];

            using (var decoder = new NativeVorbisDecoder())
            {
                NativeOggStream oggStream     = null;
                var             vorbisComment = new VorbisComment();

                try
                {
                    SafeNativeMethods.VorbisCommentInitialize(out vorbisComment);

                    using (var sync = new NativeOggSync())
                    {
                        OggPage page;

                        do
                        {
                            // Read from the buffer into a page:
                            while (sync.PageOut(out page) != 1)
                            {
                                int bytesRead = stream.Read(buffer, 0, buffer.Length);
                                if (bytesRead == 0)
                                {
                                    throw new IOException(Resources.ReadError);
                                }

                                IntPtr nativeBuffer = sync.Buffer(bytesRead);
                                Marshal.Copy(buffer, 0, nativeBuffer, bytesRead);

                                sync.Wrote(bytesRead);
                            }

                            if (oggStream == null)
                            {
                                oggStream = new NativeOggStream(SafeNativeMethods.OggPageGetSerialNumber(ref page));
                            }

                            oggStream.PageIn(ref page);

                            OggPacket packet;
                            while (oggStream.PacketOut(out packet) == 1)
                            {
                                decoder.HeaderIn(ref vorbisComment, ref packet);

                                VorbisInfo info = decoder.GetInfo();
                                return(new AudioInfo(string.Format(CultureInfo.CurrentCulture,
                                                                   "{0}kbps Ogg Vorbis", info.BitrateNominal / 1000), info.Channels, 0, info.Rate, 0));
                            }
                        } while (SafeNativeMethods.OggPageEndOfStream(ref page) == 0);

                        throw new IOException(Resources.EndOfStreamError);
                    }
                }
                finally
                {
                    oggStream?.Dispose();

                    SafeNativeMethods.VorbisCommentClear(ref vorbisComment);
                }
            }
        }
        public void WriteMetadata(Stream stream, MetadataDictionary metadata, SettingsDictionary settings)
        {
            // This buffer is used for both reading and writing:
            var buffer = new byte[4096];

            using (var tempStream = new MemoryStream())
            {
                NativeOggStream inputOggStream  = null;
                NativeOggStream outputOggStream = null;

                try
                {
                    using (var sync = new NativeOggSync())
                    {
                        OggPage inPage;

                        do
                        {
                            // Read from the buffer into a page:
                            while (sync.PageOut(out inPage) != 1)
                            {
                                int bytesRead = stream.Read(buffer, 0, buffer.Length);
                                if (bytesRead == 0)
                                {
                                    throw new IOException(Resources.ReadError);
                                }

                                IntPtr nativeBuffer = sync.Buffer(bytesRead);
                                Marshal.Copy(buffer, 0, nativeBuffer, bytesRead);

                                sync.Wrote(bytesRead);
                            }

                            // Initialize the input and output streams, if necessary:
                            if (inputOggStream == null)
                            {
                                inputOggStream = new NativeOggStream(SafeNativeMethods.OggPageGetSerialNumber(ref inPage));
                            }
                            if (outputOggStream == null)
                            {
                                outputOggStream = new NativeOggStream(inputOggStream.SerialNumber);
                            }

                            inputOggStream.PageIn(ref inPage);

                            OggPacket packet;
                            while (inputOggStream.PacketOut(out packet) == 1)
                            {
                                // Substitute the new comment packet:
                                if (packet.PacketNumber == 1)
                                {
                                    OggPacket commentPacket = GetCommentPacket(metadata);
                                    outputOggStream.PacketIn(ref commentPacket);
                                }
                                else
                                {
                                    outputOggStream.PacketIn(ref packet);
                                }

                                // Page out each packet, flushing at the end of the header:
                                OggPage outPage;
                                if (packet.PacketNumber == 2)
                                {
                                    while (outputOggStream.Flush(out outPage))
                                    {
                                        WritePage(outPage, tempStream, buffer);
                                    }
                                }
                                else
                                {
                                    while (outputOggStream.PageOut(out outPage))
                                    {
                                        WritePage(outPage, tempStream, buffer);
                                    }
                                }
                            }
                        } while (SafeNativeMethods.OggPageEndOfStream(ref inPage) == 0);

                        // If the end of the stream is reached, overwrite the original file and return:
                        Overwrite(stream, tempStream);
                    }
                }
                finally
                {
                    inputOggStream?.Dispose();
                    outputOggStream?.Dispose();
                }
            }
        }
示例#3
0
        public MetadataDictionary ReadMetadata(Stream stream)
        {
            Contract.Ensures(Contract.Result <MetadataDictionary>() != null);

            var buffer = new byte[4096];

            using (var decoder = new NativeVorbisDecoder())
            {
                NativeOggStream oggStream     = null;
                var             vorbisComment = new VorbisComment();

                try
                {
                    SafeNativeMethods.VorbisCommentInitialize(out vorbisComment);

                    using (var sync = new NativeOggSync())
                    {
                        OggPage page;

                        do
                        {
                            // Read from the buffer into a page:
                            while (sync.PageOut(out page) != 1)
                            {
                                int bytesRead = stream.Read(buffer, 0, buffer.Length);
                                if (bytesRead == 0)
                                {
                                    throw new IOException(Resources.ReadError);
                                }

                                IntPtr nativeBuffer = sync.Buffer(bytesRead);
                                Marshal.Copy(buffer, 0, nativeBuffer, bytesRead);

                                sync.Wrote(bytesRead);
                            }

                            if (oggStream == null)
                            {
                                oggStream = new NativeOggStream(SafeNativeMethods.OggPageGetSerialNumber(ref page));
                            }

                            oggStream.PageIn(ref page);

                            OggPacket packet;
                            while (oggStream.PacketOut(out packet) == 1)
                            {
                                decoder.HeaderIn(ref vorbisComment, ref packet);

                                if (packet.PacketNumber == 1)
                                {
                                    return(new VorbisCommentToMetadataAdapter(vorbisComment));
                                }
                            }
                        } while (SafeNativeMethods.OggPageEndOfStream(ref page) == 0);

                        throw new IOException(Resources.EndOfStreamError);
                    }
                }
                finally
                {
                    oggStream?.Dispose();

                    SafeNativeMethods.VorbisCommentClear(ref vorbisComment);
                }
            }
        }