我尝试使用内容观察者捕获传出的SMS事件。
//TEST OBSERVER
ContentObserver co = new SMSoutObserver(new Handler(), getApplicationContext());
ContentResolver contentResolver = getApplicationContext().getContentResolver();
contentResolver.registerContentObserver(Uri.parse("content://sms/out"),true, co);
// END TEST OBSERVER
和
public class SMSoutObserver extends ContentObserver {
private Context mCtx;
public SMSoutObserver(Handler handler, Context ctx) {
super(handler);
mCtx = ctx;
}
@Override
public void onChange(boolean selfChange) {
super.onChange(selfChange);
// save the message to the SD card here
Logger.d("On Change");
Toast.makeText(mCtx,"TEST", Toast.LENGTH_LONG).show();
}
}
但是如果我在模拟器中发送传出消息则不会触发。
我也试过使用接收器。
<receiver android:name=".receiver.SMSReceiver"
android:enabled="true"
android:exported="true"
android:priority="1000">
<intent-filter>
<action android:name="android.provider.Telephony.SMS_RECEIVED" />
<action android:name="android.provider.Telephony.SMS_SENT"/>
</intent-filter>
</receiver>
带接收器的
public class SMSReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
try {
Logger.d("SMSReceiver triggered");
if (intent.getAction().equals("android.provider.Telephony.SMS_RECEIVED")){
//do something with the received sms
Logger.d("Incoming SMS");
}else if(intent.getAction().equals("android.provider.Telephony.SMS_SENT")){
//do something with the sended sms
Logger.d("Outgoing SMS");
}
// Start reminder service
// context.startService(new Intent(context, ReminderService.class));
} catch (Exception e) {
Logger.e("onReceive method cannot be processed");
TrackingEventLogHelper.logException(e, Constants.Global.EXCEPTION,
Constants.ExceptionMessage.EXC_CANNOT_CANNOT_PROCESS_REBOOT_RECEIVER, true);
}
}
}
但是此接收器仅触发传入消息,而不是传出消息。我应该如何以正确的方式处理Android版本&gt; 5也是。
非常感谢任何建议
答案 0 :(得分:2)
SDK中没有"android.provider.Telephony.SMS_SENT"
操作,短信发送时也没有任何系统级广播,因此您的第二种方法无法正常工作。
对于ContentObserver
,您注册的Uri
必须是SMS提供商的基础Uri
。也就是说,将Uri.parse("content://sms/out")
更改为Uri.parse("content://sms")
。如果您只想处理外发邮件,则必须使用onChange()
方法查询提供程序,并检索邮件的type
列值,检查值2
,表示发送的消息。
如果您支持低于16的API级别,那么它将是这样的:
private static final Uri uri = Uri.parse("content://sms");
private static final String COLUMN_TYPE = "type";
private static final int MESSAGE_TYPE_SENT = 2;
...
@Override
public void onChange(boolean selfChange) {
Cursor cursor = null;
try {
cursor = resolver.query(uri, null, null, null, null);
if (cursor != null && cursor.moveToFirst()) {
int type = cursor.getInt(cursor.getColumnIndex(COLUMN_TYPE));
if (type == MESSAGE_TYPE_SENT) {
// Sent message
}
}
}
finally {
if (cursor != null)
cursor.close();
}
}
从API 16开始,ContentObserver
类提供onChange()
重载,该消息将为消息提供特定的Uri
作为第二个参数,您可以比其更有效地查询和检查基地Uri
。此外,如果您的最低API级别为19,则有几个具有常量的类可以替代上面示例代码中定义的那些。
作为旁注,发件箱的Uri
为"content://sms/outbox"
,而不是"content://sms/out"
。