⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 __waveinput_soundstudiofrm.cs

📁 Programing SoundStudioCS
💻 CS
📖 第 1 页 / 共 2 页
字号:
        }

        void ComputeFFT(WaveBuffer wbuf)
        {
            if (GetAudioData(wbuf.AudioData, wbuf.BytesRecorded, _wfmt))
            {
                // adjust FFT Sample to next power 2 but fill data with silence
                uint pow2Samples = FFT.NextPowerOfTwo(_numSamples);
                if (pow2Samples != _numSamples)
                {
                    double dsilence = 0.0;
                    if (_wfmt.BitsPerSample == 8)
                    {
                        dsilence = 128.0;
                    }
                    for (uint ii = _numSamples; ii < pow2Samples; ii++)
                    {
                        RealIn[ii] = dsilence;
                    }
                    _numSamples = pow2Samples;
                }

                // You may want to add 'USE_FFTLIB' under the project settings (Build->General tab)
                // to get better performance
#if USE_FFTLIB
                // Do the FFT
                FFTLib.ComputeD(_numSamples, RealIn, null, RealOut, ImagOut, false);
                // We can skip N/2 to N samples (mirror frequencies) - Digital samples are real integer
                FFTLib.NormD(_numSamples / 2, RealOut, ImagOut, AmplOut);
#else
                FFT.Compute(_numSamples, RealIn, null, RealOut, ImagOut, false);
                FFT.Norm(_numSamples / 2, RealOut, ImagOut, AmplOut);
#endif

                double maxAmpl = (_wfmt.BitsPerSample == 8) ? (127.0 * 127.0) : (32767.0 * 32767.0);

                // update meter
                int centerFreq = (int)(_wfmt.SamplesPerSecond / 2);
                for (int i = 0; i < NUM_FREQUENCY; ++i)
                {
                    if (METER_FREQUENCY[i] > centerFreq)
                        _meterData[i] = 0;
                    else
                    {
                        int indice = (int)(METER_FREQUENCY[i] * _numSamples / _wfmt.SamplesPerSecond);
                        int metervalue = (int)(100+ 20.0 * Math.Log10(AmplOut[indice] / maxAmpl));
                        _meterData[i] = metervalue;
                    }
                }
                peakMeterCtrl1.SetData(_meterData, 0, NUM_FREQUENCY);
                _numSamples = 0; // ready to do it again
            }
            else
            {
                DumpDebugMessage("GET Audio data failed.");
            }
        }

        bool GetAudioData(IntPtr ptr, int cbSize, WaveFormat wfmt)
        {
            bool samplesReady = false;
            if (cbSize == 0)
                return false; // no data
            switch (wfmt.BitsPerSample)
            {
                case 8:
                    {
                        // NOTE: waveData member is necessary to prevent using 'unsafe' code block
                        Marshal.Copy(ptr, waveData, 0, (int)cbSize);
                        if (wfmt.Channels == 1) // mono
                        {
                            for (uint i = 0; i < cbSize; ++i)
                            {
                                RealIn[i] = (double)((waveData[i] - 128) << 6);// Out = (In-128)*64
                            }
                            _numSamples = (uint)cbSize;
                        }
                        else if (wfmt.Channels == 2) // stereo
                        {
                            // Stereo has Right+Left channels
                            int Samples = cbSize >> 1;
                            for (uint i = 0, j = 0; i < Samples; ++i, j += 2)
                            {
                                RealIn[i] = (double)((waveData[j] - 128) << 6); // Out = (In-128)*64
                                // LeftIn[i] = (double)((waveData[j+1]-128)<<6); // Out = (In-128)*64
                            }
                            _numSamples = (uint)Samples;
                        }
                        samplesReady = (_numSamples != 0);
                    }
                    break;
                case 16:
                    {
                        // NOTE: waveData member is necessary to prevent using 'unsafe' code block
                        Marshal.Copy(ptr, waveData, 0, (int)cbSize);
                        if (wfmt.Channels == 1) // mono
                        {
                            int Samples = cbSize >> 1;
                            for (uint i = 0, j = 0; i < Samples; ++i, j += 2)
                            {
                                short val = (short)unchecked(((waveData[j + 1] << 8) + waveData[j]));
                                RealIn[i] = (double)val;
                            }
                            _numSamples = (uint)Samples;
                        }
                        else if (wfmt.Channels == 2) // stereo
                        {
                            // Stereo has Right+Left channels
                            int Samples = cbSize >> 2;
                            for (uint i = 0, j = 0; i < Samples; ++i, j += 4)
                            {
                                short val = unchecked((short)((waveData[j + 1] << 8) + waveData[j])); // right
                                RealIn[i] = (double)val;
                                // val = unchecked((short)((waveData[j+3] << 8) + waveData[j+2])); // left
                            }
                            _numSamples = (uint)Samples;
                        }
                        samplesReady = (_numSamples != 0);
                    }
                    break;
                default:
                    System.Diagnostics.Debug.Assert(false, "Format not supported"); // not supported
                    break;
            }
            return samplesReady;
        }
        bool PutAudioData(IntPtr pbData, int cbSize, int recvBytes, WaveFormat wfmt)
        {
            bool samplesReady = true;
            switch (wfmt.BitsPerSample)
            {
                case 8:
                    {
                        // fill with silence - no smoothing
                        if (cbSize > recvBytes)
                        {
                            MemorySet(pbData, 0x80, (cbSize - recvBytes));
                        }
                    }
                    break;
                case 16:
                default:
                    {
                        // fill with silence - no smoothing
                        if (cbSize > recvBytes)
                        {
                            MemorySet(pbData, 0x00, (cbSize - recvBytes));
                        }
                    }
                    break;
            }
            return samplesReady;
        }
        void MemorySet(IntPtr ptrData, byte val, int cb)
        {
            byte[] silence = { val };
            for (int i = 0; i < cb; ++i)
            {
                IntPtr ptrDest = (IntPtr)((int)ptrData + i);
                Marshal.Copy(silence, 0, ptrDest, 1);
            }
        }

        void CreateWaveInput()
        {
            if (_waveInput == null)
            {
                _waveInput = new WaveInDevice();
                _waveInput.SetNotifyHandler(this);
            }
        }
        void ReleaseWaveInput()
        {
            if (_waveInput != null)
            {
                _waveInput.Close();
                ReleaseBuffers();
                _waveInput.SetNotifyHandler(null);
                _waveInput = null;
            }
        }
        void CreateBuffers()
        {
            if (_waveBuffer == null)
            {
                _waveBuffer = new WaveBuffer[MAX_BUFFERS];
                for (int ii = 0; ii < MAX_BUFFERS; ++ii)
                {
                    _waveBuffer[ii] = new WaveBuffer();
                    _waveBuffer[ii].Allocate((int)_bufferSize);
                }
            }
        }
        void ReleaseBuffers()
        {
            if (_waveBuffer != null)
            {
                for (int ii = 0; ii < MAX_BUFFERS; ++ii)
                {
                    _waveBuffer[ii].Dispose();
                }
                _waveBuffer = null;
            }
        }

        void AllocFFTData()
        {
            int numSamples = (int)_bufferSize / _wfmt.BlockAlign;
            RealIn = new double[numSamples];
            RealOut = new double[numSamples];
            ImagOut = new double[numSamples];
            AmplOut = new double[numSamples];
            waveData = new byte[_bufferSize];
        }
        void ReleaseFFTData()
        {
            RealIn = null;
            RealOut = null;
            ImagOut = null;
            AmplOut = null;
            waveData = null;
        }

        [ConditionalAttribute("DEBUG")]
        void DumpWaveErrorMessage(string message, int error)
        {
            StringBuilder sError = new StringBuilder(256);
            WaveInput.waveInGetErrorTextW(error, sError, 256);
            Trace.WriteLine(string.Format("{0} {1}", message, sError.ToString()));
        }

        [ConditionalAttribute("DEBUG")]
        void DumpDebugMessage(string message)
        {
            Trace.WriteLine(message);
        }

    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -