前段时间领导说了这样一个需求:对特定的号码电话进行拦截、短信拒收,在百度了查阅了很多的资料,结果有点不尽人意。特别是AIDL通信接口废了老大劲。直接上过程

  • 创建aidl通信接口直接在main目录新建aldl类型文件ITelephony即可,自动生成包名等等如图所示此处有坑:网上基本上都是让这样写
interface ITelephony {    boolean endCall();    void answerRingingCall();}

这里导致有可能会导致项目编译错误,这里最好还是不要去网上粘贴aidl包名和ITelephony,尽量自己创建不要懒

// ITelephony.aidlpackage com.android.internal.telephony;// Declare any non-default types here with import statementsinterface ITelephony {    /**     * Demonstrates some basic types that you can use as parameters     * and return values in AIDL.     */    void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat,double aDouble, String aString);    boolean endCall();    void answerRingingCall();}

如果编译不通过重新编译一下就好。

根据需求需要配置权限如下:

我这里直接贴代码,注释我会写清楚的

import androidx.annotation.NonNull;import androidx.annotation.RequiresApi;import androidx.appcompat.app.AppCompatActivity;import androidx.core.app.ActivityCompat;import android.Manifest;import android.annotation.SuppressLint;import android.app.Service;import android.content.BroadcastReceiver;import android.content.ContentResolver;import android.content.Context;import android.content.Intent;import android.content.IntentFilter;import android.content.pm.PackageManager;import android.database.Cursor;import android.media.AudioManager;import android.net.Uri;import android.os.Build;import android.os.Bundle;import android.provider.CallLog;import android.provider.ContactsContract;import android.telephony.SmsMessage;import android.telephony.TelephonyManager;import android.util.Log;import java.lang.reflect.Method;import java.util.ArrayList;import java.util.List;public class MainActivity extends AppCompatActivity {    private static String[] PERMISSIONS_STORAGE = {            android.Manifest.permission.READ_PHONE_STATE,            android.Manifest.permission.CALL_PHONE            , Manifest.permission.RECEIVE_SMS, Manifest.permission.READ_CONTACTS, Manifest.permission.WRITE_SETTINGS,Manifest.permission.READ_CALL_LOG, Manifest.permission.WRITE_CALL_LOG};    private static final int REQUEST_PERMISSION_CODE = 666;    private TelephonyManager telMgr;    private IncomingCallReceiver mIncomingCallReceiver;    @RequiresApi(api = Build.VERSION_CODES.N)    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        //动态获取权限        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP) {            if (ActivityCompat.checkSelfPermission(MainActivity.this, Manifest.permission.WRITE_EXTERNAL_STORAGE)                    != PackageManager.PERMISSION_GRANTED) {                ActivityCompat.requestPermissions(MainActivity.this, PERMISSIONS_STORAGE, REQUEST_PERMISSION_CODE);            }        }        //注册广播        mIncomingCallReceiver = new IncomingCallReceiver();        IntentFilter mIntentFilter = new IntentFilter();        //拦截电话        mIntentFilter.addAction("android.intent.action.PHONE_STATE");        //拦截短信        mIntentFilter.addAction("android.provider.Telephony.SMS_RECEIVED");        //注册BroadcastReceiver        registerReceiver(mIncomingCallReceiver, mIntentFilter);    }    //广播接收器    public class IncomingCallReceiver extends BroadcastReceiver {        @SuppressLint("MissingPermission")        @Override        public void onReceive(Context context, Intent intent) {            String action = intent.getAction();            ContentResolver resolver = getContentResolver();            if ("android.intent.action.PHONE_STATE".equals(action)) { //拦截电话                telMgr = (TelephonyManager) context.getSystemService(Service.TELEPHONY_SERVICE);                switch (telMgr.getCallState()) {                    // 当电话呼入时                    case TelephonyManager.CALL_STATE_RINGING:                        String number = intent.getStringExtra(TelephonyManager.EXTRA_INCOMING_NUMBER);                        Log.e("111111111111-----------", "拦截电话2:" + number);                        //我这里是获取手机通讯录的联系人,如果是呼入电话是手机联系人就不拦截,反之你懂的,如果嫌麻烦当然也可以只设置一个号码                        ArrayList list = getPhoneNum();                        Log.e("111111111111-----------", "list:" + list.toString());                        if (!list.contains(number)) {                            AudioManager mAudioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);                             //先静音                            mAudioManager.setRingerMode(AudioManager.RINGER_MODE_SILENT);                            //这里就是aldl通讯接口 挂断电话                            endCall();                            // 删除该呼入电话系统通话记录                            if (null != resolver)                                resolver.delete(CallLog.Calls.CONTENT_URI, "number=?", new String[]{number});                            //恢复正常铃声                            mAudioManager.setRingerMode(AudioManager.RINGER_MODE_NORMAL);                        }                        break;                    //电话被挂起                    case TelephonyManager.CALL_STATE_OFFHOOK:                        break;                    //手机空闲了                    case TelephonyManager.CALL_STATE_IDLE:                        break;                }            }  //拦截短信else if ("android.provider.Telephony.SMS_RECEIVED".equals(action)) {                //获取短信信息                SmsMessage sms = getMessagesFromIntent(intent)[0];                //取得电话号码                String number = sms.getOriginatingAddress();                Log.e("111111111111-----------", "拦截短信2:" + number);                //把国家代码去除掉                 number = trimSmsNumber("+86", number);                 if (!getPhoneNum().contains(number)) {                  //中断短信推送                    this.abortBroadcast();                     // 删除系统短信                    if (null != resolver)                        resolver.delete(Uri.parse("content://sms/"), "address=? or address = ?", new String[]    {number, "+86" + number});                }            }        }    }    //获取短信内容    public final static SmsMessage[] getMessagesFromIntent(Intent intent) {        Object[] messages = (Object[]) intent.getSerializableExtra("pdus");        byte[][] pduObjs = new byte[messages.length][];        for (int i = 0; i < messages.length; i++) {            pduObjs[i] = (byte[]) messages[i];        }        byte[][] pdus = new byte[pduObjs.length][];        int pduCount = pdus.length;        SmsMessage[] msgs = new SmsMessage[pduCount];        for (int i = 0; i < pduCount; i++) {            pdus[i] = pduObjs[i];            msgs[i] = SmsMessage.createFromPdu(pdus[i]);        }        return msgs;    }    //去除国家代码     public final static String trimSmsNumber(String prefix, String number) {        String s = number;        if (prefix.length() > 0 && number.startsWith(prefix)) {            s = number.substring(prefix.length());        }        return s;    }    /**     * 挂断电话     */    private void endCall() {        Class c = TelephonyManager.class;        try {            Method getITelephonyMethod = c.getDeclaredMethod("getITelephony", (Class[]) null);            getITelephonyMethod.setAccessible(true);            ITelephony iTelephony = null;            iTelephony = (ITelephony) getITelephonyMethod.invoke(telMgr, (Object[]) null);            //挂断电话            iTelephony.endCall();        } catch (Exception e) {            //如果有异常查看动态权限有没有遗漏            Log.e("111111111111-----------", "Exception:" + e);        }    }    //权限请求回调,如果返回无权限,卸载重装即可    @Override    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[]         grantResults) {        switch (requestCode) {            case REQUEST_PERMISSION_CODE:                if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {                    Log.e("111111111111-----------", "有权限");                } else {                    Log.e("111111111111-----------", "无权限");                }        }    }      //获取所有联系人    private ArrayList getPhoneNum() {        ArrayList numList = new ArrayList();        //得到ContentResolver对象        ContentResolver cr = getContentResolver();        //取得电话本中开始一项的光标        Cursor cursor = cr.query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);        while (cursor.moveToNext()) {            // 取得联系人ID            String contactId = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts._ID));            Cursor phone = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,                    ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = " + contactId, null, null);            // 取得电话号码(可能存在多个号码)            while (phone.moveToNext()) {                String strPhoneNumber = phone.getString(phone.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));                String str1 = strPhoneNumber.replaceAll(" ", "");                String str2 = str1.replaceAll("-", "");                numList.add(str2);            }            phone.close();        }        cursor.close();        return numList;    }    @Override    protected void onDestroy() {        super.onDestroy();        //注销广播        if (null != mIncomingCallReceiver)            unregisterReceiver(mIncomingCallReceiver);    }}

好嘞这样就可以了,可以根据自己的需求改吧改吧就可以用了。目前在我的真机上的测试效果如下:

手机通讯录外的号码呼入拒接,短信拒收(在信息里面也找不到痕迹)

 

 

 

更多相关文章

  1. 浅入浅出 Android(安卓)安全:第四章 Android(安卓)框架层安全
  2. Android(安卓)Zxing集成
  3. 关于Android(安卓)5.0 安装部分应用失败解决方案
  4. Android权限管理详解
  5. Android(安卓)限制textview Edittext 只能输入电话号码和特定字
  6. Android(安卓)运行时权限申请之电话权限(兼容6.0以上)
  7. Android动态权限申请
  8. Android(安卓)系统 root 破解原理分析
  9. Eclipse如何快速调试系统App(具有系统权限的Android(安卓)App)即Ec

随机推荐

  1. Android常用代码
  2. Android(安卓)MediaPlayer 简单综合应用
  3. Android自动补全(二)
  4. Android中自定义Dialog样式
  5. android侧滑菜单实现
  6. Android之Loader理解
  7. android与js交互-jsbridge
  8. Android(安卓)Studio生成APK自动追加版本
  9. Android官方入门文档[6]添加Action按钮
  10. Android(安卓)通话记录分析