代码拉取完成,页面将自动刷新
#include "sound.h"
sound::sound()
{
}
#define BUFFER_SIZE 1024
unsigned int buffer_time = 1000000; // 设置缓冲区时间为 1000 ms
unsigned int period_time = 100000; // 设置周期时间为 100 ms
// 计算 RMS (均方根)
double sound:: calculate_rms(const int16_t *buffer, size_t len)
{
double sum = 0.0;
for (size_t i = 0; i < len; ++i)
{
sum += buffer[i] * buffer[i];
}
return sqrt(sum / len);
}
// 计算 dB (分贝)
double sound::calculate_db(double rms, double reference)
{
reference = 32768.0;
return 20.0 * log10(rms / reference);
}
void sound::main_sound()
{
snd_pcm_t *capture_handle;
snd_pcm_hw_params_t *hw_params;
int16_t buffer[BUFFER_SIZE];
unsigned int rate = 44100; // 采样率 44100 Hz
int err;
// 打开默认音频设备进行捕获
if ((err = snd_pcm_open(&capture_handle, "hw:0,1", SND_PCM_STREAM_CAPTURE, 0)) < 0)
{
std::cerr << "Cannot open audio device (" << snd_strerror(err) << ")" << std::endl;
return ;
}
// 设置音频设备硬件参数
snd_pcm_hw_params_alloca(&hw_params);
snd_pcm_hw_params_any(capture_handle, hw_params);
snd_pcm_hw_params_set_access(capture_handle, hw_params, SND_PCM_ACCESS_RW_INTERLEAVED);
snd_pcm_hw_params_set_format(capture_handle, hw_params, SND_PCM_FORMAT_S16_LE);
snd_pcm_hw_params_set_rate_near(capture_handle, hw_params, &rate, 0);
snd_pcm_hw_params_set_channels(capture_handle, hw_params, 1); // 单声道
snd_pcm_hw_params_set_buffer_time_near(capture_handle, hw_params, &buffer_time, 0);
snd_pcm_hw_params_set_period_time_near(capture_handle, hw_params, &period_time, 0);
if ((err = snd_pcm_hw_params(capture_handle, hw_params)) < 0)
{
std::cerr << "Cannot set hardware parameters (" << snd_strerror(err) << ")" << std::endl;
return ;
}
// 准备捕获
if ((err = snd_pcm_prepare(capture_handle)) < 0)
{
std::cerr << "Cannot prepare audio interface for use (" << snd_strerror(err) << ")" << std::endl;
return ;
}
// 累积音频数据,直到积累了1秒的数据
std::vector<int16_t> accumulated_data;
size_t samples_per_second = rate; // 1秒内的样本数
while (true)
{
err = snd_pcm_readi(capture_handle, buffer, BUFFER_SIZE);
if (err == -EPIPE)
{
// 处理缓冲区溢出
snd_pcm_prepare(capture_handle);
std::cerr << "Buffer overrun occurred" << std::endl;
}
else if (err < 0)
{
std::cerr << "Read from audio interface failed (" << snd_strerror(err) << ")" << std::endl;
break;
}
else
{
// 将读取的数据累积到向量中
accumulated_data.insert(accumulated_data.end(), buffer, buffer + err);
// 如果累积的数据达到1秒,则处理数据
if (accumulated_data.size() >= samples_per_second)
{
double rms = calculate_rms(accumulated_data.data(), accumulated_data.size());
double db = calculate_db(rms);
qDebug()<<db<<"111111111";
sound_db = db;
std::cout << "RMS: " << rms << ", dB: " << db << std::endl;
// 清空累积的数据,准备下一次读取
accumulated_data.clear();
break;
}
}
}
// 关闭音频设备
snd_pcm_close(capture_handle);
return ;
}
此处可能存在不合适展示的内容,页面不予展示。您可通过相关编辑功能自查并修改。
如您确认内容无涉及 不当用语 / 纯广告导流 / 暴力 / 低俗色情 / 侵权 / 盗版 / 虚假 / 无价值内容或违法国家有关法律法规的内容,可点击提交进行申诉,我们将尽快为您处理。