Esempio n. 1
0
        public VirtualFlacTrack(string flacImage, VirtualTrack track)
        {
            track_ = track;

            inStream_ = new FlacStream(flacImage, FlacStream.StreamMode.OpenExisting, FlacStream.StreamAccessMode.Read);
            inStream_.BeforeFrameDataRead += new FrameCallback(inStream__BeforeFrameDataRead);
            inStream_.Decode();
            outStream_ = new FlacStream(Path.GetTempFileName(), FlacStream.StreamMode.CreateNew, FlacStream.StreamAccessMode.Both);

            ReadHeader();
        }
Esempio n. 2
0
        public static VirtualTrack[] GetTracks(string virtualFlacFile)
        {
            List<VirtualTrack> tracks_ = new List<VirtualTrack>();

            XmlDocument doc = new XmlDocument();
            doc.Load(virtualFlacFile);

            string imageName = doc.SelectSingleNode("/virtualFlac/flacImage").Attributes["uri"].Value;
            XmlNodeList list = doc.SelectNodes("/virtualFlac/flacImage/tracks/track");

            string dir = Directory.GetParent(virtualFlacFile).FullName;

            foreach (XmlNode n in list)
            {
                VirtualTrack vt = new VirtualTrack();
                vt.LoadFromXml(dir, n);
                vt.ImageFile = imageName;
                tracks_.Add(vt);
            }
            return tracks_.ToArray();
        }
        private void ProcessFrame(FlacStream inStream, Frame frame, long offset)
        {
            long startSample = frame.Header.StartingSampleNumber;
            long endSample = startSample + frame.Header.BlockSize;
            int frameSize = (int)(inStream.Reader.Debug_BytesRead - offset);

            if (blockingStrategy_ == -1)
            {
                blockingStrategy_ = frame.Header.BlockingStrategy;
            }
            else
            {
                // whole stream must have the same blocking strategy
                Debug.Assert(frame.Header.BlockingStrategy == blockingStrategy_);
            }

            if (currentTrack_ != null)
            {
                long start = startSample;
                long end = endSample;

                if (start <= currentTrack_.EndSample && currentTrack_.EndSample <= end)
                {
                    end = currentTrack_.EndSample;
                    WriteFrame(frame, currentTrack_, start, end, frameSize, startSample, offset);
                    currentTrack_.TotalSamples = sampleCount_;

                    currentTrack_.Frames.Values[0].CalculateVirtualBlockSizeDifference(currentTrack_.StartSample, true);
                    currentTrack_.Frames.Values[currentTrack_.Frames.Count - 1].CalculateVirtualBlockSizeDifference(currentTrack_.EndSample, false);

                    RefreshFrame(inStream, ref frame, offset);
                    currentTrack_ = null;
                    goto loop;
                }
                else
                {
                    WriteFrame(frame, currentTrack_, start, end, frameSize, startSample, offset);
                    goto done;
                }
            }
            else
            {
                goto loop;
            }

            loop:
            foreach (ITrackInfo file in tracksInfo_)
            {
                long start = startSample;
                long end = endSample;
                if (start <= file.StartSample && file.StartSample <= end)
                {
                    VirtualTrack lastTrack = null;
                    if (virtualTracks_.Count > 0)
                    {
                        lastTrack = virtualTracks_[virtualTracks_.Count - 1];
                    }
                    if (lastTrack != null)
                    {
                        Debug.Assert(lastTrack.Frames.Values[lastTrack.Frames.Count - 1].imageEndSample == endSample);
                    }

                    currentTrack_ = new VirtualTrack();
                    currentTrack_.StartSample =file.StartSample;
                    currentTrack_.EndSample = file.EndSample;
                    currentTrack_.FileName = file.Name;
                    currentTrack_.Size = TRACK_HEADER_SIZE;
                    virtualTracks_.Add(currentTrack_);

                    sampleCount_ = 0;

                    start = file.StartSample;

                    bool next = false;
                    if (start <= file.EndSample && file.EndSample <= end)
                    {
                        // track ends in the same frame
                        end = file.EndSample;

                        // write (probably) partial first frame of track
                        WriteFrame(frame, currentTrack_, start, end, frameSize, startSample, offset);
                        RefreshFrame(inStream, ref frame, offset);
                        next = true;
                    }
                    else
                    {
                        // write (probably) partial first frame of track
                        WriteFrame(frame, currentTrack_, start, end, frameSize, startSample, offset);
                    }
                    if (next)
                    {
                        continue;
                    }
                    break;
                }
            }
            done:
            return;
        }
        private void WriteFrame(Frame frame, VirtualTrack track, long start, long end, int frameSize, long imageStartSample, long offset)
        {
            TrackFrame trackFrame = new TrackFrame(offset, frameSize, imageStartSample);
            trackFrame.imageBlockSize = frame.Header.BlockSize;
            trackFrame.startSample = sampleCount_;
            trackFrame.virtualOffset = track.Size;

            int count = (int)(end - start);

            int virtualSize;
            int sizeDifference = 0;
            if (frame.Header.BlockSize == count)
            {
                sizeDifference = flac.Io.UTF8Encoder.GetUtf8ULong(sampleCount_).Length - frame.Header.SampleIdSize;
                virtualSize = frameSize + sizeDifference;
            #if DEBUG
                frame.Header.StartingSampleNumber = sampleCount_;
                frame.Header.BlockingStrategy = FrameHeader.BLOCKING_STRATEGY_VARIABLE;

                outStream_.Writer.Truncate(0);
                frame.Write(outStream_);

                Debug.Assert(virtualSize == outStream_.Writer.Debug_BytesWritten);
            #endif
            }
            else
            {
                frame.Header.StartingSampleNumber = sampleCount_;
                frame.Header.BlockingStrategy = FrameHeader.BLOCKING_STRATEGY_VARIABLE;
                frame.Header.BlockSize = count;

                outStream_.Writer.Truncate(0);
                frame.Write(outStream_, (int)(start - imageStartSample), count);
                virtualSize = Convert.ToInt32(outStream_.Writer.Debug_BytesWritten);
                sizeDifference = virtualSize - frameSize;
            }
            trackFrame.sizeDifference = sizeDifference;
            track.Frames.Add(trackFrame.virtualOffset, trackFrame);

            track.Size += virtualSize;

            track.MinBlockSize = Math.Min(track.MinBlockSize, frame.Header.BlockSize);
            track.MaxBlockSize = Math.Max(track.MaxBlockSize, frame.Header.BlockSize);
            track.MinFrameSize = (int)Math.Min(track.MinFrameSize, virtualSize);
            track.MaxFrameSize = (int)Math.Max(track.MaxFrameSize, virtualSize);

            sampleCount_ += frame.Header.BlockSize;
        }