예제 #1
0
        /// <summary>
        /// Constructs an optimized convolution.
        /// </summary>
        public FastConvolver(float[] impulse, int delay = 0)
        {
            int fftSize = 2 << QMath.Log2Ceil(impulse.Length); // Zero padding for the falloff to have space

            cache  = new FFTCache(fftSize);
            filter = new Complex[fftSize];
            for (int sample = 0; sample < impulse.Length; ++sample)
            {
                filter[sample].Real = impulse[sample];
            }
            filter.InPlaceFFT(cache);
            present    = new Complex[fftSize];
            future     = new float[fftSize + delay];
            this.delay = delay;
        }
예제 #2
0
        /// <summary>
        /// Constructs an optimized convolution.
        /// </summary>
        public DualConvolver(float[] impulse1, float[] impulse2, int delay1 = 0, int delay2 = 0)
        {
            int impulseLength = Math.Max(impulse1.Length, impulse2.Length);
            int fftSize       = 2 << QMath.Log2Ceil(impulseLength); // Zero padding for the falloff to have space

            cache  = new FFTCache(fftSize);
            filter = new Complex[fftSize];
            for (int sample = 0; sample < impulse1.Length; ++sample)
            {
                filter[sample].Real = impulse1[sample];
            }
            for (int sample = 0; sample < impulse2.Length; ++sample)
            {
                filter[sample].Imaginary = impulse2[sample];
            }
            filter.InPlaceFFT(cache);
            present     = new Complex[fftSize];
            future      = new Complex[fftSize + Math.Max(delay1, delay2)];
            this.delay1 = delay1;
            this.delay2 = delay2;
        }
예제 #3
0
        /// <summary>
        /// For E-AC-3, data for multiple blocks is included in an audio frame header.
        /// </summary>
        void AudioFrame()
        {
            expstre      = header.Blocks != 6 || extractor.ReadBit();
            ahte         = header.Blocks == 6 && extractor.ReadBit();
            snroffststr  = extractor.Read(2);
            transproce   = extractor.ReadBit();
            blkswe       = extractor.ReadBit();
            dithflage    = extractor.ReadBit();
            bamode       = extractor.ReadBit();
            frmfgaincode = extractor.ReadBit();
            dbaflde      = extractor.ReadBit();
            skipflde     = extractor.ReadBit();
            spxattene    = extractor.ReadBit();

            if (header.ChannelMode > 1)   // Not mono
            {
                cplstre[0] = true;
                cplinu[0]  = extractor.ReadBit();
                for (int block = 1; block < cplstre.Length; ++block)
                {
                    if (cplstre[block] = extractor.ReadBit())
                    {
                        cplinu[block] = extractor.ReadBit();
                    }
                    else
                    {
                        cplinu[block] = cplinu[block - 1];
                    }
                }
            }
            else
            {
                for (int block = 1; block < cplstre.Length; ++block)
                {
                    cplinu[block] = false;
                }
            }

            // Exponent strategy data init
            if (expstre)
            {
                for (int block = 0; block < cplexpstr.Length; ++block)
                {
                    if (cplinu[block])
                    {
                        cplexpstr[block] = (ExpStrat)extractor.Read(2);
                    }
                    for (int channel = 0; channel < channels.Length; ++channel)
                    {
                        chexpstr[block][channel] = (ExpStrat)extractor.Read(2);
                    }
                }
            }
            else
            {
                int ncplblks = 0;
                for (int block = 0; block < cplinu.Length; ++block)
                {
                    if (cplinu[block])
                    {
                        ++ncplblks;
                    }
                }
                if (header.ChannelMode > 1 && ncplblks > 0)
                {
                    frmcplexpstr = extractor.Read(5);
                }
                for (int channel = 0; channel < channels.Length; ++channel)
                {
                    frmchexpstr[channel] = extractor.Read(5);
                }

                for (int block = 0; block < cplexpstr.Length; ++block)
                {
                    cplexpstr[block] = frmcplexpstr_tbl[frmcplexpstr][block];
                    for (int channel = 0; channel < channels.Length; ++channel)
                    {
                        chexpstr[block][channel] = frmcplexpstr_tbl[frmchexpstr[channel]][block];
                    }
                }
            }

            if (header.LFE)
            {
                for (int block = 0; block < lfeexpstr.Length; ++block)
                {
                    lfeexpstr[block] = extractor.ReadBit();
                }
            }

            // Converter exponent strategy data
            if (header.StreamType == StreamTypes.Independent &&
                (convexpstre = header.Blocks == 6 || extractor.ReadBit()))
            {
                for (int channel = 0; channel < channels.Length; ++channel)
                {
                    convexpstr[channel] = extractor.Read(5);
                }
            }

            // AHT data
            if (ahte)
            {
                throw new UnsupportedFeatureException("AHT");
            }

            // Audio frame SNR offset data
            if (snroffststr == 0)
            {
                frmcsnroffst = extractor.Read(6);
                frmfsnroffst = extractor.Read(4);
            }

            // Transient pre-noise processing data
            if (transproce)
            {
                for (int channel = 0; channel < channels.Length; ++channel)
                {
                    if (chintransproc[channel] = extractor.ReadBit())
                    {
                        transprocloc[channel] = extractor.Read(10);
                        transproclen[channel] = extractor.Read(8);
                    }
                }
            }

            // Spectral extension attenuation data
            if (spxattene)
            {
                for (int ch = 0; ch < channels.Length; ++ch)
                {
                    if (chinspxatten[ch] = extractor.ReadBit())
                    {
                        spxattencod[ch] = extractor.Read(5);
                    }
                }
            }

            if (blkstrtinfoe = header.Blocks != 1 && extractor.ReadBit())
            {
                int nblkstrtbits = (header.Blocks - 1) * (4 + QMath.Log2Ceil(header.WordsPerSyncframe));
                blkstrtinfo = extractor.Read(nblkstrtbits);
            }

            // Syntax state init
            for (int channel = 0; channel < channels.Length; ++channel)
            {
                firstspxcos[channel] = true;
                firstcplcos[channel] = true;
            }
            firstcplleak = true;
        }