效果展示
就是点击发送短信,然后能够读取短信的内容显示在TextView中。
首先,读取SMS是需要权限的,因为版本升级,对权限的申请也繁琐了些,需要先在Manifest文件写入允许权限的配置:
<uses-permission android:name="android.permission.READ_CONTACTS"/>
<uses-permission android:name="android.permission.WRITE_CONTACTS"/>
<uses-permission android:name="android.permission.READ_SMS"/>
<uses-permission android:name="android.permission.SEND_SMS"/>
然后需要进行权限的申请:
final private int REQUEST_CODE_ASK_PERMISSIONS = 123;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.M) {
int hasReadSmsPermission = checkSelfPermission(Manifest.permission.READ_SMS);
if (hasReadSmsPermission != PackageManager.PERMISSION_GRANTED) {
requestPermissions(new String[]{Manifest.permission.READ_SMS}, REQUEST_CODE_ASK_PERMISSIONS);
return;
}
}
核心代码如下:
package demo.demo;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import android.Manifest;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.pm.PackageManager;
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;
import android.widget.TextView;
public class MainActivity extends AppCompatActivity {
final private int REQUEST_CODE_ASK_PERMISSIONS = 123;
TextView m_address;
TextView m_content;
SmsGetObserver mObserver;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
this.m_address = findViewById(R.id.address);
this.m_content = findViewById(R.id.content);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.M) {
int hasReadSmsPermission = checkSelfPermission(Manifest.permission.READ_SMS);
if (hasReadSmsPermission != PackageManager.PERMISSION_GRANTED) {
requestPermissions(new String[]{Manifest.permission.READ_SMS}, REQUEST_CODE_ASK_PERMISSIONS);
return;
}
}
Uri uri = Uri.parse("content://sms");
mObserver = new SmsGetObserver(this);
// 监听短信内容是否发送变化
getContentResolver().registerContentObserver(uri, true, mObserver);
}
@Override
protected void onDestroy() {
super.onDestroy();
getContentResolver().unregisterContentObserver(mObserver);
}
public 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);
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"));
m_content.setText(content);
m_address.setText(sender);
Log.d("Hunter", String.format("sender %s, content: %s", sender, content));
}
cursor.close();
}
}
}
发送短信
点击虚拟机上面三个点,就会跳出一个界面。
选择左侧的Phone
就能对我们的虚拟机进行打电话和发短信了。
这样就完成了对短信的发送和读取了、
完整实例代码:Android移动应用开发之接收短信读取并显示在TextView
参考
Permission Denial: reading com.android.providers.telephony.SmsProvider uri content://sms/ 异常解决