Android Messenger實(shí)現(xiàn)進(jìn)程間雙向通信
簡(jiǎn)介
Messenger是安卓進(jìn)程間通信 (IPC) 最為簡(jiǎn)單的方式,可以實(shí)現(xiàn)進(jìn)程間雙向通信。詳見官網(wǎng)介紹
代碼實(shí)現(xiàn)
服務(wù)端應(yīng)用實(shí)現(xiàn)
MessengerService接收客戶端發(fā)送的消息:
package com.test.messengerservice; import android.app.Service; import android.content.Intent; import android.os.Handler; import android.os.IBinder; import android.os.Message; import android.os.Messenger; import android.os.RemoteException; import android.util.Log; import androidx.annotation.NonNull; public class MessengerService extends Service { //接收客戶端的消息類型 private static final int SEND_MESSENGER = 0; private static final int CONFIG_NET = 1; private static final int CANCEL = 2; //發(fā)送給客戶端的消息類型 private static final int FIND_DEVICE = 10; public MessengerService() { } private Messenger messenger = new Messenger(new ServiceHandler()); private static Messenger mClient; public class ServiceHandler extends Handler { @Override public void handleMessage(@NonNull Message msg) { // 處理消息 switch(msg.what){ case SEND_MESSENGER: Log.d("service", "receive messenger"); mClient = msg.replyTo; break; case CONFIG_NET: Log.d("service", "config net task"); mClient = msg.replyTo; break; case CANCEL: Log.d("service", "cancel task"); mClient = msg.replyTo; break; default: break; } } } @Override public IBinder onBind(Intent intent) { Log.i("service", "service bind"); return messenger.getBinder(); } @Override public boolean onUnbind(Intent intent) { Log.i("service", "service unbind"); mClient = null; return super.onUnbind(intent); } //向客戶端發(fā)送消息 public static void sendMessage() { if (null == mClient) { Log.d("service", "client is null"); return; } try { Message message = Message.obtain(null, FIND_DEVICE); mClient.send(message); } catch (RemoteException e) { e.printStackTrace(); } } }
AndroidManifest.xml中注冊(cè)messenger服務(wù):
<service android:name=".MessengerService" android:enabled="true" android:exported="true"> <intent-filter> <action android:name="android.intent.action.MESSENGER"/> </intent-filter> </service>
MainActivity中設(shè)置按鈕用于向客戶端主動(dòng)發(fā)送消息:
package com.test.messengerservice; import androidx.appcompat.app.AppCompatActivity; import android.os.Bundle; import android.view.View; import android.widget.Button; public class MainActivity extends AppCompatActivity { private Button button; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); button = findViewById(R.id.findDeviceButton); button.setOnClickListener( new View.OnClickListener() { @Override public void onClick(View v) { MessengerService.sendMessage(); } }); } }
客戶端應(yīng)用實(shí)現(xiàn)
MainActivity中綁定服務(wù)端的service,并設(shè)置向客戶端發(fā)送消息的按鈕:
package com.test.messengerclient; import androidx.annotation.NonNull; import androidx.appcompat.app.AppCompatActivity; import android.content.ComponentName; import android.content.Context; import android.content.Intent; import android.content.ServiceConnection; import android.os.Bundle; import android.os.Handler; import android.os.IBinder; import android.os.Message; import android.os.Messenger; import android.os.RemoteException; import android.util.Log; import android.view.View; import android.widget.Button; public class MainActivity extends AppCompatActivity { // 服務(wù)端的Messenger private Messenger mService; // 客戶端的Messenger private Messenger mMessenger; private Button buttonConfigNet; private Button buttonCancel; //發(fā)送給服務(wù)端的消息類型 private static final int SEND_MESSENGER = 0; private static final int CONFIG_NET = 1; private static final int CANCEL = 2; //接收服務(wù)端的消息類型 private static final int FIND_DEVICE = 10; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //客戶端Messenger mMessenger = new Messenger(new ClientHandler()); //綁定服務(wù) bindServiceInvoked(); //設(shè)置點(diǎn)擊事件 buttonConfigNet = findViewById(R.id.buttonConfigNet); buttonCancel = findViewById(R.id.buttonCancel); buttonConfigNet.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if(mService != null) { try { Log.d("client", "send config net"); Message message = Message.obtain(null, CONFIG_NET); message.replyTo = mMessenger; mService.send(message); } catch (RemoteException e) { e.printStackTrace(); } } } }); buttonCancel.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if(mService != null) { try { Log.d("client", "send cancel"); Message message = Message.obtain(null, CANCEL); message.replyTo = mMessenger; mService.send(message); } catch (RemoteException e) { e.printStackTrace(); } } } }); } //接收服務(wù)連接和斷開消息 ServiceConnection serviceConnection = new ServiceConnection() { @Override public void onServiceConnected(ComponentName name, IBinder service) { Log.i("client", "service connected"); mService = new Messenger(service); //由于綁定后服務(wù)端沒有客戶端的Messenger ,綁定后先將客戶端Messenger發(fā)送給服務(wù)端 if(mService != null) { try { Log.d("client", "send messenger"); Message message = Message.obtain(null, SEND_MESSENGER); message.replyTo = mMessenger; mService.send(message); } catch (RemoteException e) { e.printStackTrace(); } } } @Override public void onServiceDisconnected(ComponentName name) { Log.i("client", "service disconnected"); mService = null; } }; //從服務(wù)端接收消息 public class ClientHandler extends Handler { @Override public void handleMessage(@NonNull Message msg) { switch (msg.what){ case FIND_DEVICE: Log.i("client", "find device"); break; } } } //綁定服務(wù)端的service private void bindServiceInvoked() { Intent intent = new Intent(); intent.setAction("android.intent.action.MESSENGER"); intent.setPackage("com.test.messengerservice"); bindService(intent, serviceConnection, Context.BIND_AUTO_CREATE); } }
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
Android實(shí)現(xiàn)底部滾輪式選擇彈跳框
這篇文章主要為大家詳細(xì)介紹了Android實(shí)現(xiàn)底部滾輪式選擇彈跳框,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2022-08-08android Activity相對(duì)布局的使用方法
Activity相對(duì)布局控件的位置是與其周圍控件的位置相關(guān)的,從名字可以看出來,這些位置都是相對(duì)的,確定出了其中一個(gè)控件的位置就可以確定另一個(gè)控件的位置,下面用實(shí)例說明Activity相對(duì)布局的使用方法2013-11-11android listview進(jìn)階實(shí)例分享
這篇文章主要介紹了android listview進(jìn)階實(shí)例分享,具有一定借鑒價(jià)值,需要的朋友可以參考下2018-01-01Android scheme 跳轉(zhuǎn)的設(shè)計(jì)與實(shí)現(xiàn)詳解
這篇文章主要介紹了Android scheme 跳轉(zhuǎn)的設(shè)計(jì)與實(shí)現(xiàn),本文通過實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-06-06Android項(xiàng)目中使用HTTPS配置的步驟詳解
這篇文章主要給大家介紹了關(guān)于Android項(xiàng)目中使用HTTPS配置步驟的相關(guān)資料,文中介紹的非常詳細(xì),對(duì)大家具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起看看吧。2017-06-06深入理解Android中的Handler異步通信機(jī)制
這篇文章主要介紹了Android中的Handler異步通信機(jī)制,文中舉了兩個(gè)例子介紹了Handler里面實(shí)用的API中的方法,需要的朋友可以參考下2016-03-03Android?Studio調(diào)試Gradle插件詳情
這篇文章主要介紹了Android?Studio調(diào)試Gradle插件詳情,文章圍繞主題展開詳細(xì)的內(nèi)容戒殺,具有一定的參考價(jià)值,需要的小伙伴可以參考一下2022-09-09解決Android studio xml界面無法預(yù)覽問題
這篇文章主要介紹了解決Android studio xml界面無法預(yù)覽問題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2020-03-03Android開發(fā)之Notification手機(jī)狀態(tài)欄通知用法實(shí)例分析
這篇文章主要介紹了Android開發(fā)之Notification手機(jī)狀態(tài)欄通知用法,結(jié)合實(shí)例形式分析了Android Notification手機(jī)狀態(tài)欄通知的常見函數(shù)、功能及使用技巧,需要的朋友可以參考下2019-03-03