Exemplo n.º 1
0
        private void ReduceBitsPerSample24Ns2(ConvertParams args, DataSubChunk toDsc)
        {
            var ns = new NoiseShaper2[mFsc.numChannels];

            for (int ch = 0; ch < mFsc.numChannels; ++ch)
            {
                ns[ch] = new NoiseShaper2(args.order, args.filter, args.newQuantizationBitrate);
            }

            int bytesPerFrame = mFsc.numChannels * mFsc.bitsPerSample / 8;
            int numFrames     = toDsc.data.Length / bytesPerFrame;

            int readPos  = 0;
            int writePos = 0;

            for (int i = 0; i < numFrames; ++i)
            {
                for (int ch = 0; ch < mFsc.numChannels; ++ch)
                {
                    int sample = 0;

                    sample   = ns[ch].Filter24(ReadSampleValue24(toDsc, readPos));
                    readPos += mFsc.bitsPerSample / 8;

                    WriteSampleValue24(toDsc, writePos, sample);
                    writePos += mFsc.bitsPerSample / 8;
                }
            }
        }
Exemplo n.º 2
0
        public void Convert(ConvertParams args, BinaryWriter bw)
        {
            var toDsc = new DataSubChunk();
            toDsc.Setup(mDsc.subChunk2Size, mDsc.data);

            switch (args.ditherType) {
            case ConvertParams.DitherType.NoiseShaping:
                args.order = 1;
                args.filter = new double[] {1, -1};
                ReduceBitsPerSample24Ns2(args, toDsc);
                break;
            case ConvertParams.DitherType.NoiseShaping2:
                args.order = 2;
                args.filter = new double[] {1, -2, 1};
                ReduceBitsPerSample24Ns2(args, toDsc);
                break;
            case ConvertParams.DitherType.NoiseShapingMash2:
                ReduceBitsPerSample24Mash2(args, toDsc);
                break;
            default:
                ReduceBitsPerSample24Other(args, toDsc);
                break;
            }

            mRcd.Write(bw);
            mFsc.Write(bw);
            toDsc.Write(bw);
        }
Exemplo n.º 3
0
        public void Convert(ConvertParams args, BinaryWriter bw)
        {
            var toDsc = new DataSubChunk();

            toDsc.Setup(mDsc.subChunk2Size, mDsc.data);

            switch (args.ditherType)
            {
            case ConvertParams.DitherType.NoiseShaping:
                args.order  = 1;
                args.filter = new double[] { 1, -1 };
                ReduceBitsPerSample24Ns2(args, toDsc);
                break;

            case ConvertParams.DitherType.NoiseShaping2:
                args.order  = 2;
                args.filter = new double[] { 1, -2, 1 };
                ReduceBitsPerSample24Ns2(args, toDsc);
                break;

            case ConvertParams.DitherType.NoiseShapingMash2:
                ReduceBitsPerSample24Mash2(args, toDsc);
                break;

            default:
                ReduceBitsPerSample24Other(args, toDsc);
                break;
            }

            mRcd.Write(bw);
            mFsc.Write(bw);
            toDsc.Write(bw);
        }
Exemplo n.º 4
0
        private int ReadSampleValue24(DataSubChunk fromDsc, int pos)
        {
            switch (mFsc.bitsPerSample)
            {
            case 16:
                return(256 * fromDsc.GetSampleValue16(pos));

            case 24:
                return(fromDsc.GetSampleValue24(pos));

            default:
                throw new NotImplementedException();
            }
        }
Exemplo n.º 5
0
        private void WriteSampleValue24(DataSubChunk toDsc, int pos, int value24)
        {
            switch (mFsc.bitsPerSample)
            {
            case 16:
                toDsc.SetSampleValue16(pos, (short)(value24 / 256));
                break;

            case 24:
                toDsc.SetSampleValue24(pos, value24);
                break;

            default:
                throw new NotImplementedException();
            }
        }
Exemplo n.º 6
0
        public bool ReadFromFile(BinaryReader br)
        {
            mRcd = null;
            mFsc = null;
            mDsc = null;

            try {
                while (true)
                {
                    var subChunk1Id = br.ReadInt32();
                    switch (subChunk1Id)
                    {
                    case ((int)('R')) + (((int)('I')) << 8) + (((int)('F')) << 16) + (((int)('F')) << 24):
                        mRcd = new RiffChunkDescriptor();
                        if (!mRcd.Read(br))
                        {
                            return(false);
                        }
                        break;

                    case ((int)('f')) + (((int)('m')) << 8) + (((int)('t')) << 16) + (((int)(' ')) << 24):
                        mFsc = new FmtSubChunk();
                        if (!mFsc.Read(br))
                        {
                            return(false);
                        }
                        break;

                    case ((int)('d')) + (((int)('a')) << 8) + (((int)('t')) << 16) + (((int)('a')) << 24):
                        mDsc = new DataSubChunk();
                        if (!mDsc.Read(br))
                        {
                            return(false);
                        }
                        break;

                    default:
                        SkipUnknownChunk(br);
                        break;
                    }
                }
            } catch (EndOfStreamException ex) {
                // 正常終了wwww
            }

            return(mRcd != null && mFsc != null && mDsc != null);
        }
Exemplo n.º 7
0
        private void ReduceBitsPerSample24Mash2(ConvertParams args, DataSubChunk toDsc)
        {
            var mash = new NoiseShaperMash[mFsc.numChannels];

            for (int ch = 0; ch < mFsc.numChannels; ++ch)
            {
                mash[ch] = new NoiseShaperMash(args.newQuantizationBitrate);
            }

            int bytesPerFrame = mFsc.numChannels * mFsc.bitsPerSample / 8;
            int numFrames     = toDsc.data.Length / bytesPerFrame;

            int readPos  = 0;
            int writePos = 0;

            // 1サンプル遅延するので…。
            for (int i = 0; i < numFrames + 1; ++i)
            {
                for (int ch = 0; ch < mFsc.numChannels; ++ch)
                {
                    int sample = 0;

                    if (i < numFrames)
                    {
                        sample   = mash[ch].Filter24(ReadSampleValue24(toDsc, readPos));
                        readPos += mFsc.bitsPerSample / 8;
                    }
                    else
                    {
                        sample = mash[ch].Filter24(0);
                    }

                    if (1 <= i)
                    {
                        WriteSampleValue24(toDsc, writePos, sample);
                        writePos += mFsc.bitsPerSample / 8;
                    }
                }
            }
        }
Exemplo n.º 8
0
        public bool ReadFromFile(BinaryReader br)
        {
            mRcd = null;
            mFsc = null;
            mDsc = null;

            try {
                while (true) {
                    var subChunk1Id = br.ReadInt32();
                    switch (subChunk1Id) {
                    case ((int)('R')) + (((int)('I')) << 8) + (((int)('F')) << 16) + (((int)('F')) << 24):
                        mRcd = new RiffChunkDescriptor();
                        if (!mRcd.Read(br)) {
                            return false;
                        }
                        break;

                    case ((int)('f')) + (((int)('m')) << 8) + (((int)('t')) << 16) + (((int)(' ')) << 24):
                        mFsc = new FmtSubChunk();
                        if (!mFsc.Read(br)) {
                            return false;
                        }
                        break;
                    case ((int)('d')) + (((int)('a')) << 8) + (((int)('t')) << 16) + (((int)('a')) << 24):
                        mDsc = new DataSubChunk();
                        if (!mDsc.Read(br)) {
                            return false;
                        }
                        break;
                    default:
                        SkipUnknownChunk(br);
                        break;
                    }
                }
            } catch (EndOfStreamException ex) {
                // 正常終了wwww
            }

            return mRcd != null && mFsc != null && mDsc != null;
        }
Exemplo n.º 9
0
        private void ReduceBitsPerSample24Other(ConvertParams args, DataSubChunk toDsc)
        {
            uint mask           = 0xffffffff << (24 - args.newQuantizationBitrate);
            uint maskError      = ~mask;
            var  gen            = new RNGCryptoServiceProvider();
            var  gng            = new GaussianNoiseGenerator();
            var  randomNumber   = new byte[3];
            int  noiseMagnitude = (int)Math.Pow(2, (24 - args.newQuantizationBitrate)) / 2;

            Console.WriteLine("D: maskErr={0:X}", maskError);

            int bytesPerFrame = mFsc.numChannels * mFsc.bitsPerSample / 8;
            int numFrames     = toDsc.data.Length / bytesPerFrame;

            int pos = 0;

            for (int i = 0; i < numFrames; ++i)
            {
                for (int ch = 0; ch < mFsc.numChannels; ++ch)
                {
                    double sample = ReadSampleValue24(toDsc, pos);
                    uint   error  = (uint)sample & maskError;
                    sample -= error;

                    switch (args.ditherType)
                    {
                    case ConvertParams.DitherType.Truncate:
                        break;

                    case ConvertParams.DitherType.RpdfDither:
                        gen.GetBytes(randomNumber);
                        int randDither = (int)((randomNumber[0]) + (randomNumber[1] << 8) + (randomNumber[2] << 16) & ~mask);
                        sample += randDither;
                        break;

                    case ConvertParams.DitherType.GaussianDither:
                        float noise = gng.NextFloat();
                        noise  *= noiseMagnitude;
                        sample += (int)noise;
                        break;

                    default:
                        System.Diagnostics.Debug.Assert(false);
                        break;
                    }

                    if (0x7fffff < sample)
                    {
                        sample = 0x7fffff;
                    }
                    if (sample < -0x800000)
                    {
                        sample = -0x800000;
                    }

                    WriteSampleValue24(toDsc, pos, (int)sample);

                    pos += mFsc.bitsPerSample / 8;
                }
            }
        }
Exemplo n.º 10
0
 private int ReadSampleValue24(DataSubChunk fromDsc, int pos)
 {
     switch (mFsc.bitsPerSample) {
     case 16:
         return 256 * fromDsc.GetSampleValue16(pos);
     case 24:
         return fromDsc.GetSampleValue24(pos);
     default:
         throw new NotImplementedException();
     }
 }
Exemplo n.º 11
0
 private void WriteSampleValue24(DataSubChunk toDsc, int pos, int value24)
 {
     switch (mFsc.bitsPerSample) {
     case 16:
         toDsc.SetSampleValue16(pos, (short)(value24 / 256));
         break;
     case 24:
         toDsc.SetSampleValue24(pos, value24);
         break;
     default:
         throw new NotImplementedException();
     }
 }
Exemplo n.º 12
0
        private void ReduceBitsPerSample24Other(ConvertParams args, DataSubChunk toDsc)
        {
            uint mask = 0xffffffff << (24 - args.newQuantizationBitrate);
            uint maskError = ~mask;
            var gen = new RNGCryptoServiceProvider();
            var gng = new GaussianNoiseGenerator();
            var randomNumber = new byte[3];
            int noiseMagnitude = (int)Math.Pow(2, (24 - args.newQuantizationBitrate))/2;

            Console.WriteLine("D: maskErr={0:X}", maskError);

            int bytesPerFrame = mFsc.numChannels * mFsc.bitsPerSample / 8;
            int numFrames = toDsc.data.Length / bytesPerFrame;

            int pos = 0;
            for (int i=0; i < numFrames; ++i) {
                for (int ch=0; ch < mFsc.numChannels; ++ch) {
                    double sample = ReadSampleValue24(toDsc, pos);
                    uint error = (uint)sample & maskError;
                    sample -= error;

                    switch (args.ditherType) {
                    case ConvertParams.DitherType.Truncate:
                        break;
                    case ConvertParams.DitherType.RpdfDither:
                        gen.GetBytes(randomNumber);
                        int randDither = (int)((randomNumber[0]) + (randomNumber[1] << 8) + (randomNumber[2]<<16) & ~mask);
                        sample += randDither;
                        break;
                    case ConvertParams.DitherType.GaussianDither:
                        float noise = gng.NextFloat();
                        noise *= noiseMagnitude;
                        sample += (int)noise;
                        break;
                    default:
                        System.Diagnostics.Debug.Assert(false);
                        break;
                    }

                    if (0x7fffff < sample) {
                        sample = 0x7fffff;
                    }
                    if (sample < -0x800000) {
                        sample = -0x800000;
                    }

                    WriteSampleValue24(toDsc, pos, (int)sample);

                    pos += mFsc.bitsPerSample / 8;
                }
            }
        }
Exemplo n.º 13
0
        private void ReduceBitsPerSample24Ns2(ConvertParams args, DataSubChunk toDsc)
        {
            var ns = new NoiseShaper2[mFsc.numChannels];
            for (int ch=0; ch < mFsc.numChannels; ++ch) {
                ns[ch] = new NoiseShaper2(args.order, args.filter, args.newQuantizationBitrate);
            }

            int bytesPerFrame = mFsc.numChannels * mFsc.bitsPerSample / 8;
            int numFrames = toDsc.data.Length / bytesPerFrame;

            int readPos = 0;
            int writePos = 0;
            for (int i=0; i < numFrames; ++i) {
                for (int ch=0; ch < mFsc.numChannels; ++ch) {
                    int sample = 0;

                    sample = ns[ch].Filter24(ReadSampleValue24(toDsc, readPos));
                    readPos += mFsc.bitsPerSample / 8;

                    WriteSampleValue24(toDsc, writePos, sample);
                    writePos += mFsc.bitsPerSample / 8;
                }
            }
        }
Exemplo n.º 14
0
        private void ReduceBitsPerSample24Mash2(ConvertParams args, DataSubChunk toDsc)
        {
            var mash = new NoiseShaperMash[mFsc.numChannels];
            for (int ch=0; ch < mFsc.numChannels; ++ch) {
                mash[ch] = new NoiseShaperMash(args.newQuantizationBitrate);
            }

            int bytesPerFrame = mFsc.numChannels * mFsc.bitsPerSample / 8;
            int numFrames = toDsc.data.Length / bytesPerFrame;

            int readPos = 0;
            int writePos = 0;

            // 1サンプル遅延するので…。
            for (int i=0; i < numFrames + 1; ++i) {
                for (int ch=0; ch < mFsc.numChannels; ++ch) {
                    int sample = 0;

                    if (i < numFrames) {
                        sample = mash[ch].Filter24(ReadSampleValue24(toDsc, readPos));
                        readPos += mFsc.bitsPerSample / 8;
                    } else {
                        sample = mash[ch].Filter24(0);
                    }

                    if (1 <= i) {
                        WriteSampleValue24(toDsc, writePos, sample);
                        writePos += mFsc.bitsPerSample / 8;
                    }
                }
            }
        }