Ejemplo n.º 1
0
        public void PacketIn(OggPacket packet)
        {
            if (packet == null)
            {
                return;
            }

            ClearReturnedBody();

            var bytes            = packet.PacketData.Length;
            var lacingValueCount = (int)(bytes / 255f + 1);

            // make sure we have the buffer storage
            ExpandBody(bytes);
            ExpandLacing(lacingValueCount);

            // Copy in the submitted packet.
            Array.Copy(packet.PacketData, 0, _bodyData, _bodyFill, bytes);
            _bodyFill += bytes;

            // Store lacing vals for this packet
            int i;

            for (i = 0; i < lacingValueCount - 1; i++)
            {
                _lacingValues[_lacingFill + i]  = 255;
                _granuleValues[_lacingFill + i] = _granulePosition;
            }

            _lacingValues[_lacingFill + i] = (int)(bytes % 255f);
            _granulePosition = _granuleValues[_lacingFill + i] = packet.GranulePosition;

            // flag the first segment as the beginning of the packet
            _lacingValues[_lacingFill] |= 0x100;

            _lacingFill += lacingValueCount;

            if (packet.EndOfStream)
            {
                Finished = true;
            }
        }
Ejemplo n.º 2
0
        public bool PacketOut(out OggPacket packet)
        {
            packet = null;

            // Have we started?
            if (!_preExtrapolated)
            {
                return(false);
            }

            // Are we done?
            if (_eofFlag == -1)
            {
                return(false);
            }

            var codecSetup = _vorbisInfo.CodecSetup;

            // By our invariant, we have lW, W and centerW set.  Search for
            // the next boundary so we can determine nW (the next window size)
            // which lets us compute the shape of the current block's window
            // we do an envelope search even on a single blocksize; we may still
            // be throwing more bits at impulses, and envelope search handles
            // marking impulses too.
            var testWindow =
                _centerWindow +
                codecSetup.BlockSizes[_currentWindow] / 4 +
                codecSetup.BlockSizes[1] / 2 +
                codecSetup.BlockSizes[0] / 4;

            var bp = _lookups.EnvelopeLookup.Search(_pcm, _pcmCurrent, _centerWindow, testWindow);

            if (bp == -1)
            {
                if (_eofFlag == 0)
                {
                    return(false); // not enough data currently to search for a full int block
                }
                _nextWindow = 0;
            }
            else
            {
                _nextWindow = codecSetup.BlockSizes[0] == codecSetup.BlockSizes[1] ? 0 : bp;
            }

            var centerNext = _centerWindow
                             + codecSetup.BlockSizes[_currentWindow] / 4
                             + codecSetup.BlockSizes[_nextWindow] / 4;

            // center of next block + next block maximum right side.
            var blockbound = centerNext + codecSetup.BlockSizes[_nextWindow] / 2;

            // Not enough data yet
            if (_pcmCurrent < blockbound)
            {
                return(false);
            }

            // copy the vectors; ampPtr uses the local storage in vb
            // ampPtr tracks 'strongest peak' for later psychoacoustics
            var n = codecSetup.BlockSizes[_currentWindow] / 2;

            _lookups.PsyGlobalLookup.DecayAmpMax(n, _vorbisInfo.SampleRate);

            var pcmEnd      = codecSetup.BlockSizes[_currentWindow];
            var pcm         = new float[_pcm.Length][];
            var beginWindow = _centerWindow - codecSetup.BlockSizes[_currentWindow] / 2;

            for (var channel = 0; channel < _pcm.Length; channel++)
            {
                pcm[channel] = new float[pcmEnd];
                Array.Copy(_pcm[channel], beginWindow, pcm[channel], 0, pcm[channel].Length);
            }

            // handle eof detection: eof==0 means that we've not yet received EOF eof>0
            // marks the last 'real' sample in pcm[] eof<0  'no more to do'; doesn't get here
            var eofFlag = false;

            if (_eofFlag != 0)
            {
                if (_centerWindow >= _eofFlag)
                {
                    _eofFlag = -1;
                    eofFlag  = true;
                }
            }

            var data = PerformAnalysis(pcm, pcmEnd);

            packet = new OggPacket(data, eofFlag, _granulePosition, _sequence++);

            if (!eofFlag)
            {
                AdvanceStorageVectors(centerNext);
            }

            return(true);
        }