如何在Android中挂断电话?

问题描述 投票:46回答:8

我正在开发一个应用程序,其中我们需要做的一件事情是控制拨出电话,至少可以阻止它从我们的应用程序中停止。

我已经尝试使用现有活动中的Intent.ACTION_CALL

Intent callIntent = new Intent(Intent.ACTION_CALL, Uri.parse("tel:" + phoneNumber)); 
startActivity(callIntent); 

但是通过API似乎不允许停止调用。

您能建议一些解决方法吗?

例如:在通话中启用飞行模式?只是一个例子;此hack对我不起作用。

android telephony telephonymanager
8个回答
27
投票
编辑:对于Android P或更高版本,请参阅:https://stackoverflow.com/a/51121175/450148

尝试一下:

((我使用了Reflection to access advanced telephony features并修改了一些内容)

// required permission <uses-permission android:name="android.permission.CALL_PHONE"/> try { //String serviceManagerName = "android.os.IServiceManager"; String serviceManagerName = "android.os.ServiceManager"; String serviceManagerNativeName = "android.os.ServiceManagerNative"; String telephonyName = "com.android.internal.telephony.ITelephony"; Class telephonyClass; Class telephonyStubClass; Class serviceManagerClass; Class serviceManagerStubClass; Class serviceManagerNativeClass; Class serviceManagerNativeStubClass; Method telephonyCall; Method telephonyEndCall; Method telephonyAnswerCall; Method getDefault; Method[] temps; Constructor[] serviceManagerConstructor; // Method getService; Object telephonyObject; Object serviceManagerObject; telephonyClass = Class.forName(telephonyName); telephonyStubClass = telephonyClass.getClasses()[0]; serviceManagerClass = Class.forName(serviceManagerName); serviceManagerNativeClass = Class.forName(serviceManagerNativeName); Method getService = // getDefaults[29]; serviceManagerClass.getMethod("getService", String.class); Method tempInterfaceMethod = serviceManagerNativeClass.getMethod( "asInterface", IBinder.class); Binder tmpBinder = new Binder(); tmpBinder.attachInterface(null, "fake"); serviceManagerObject = tempInterfaceMethod.invoke(null, tmpBinder); IBinder retbinder = (IBinder) getService.invoke(serviceManagerObject, "phone"); Method serviceMethod = telephonyStubClass.getMethod("asInterface", IBinder.class); telephonyObject = serviceMethod.invoke(null, retbinder); //telephonyCall = telephonyClass.getMethod("call", String.class); telephonyEndCall = telephonyClass.getMethod("endCall"); //telephonyAnswerCall = telephonyClass.getMethod("answerRingingCall"); telephonyEndCall.invoke(telephonyObject); } catch (Exception e) { e.printStackTrace(); Log.error(DialerActivity.this, "FATAL ERROR: could not connect to telephony subsystem"); Log.error(DialerActivity.this, "Exception object: " + e); }


21
投票
创建优先级为0的BroadcastReceiver
    在BC中以其ACTION_NEW_OUTGOING_CALL方法拦截onReceive意图
  1. 以相同方法调用setResultData(null)
  • 这将阻止发起呼叫(只要您的接收者是最后一个处理我认为的意图的人)

  • 6
    投票
    在清单中,添加此:

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

    在代码中,使用此:

    Java:

    @SuppressLint("PrivateApi") public static boolean endCall(Context context) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { final TelecomManager telecomManager = (TelecomManager) context.getSystemService(Context.TELECOM_SERVICE); if (telecomManager != null && ContextCompat.checkSelfPermission(context, Manifest.permission.ANSWER_PHONE_CALLS) == PackageManager.PERMISSION_GRANTED) { telecomManager.endCall(); return true; } return false; } //use unofficial API for older Android versions, as written here: https://stackoverflow.com/a/8380418/878126 try { final Class<?> telephonyClass = Class.forName("com.android.internal.telephony.ITelephony"); final Class<?> telephonyStubClass = telephonyClass.getClasses()[0]; final Class<?> serviceManagerClass = Class.forName("android.os.ServiceManager"); final Class<?> serviceManagerNativeClass = Class.forName("android.os.ServiceManagerNative"); final Method getService = serviceManagerClass.getMethod("getService", String.class); final Method tempInterfaceMethod = serviceManagerNativeClass.getMethod("asInterface", IBinder.class); final Binder tmpBinder = new Binder(); tmpBinder.attachInterface(null, "fake"); final Object serviceManagerObject = tempInterfaceMethod.invoke(null, tmpBinder); final IBinder retbinder = (IBinder) getService.invoke(serviceManagerObject, "phone"); final Method serviceMethod = telephonyStubClass.getMethod("asInterface", IBinder.class); final Object telephonyObject = serviceMethod.invoke(null, retbinder); final Method telephonyEndCall = telephonyClass.getMethod("endCall"); telephonyEndCall.invoke(telephonyObject); return true; } catch (Exception e) { e.printStackTrace(); LogManager.e(e); } return false; }

    或在科特林:

    @SuppressLint("PrivateApi")
    fun endCall(context: Context): Boolean {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
            val telecomManager = context.getSystemService(Context.TELECOM_SERVICE) as TelecomManager
            if (ContextCompat.checkSelfPermission(context, Manifest.permission.ANSWER_PHONE_CALLS) == PackageManager.PERMISSION_GRANTED) {
                telecomManager.endCall()
                return true
            }
            return false
        }
        //use unofficial API for older Android versions, as written here: https://stackoverflow.com/a/8380418/878126
        try {
            val telephonyClass = Class.forName("com.android.internal.telephony.ITelephony")
            val telephonyStubClass = telephonyClass.classes[0]
            val serviceManagerClass = Class.forName("android.os.ServiceManager")
            val serviceManagerNativeClass = Class.forName("android.os.ServiceManagerNative")
            val getService = serviceManagerClass.getMethod("getService", String::class.java)
            val tempInterfaceMethod = serviceManagerNativeClass.getMethod("asInterface", IBinder::class.java)
            val tmpBinder = Binder()
            tmpBinder.attachInterface(null, "fake")
            val serviceManagerObject = tempInterfaceMethod.invoke(null, tmpBinder)
            val retbinder = getService.invoke(serviceManagerObject, "phone") as IBinder
            val serviceMethod = telephonyStubClass.getMethod("asInterface", IBinder::class.java)
            val telephonyObject = serviceMethod.invoke(null, retbinder)
            val telephonyEndCall = telephonyClass.getMethod("endCall")
            telephonyEndCall.invoke(telephonyObject)
            return true
        } catch (e: Exception) {
            e.printStackTrace()
            return false
        }
    }
    

    5
    投票

    4
    投票

    3
    投票

    0
    投票
    © www.soinside.com 2019 - 2024. All rights reserved.