您的位置:首页 > 新闻 > 资讯 > 网站运营与管理规划书_长沙百度网站推广厂家_网站seo排名优化价格_福建seo搜索引擎优化

网站运营与管理规划书_长沙百度网站推广厂家_网站seo排名优化价格_福建seo搜索引擎优化

2024/12/23 16:11:37 来源:https://blog.csdn.net/qq_42956179/article/details/143178816  浏览:    关键词:网站运营与管理规划书_长沙百度网站推广厂家_网站seo排名优化价格_福建seo搜索引擎优化
网站运营与管理规划书_长沙百度网站推广厂家_网站seo排名优化价格_福建seo搜索引擎优化

文章目录

  • 前言
  • 一、webrtc开启3A
    • 1.3A对象的创建
    • 2. 3A的配置
    • 3.注册到Peerconnection
  • 二、webrtc中3A的调用流程
  • 总结


前言

在上一篇文章中,音频3A——初步了解音频3A,大致介绍了3A的作用、使用场景以及带来了哪些问题,同时列举了一些各个平台常用的3A开源库,再接下来的文章中,博主打算以webrtc(实在过于经典)来介绍具体的3A算法,所以需要读者对于webrtc拥有一定的了解。

由于webrtc过于庞大,3A只是webrtc中的一个模块,并且博主在接下来的文章中会涉及到很多webrtc中具体的实现,所以在正式进入到webrtc 3A算法之前,先介绍webrtc中3A的具体使用流程,以便于有兴趣的读者可以对照具体代码进行查看。

|版本声明:山河君,未经博主允许,禁止转载


一、webrtc开启3A

1.3A对象的创建

webrtc中所有的对外3A接口都在webrtc\src\api\audio\audio_processing.h文件中,创建方法也在里面

class RTC_EXPORT AudioProcessingBuilder {......// Creates an APM instance with the specified config or the default one if// unspecified. Injects the specified components transferring the ownership// to the newly created APM instance - i.e., except for the config, the// builder is reset to its initial state.rtc::scoped_refptr<AudioProcessing> Create();.....
};

通过_audioProcessingPtr = webrtc::AudioProcessingBuilder().Create(); 先创建3A的实例对象

2. 3A的配置

创建实例后,可以选择对应的3A配置,这个配置选项是AudioProcessing的内部类,内部类存在大量的配置选项

class RTC_EXPORT AudioProcessing : public RefCountInterface {public:struct RTC_EXPORT Config {.....};.....}

下面是具体的设置项:

  1. HighPassFilter
struct HighPassFilter {bool enabled = false;bool apply_in_full_band = true;
} high_pass_filter;
  • enabled:开启高通滤波器
  • apply_in_full_band:全屏段使用
  • 备注:过滤低频声音,人耳对于低频声音不敏感,且回声大多是低频
  1. EchoCanceller
struct EchoCanceller {bool enabled = false;bool mobile_mode = false;bool export_linear_aec_output = false;// Enforce the highpass filter to be on (has no effect for the mobile// mode).bool enforce_high_pass_filtering = true;
} echo_canceller;
  • enabled:表示是否启用回声消除。设置为 true 时启用此功能。
  • mobile_mode:表示是否使用移动模式。当为 true 时,会调整算法以适应移动设备的音频特性。
  • export_linear_aec_output:如果设置为 true,将导出线性 AEC 输出。这通常用于调试和分析。
  • enforce_high_pass_filtering:强制开启高通滤波器。此选项在移动模式下没有效果,但在其他情况下有助于去除低频噪声。
  1. NoiseSuppression
 struct NoiseSuppression {bool enabled = false;enum Level { kLow, kModerate, kHigh, kVeryHigh };Level level = kModerate;bool analyze_linear_aec_output_when_available = false;} noise_suppression;
  • enabled:指示是否启用噪声抑制功能。如果设置为 true,则噪声抑制将被应用于音频流。
  • level: 设置噪声抑制的强度。可能的值包括:
    1)kLow: 低级别的噪声抑制,适合较轻的背景噪声。
    2)kModerate: 中等级别的噪声抑制,适用于一般背景噪声。
    3)kHigh: 高级别的噪声抑制,适合较强的背景噪声。
    4)kVeryHigh: 非常高的噪声抑制,适合极其嘈杂的环境。
  • analyze_linear_aec_output_when_available: 指示在可能的情况下是否分析线性回声消除(AEC)输出。当设置为 true 时,噪声抑制算法将尝试分析回声消除的输出,以便更好地去除背景噪声。这可以提高噪声抑制的效果,尤其是在有回声的环境中
  1. TransientSuppression
struct TransientSuppression {bool enabled = false;} transient_suppression;
  • enabled: 指示是否启用瞬态抑制功能。如果设置为 true,则启用瞬态抑制,音频处理模块会尝试检测并减少瞬态噪声。如果设置为 false,则不进行瞬态抑制处理。
  1. GainController1/GainController2
    调整AGC的配置有两个GainController1和GainController2,前者是针对麦克风输入,后者是针对扬声器输出,AGC为了针对不同场景,存在很多参数,比如需要限制增益范围,最大限制等等,这里只针对常用场景进行介绍,有需要的小伙伴可以再根据需要选择
  • enabled:开启增益
  • Mode: 枚举类型,定义增益控制的工作模式:
    1)kAdaptiveAnalog: 适用于有模拟音量控制的设备,结合模拟增益和数字压缩。
    2)kAdaptiveDigital: 适用于没有模拟音量控制的设备,主要在数字域中进行增益调整和压缩。
    3)kFixedDigital: 只启用数字压缩,通过固定增益来处理输入信号,适合信号级别可预测的嵌入式设备。
  • target_level_dbfs: 目标峰值水平,以 dBFs(相对于数字满刻度的分贝)表示。通常使用正值。例如,3 表示目标水平为 -3 dBFs。
  • compression_gain_db: 数字压缩阶段可以施加的最大增益,以 dB 表示。数值越大,压缩效果越强。0 表示不进行压缩,范围为 [0, 90]。
  • enable_limiter:指示是否启用限制器功能。如果启用,压缩阶段会将信号限制在目标水平之下。

配置完成后调用 _audioProcessingPtr->ApplyConfig(config);完成设置。

3.注册到Peerconnection

3A实例创建完成后,在一开始创建peerconnection时就可以注册进去,当然因为3A是独立的模块,也可以在创建媒体引擎时或者开启voiceengine时单独在别的地方进行创建

RTC_EXPORT rtc::scoped_refptr<PeerConnectionFactoryInterface>
CreatePeerConnectionFactory(rtc::Thread* network_thread,rtc::Thread* worker_thread,rtc::Thread* signaling_thread,rtc::scoped_refptr<AudioDeviceModule> default_adm,rtc::scoped_refptr<AudioEncoderFactory> audio_encoder_factory,rtc::scoped_refptr<AudioDecoderFactory> audio_decoder_factory,std::unique_ptr<VideoEncoderFactory> video_encoder_factory,std::unique_ptr<VideoDecoderFactory> video_decoder_factory,rtc::scoped_refptr<AudioMixer> audio_mixer,rtc::scoped_refptr<AudioProcessing> audio_processing,std::unique_ptr<AudioFrameProcessor> audio_frame_processor = nullptr,std::unique_ptr<FieldTrialsView> field_trials = nullptr);

二、webrtc中3A的调用流程

  1. 在创建PeerConnection时把3A实例注册进去后,PeerConnection会记录所有的依赖项
rtc::scoped_refptr<PeerConnectionFactoryInterface> CreatePeerConnectionFactory(rtc::Thread* network_thread,rtc::Thread* worker_thread,rtc::Thread* signaling_thread,rtc::scoped_refptr<AudioDeviceModule> default_adm,rtc::scoped_refptr<AudioEncoderFactory> audio_encoder_factory,rtc::scoped_refptr<AudioDecoderFactory> audio_decoder_factory,std::unique_ptr<VideoEncoderFactory> video_encoder_factory,std::unique_ptr<VideoDecoderFactory> video_decoder_factory,rtc::scoped_refptr<AudioMixer> audio_mixer,rtc::scoped_refptr<AudioProcessing> audio_processing,std::unique_ptr<AudioFrameProcessor> audio_frame_processor,std::unique_ptr<FieldTrialsView> field_trials) {PeerConnectionFactoryDependencies dependencies;.....if (audio_processing) {dependencies.audio_processing = std::move(audio_processing);} else {dependencies.audio_processing = AudioProcessingBuilder().Create();}.....EnableMedia(dependencies);return CreateModularPeerConnectionFactory(std::move(dependencies));
}
  1. 在创建Peerconnection时,会创建连接上下文

// Static
rtc::scoped_refptr<PeerConnectionFactory> PeerConnectionFactory::Create(PeerConnectionFactoryDependencies dependencies) {.......auto context = ConnectionContext::Create(CreateEnvironment(std::move(dependencies.trials),std::move(dependencies.task_queue_factory)),.....
}
  1. 在创建上下文中,会创建媒体引擎MediaEngine,同时把audio_processing传入

ConnectionContext::ConnectionContext(const Environment& env,PeerConnectionFactoryDependencies* dependencies).....media_engine_(dependencies->media_factory != nullptr? dependencies->media_factory->CreateMediaEngine(env_,*dependencies): nullptr),.....
  1. 媒体引擎会MediaEngine ,分别创建音频引擎audio_engine 和视频引擎video_engine ,同时把audio_processing传入音频引擎
std::unique_ptr<MediaEngineInterface> CreateMediaEngine(const Environment& env,PeerConnectionFactoryDependencies& deps) override {auto audio_engine = std::make_unique<WebRtcVoiceEngine>(....auto video_engine = std::make_unique<WebRtcVideoEngine>(....
}
  1. 音频引擎持有3A实例
WebRtcVoiceEngine::WebRtcVoiceEngine(....rtc::scoped_refptr<webrtc::AudioProcessing> audio_processing,.....): .....apm_(audio_processing),....
{...}
  1. 音频引擎audio_engine 初始化时,创建AudioState

void WebRtcVoiceEngine::Init() {
...audio_state_ = webrtc::AudioState::Create(config);
...
}
  1. AudioState拥有AudioTransportImpl实例,同时会把一些资源包括3A实例注册进去
AudioState::AudioState(const AudioState::Config& config): config_(config),audio_transport_(config_.audio_mixer.get(),config_.audio_processing.get(),config_.async_audio_processing_factory.get()) {....
}
  1. 此时AudioTransportImpl会在音频采集和渲染过程中,将近端信号和远端信号塞入到3A里
  • 近端信号的塞入
int32_t AudioTransportImpl::RecordedDataIsAvailable(const void* audio_data,size_t number_of_frames,size_t bytes_per_sample,size_t number_of_channels,uint32_t sample_rate,uint32_t audio_delay_milliseconds,int32_t /*clock_drift*/,uint32_t /*volume*/,bool key_pressed,uint32_t& /*new_mic_volume*/,absl::optional<int64_t>estimated_capture_time_ns) {  ....ProcessCaptureFrame(audio_delay_milliseconds, key_pressed,swap_stereo_channels, audio_processing_,audio_frame.get());....
}
void ProcessCaptureFrame(uint32_t delay_ms,bool key_pressed,bool swap_stereo_channels,AudioProcessing* audio_processing,AudioFrame* audio_frame) {....                     if (audio_processing) {audio_processing->set_stream_delay_ms(delay_ms);audio_processing->set_stream_key_pressed(key_pressed);int error = ProcessAudioFrame(audio_processing, audio_frame);}....
}
int ProcessAudioFrame(AudioProcessing* ap, AudioFrame* frame) {...int result = ap->ProcessStream(frame->data(), input_config, output_config,frame->mutable_data());AudioProcessingStats stats = ap->GetStatistics();...
}
  • 远端信号的塞入
int32_t AudioTransportImpl::NeedMorePlayData(const size_t nSamples,const size_t nBytesPerSample,const size_t nChannels,const uint32_t samplesPerSec,void* audioSamples,size_t& nSamplesOut,int64_t* elapsed_time_ms,int64_t* ntp_time_ms) {....if (audio_processing_) {const auto error =ProcessReverseAudioFrame(audio_processing_, &mixed_frame_);RTC_DCHECK_EQ(error, AudioProcessing::kNoError);}....
}
int ProcessReverseAudioFrame(AudioProcessing* ap, AudioFrame* frame) {
....int result = ap->ProcessReverseStream(frame->data(), input_config,output_config, frame->mutable_data());
....
}

总结

本篇博客是为了在后面更深入的进入到3A算法之前,对于webrtc中3A调用的配置以及3A工作流程的介绍,但是这一系列的博客最终目的是为了介绍3A算法的具体实现,在下一篇博客里,就会进入真正的算法细节了,会有大量的数学公式,建议如果读者想要进一步了解的话,可以先看看博主之前对于音频进阶的文章。

如果对您有所帮助,请帮忙点个赞吧!

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com