【问题标题】:TelephonyManager deprecated listen() CALL_STATE_RINGING on android 12TelephonyManager 在 android 12 上弃用了 listen() CALL_STATE_RINGING
【发布时间】:2021-10-14 12:49:26
【问题描述】:

当我的应用在前台时,我想听听是否有来电。

以前是这样,但现在不推荐使用 listen():

val tm = context.getSystemService(Context.TELEPHONY_SERVICE) as TelephonyManager
            tm.listen(object : PhoneStateListener() {
                override fun onCallStateChanged(state: Int, phoneNumber: String?) {
                    super.onCallStateChanged(state, phoneNumber)
                    when (state) {
                        TelephonyManager.CALL_STATE_RINGING -> transcribingAudioConsumer.stopTranscription(null)
                        else -> {}
                    }
                }
            }, PhoneStateListener.LISTEN_CALL_STATE)

我尝试了类似的方法,但找不到正确的实现方法。

         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
                        tm.registerTelephonyCallback({ it.run() }, MyPhoneStateListener())
                    }
  @RequiresApi(Build.VERSION_CODES.S)
    class MyPhoneStateListener : TelephonyCallback(), TelephonyCallback.CallStateListener {
        override fun onCallStateChanged(state: Int) {
            when (state) {
                TelephonyManager.CALL_STATE_RINGING -> {
                    Timber.e("omg RING")
                }

                TelephonyManager.CALL_STATE_OFFHOOK -> {
                    Timber.e("omg hook")
                }
                TelephonyManager.CALL_STATE_IDLE -> {
                    Timber.e("omg idle")
                }
            }
        }
    }

【问题讨论】:

    标签: android telephony telephonymanager android-12


    【解决方案1】:

    由于从 api 31 android 12 开始不推荐使用 listen 方法,因此我采用了一种简单的方法来收听电话回调。

    val telephonyManager: TelephonyManager =
        context.getSystemService(Context.TELEPHONY_SERVICE) as TelephonyManager
    
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
        telephonyManager.registerTelephonyCallback(
            context.mainExecutor,
            object : TelephonyCallback(), TelephonyCallback.CallStateListener {
                override fun onCallStateChanged(state: Int) {
                }
            })
    } else {
        telephonyManager.listen(object : PhoneStateListener() {
            override fun onCallStateChanged(state: Int, phoneNumber: String?) {
            }
        }, PhoneStateListener.LISTEN_CALL_STATE)
    }
    

    请注意,新回调不包含电话号码。 至少对于广播接收器,电话号码可以通过

    intent.extras.getString("incoming_number")
    

    【讨论】:

    • 添加后,我在 Android 12 中收到安全异常,我们需要在 Android 12 中添加任何权限吗?
    • @RaviGadipudi,你需要检查READ_PHONE_STATE权限private fun isReadPhoneStateGranted() = ActivityCompat.checkSelfPermission(this.context, Manifest.permission.READ_PHONE_STATE) == PackageManager.PERMISSION_GRANTED
    • 是的,通过 Android 12 文档的行为变化找到了它。谢谢回复。 @OrcunSevsay
    • 谁能把这段代码转换成java?这是因为我不懂 kotlin。提前致谢。
    【解决方案2】:

    我使用了你所做的,android 12 模拟器也可以工作。我将它用于低于 android 12 的版本,我希望它可以工作。

        class MyPhoneStateListener() : PhoneStateListener() {
        override fun onCallStateChanged(state: Int, incomingNumber: String) {
            when (state) {
                TelephonyManager.CALL_STATE_IDLE -> {
                    Log.e("MyPhoneStateListener", "IDLE")
                
                }
                TelephonyManager.CALL_STATE_OFFHOOK -> {
                    Log.e("MyPhoneStateListener", "OFFHOOK")
                }
                TelephonyManager.CALL_STATE_RINGING -> {
                    Log.e("MyPhoneStateListener", "RINGING")
                }
            }
        }
    
    
    }
    

    我用这个来听电话


     phoneListener = MyPhoneStateListener()
                 var telephony: TelephonyManager? = null
                    telephony = context
                        .getSystemService(TELEPHONY_SERVICE) as TelephonyManager?
    
                    telephony!!.listen(phoneListener, PhoneStateListener.LISTEN_CALL_STATE)
    

    最后你应该像这里一样创建一个 ServiceReceiver 类。 Add PhoneStateListener

    Android 12:我在这里找到了一个示例。我希望这个对你有用。 https://note.com/koh_49/n/n94a5c2ae3aa2

      @RequiresApi(Build.VERSION_CODES.S)
    class CustomTelephonyCallback(private val func: (state: Int) -> Unit) :
    TelephonyCallback(),
    TelephonyCallback.CallStateListener {
        override fun onCallStateChanged(state: Int) {
            func(state)
        }
    }
    @RequiresApi(Build.VERSION_CODES.S)
    fun registerCustomTelephonyCallback(){
    
         var callback: CustomTelephonyCallback? = null
    
    
            (getSystemService(Context.TELEPHONY_SERVICE) as? TelephonyManager)?.
            registerTelephonyCallback(
                mainExecutor,
                CustomTelephonyCallback {
                    //
                    var state=it
                 
    
                }.also {
                    callback = it
                }
            )
    
    
    }
    
      
    

    清单

        <receiver android:name=".data.service.receiver.ServiceReceiver"
            android:exported="false">
            <intent-filter>
                <action android:name="android.intent.action.PHONE_STATE" />
            </intent-filter>
        </receiver>
    

    服务接收者

    import android.content.BroadcastReceiver
    import android.content.Context
    import android.content.Intent
    import android.os.Build
    import android.telephony.TelephonyCallback
    import android.telephony.TelephonyManager
    import androidx.annotation.RequiresApi
    import androidx.core.content.ContextCompat.getMainExecutor
    
    
    class ServiceReceiver: BroadcastReceiver() {
    @RequiresApi(Build.VERSION_CODES.S)
    override fun onReceive(context: Context?, intent: Intent?) {
    
        registerCustomTelephonyCallback(context)
    
    
    }
    
    @RequiresApi(Build.VERSION_CODES.S)
    class CustomTelephonyCallback(private val func: (state: Int) -> Unit) :
        TelephonyCallback(),
        TelephonyCallback.CallStateListener {
        override fun onCallStateChanged(state: Int) {
            func(state)
        }
    }
    
    @RequiresApi(Build.VERSION_CODES.S)
    fun registerCustomTelephonyCallback(context: Context?){
    
        var callback: CustomTelephonyCallback? = null
    
        (context?.getSystemService(Context.TELEPHONY_SERVICE) as? TelephonyManager)?.
        registerTelephonyCallback(
            getMainExecutor(context),
            CustomTelephonyCallback {
                //
                var state=it
    
    
            }.also {
                callback = it
            }
        )
    
    
    }
    

    }

    【讨论】:

    • telephony.listen() 和 PhoneStateListener() 已弃用。我知道它仍在 Android 12 上运行,但我想与 registerTelephonyCallback(Executor, TelephonyCallback) 集成。
    • Deprecated Use registerTelephonyCallback(Executor, TelephonyCallback). Params: listener – The PhoneStateListener object to register (or unregister) events – The telephony state(s) of interest to the listener, as a bitwise-OR combination of PhoneStateListener LISTEN_ flags. 您可能会在 TelephonyManager.java listen(..) 类下看到已弃用和建议消息
    • 感谢您的回答。是的,我在项目中使用它时看到它已弃用“telephony.listen()”,然后我开始研究。我找到了你的问题和解决方案。这种使用“registerTelephonyCallback(Executor,TelephonyCallback”不正确?我现在将您的解决方案用于 android 12
    • 我更新了答案。我的项目中没有接收器类。我写了这个并尝试了它现在可以工作了。@Orcun Sevsay
    • 我分享了一个 Java 示例。希望它可以帮助你@Saurabh
    【解决方案3】:

    服务接收器(Java)

    import android.content.BroadcastReceiver;
    import android.content.Context;
    import android.content.Intent;
    import android.os.Build;
    import android.telephony.TelephonyCallback;
    import android.telephony.TelephonyManager;
    
    public class ServiceReceiver extends BroadcastReceiver {
    
    @RequiresApi(api = Build.VERSION_CODES.S)
    @Override
    public void onReceive(Context context, Intent intent) {
        registerCustomTelephonyCallback(context);
    }
    
    @RequiresApi(Build.VERSION_CODES.S)
    class CustomTelephonyCallback extends TelephonyCallback implements TelephonyCallback.CallStateListener {
        private CallBack mCallBack;
    
        public CustomTelephonyCallback(CallBack callBack) {
            mCallBack = callBack;
        }
    
        @Override
        public void onCallStateChanged(int state) {
    
            mCallBack.callStateChanged(state);
    
        }
    }
    
    
    @RequiresApi(Build.VERSION_CODES.S)
    public void registerCustomTelephonyCallback(Context context) {
        TelephonyManager telephony = (TelephonyManager) context
                .getSystemService(Context.TELEPHONY_SERVICE);
    
        telephony.registerTelephonyCallback(context.getMainExecutor(), new CustomTelephonyCallback(new CallBack() {
            @Override
            public void callStateChanged(int state) {
    
                int myState=state;
    
            }
        }));
    
    
    }
    
    interface CallBack {
        void callStateChanged(int state);
    }
    

    }

    【讨论】:

    • 谢谢,但从未调用过 onReceive。我正在 android 模拟器上对其进行测试。
    • 编写的代码仅适用于android 12。请确保您的设备是android 12。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-12-15
    • 1970-01-01
    • 2012-03-02
    • 2022-11-15
    相关资源
    最近更新 更多