android 2.3 & 4.2 Audio静音过程分析

来源:互联网 发布:js 解压缩 编辑:程序博客网 时间:2024/05/01 04:02

Android静音过程分析

当接通电话时,有时候我们需要mute我们的microphone.

在系统里是如何工作的.下面简要分析一下:


通过以下结构体来完成新的audiohardware 与 legacy audiohardware的兼容

typedefstruct audio_config audio_config_t

typedefstruct audio_hw_device audio_hw_device_t;

typedefstruct audio_stream_in audio_stream_in_t;

typedefstruct audio_stream_out audio_stream_out_t;


structlegacy_audio_module {

structaudio_module module;

};

structlegacy_stream_out {

structaudio_stream_out stream;

AudioStreamOut*legacy_out;

};

structlegacy_stream_in {

structaudio_stream_in stream;

AudioStreamIn*legacy_in;

};

structlegacy_audio_device {

structaudio_hw_device device;

structAudioHardwareInterface *hwif;

};

classAudioStreamInALSA : public AudioStreamIn, public RefBase

classAudioStreamOutALSA : public AudioStreamOut, public RefBase

classAudioHardware : public AudioHardwareBase




  最终由AudioHardware.cpp set_mic_mute 函数完成mute功能。

 AudioHardware::setMicMute(bool state)

 if (mic_volume_ctl) {
                        mic_volume_max = mixer_ctl_get_range_max(mic_volume_ctl);
                        mic_volume_min = mixer_ctl_get_range_min(mic_volume_ctl);
                        volume_num = mixer_ctl_get_num_values(mic_volume_ctl);
                        for ( i = 0; i < volume_num; i++) {
                                if (mMicMute)
                                        mixer_ctl_set_value(mic_volume_ctl, i, mic_volume_min);
                                else
                                        mixer_ctl_set_value(mic_volume_ctl, i, mic_volume_max);

但是有些麦克的硬件不能完成真正的静音,也就是设置到最小音量值,依然保留很小的声音。

为了实现完全的静音,可以从软件层面来实现。

status_t AudioHardware::AudioStreamInALSA::getNextBuffer(struct resampler_buffer *buffer)
 {
+    bool state;
+    mHardware->getMicMute(&state);
+    if (state)
+       memset(buffer->i16, 0, buffer->frame_count*2);
 
 }


android 2.3 静音过程分析


尤其需要注意文件PhoneUtils.java中的以下函数:

================================================

private static void setMuteInternal(Phone phone, boolean muted) {

if (DBG) log("setMuteInternal: " + muted);

Context context = phone.getContext();

boolean routeToAudioManager =

context.getResources().getBoolean(R.bool.send_mic_mute_to_AudioManager);

if (routeToAudioManager) {

AudioManager audioManager =

(AudioManager) phone.getContext().getSystemService(Context.AUDIO_SERVICE);

if (DBG) log("setMicrophoneMute: " + muted);

audioManager.setMicrophoneMute(muted);

} else {

phone.setMute(muted);

=================================

It will call different branch according to the <R.bool.send_mic_mute_to_AudioManager>value defined at android/packages/apps/phone/res/values/config.xml

By default: <bool name="send_mic_mute_to_AudioManager">false</bool>

If the value is false, it will call [ phone.setMute(muted); ];

if the value is true, it will call audioManager.setMicrophoneMute(muted);



    

0 0