本人是Android新手,最近做了一个关于监听手机短信功能的应用,我在网上看资料了解到广播分为有序广播和无序广播,有序广播;无序广播又称普通广播,其中的利弊我也一时没搞清楚,我用的是有序广播实现的,具体思路如下
1、定义一个接收短信的广播
2、当系统接收到短信时,拦截短信,获取短信内容
3、将指定的短信内容转发到服务器
下面是我的实现方法
1、添加一个短消息接收类
class="code_img_closed" src="/Upload/Images/2013110211/0015B68B3C38AA5B.gif" alt="" />logs_code_hide('abec416b-15d5-4b63-a5f9-345ecb88c422',event)" src="/Upload/Images/2013110211/2B1B950FA3DF188F.gif" alt="" />import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import org.apache.http.HttpResponse; import org.apache.http.NameValuePair; import org.apache.http.client.entity.UrlEncodedFormEntity; import org.apache.http.client.methods.HttpPost; import org.apache.http.impl.client.DefaultHttpClient; import org.apache.http.message.BasicNameValuePair; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.telephony.SmsMessage; import android.telephony.TelephonyManager; import android.util.Log; import android.widget.Toast; public class MessageBroadcastReceiver extends BroadcastReceiver { private static final String ACTION = "android.provider.Telephony.SMS_RECEIVED"; String uri="http://218.28.130.36:8080/Home/SmsHandler"; @Override public void onReceive(Context context, Intent intent) { //监听短信广播 if (intent != null && intent.getAction() != null && ACTION.compareToIgnoreCase(intent.getAction()) == 0) { Object[] pduArray = (Object[]) intent.getExtras().get("pdus"); SmsMessage[] messages = new SmsMessage[pduArray.length]; //SmsManager sms=SmsManager.getDefault(); String localTelPhoneNumber=getPhoneNumber(context); //String localTelPhoneNumber="13014696166"; for (int i = 0; i < pduArray.length; i++) { messages[i] = SmsMessage.createFromPdu((byte[]) pduArray[i]); if(messages[i].getDisplayMessageBody().contains("安阳市驾管科")) //制定短信转发过滤条件 { String filterSms=messages[i].getDisplayMessageBody(); Map<String, String> params=new HashMap<String, String>(); params.put("phoneNumber", localTelPhoneNumber); params.put("smsContent", filterSms); try { sendHttpClientPOSTRequest(uri,params,"UTF-8"); Toast.makeText(context, "短信验证码已转发!", Toast.LENGTH_LONG).show(); // show first message } catch (Exception e) { Toast.makeText(context, e.toString(), Toast.LENGTH_LONG).show(); e.printStackTrace(); } } } Log.d("ConvertToMsg", "SMS Message Received."); } } /** * 通过HttpClient发送Post请求 * @param path 请求路径 * @param params 请求参数 * @param ecoding 请求编码 * @return 请求是否成功 */ private boolean sendHttpClientPOSTRequest(String path, Map<String, String> params, String ecoding) throws Exception { List<NameValuePair> pair=new ArrayList<NameValuePair>();//存放请求参数 if(params!=null && !params.isEmpty()){ for (Map.Entry<String, String> entry : params.entrySet()) { pair.add(new BasicNameValuePair(entry.getKey(),entry.getValue())); } } UrlEncodedFormEntity enFormEntity=new UrlEncodedFormEntity(pair,ecoding); HttpPost httpPost=new HttpPost(path); httpPost.setEntity(enFormEntity); DefaultHttpClient client=new DefaultHttpClient(); HttpResponse response=client.execute(httpPost); if(response.getStatusLine().getStatusCode()==200){ return true; } return false; } /* getPhoneNumber方法返回当前手机的电话号码, * 同时必须在androidmanifest.xml中 * 加入 android.permission.READ_PHONE_STATE 这个权限 */ private String getPhoneNumber(Context context){ TelephonyManager mTelephonyMgr; mTelephonyMgr = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE); return mTelephonyMgr.getLine1Number(); } }短信接收广播类
1 package com.example.testdemo; 2 import com.example.testdemo.MessageBroadcastReceiver; 3 import com.example.testdemo.R; 4 import android.os.Bundle; 5 import android.app.Activity; 6 import android.content.ActivityNotFoundException; 7 import android.content.BroadcastReceiver; 8 import android.content.ComponentName; 9 import android.content.Context; 10 import android.content.Intent; 11 import android.content.IntentFilter; 12 import android.content.pm.ActivityInfo; 13 import android.content.pm.PackageManager; 14 import android.content.pm.ResolveInfo; 15 import android.telephony.TelephonyManager; 16 import android.view.KeyEvent; 17 import android.view.Menu; 18 import android.widget.Toast; 19 public class MainActivity extends Activity { 20 @Override 21 protected void onCreate(Bundle savedInstanceState) { 22 super.onCreate(savedInstanceState); 23 setContentView(R.layout.activity_main); 24 25 String phoneNumber = getPhoneNumber(this); 26 27 if(phoneNumber == ""){ 28 Toast.makeText(this, 29 "程序错误!", 30 Toast.LENGTH_LONG).show(); 31 return; 32 }else{ 33 Toast.makeText(this, 34 phoneNumber, 35 Toast.LENGTH_LONG).show(); 36 } 37 38 //注册短信广播 39 final String SMS_RECEIVED = "android.provider.Telephony.SMS_RECEIVED"; 40 IntentFilter filter = new IntentFilter(SMS_RECEIVED); 41 BroadcastReceiver receiver = new MessageBroadcastReceiver(); 42 registerReceiver(receiver, filter); 43 } 44 45 @Override 46 public boolean onCreateOptionsMenu(Menu menu) { 47 // Inflate the menu; this adds items to the action bar if it is present. 48 getMenuInflater().inflate(R.menu.main, menu); 49 return true; 50 } 51 52 @Override 53 protected void onDestroy() { 54 super.onDestroy(); 55 } 56 57 /*重写Home键盘事件,使程序后台运行*/ 58 @Override 59 public boolean onKeyDown(int keyCode, KeyEvent event) { 60 PackageManager pm = getPackageManager(); 61 ResolveInfo homeInfo = 62 pm.resolveActivity(new Intent(Intent.ACTION_MAIN).addCategory(Intent.CATEGORY_HOME), 0); 63 if (keyCode == KeyEvent.KEYCODE_BACK) { 64 ActivityInfo ai = homeInfo.activityInfo; 65 Intent startIntent = new Intent(Intent.ACTION_MAIN); 66 startIntent.addCategory(Intent.CATEGORY_LAUNCHER); 67 startIntent.setComponent(new ComponentName(ai.packageName, ai.name)); 68 startActivitySafely(startIntent); 69 return true; 70 } else 71 return super.onKeyDown(keyCode, event); 72 } 73 74 private void startActivitySafely(Intent intent) { 75 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 76 try { 77 startActivity(intent); 78 } catch (ActivityNotFoundException e) { 79 Toast.makeText(this, "null", 80 Toast.LENGTH_SHORT).show(); 81 } catch (SecurityException e) { 82 Toast.makeText(this, "null", 83 Toast.LENGTH_SHORT).show(); 84 } 85 } 86 87 /** 88 * 1. getPhoneNumber方法返回当前手机的电话号码, 89 * 同时必须在androidmanifest.xml中 90 * 加入 android.permission.READ_PHONE_STATE 这个权限 91 */ 92 private String getPhoneNumber(Context context){ 93 TelephonyManager mTelephonyMgr; 94 mTelephonyMgr = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE); 95 return mTelephonyMgr.getLine1Number().trim(); 96 } 97 }在MainActity里调用广播
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.testdemo" android:versionCode="1" android:versionName="1.0" > <uses-sdk android:minSdkVersion="5" android:targetSdkVersion="5" /> <uses-permission android:name="android.permission.RECEIVE_SMS"></uses-permission> <uses-permission android:name="android.permission.READ_SMS"></uses-permission> <!-- <uses-permission android:protectionLevel="normal" android:name="android.permission.SEND_SMS"></uses-permission> --> <!-- Http权限 --> <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.READ_PHONE_STATE" /> <!-- 开机启动完成权限 --> <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"></uses-permission> <application android:allowBackup="true" android:icon="@drawable/ic_launcher" android:label="@string/app_name" android:theme="@style/AppTheme" > <activity android:name="com.example.testdemo.MainActivity" android:label="@string/app_name" > <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <!-- 注册广播接收器,用于接收开机启动完成的广播 --> <receiver android:name=".BootStartBroadcastReceiver"> <intent-filter> <action android:name="android.intent.action.BOOT_COMPLETED" /> </intent-filter> </receiver> </application> </manifest>在MainFest.xml添加权限
好了,配置好之后就可以编译你的项目了,在手机上安装测试可以正常运行,但是有一些问题,就是在某些手机上短信广播接收不到,例如小米和以前的某些牌子的老款智能手机,我在网上查了查,有认说是广播优先级问题,同是短信应用软件,先安装的优先级高,还有一种情况,是软件本身的优先级高,但是都没有提出具体的解决方案,还有一个原因就是系统本身的安全机制,由于某些设置导致短信应用软件不能正常使用,例如小米手机,在短信设置里面好像有一项和短信接收有关的设置,调整之后就可以接收了,但其他手机还没有解决,如果有哪个大牛有好的解决方案,给小弟指点迷津,感激不尽。
网友 2014/8/20 11:13:59 发表
还可以