AndroidのSMSメッセージ
-
概要
私たちがよく利用するSMS(ショートメッセージサービス)は、保存と転送のサービスです。保存と転送のサービスです。つまり、SMSのメッセージは送信者から受信者に直接送られるのではなく、必ずSMSセンターを通して転送される。受信者が接続していない場合(おそらく電話の電源が切れている)、受信者が再び接続したときにメッセージが送信されます。
SMSメッセージの長さは通常140バイト、文字数は70文字です。私たちはSMSをよく使うので、今日はSMSの実装を分解してみましょう。
注:この記事は主にandroidアプリケーション層のsmsコードをベースに、SMSpopupと組み合わせたものです。
SMSの構造
_id // ショートメッセージシリアル番号
thread_id // 会話の通し番号
アドレス // 受信者
人
日付 // 日付
プロトコル // プロトコル
read // 読むかどうか
status // 状態
type // タイプ (送信/受信)
reply_path_present //
件名 // 件名
本文 // メッセージの内容
service_center // サービスセンター
関連するクラス図
上記のクラスは、SMSに関わるいくつかのクラスのクラス図です。キーパッドのロック状態、インジケーターのプロンプト、通話状態などを判断し、SMSメッセージが来たときにどのように処理しプロンプトを出すかを決定することに関係します。
SMS受信
まず、SMSの受信について見てみましょう。androidでは、SMS受信には、以下のようにmanifest.xmlにブロードキャストレシーバーを設定する必要があります。
<receiver android:name=".SmsReceiver"> <intent-filter> <action android:name="android.provider.Telephony.SMS_RECEIVED" /> </intent-filter> </receiver>
-
タイミング図を見るには
/** * The processing of incoming SMS messages is placed in this service to be processed */ public static void beginStartingService(Context context, Intent intent) { synchronized (mStartingServiceSync) { if (Log.DEBUG) Log.v("SMSReceiverService: beginStartingService()"); if (mStartingService == null) { // power management, decide whether to light the indicator, keyboard, screen, etc. PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE); mStartingService = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, Log.LOGTAG+".SmsReceiverService"); mStartingService.setReferenceCounted(false); } mStartingService.acquire(); context.startService(intent); } }
テキストメッセージを受信したときに、インジケーターが点灯する、画面が点灯する、キーボードが点灯するなど、何らかの表示が必要です。これは主にPowerManagerで制御します。PowerManagerについては、合間に書いた記事を参照してください。 http://blog.csdn.net/xieqibao/article/details/6562256
ServiceHandlerのhandleMessageメソッドは、メッセージを処理し、メッセージのタイプがmms、smsであることを決定し、handleSmsReceivedで受信したsmsメッセージを処理します。
/** * Process incoming short messages */ private void handleSmsReceived(Intent intent) { Bundle bundle = intent.getExtras(); if (bundle ! = null) { //Get the message SmsMessage[] messages = SmsPopupUtils.getMessagesFromIntent(intent); if (messages ! = null) { notifyMessageReceived(new SmsMmsMessage(context, messages,System.currentTimeMillis())); } } }
次のメソッドは、pdu から情報を取得することに重点を置いています。pdu の詳細については、こちらを参照してください。 http://wenku.baidu.com/view/d0d0093e0912a216147929b1.html
/** * Get pdu information from an intent wrapped with SMS_RECEIVED_ACTION */ public static final SmsMessage[] getMessagesFromIntent(Intent intent) { Object[] messages = (Object[]) intent.getSerializableExtra("pdus"); if (messages == null) { return null; } if (messages.length == 0) { return null; } byte[][] pduObjs = new byte[messages.length][]; for (int i = 0; i < messages.length; i++) { pduObjs[i] = (byte[]) messages[i]; } byte[][] pdus = new byte[pduObjs.length][]; int pduCount = pdus.length; SmsMessage[] msgs = new SmsMessage[pduCount]; for (int i = 0; i < pduCount; i++) { pdus[i] = pduObjs[i]; msgs[i] = SmsMessage.createFromPdu(pdus[i]); } return msgs; }
取得後のショートメッセージをどのように表示するかは、smspopupでアクティビティにポップアップウィンドウとして表示させることで最終決定しています
/** * Get the short message and add it to the view */ private void setupMessages(Bundle b, boolean newIntent) { // Store bundle bundle = b; // Get the short message from the bundle SmsMmsMessage message = new SmsMmsMessage(getApplicationContext(), bundle); mSmsPopups.addMessage(message); if (!newIntent) { // TODO: move off UI thread mSmsPopups.addMessages( SmsPopupUtils.getUnreadMessages(this, message.getMessageId())); } mSmsPopups.refreshPrivacy(); }
SMS送信
/**
* Reply to a short message
*
*/
public boolean replyToMessage(StringquickReply) {
// first mark the SMS as read
setMessageRead();
// Send a new short message
SmsMessageSender sender =
new SmsMessageSender(context, newString[] {fromAddress}, quickReply, getThreadId());
return sender.sendMessage();
}
/**
* Sending SMS message entry
* @return
*/
@SuppressWarnings("deprecation")
public boolean sendMessage() {
if (! (mThreadId > 0)) {
return false;
}
//If the message text is empty, then no message will be sent
if ((mMessageText == null) ||(mNumberOfDests == 0)) {
return false;
}
//get the sms manager
SmsManager smsManager = SmsManager.getDefault();
for (int i = 0; i < mNumberOfDests; i++){
// Split SMS messages according to the maximum number of words allowed in the SMS
ArrayList<String> messages = smsManager.divideMessage(mMessageText);
int messageCount = messages.size();
ArrayList<PendingIntent>deliveryIntents = new ArrayList<PendingIntent>(messageCount);
ArrayList<PendingIntent>sentIntents = new ArrayList<PendingIntent>(messageCount);
// 140 bytes, 70 characters.
if (splitMessage) {
for (int j = 0; j < messageCount;j++) {
Uri uri = null;
try
// Add the short message to the provider
uri =addMessage(mContext.getContentResolver(), mDests[i], messages.get(j),
null, mTimestamp,requestDeliveryReport, mThreadId);
} catch (SQLiteException e) {
// TODO: show error here
// SqliteWrapper.checkSQLiteException(mContext, e);
}
PendingIntent deliveryReportIntent =null;
if (requestDeliveryReport) {
deliveryReportIntent =
PendingIntent.getBroadcast(mContext, 0,
newIntent(MESSAGING_STATUS_RECEIVED_ACTION, uri)
.setClassName(MESSAGING_PACKAGE_NAME, MESSAGING_STATUS_CLASS_NAME), 0);
}
PendingIntent sentIntent =
PendingIntent.getBroadcast(mContext, 0,
newIntent(SmsReceiverService.MESSAGE_SENT_ACTION, uri)
.setClass(mContext,SmsReceiver.class), 0);
smsManager.sendTextMessage(
mDests[i], mServiceCenter,messages.get(j), sentIntent, deliveryReportIntent);
}
}
return false;
}
概要
1. sms smsは主にsmsの送信、受信、アラート、ローカル保存などがあり、比較的多くのポイントを含んでいます。それを理解することが必要である。
関連
-
Android のリストビューでアダプタを使用しているときに null オブジェクトの参照に対して仮想メソッド xxxxxxxx を呼び出そうとする問題が解決されました。
-
Androidでの録音とMP3へのローカルトランスコード
-
AndroidStudioのコンパイル時のエラーを解決します。構成 ':classpath' のすべてのアーティファクトを解決できませんでした。
-
jniとjavaの間でbytearrayを受け渡しする
-
アプリケーションがメインスレで仕事をしすぎている可能性がある
-
Android 高機能版 (xxv) setTextColor() パラメータ設定方法
-
Android Studioの設定 Gradleの概要
-
MPAndroidChartのPieChartで、セクターが表示されず、中央のテキストのみが表示される。
-
android.content.res.Resources$NotFoundException: 文字列リソースID #0x1
-
android studioエミュレータの起動に失敗しました
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
armeabi-v7a、arm64-v8a、armeabi、x86、x86_64の違いについて
-
Androidでコンストラクタのインテントを解決できない原因と解決策
-
ADBサーバーがACKしない問題を解決しました。
-
アプリの実行エラー。Default ActivityNot Found 完璧な解決策
-
Solve アクティビティのメソッドを実行できませんでした
-
ConstraintLayoutにおけるChainとGuidelineの利用について
-
java.lang.SecurityException を解決してください。android パッケージは 10065 に属していません。
-
Androidにおける縦の点線
-
Androidで色を取得するいくつかの方法
-
React Native エラー。アプリケーション XXX は登録されていません ソリューション