Clic en notificación: actividad ya abierta


Tengo una aplicación con notificaciones que abren una determinada actividad si hago clic en ellas. Quiero que, si hago clic en la notificación y la actividad ya está abierta, es no comenzó de nuevo, sino que acaba de ponerse al frente.

Pensé que podría hacerlo con la bandera FLAG_ACTIVITY_BROUGHT_TO_FRONT o FLAG_ACTIVITY_REORDER_TO_FRONT, pero sigue abriéndola de nuevo, así que tengo la actividad dos veces.

Este es mi código:

event_notification = new Notification(R.drawable.icon,
            mContext.getString(R.string.event_notif_message), System.currentTimeMillis()); 
Intent notificationIntent = new Intent(mContext, EventListActivity.class);
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT);
sendNotification(event_notification, notificationIntent, mContext.getString(R.string.event_notif_title),
                body, Utils.PA_NOTIFICATIONS_ID);

Puedo gestionarlo con flags o debo almacenar una variable en SharedPreferences para comprobar si ¿está abierto o no?

Gracias!

Author: Jonik, 2012-08-20

6 answers

Necesita establecer el atributo launchMode del Activity que está comenzando a singleTop. Esto hará que las Intents entrantes se entreguen a la instancia existente en lugar de iniciar una nueva instancia cuando Activity ya esté en la parte superior de la pila de la tarea.

Esto se hace en el manifiesto añadiendo android:launchMode="singleTop" al elemento <activity>. Para acceder a la última Intent (si está interesado en cualquier dato que pueda haber pasado con ella), anule onNewIntent() en su Activity.

 242
Author: Devunwired,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-08-20 19:16:32

Intente establecer las banderas en Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP en su lugar.

De la documentación para FLAG_ACTIVITY_CLEAR_TOP (énfasis mío):

Si se establece, y la actividad que se inicia ya se está ejecutando en el tarea actual, entonces en lugar de lanzar una nueva instancia de actividad, todas las demás actividades en la parte superior de la misma se cerrarán y esta intención se entregará a la (ahora en la parte superior) actividad antigua como un nueva Intención.

Por ejemplo, considere una tarea compuesto por las actividades: A, B, C, D. Si D llama a startActivity() con una Intent que resuelve componente de la actividad B, entonces C y D serán terminados y B recibir la Intención dada, dando como resultado que la pila ahora sea: A, B.

La instancia actualmente en ejecución de la actividad B en el ejemplo anterior o bien recibir la nueva intención que está empezando aquí en su onNewIntent (), o ser él mismo terminado y reiniciado con el nuevo intención. Si ha declarado su lanzamiento modo de ser " múltiple "(el predeterminado) y no ha establecido FLAG_ACTIVITY_SINGLE_TOP en el mismo intent, luego se terminará y se volverá a crear; para todos los demás lanzamientos modes o si se establece FLAG_ACTIVITY_SINGLE_TOP, esta Intent será entregado a onNewIntent () de la instancia actual.

 30
Author: user113215,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-08-20 19:19:52

Use onNewIntent() para manejar nuevos datos de notificación haga clic y actualice la actividad.

En onNewIntent obtener los nuevos datos de la nueva intent (que sirvió por la nueva notificación) y capturarlos, por ejemplo:

title = intent.getStringExtra("title")

En onCreate anteriormente:)

Actualizará la actividad actual con nuevos datos de notificación.

También puedes seguir este tutorial: http://androidrace.com/2016/12/10/how-to-refresh-activity-on-new-notification-click-android-developer/

 4
Author: Afjalur Rahman Rana,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-12-10 21:48:20
Notification.Builder mBuilder =
            new Notification.Builder(this)
            .setSmallIcon(R.drawable.cmplayer)
            .setContentTitle("CoderoMusicPlayer")
            .setContentText("PLayer0!");

    Intent resultIntent = new Intent(this, 

    AndroidBuildingMusicPlayerActivity.class);
        resultIntent.setAction(Intent.ACTION_MAIN);
        resultIntent.addCategory(Intent.CATEGORY_LAUNCHER);

        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0,
                resultIntent, 0);

        mBuilder.setContentIntent(pendingIntent);
        NotificationManager mNotificationManager =
            (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        mNotificationManager.notify(1, mBuilder.build());

Simplemente copie el código y péguelo en su actividad principal del lanzador.

Aquí está la respuesta original

 2
Author: Community,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 11:55:03

Creo que debería agregar algo de lógica para que funcione, tal vez esto pueda ayudar:

Por ejemplo, tengo una pantalla de bienvenida (Lanzador y PRINCIPAL) de la APLICACIÓN:

public class SplashScreen extends AppCompatActivity {
    private final int TIME_OUT = 2000;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_splash_screen);

        // Suscribirse al tema Notificaciones
        FirebaseMessaging.getInstance().subscribeToTopic("NOTA");
        if (getIntent().getExtras() != null) {
            if (getIntent().getExtras().size()>1){
                Intent home_activity = new Intent(getApplicationContext(), Home.class);
                home_activity.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
                if (getIntent().getExtras() != null) {
                    for (String key : getIntent().getExtras().keySet()) {
                        String value = "" + getIntent().getExtras().getString(key);
                        Log.d("TAG", key + "=" + value);
                        switch (key) {
                            case "url":
                                home_activity.putExtra("url", value);
                                break;
                        }
                    }
                }
                startActivity(home_activity);
                finish();

            }else{
                new Handler().postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        try {
                            Intent home_activity = new Intent(getApplicationContext(), Home.class);
                            home_activity.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
                            startActivity(home_activity);
                            finish();
                        } catch (Exception ex) {
                            ex.printStackTrace();
                        }
                    }
                }, TIME_OUT);
            }


        } else {
            new Handler().postDelayed(new Runnable() {
                @Override
                public void run() {
                    try {
                        Intent home_activity = new Intent(getApplicationContext(), Home.class);
                        home_activity.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
                        startActivity(home_activity);
                        finish();
                    } catch (Exception ex) {
                        ex.printStackTrace();
                    }
                }
            }, TIME_OUT);
        }

    }

}

Y en mi servicio de fuego he hecho lo siguiente:

public class FCMessagingService extends FirebaseMessagingService {

    private final String TAG = "PUSH";
    private String body = "";
    private static String _url = "";
    private static int numMessage = 0;

    @Override
    public void onMessageReceived(RemoteMessage remoteMessage) {
        super.onMessageReceived(remoteMessage);

        String from = remoteMessage.getFrom();
        Log.d(TAG, "Mensaje recibido de: " + from);

        if (remoteMessage.getNotification() != null) {
            Log.d(TAG, "Notificación: " + remoteMessage.getNotification().getBody());

            if (remoteMessage.getData().size() > 0) {
                Log.d(TAG, "Data: " + remoteMessage.getData());
                try {
                    JSONObject data = new JSONObject(remoteMessage.getData());
                    String url = data.getString("url");
                    Log.d(TAG, "onMessageReceived: \n" + "Extra Information: " + url);
                    this._url = url;
                    Log.d("_URL",_url);
                    mostrarNotificacion(remoteMessage.getNotification().getTitle(), remoteMessage.getNotification().getBody());
                    mensaje(url, remoteMessage.getNotification().getTitle(), remoteMessage.getNotification().getBody());
                } catch (JSONException e) {
                    e.printStackTrace();
                }
            }
        }



    }


    private void mensaje(String url, String title, String body){
        boolean acti =  Util.comprobarActivityALaVista(getApplicationContext(), "com.dev.android.subagan.MainActivity");
        if(acti){

            Intent imain = new Intent(MainActivity.URL);

            imain.putExtra("key_url",url);
            imain.putExtra("key_title",title);
            imain.putExtra("key_body",body);

            LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(imain);

        }else{

            Intent ihome = new Intent(Home.URL);

            ihome.putExtra("key_url",url);
            ihome.putExtra("key_title",title);
            ihome.putExtra("key_body",body);
            LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(ihome);

        }

    }




    private void mostrarNotificacion(String title, String body) {

        final int NOTIFICATION_ID = 3000;

        Intent intent = new Intent(this, MainActivity.class);
        intent.putExtra("url",_url);
        intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);


        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent,PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_ONE_SHOT  );



        Uri soundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);

        NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
                .setSmallIcon(R.mipmap.ic_launcher)
                .setContentTitle(title)
                .setContentText(body)
                .setAutoCancel(true)
                .setSound(soundUri)
                .setTicker(body)
                .setContentIntent(pendingIntent);

        NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
        notificationManager.notify(0, notificationBuilder.build());

    }

}
 0
Author: Carlos Alberto Gonzalez,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-10-02 22:02:45
Intent intent = new Intent(this, MainActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent contentIntent = PendingIntent.getActivity(this, new Random().nextInt(), intent, 0);
 0
Author: Manjunath,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-06-28 00:21:22