Android:未经许可的来电监听器

时间:2017-03-14 11:33:53

标签: android phone-call

我知道我们可以通过带过滤器的广播接收器来收听电话状态

  

动作android:name =" android.intent.action.PHONE_STATE"

但这种方式需要许可

  

uses-permission android:name =" android.permission.READ_PHONE_STATE"

如何在没有此权限的情况下确定传入的GSM通话?

P.S。

我确定这可能是因为Whatsapp正在做这件事。
 当我在Whatsapp音频电话上谈话然后接到gsm电话时 - whatsapp检查它并设置自己的电话暂停。他们如何理解需要设置暂停?

Whatsapp在Manifest文件中具有READ_PHONE_STATE权限,但是我检查了Android 6上的调用并且没有授予此权限。此权限已被禁用。

如果禁用此权限,我的Receiver将无法接收操作 android.intent.action.PHONE_STATE ,并且PhoneStateListener无效。

5 个答案:

答案 0 :(得分:10)

我在没有此许可的情况下找到了解决方案。

首先(当我们的sip call开始时)我们需要使用lisener

请求音频焦点
 mAudioManager.requestAudioFocus(afChangeListener, AudioManager.STREAM_VOICE_CALL, AudioManager.AUDIOFOCUS_GAIN);

afChangeListener可以告诉我们然后某些人改变了音频焦点,然后我们可以检查当前的音频通道。如果当前模式是AudioManager.MODE_IN_CALL或AudioManager.MODE_RINGTONE,那么我们就知道gsm调用已经开始。

AudioManager.OnAudioFocusChangeListener afChangeListener =
        new AudioManager.OnAudioFocusChangeListener() {
            public void onAudioFocusChange(int focusChange) {

                if (focusChange == AudioManager.AUDIOFOCUS_LOSS) {
                    // Permanent loss of audio focus
                    // Pause playback immediately
                } else if (focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT) {
                    ScheduledExecutorService scheduler = App.getInstance().obtainScheduler();
                    scheduler.schedule(() -> {
                         Logging.i(TAG, "onAudioFocusChange defer mode = " + mAudioManager.getMode());
                         switch (mAudioManager.getMode()) {
                             case AudioManager.MODE_RINGTONE:
                             case AudioManager.MODE_IN_CALL:
                                 //**there we can start standby mode**
                                 break;
                         }
                    }, 100, TimeUnit.MILLISECONDS);

                } else if (focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK) {
                    Logging.i(TAG, "onAudioFocusChange AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK");
                    // Lower the volume, keep playing
                } else if (focusChange == AudioManager.AUDIOFOCUS_GAIN) {
                    // Your app has been granted audio focus again
                    //**there we can stop standby mode**
                }

            }
        };

答案 1 :(得分:1)

首先,whatsapp使用了获得电话状态所需的许可

<uses-permission android:name="android.permission.READ_PHONE_STATE" />

这是WhatsApp清单文件link

你可以看到他们已经添加并使用了它们。

Android本身提供了使用广播接收器处理它的最佳解决方案。您应该使用这些,否则您的系统将是hacky。

按照这些link使用广播接收器来检测电话。

希望这些可以帮到你。

答案 2 :(得分:0)

当Android设备收到onPause的{​​{1}}电话时,会在电话呼叫被自动呼叫之前显示,并且您可以在那里暂停呼叫。

答案 3 :(得分:0)

您可以使用带有电话号码的onReceive方法和来电的所有详细信息来获取此信息。

答案 4 :(得分:0)

简单回答:

1- 查看来电功能

private boolean isIncomingCall(Context context) {
    AudioManager manager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);
    return manager.getMode() == AudioManager.MODE_IN_CALL || manager.getMode() == AudioManager.MODE_RINGTONE;
}

2- 处理程序每​​ 2 秒重复一次

Handler handler = new Handler();
Runnable runnableCheckOngoingCall;

   runnableCheckOngoingCall = new Runnable() {
        @Override
        public void run() {
            if (handler != null) {
                if (isIncomingCall(ActivityName.this)) {

                    // Write your logic code here

                    handler.removeCallbacks(runnableCheckOngoingCall);
                } else {
                    handler.postDelayed(runnableCheckOngoingCall, 2000);
                }
            }

        }
    };

 handler.postDelayed(runnableCheckOngoingCall, 2000);

3- 销毁活动时不要忘记删除处理程序回调

@Override
public void onDestroy() {
    super.onDestroy();
    if (handler != null)  handler.removeCallbacks(runnableCheckOngoingCall);
}