在来电时停止和启动音乐

use*_*231 54 android media-player android-activity incoming-call

我已经实现了一个Activity,它从android中的URL播放媒体

为了在传入呼叫进入时添加暂停功能,我创建了一个接收器,在呼叫到来时设置一个变量.活动读取此变量,然后在其onPause()方法中暂停音乐,并且重置是在完成调用并且活动在其onResume()方法中恢复音乐时

只要活动具有焦点,这就可以正常工作.如果我在播放音乐时返回主屏幕然后通话,则不会调用活动的暂停,因此我可以"停止并启动音乐"

这是什么出路?有人实施了一个媒体播放器,以便它一直拦截来电和拨出电话并停止并正确启动音乐?

Kal*_*oer 91

你可以做一些事情:

首先,您可以使用a监听呼叫状态的变化PhoneStateListener.您可以在TelephonyManager中注册侦听器:

PhoneStateListener phoneStateListener = new PhoneStateListener() {
    @Override
    public void onCallStateChanged(int state, String incomingNumber) {
        if (state == TelephonyManager.CALL_STATE_RINGING) {
            //Incoming call: Pause music
        } else if(state == TelephonyManager.CALL_STATE_IDLE) {
            //Not in call: Play music
        } else if(state == TelephonyManager.CALL_STATE_OFFHOOK) {
            //A call is dialing, active or on hold
        }
        super.onCallStateChanged(state, incomingNumber);
    }
};
TelephonyManager mgr = (TelephonyManager) getSystemService(TELEPHONY_SERVICE);
if(mgr != null) {
    mgr.listen(phoneStateListener, PhoneStateListener.LISTEN_CALL_STATE);
}
Run Code Online (Sandbox Code Playgroud)

请记住在不再需要使用以下情况时取消注册侦听器PhoneStateListener.LISTEN_NONE:

TelephonyManager mgr = (TelephonyManager) getSystemService(TELEPHONY_SERVICE);
if(mgr != null) {
    mgr.listen(phoneStateListener, PhoneStateListener.LISTEN_NONE);
}
Run Code Online (Sandbox Code Playgroud)

有关更多信息,请阅读文档.

你可以做的另一件事就是收听广播android.intent.action.PHONE_STATE.它将包含额外的内容TelephonyManager.EXTRA_STATE,它将为您提供有关呼叫的信息.看一下这里的文档.

请注意,android.permission.READ_PHONE_STATE在这两种情况下你都需要 - 许可.

  • 您还应该请求AudioManager :: requestAudioFocus(),因此当焦点被授予时,您可以播放流; AudioManager.OnAudioFocusChangeListener :: onAudioFocusChange(int)取决于应用程序应该暂停/播放的更改,请参阅AudioManager和OnAudioFocusChangeListener文档. (3认同)
  • 是的,听众需要在播放音乐的活动中注册,如果活动失去焦点(只要它没有被杀死),它就会被调用.但是,使用服务播放音乐而不是活动可能更合适,因为活动可能会被杀死. (2认同)
  • 这对我有用.我创建了一个服务并在其中注册了phonestatelistener.现在,即使我的活动失去焦点(如用户按下主页按钮进入主屏幕),也会检测到来电并且我能够停止和启动音乐 (2认同)

小智 49

我认为AudioManager是最好,最快的解决方案.这里有我的实​​现示例:

public class MyActivity extends Activity implements OnAudioFocusChangeListener {

private AudioManager mAudioManager;

@Override
public void onCreate(Bundle savedInstanceState) {
    ...
    mAudioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
    mAudioManager.requestAudioFocus(this, AudioManager.STREAM_MUSIC, AudioManager.AUDIOFOCUS_GAIN);
    ...
}

@Override
 public void onDestroy(){
     super.onDestroy();
     ...
     mAudioManager.abandonAudioFocus(this);
     ...
 }


@Override
public void onAudioFocusChange(int focusChange) {
    if(focusChange<=0) {
        //LOSS -> PAUSE
    } else {
        //GAIN -> PLAY
    }
}   
Run Code Online (Sandbox Code Playgroud)

}

我希望它对你有帮助:-)

  • 那些想要控制不仅是GSM接入而且还要控制VOIP呼叫的人,比如Skype,Facebook消息,然后按照@mickesource解释的那样. (6认同)
  • 我已经在我的音乐服务中实现了这一点,如"公共类ServiceMusicPlayer扩展服务实现AudioManager.OnAudioFocusChangeListener",并且非常感谢! (3认同)

小智 13

或者 - 您可以尝试接收器应用程序.

创建一个名为CallRecord.java的Receiver

package com.example.callreceiver;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.telephony.PhoneStateListener;
import android.telephony.TelephonyManager;

public class CallReceiver extends BroadcastReceiver{
    TelephonyManager telManager;
    Context context;

@Override
public void onReceive(Context context, Intent intent) {


    this.context=context;

    telManager = (TelephonyManager)context.getSystemService(Context.TELEPHONY_SERVICE);
    telManager.listen(phoneListener, PhoneStateListener.LISTEN_CALL_STATE);

}

private final PhoneStateListener phoneListener = new PhoneStateListener() {
    @Override
    public void onCallStateChanged(int state, String incomingNumber) {
        try {
            switch (state) {
            case TelephonyManager.CALL_STATE_RINGING: {
                //PAUSE
            break;
            }
            case TelephonyManager.CALL_STATE_OFFHOOK: {

            break;
            }
            case TelephonyManager.CALL_STATE_IDLE: {
                //PLAY
            break;
            }
            default: { }
            }
            } catch (Exception ex) {

            }
        }
    };
 }
Run Code Online (Sandbox Code Playgroud)

然后在manifest.xml文件中添加此行以在App上注册它

<receiver android:name="CallReceiver" >
        <intent-filter>
            <action android:name="android.intent.action.PHONE_STATE" >
            </action>
        </intent-filter>
    </receiver>
Run Code Online (Sandbox Code Playgroud)

  • 我不喜欢那个接收器的名字:) (2认同)

小智 12

我认为requestAudioFocus()应该能够自动处理这种情况.您无需明确检查呼叫状态.

Audio Focus本质上是合作的.也就是说,预期(并且极力鼓励)应用程序遵守音频焦点指南,但系统不会强制执行这些规则.如果应用程序想要在失去音频焦点后播放嘈杂的音乐,系统中的任何内容都不会阻止它.但是,用户更有可能遇到不良体验,并且更有可能卸载行为不当的应用程序.

要请求音频焦点,您必须从AudioManager调用requestAudioFocus(),如下例所示:

AudioManager audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
int result = audioManager.requestAudioFocus(this, AudioManager.STREAM_MUSIC,
AudioManager.AUDIOFOCUS_GAIN);

if (result != AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
    // could not get audio focus.
}
Run Code Online (Sandbox Code Playgroud)

  • 这是根据文档推荐的方式:http://developer.android.com/intl/ru/guide/topics/media/mediaplayer.html (2认同)

Ant*_*hov 5

恕我直言的更好方法在关闭文档中描述:http://developer.android.com/training/managing-audio/audio-focus.html