gpt4 book ai didi

android - 如何在 Firebase 消息服务和 Activity 之间进行通信?安卓

转载 作者:IT王子 更新时间:2023-10-28 23:34:10 24 4
gpt4 key购买 nike

我知道关于如何在服务和 Activity 之间进行通信的问题已经回答了很多次,但我也希望我自己的方式得到审查,并知道它是否是可接受的和正确的方式,以及什么是我如何处理它的缺点。首先,我将尽可能详细地陈述问题陈述。

我必须构建一个应用程序,在其中使用 Firebase 消息服务在两台设备之间进行通信。假设它是一个类似优步的系统。一个应用程序用于服务提供商(司机),一个应用程序用于客户(乘客)。当乘客请求使用他们的位置旅行时,一定半径内的司机将使用 Firebase 收到带有有效负载的推送通知。 Firebase 服务在后台运行。当服务收到推送通知时,onMessageReceived方法被调用。生成一个事件。我没有在这里使用 Firebase 来生成通知,而是在我需要使用 data 时在设备之间传输数据。 Firebase 推送通知字段。现在,驱动程序应用程序将在 Firebase 推送通知的有效负载中接收用户想要汽车的位置的坐标。我可以简单地使用 extras 中的这些数据启动一个 Activity ,并向驱动程序显示收到了一个请求。

现在在客户方面,在客户提交请求后,他们将被带到下一个 Activity ,在那里他们被显示一种加载屏幕,告诉他们等待一个司机接受他们的请求。当其中一个驱动程序接受该用户的请求时,该用户现在将收到一个 Firebase 推送通知,该通知的有效负载中包含指定驱动程序的信息。同样,目的不是生成任何通知,而是在设备之间传输数据。

现在您了解了用例,我将继续讨论这个问题。

当用户提交请求并移动到下一个等待屏幕时,就会出现问题,在那里他会看到一个加载屏幕,告诉他们等待,而请求正在等待其中一位司机接受。当驱动程序接受请求时,正如我所说,用户将收到 Firebase 推送通知,其中驱动程序的信息包含在推送通知的有效负载中。我如何在服务和 Activity 之间进行通信,告诉 Activity 停止显示加载屏幕并用推送通知的有效负载中收到的数据填充 TextView。

以下是我的处理方式。假设我有一个名为 AwaitingDriver 的 Activity ,其中有要由驱动程序数据填充的 TextView。但目前该 Activity 正在显示加载屏幕,因为该请求尚未被接受。现在,用户在后台运行的服务中收到带有驾驶员信息的推送通知,未以任何方式连接到 Activity 。这是我的onMessageReceived方法

    @Override
public void onMessageReceived(RemoteMessage remoteMessage){
SharedPreferences rideInfoPref = getSharedPreferences(getString(R.string.rideInfoPref), MODE_PRIVATE);
SharedPreferences.Editor rideInfoPrefEditor = rideInfoPref.edit();
String msgType = remoteMessage.getData().get("MessageType");
if (msgType.equals("RequestAccepted")){
rideInfoPrefEditor.putBoolean(getString(R.string.is_request_accepted), true);
rideInfoPrefEditor.putString(getString(R.string.driver_phone), remoteMessage.getData().get("DriverPhone"));
rideInfoPrefEditor.putString(getString(R.string.driver_lat), remoteMessage.getData().get("DriverLatitude"));
rideInfoPrefEditor.putString(getString(R.string.driver_lng), remoteMessage.getData().get("DriverLongitude"));

rideInfoPrefEditor.commit();
AwaitingDriver.requestAccepted(); // A static method in AwaitingDriver Activity
}
}

在这里, AwaitingDriver.requestAccepted()AwaitingDriver 的静态方法 Activity 。里面 AwaitingDriver Activity 本身,它显示一个进度对话框来告诉客户等待,这是方法 AwaitingDriver.requestAccepted()是在做。
public static void requestAccepted(){
try{
awaitingDriverRequesting.dismiss(); //ProgressDialog for telling user to wait
}catch (Exception e){
e.printStackTrace();
}
if (staticActivity != null){
staticActivity.new TaskFindSetValues().execute();
}
}

这里 staticActivityAwaitingDriver 的静态对象在此类中声明的 Activity 类。我将其值设置为 onResumeonPause方法。这意味着如果 Activity 在前面,显示在屏幕上,那么 staticActivity 的值才会显示。不是 null .这里是 onResumeonPause方法。
@Override
public void onResume(){
super.onResume();
staticActivity = this;
Boolean accepted = rideInfoPref.getBoolean(getString(R.string.is_request_accepted), false);
if (accepted){
new TaskFindSetValues().execute();
}
}
@Override
protected void onPause(){
super.onPause();
staticActivity = null;
}

在这里, TaskFindSetValues是在 AwaitingDriver 中定义的 AsyncTask Activity 课。这是 TaskFindSetValues 的代码
public class TaskFindSetValues extends AsyncTask<String, Void, String>{
String phone;
String lat;
String lng;
@Override
protected void onPreExecute(){
SharedPreferences pref = getSharedPreferences(getString(R.string.rideInfoPref), MODE_PRIVATE);
phone = pref.getString(getString(R.string.driver_phone), "");
lat = pref.getString(getString(R.string.driver_lat), "");
lng = pref.getString(getString(R.string.driver_lng), "");
}
@Override
protected String doInBackground(String... arg0){
return null;
}

@Override
protected void onPostExecute(String returnValue){
awaitingDriverPhone.setText(phone); //setting values to the TextViews
awaitingDriverLat.setText(lat);
awaitingDriverLng.setText(lng);
}
}

请查看此代码并告诉我这样做而不是其他解决方案的缺点,如果您还可以用相同的示例解释建议的方式,我将非常感激。

最佳答案

你为什么使用 AsyncTask?这没有意义。无论如何,如果您想与 Activity 进行通信,您可以使用 BroadcastReceiver .

public class MyFirebaseMessagingService extends FirebaseMessagingService{
private LocalBroadcastManager broadcaster;

@Override
public void onCreate() {
broadcaster = LocalBroadcastManager.getInstance(this);
}

@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
Intent intent = new Intent("MyData");
intent.putExtra("phone", remoteMessage.getData().get("DriverPhone"));
intent.putExtra("lat", remoteMessage.getData().get("DriverLatitude"));
intent.putExtra("lng", remoteMessage.getData().get("DriverLongitude"));
broadcaster.sendBroadcast(intent);
}
}

在你的 Activity 中
 @Override
protected void onStart() {
super.onStart();
LocalBroadcastManager.getInstance(this).registerReceiver((mMessageReceiver),
new IntentFilter("MyData")
);
}

@Override
protected void onStop() {
super.onStop();
LocalBroadcastManager.getInstance(this).unregisterReceiver(mMessageReceiver);
}

private BroadcastReceiver mMessageReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
awaitingDriverRequesting.dismiss();
awaitingDriverPhone.setText(intent.getExtras().getString("phone")); //setting values to the TextViews
awaitingDriverLat.setText(intent.getExtras().getDouble("lat"));
awaitingDriverLng.setText(intent.getExtras().getDouble("lng"));
}
};

编辑

根据@xuiqzy LocalBroadcastManager现在已弃用!谷歌说要使用 LiveData 或 Reactive Streams。

关于android - 如何在 Firebase 消息服务和 Activity 之间进行通信?安卓,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41925692/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com