在监听手机来电一文中,已经实现了监听手机来电的功能,本文在此基础上,增加黑名单来电自动挂断的功能,不幸的是,Android没有对外公开挂断电话的API,如果需要挂断电话,必须使用AIDL与电话管理服务进行通信,并调用服务中的API实现结束通话。为了调用远程的AIDL Service,需要将Android源代码中的如下两个文件复制到项目的相应位置:
com.android.internal.telephony包下的ITelephony.aidl
android.telephony包下的NeighboringCellInfo.aidl
开发者需要在项目中建立对应的包,然后将这两个文件复制到相应的包下。ADT会在根目录下自动生成源文件。
接下来就可以使用ITelephony的endCall方法来挂断电话了。代码如下:
package com.guyun.activity; import java.lang.reflect.Method; import java.util.ArrayList; import com.android.internal.telephony.ITelephony; import android.app.Activity; import android.os.Bundle; import android.os.IBinder; import android.telephony.PhoneStateListener; import android.telephony.TelephonyManager; public class MainActivity extends Activity { // 记录黑名单的集合 ArrayList<String> blockList = new ArrayList<String>(); // 声明电话管理器对象 TelephonyManager tManager; // 声明监听通话状态的监听器 CustomPhoneCallListener cpListener; public class CustomPhoneCallListener extends PhoneStateListener { @Override public void onCallStateChanged(int state, String incomingNumber) { switch (state) { case TelephonyManager.CALL_STATE_IDLE: break; case TelephonyManager.CALL_STATE_OFFHOOK: break; case TelephonyManager.CALL_STATE_RINGING: // 如果该号码属于黑名单 if (isBlock(incomingNumber)) { try { Method method = Class.forName( "android.os.ServiceManager").getMethod( "getService", String.class); // 获取远程TELEPHONY_SERVICE的IBinder对象的代理 IBinder binder = (IBinder) method.invoke(null, new Object[] { TELEPHONY_SERVICE }); // 将IBinder对象的代理转换为ITelephony对象 ITelephony telephony = ITelephony.Stub .asInterface(binder); // 挂断电话 telephony.endCall(); } catch (Exception e) { e.printStackTrace(); } } break; } super.onCallStateChanged(state, incomingNumber); } } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // 初始化黑名单集合 initBlockList(); // 获取系统的TelephonyManager管理器 tManager = (TelephonyManager) getSystemService(TELEPHONY_SERVICE); cpListener = new CustomPhoneCallListener(); // 通过TelephonyManager监听通话状态的改变 tManager.listen(cpListener, PhoneStateListener.LISTEN_CALL_STATE); } /** * 初始化黑名单集合 */ private void initBlockList() { blockList.add("15402817757"); blockList.add("15680768382"); blockList.add("15680768383"); blockList.add("15680768284"); blockList.add("15680768385"); blockList.add("15680768386"); blockList.add("15680768387"); blockList.add("15680768388"); blockList.add("15680768389"); } /** * 判断某个电话号码是否在黑名单之内 * * @param phone * 来电号码 * @return */ public boolean isBlock(String phone) { for (String s1 : blockList) { if (s1.equals(phone)) { return true; } } return false; } }
加上权限:
<uses-permission android:name="android.permission.CALL_PHONE" /> <uses-permission android:name="android.permission.READ_PHONE_STATE" />
注意:本文只是简单地初始化黑名单,此示例可以做如下改进:
1、黑名单来源应该从系统联系人中选取,即需要读取系统联系人,以ListView形式显示出来并提供复选框供用户选择。
2、选择的黑名单可以保存在文件或数据库中,当然判断某个号码是否为黑名单也是根据此文件或数据库,这样即使程序退出,手机关机,黑名单也不会消失。
3、添加黑名单可以在Activity实现,而监听来电和挂断黑名单可以在后台Service实现,并随系统开机而自动运行。