获取麦克风音量分贝值


实习公司让我用C++ vs编辑工具做一个获取电脑麦克风分贝值的工具。我在网上查了一下相关的源码很少,几乎不能用。我就试着写了一个。其实没有什么技术含量,只不过就是调用一下windowAPI。重要的还是计算分贝的算法。

我先展现一下计算分贝的代码:

 1 int CMicDlg:: getPcmDB(const unsigned char* pcmdata, size_t size) 
 2 {
 3 
 4     int db = 0;
 5     short int value = 0;
 6     double sum = 0;
 7     for (int i = 0; i < size; i += 2)
 8     {
 9         memcpy(&value, pcmdata + i, 2); //获取2个字节的大小(值)  
10         sum += abs(value); //绝对值求和  
11     }
12     sum = sum / (size / 2); //求平均值(2个字节表示一个振幅,所以振幅个数为:size/2个)  
13     if (sum > 0)
14     {
15         db = (int)(20.0 * log10(sum));
16     }
17     return db;
18 }
View Code

这是计算声音分贝值的函数

用到的公式  

公式说明

参数:Pref:就是声音总的振幅最大值;Prms:就是当前声音的振幅值;Lp:就是我们需要的声音分贝值了。

计算分贝值我有一个很好的链接他写比较好https://www.cnblogs.com/waimen/p/9062814.html

其实分贝值的计算本就没有什么物理意义。它只不过就是把很大数简短的表示出来。

这是录音的代码:

变量定义:

HWAVEIN hWaveIn;  //输入设备
WAVEFORMATEX waveform; //采集音频的格式,结构体
BYTE* pBuffer1;//采集音频时的数据缓存
WAVEHDR wHdr1; //采集音频时包含数据缓存的结构体
HANDLE          wait;
View Code

初始化变量:

1     waveform.wFormatTag = WAVE_FORMAT_PCM;//声音格式为PCM
2     waveform.nSamplesPerSec = 8000;//采样率,16000次/秒
3     waveform.wBitsPerSample = 16;//采样比特,16bits/次
4     waveform.nChannels = 1;//采样声道数,2声道
5     waveform.nAvgBytesPerSec = 16384;//每秒的数据率,就是每秒能采集多少字节的数据
6     waveform.nBlockAlign = 2;//一个块的大小,采样bit的字节数乘以声道数
7     waveform.cbSize = 0;//一般为0
View Code

开始录音

 1 int CMicDlg::GetAudio()
 2 {   
 3     
 4     wait = CreateEvent(NULL, 0, 0, NULL);
 5     //使用waveInOpen函数开启音频采集
 6     waveInOpen(&hWaveIn, WAVE_MAPPER, &waveform, (DWORD_PTR)wait, 0L, CALLBACK_EVENT);
 7     //建立两个数组(这里可以建立多个数组)用来缓冲音频数据
 8     DWORD bufsize = 1024;//每次开辟1k的缓存存储录音数据
 9    
10         //结合音频解码和网络传输可以修改为实时录音播放的机制以实现对讲功能
11         pBuffer1 = new BYTE[bufsize];
12         wHdr1.lpData = (LPSTR)pBuffer1;
13         wHdr1.dwBufferLength = bufsize;
14         wHdr1.dwBytesRecorded = 0;
15         wHdr1.dwUser = 0;
16         wHdr1.dwFlags = 0;
17         wHdr1.dwLoops = 1;
18         waveInPrepareHeader(hWaveIn, &wHdr1, sizeof(WAVEHDR));//准备一个波形数据块头用于录音
19         waveInAddBuffer(hWaveIn, &wHdr1, sizeof(WAVEHDR));//指定波形数据块为录音输入缓存
20         waveInStart(hWaveIn);//开始录音
21         Sleep(1000);
22       
23         CString mic;
24         int sum = getPcmDB(pBuffer1, 1024);
25         mic.Format(_T("%d"), sum );
26         edit.SetWindowTextW(mic);
27         waveInReset(hWaveIn);//重置输入
28         delete[]pBuffer1;
29    // waveInClose(hWaveIn);
30     return 0;
31 }
View Code

代码逻辑:

我用公式计算出声波一段的分贝值,每一秒计算一次。

我用的是mfc里的onTimer()函数来实现的。


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM