Android ContentObserver 监听短信思路详解
目录
- 概述
- 思路
- 拓展
- 案例
概述
内容观察器ContentObserver给目标内容注册一个观察器,目标内容的数据一旦发生变化,观察器规定好的动作马上触发,从而执行开发者预先定义的代码。
思路
注册一个监听
getContentResolver().registerContentObserver(uri, true, mObserver);
继承 ContentObserver 实现一个用于回调的监听类
private static class SmsGetObserver extends ContentObserver { private final Context mContext; public SmsGetObserver(Context context) { super(new Handler(Looper.getMainLooper())); this.mContext = context; } @SuppressLint("Range") @Override public void onChange(boolean selfChange, @Nullable Uri uri) { super.onChange(selfChange, uri); // onChange会多次调用,收到一条短信会调用两次onChange // mUri===content://sms/raw/20 // mUri===content://sms/inbox/20 // 安卓7.0以上系统,点击标记为已读,也会调用一次 // mUri===content://sms // 收到一条短信都是uri后面都会有确定的一个数字,对应数据库的_id,比如上面的20 Log.d("aabb",uri.toString()); if (uri == null) { return; } if (uri.toString().contains("content://sms/raw") || uri.toString().equals("content://sms")) { return; } // 通过内容解析器获取符合条件的结果游标集 Cursor cursor = mContext.getContentResolver().query(uri, new String[]{"address", "body", "date"}, null, null, "date Desc"); if (cursor.moveToNext()) { // 短信的发送号码 String sender = cursor.getString(cursor.getColumnIndex("address")); // 短信内容 String content = cursor.getString(cursor.getColumnIndex("body")); Log.d("AAAA", Sandroidtring.format("sender:%s,content:%s", sender, content)); } cursor.close(); } }
短信相关权限
<uses-permission android:name="android.permission.SEND_SMS" /> &ljst;uses-permission android:name="android.permission.READ_SMS" />
完整代码
package com.example.cpclient; import androidx.annotation.Nullable; import androidx.appcompat.app.AppCompatActivity; import android.annotation.SuppressLint; import android.content.Context; import android.database.ContentObserver; import android.database.Cursor; import android.net.Uri; import android.os.Bundle; import android.os.Handler; import android.os.Looper; import android.util.Log; public class MonitorSmsActivity extends AppCompaKebRPtActivity { private SmsGetObserver mObserver; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_monitor_sms); // 给指定Uri注册内容观察器,一旦发生数据变化,就触发观察器的onChange方法 Uri uri = Uri.parse("content://sms"); // notifyForDescendents: // false :表示精确匹配,即只匹配该Uri,true :表示可以同时匹配其派生的Uri // 假设UriMatcher 里注册的Uri共有以下类型: // 1.content://AUTHORITIES/[table] // 2.content://AUTHORITIES/[table]/# // 3.content://AUTHORITIES/[table]/[subtable] // 假设我们当前需要观察的Uri为content://AUTHORITIES/student: // 如果发生数据变化的 Uri 为 3。 // 当notifyForDescendents为false,那么该ContentObserver会监听不到,但是当notifyForDescendents 为ture,能捕捉该Uri的数据库变化。 mObserver = new SmsGetObserver(this); getContentResolver().registerContentObserver(uri, true, mObserver); } @Override protected void onDestroy() { super.onDestroy(); getContentResolver().unregisterContentObserver(mObserver); } private static class SmsGetObserver extends ContentObserver { private final Context mContext; public SmsGetObserver(Context context) { super(new Handler(Looper.getMainLooper())); this.mContext = context; } @SuppressLint("Range") @Override public void onChange(boolean selfChange, @Nullable Uri uri) { super.onChange(selfChange, uri); // onChange会多次调用,收到一条短信会调用两次onChange // mUri===content://sms/raw/20 // mUri===content://sms/inbox/20 // 安卓7.0以上系统,点击标记为已读,也会调用一次 // mUri===content://sms // 收到一条短信都是uri后面都会有确定的一个数字,对应数据库的_id,比如上面的20 Log.d("aabb",uri.toString()); if (uri == null) { return; } if (uri.toString().contains("content://sms/raw") || uri.toString().equals("content://sms")) { return; } // 通过内容解析器获取符合条件的结果游标集 Cursor cursor = mContext.getContentResolver().query(uri, new String[]{"address", "body", "date"}, null, null, "date Desc"); if (cursor.moveToNjavascriptext()) { // 短信的发送号码 String sender = cursor.getString(cursor.getColumnIndex("address")); // 短信内容 String content = cursor.getString(cursor.getColumnIndex("body")); Log.d("AAAA", String.format("sender:%s,content:%s", sender, content)); } cursor.close(); } } }
拓展
当在你的provider中,别人insert了一条数据,你要告知他是否成功了
使用 notifyChange进行通知回调
getContext().getContentResolver().notifyChange()
案例
@Override public Uri insert(Uri uri, ContentValues values) { if (URI_MATCHER.match(uri) == USERS) { SQLiteDatabase db = dbHelper.getWritableDatabase(); long rowId = db.insert(UserDBHelper.TABLE_NAME, null, values); if (rowId > 0) { // 如果添加成功,就利用新记录的行号生成新的地址 Uri newUri = ContentUris.withAppendedId(UserInfoContent.CONTENT_URI, rowId); // 通知监听器,数据已经改变 getContext().getContentResolver().notifyChange(newUri, null); } } return uri; }
案例代码
到此这篇关于Android ContentObserver 监听短信的文章就介绍到这了,更多相关Android ContentObserver 监听短信内容请搜索编程客栈(www.devze.com)以前的文章或继续浏览下面的相关文章希望大家以javascript后多多支持编程客栈(www.devze.com)!
精彩评论