Firebase Cloud Messaging:在 onMessageReceived() 中访问 UI 元素



在我的安卓应用中,我使用 Firebase 云消息传递向应用发送一些数据。

当应用程序通过 onMessageReceived() 接收消息时,我检查MainActivity当前是否可见(MainActivity具有对当前可见MainActivity的静态引用(,如果活动可见,我会对活动进行一些修改。

由于onMessageReceived()不在主线程中调用,因此我使用Handler在主线程中执行代码。

@Override
public void onMessageReceived(final RemoteMessage remoteMessage) {
    Handler handler = new Handler(Looper.getMainLooper());
    handler.post(new Runnable() {
        //Access UI
    });
}

这种方法有什么问题吗?如果没有,是否有其他方法可以在收到云消息时更新当前可见的 UI?

应避免在特定活动中为 UI 更改编写onMessageReceived()直接代码。您可以通过本地广播接收器进行频道传输。

当您倾向于直接在onMessageReceived()中编写代码时,您的FirebaseMessagingService类将变得混乱。例如,如果您有 4 种不同类型的通知数据,并且每个数据调用不同的活动。然后你的代码将看起来像这样:

@Override
public void onMessageReceived(final RemoteMessage remoteMessage) {
    if(remoteMessage.getData() != null 
        && remoteMessage.getData().containsKey("notification_type")){
        switch(remoteMessage.getData().containsKey("notification_type")){
            case "type1":
                Handler handler = new Handler(Looper.getMainLooper());
                handler.post(new Runnable() {
                    //Access UI for some activity
                    .
                    .
                    .
                });
                break;
            case "type2":
                Handler handler = new Handler(Looper.getMainLooper());
                handler.post(new Runnable() {
                     //Access UI for some activity
                    .
                    .
                    .
                });
                break;
            case "type3":
                Handler handler = new Handler(Looper.getMainLooper());
                handler.post(new Runnable() {
                     //Access UI for some activity
                    .
                    .
                    .
                });
                break;
            case "type4":
                Handler handler = new Handler(Looper.getMainLooper());
                handler.post(new Runnable() {
                     //Access UI for some activity
                    .
                    .
                    .
                });
                break;
        }
    }
}

或者,如果您使用本地广播,那么您的代码将更加模块化和有条理。您的代码将如下所示:

@Override
public void onMessageReceived(final RemoteMessage remoteMessage) {
    if(remoteMessage.getData() != null 
        && remoteMessage.getData().containsKey("notification_type")){
        Intent intent = new Intent();
        intent.putExtra("body",messageBody); // Put info that you want to send to the activity
        switch(remoteMessage.getData().containsKey("notification_type")){
            case "type1":
                intent.setAction("ACTION_1") // For activity1
                break;
            case "type2":
                intent.setAction("ACTION_2") //For activity2
                break;
            case "type3":
                intent.setAction("ACTION_3") //For activity3
                break;
            case "type4":
                intent.setAction("ACTION_4") //For activity4
                break;
        }
        sendBroadcast(intent);
    }
}

您的活动(例如活动 1(将如下所示: 私人广播接收器 m接收器;

@Override
protected void onResume() {
    // TODO Auto-generated method stub
    super.onResume();
    IntentFilter intentFilter = new IntentFilter(
            "ACTION_1"); // Put appropriate action string 
    mReceiver = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            //Get message from intent
            String msg_for_me = intent.getStringExtra("some_msg");
            //Do your UI Changes stuff here.
        }
    };
    //registering our receiver
    this.registerReceiver(mReceiver, intentFilter);
}
@Override
protected void onPause() {
    super.onPause();
    this.unregisterReceiver(this.mReceiver);//unregister receiver
}

根据我的说法,这将帮助您在活动本身中编写UI更改,并引导您进行更好的代码管理。

希望有用!

最新更新