实际应用开发中,会经常用到短信验证的功能,这个时候如果再让用户就查看短信.然后再回到界面进行短信的填写,难免有多少有些不方便,作为开发者.本着用户至上的原则我们也应该来实现验证码的自动填写功能,实现短信验证码自动填写有两种方式: 第一种,实现Content
实际应用开发中,会经常用到短信验证的功能,这个时候如果再让用户就查看短信.然后再回到界面进行短信的填写,难免有多少有些不方便,作为开发者.本着用户至上的原则我们也应该来实现验证码的自动填写功能,实现短信验证码自动填写有两种方式:
第一种,实现ContentObserver,把我们自己的Observer注册到短信服务,短信应用收到新的短信的时候会发送给我我们自己的Observer,然后我们在自己的Observer中.通过代码发送给我们的需要填充的界面就行了.这种方式是利用了观察者模式 .
SmsObserver的代码:
-
-
-
-
package com.example.testgetsmscode;
-
-
import java.util.regex.Matcher;
-
import java.util.regex.Pattern;
-
-
import android.content.Context;
-
import android.database.ContentObserver;
-
import android.database.Cursor;
-
import android.net.Uri;
-
import android.os.Handler;
-
import android.os.Message;
-
import android.util.Log;
-
-
-
-
-
public class SmsObserver extends ContentObserver {
-
-
private Context context;
-
private Handler handler;
-
private String compileValue;
-
-
-
-
-
-
-
-
-
-
public SmsObserver(Context context, Handler handler, int codeLength) {
-
super(handler);
-
-
this.context = context;
-
this.handler = handler;
-
compileValue = "\\d{" + codeLength + "}";
-
}
-
-
-
-
-
-
@Override
-
public void onChange(boolean selfChange, Uri uri) {
-
Log.e("smsobserver", "selfChange:" + selfChange + "Uri:" + uri.toString());
-
-
if (uri.toString().equals("content://sms/raw")) {
-
return;
-
}
-
-
-
Cursor cursor = context.getContentResolver().query(uri, null, null, null, null);
-
if (cursor != null) {
-
if (cursor.moveToFirst()) {
-
String address = cursor.getString(cursor.getColumnIndex("address"));
-
String body = cursor.getString(cursor.getColumnIndex("body"));
-
Log.e("smsobserver", "get sms:address:" + address + "body:" + body);
-
cursor.close();
-
-
-
-
-
-
-
-
-
Pattern pattern = Pattern.compile(compileValue);
-
Matcher matcher = pattern.matcher(body);
-
if (matcher.find()) {
-
-
Log.e("smsobserver", "code:" + matcher.group(0));
-
Log.e("smsobserver", "contentObserver get code time:" + System.currentTimeMillis());
-
-
-
Message msg = Message.obtain();
-
msg.what = MainActivity.msg_received_code;
-
msg.obj = matcher.group(0);
-
handler.sendMessage(msg);
-
} else {
-
Log.e("smsobserver", "没有在短信中获取到合格的验证码");
-
}
-
-
} else {
-
Log.e("smsobserver", "movetofirst为false了");
-
}
-
} else {
-
Log.e("smsobserver", "cursor为null了");
-
}
-
}
-
-
}
主界面中的使用方法:
-
@Override
-
protected void onCreate(Bundle savedInstanceState) {
-
super.onCreate(savedInstanceState);
-
setContentView(R.layout.activity_main);
-
initView();
-
}
-
-
-
-
-
private void initView() {
-
-
et_main = (EditText) findViewById(R.id.et_main);
-
-
mSmsObserver = new SmsObserver(MainActivity.this, mHandler, 6);
-
Uri uri = Uri.parse("content://sms");
-
getContentResolver().registerContentObserver(uri, true, mSmsObserver);
-
}
注册之后,肯定要在界面销毁的时候取消注册咯:
-
-
-
-
-
-
@Override
-
protected void onDestroy() {
-
super.onDestroy();
-
getContentResolver().unregisterContentObserver(mSmsObserver);
-
}
在ContentObserver构造方法中,我们传递了一个handler对象,目的就是通过handler把我们得到的短信验证码给接收过来:
-
public static final int msg_received_code = 1;
-
public Handler mHandler = new Handler() {
-
public void handleMessage(android.os.Message msg) {
-
if (msg.what == msg_received_code) {
-
String code = (String) msg.obj;
-
et_main.setText(code);
-
Log.e("mainactivity", "activity get code time:" + System.currentTimeMillis());
-
-
}
-
};
-
};
最后的最后,一定不要忘记加权限:
-
-
<uses-permission android:name="android.permission.READ_SMS" />
顺便一提:这种方式实现的验证码自动填写功能,在android2.3上竟然没有效果,在4.0上没问题,欢迎纠正和补充..
第二种,我们自己的应用创建一个广播接收器,接受短信变化的广播,然后在收到广播的时候,再把验证码提取出来发送给我们的需要填充验证码的地方就行了
广播接收器的代码:
-
-
-
-
package com.example.testsendandreceivesms;
-
-
import java.util.regex.Matcher;
-
import java.util.regex.Pattern;
-
-
import android.content.BroadcastReceiver;
-
import android.content.Context;
-
import android.content.Intent;
-
import android.os.Bundle;
-
import android.os.Handler;
-
import android.telephony.SmsMessage;
-
import android.util.Log;
-
-
-
-
-
-
public class SmsReceiveBroadcastReceiver extends BroadcastReceiver {
-
-
private Context context;
-
private Handler handler;
-
private int codeLength = 0;
-
-
-
-
-
public SmsReceiveBroadcastReceiver(Context context, Handler handler, int codeLength) {
-
-
this.context = context;
-
this.handler = handler;
-
this.codeLength = codeLength;
-
}
-
-
@Override
-
public void onReceive(Context context, Intent intent) {
-
-
Bundle bundle = intent.getExtras();
-
Object[] objects = (Object[]) bundle.get("pdus");
-
if (objects != null) {
-
String phone = null;
-
StringBuffer content = new StringBuffer();
-
for (int i = 0; i < objects.length; i++) {
-
SmsMessage sms = SmsMessage.createFromPdu((byte[]) objects[i]);
-
phone = sms.getDisplayOriginatingAddress();
-
content.append(sms.getDisplayMessageBody());
-
}
-
Log.e("smsbc", "phone:" + phone + "\ncontent:" + content.toString());
-
checkCodeAndSend(content.toString());
-
}
-
}
-
-
-
-
-
private void checkCodeAndSend(String content) {
-
-
-
Pattern pattern = Pattern.compile("\\d{" + codeLength + "}");
-
Matcher matcher = pattern.matcher(content);
-
if (matcher.find()) {
-
String code = matcher.group(0);
-
Log.e("smsbc", "短信中找到了符合规则的验证码:" + code);
-
handler.obtainMessage(MainActivity.BC_SMS_RECEIVE, code).sendToTarget();
-
Log.e("smsbc", "广播接收器接收到短信的时间:" + System.currentTimeMillis());
-
} else {
-
Log.e("smsbc", "短信中没有找到符合规则的验证码");
-
}
-
}
-
-
}
主界面中的使用:
-
@Override
-
protected void onCreate(Bundle savedInstanceState) {
-
super.onCreate(savedInstanceState);
-
setContentView(R.layout.activity_main);
-
-
broadcastReceiver = new SmsReceiveBroadcastReceiver(MainActivity.this, handler, 6);
-
IntentFilter intentFilter = new IntentFilter("android.provider.Telephony.SMS_RECEIVED");
-
registerReceiver(broadcastReceiver, intentFilter);
-
initView();
-
}
-
-
-
-
-
-
-
@Override
-
protected void onDestroy() {
-
-
super.onDestroy();
-
unregisterReceiver(broadcastReceiver);
-
}
handler:
-
private Handler handler = new Handler() {
-
public void handleMessage(android.os.Message msg) {
-
if (msg.what == BC_SMS_RECEIVE) {
-
String code = (String) msg.obj;
-
tv_sms_code.setText(code);
-
Log.e("mainactivity", "界面收到短信的时间:" + System.currentTimeMillis());
-
}
-
};
-
};
特别注意权限:
-
<uses-permission android:name="android.permission.RECEIVE_SMS"/>
这种实现方式在android2.3上和android4.0上都表现良好,别的没测试,
和上一种方法一样,也是需要注册和取消注册操作的,而且,因为同样都是利用了handler把得到的内容发送回来.所以发送内容的效率产不多,不过在接受短信的效率上要比上一种方式要好.毕竟上一种方式是短信应用收到短信,然后再向他发送,而使用广播的话.直接就是从源头上进行接收短信了
短信自动填充demo下载:https://github.com/zhouxu88/SMSContentObserver
android开发两种方式实现短信验证码自动填写功能
转载https://www.codesocang.com/appboke/36677.html