PendingIntent не отправляет дополнительные сведения о намерениях

Мой MainActicity начинается RefreshService с Intent, у которого есть boolean дополнительный, называемый isNextWeek.

Мой RefreshService создает Notification, который запускает мой MainActivity, когда пользователь нажимает на него.

это выглядит так:

    Log.d("Refresh", "RefreshService got: isNextWeek: " + String.valueOf(isNextWeek));

    Intent notificationIntent = new Intent(this, MainActivity.class);
    notificationIntent.putExtra(MainActivity.IS_NEXT_WEEK, isNextWeek);

    Log.d("Refresh", "RefreshService put in Intent: isNextWeek: " + String.valueOf(notificationIntent.getBooleanExtra(MainActivity.IS_NEXT_WEEK,false)));
    pendingIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0);

    builder = new NotificationCompat.Builder(this).setContentTitle("Title").setContentText("ContentText").setSmallIcon(R.drawable.ic_notification).setContentIntent(pendingIntent);
    notification = builder.build();
    // Hide the notification after its selected
    notification.flags |= Notification.FLAG_AUTO_CANCEL;
    notificationManager.notify(NOTIFICATION_REFRESH, notification);

Как видите, notificationIntent должен иметь booleanextra IS_NEXT_WEEK со значением isNextWeek, которое вставлено в PendingIntent.

Когда я нажимаю сейчас это Notification, я всегда получаю false как значение isNextWeek

Вот как я получаю значение в MainActivity:

    isNextWeek = getIntent().getBooleanExtra(IS_NEXT_WEEK, false);

Бревно:

08-04 00:19:32.500  13367-13367/de.MayerhoferSimon.Vertretungsplan D/Refresh: MainActivity sent: isNextWeek: true
08-04 00:19:32.510  13367-13573/de.MayerhoferSimon.Vertretungsplan D/Refresh: RefreshService got: isNextWeek: true
08-04 00:19:32.510  13367-13573/de.MayerhoferSimon.Vertretungsplan D/Refresh: RefreshService put in Intent: isNextWeek: true
08-04 00:19:41.990  13367-13367/de.MayerhoferSimon.Vertretungsplan D/Refresh: MainActivity.onCreate got: isNextWeek: false

Когда я напрямую начинаю MainActivity с Intent с «sNextValue» следующим образом:

    Intent i = new Intent(this, MainActivity.class);
    i.putExtra(IS_NEXT_WEEK, isNextWeek);
    finish();
    startActivity(i);

все работает нормально, и я получаю true, когда isNextWeek равно true.

Что я не так делаю, что всегда есть значение false?

ОБНОВИТЬ

это решает проблему: https://stackoverflow.com/a/18049676/2180161

Цитата:

Я подозреваю, что, поскольку единственное, что меняется в намерении, - это дополнительные функции, фабричный метод PendingIntent.getActivity(...) просто повторно использует старое намерение в качестве оптимизации.

В RefreshService попробуйте:

PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, notificationIntent, PendingIntent.FLAG_CANCEL_CURRENT);

Видеть:

http://developer.android.com/reference/android/app/PendingIntent.html#FLAG_CANCEL_CURRENT

ОБНОВЛЕНИЕ 2

См. ответ ниже, почему лучше использовать PendingIntent.FLAG_UPDATE_CURRENT.


person maysi    schedule 03.08.2013    source источник
comment
PendingIntent.FLAG_CANCEL_CURRENT работал у меня, спасибо   -  person Pelanes    schedule 16.06.2014
comment
сэкономил мне много часов работы. правильный ответ!   -  person TharakaNirmana    schedule 06.12.2014
comment
у вас есть вопрос и решение: D отлично. Думаю, вам стоит добавить его в качестве ответа на вопросы. +10 лучше, чем +5;)   -  person Muhammed Refaat    schedule 18.04.2017
comment
Ссылаясь на это решение: stackoverflow.com/questions/1198558/   -  person M.Noman    schedule 07.11.2017
comment
FLAG_UPDATE_CURRENT в моем случае не хватило, так как тот же PendingIntent был повторно использован моим виджетом. В итоге я использовал FLAG_ONE_SHOT для действия, которое происходит редко, и оставил виджет PendingIntent без изменений.   -  person Eir    schedule 23.04.2020


Ответы (3)


Использование PendingIntent.FLAG_CANCEL_CURRENT - не лучшее решение из-за неэффективного использования памяти. Вместо этого используйте PendingIntent.FLAG_UPDATE_CURRENT.

Также используйте Intent.FLAG_ACTIVITY_SINGLE_TOP < / strong> (действие не будет запущено, если оно уже запущено на вершине стека истории).

Intent resultIntent = new Intent(this, FragmentPagerSupportActivity.class).
                    addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP);  
resultIntent.putExtra(FragmentPagerSupportActivity.PAGE_NUMBER_KEY, pageNumber);

PendingIntent resultPendingIntent =
                PendingIntent.getActivity(
                        this,
                        0,
                        resultIntent,
                        PendingIntent.FLAG_UPDATE_CURRENT
                );

Потом:

@Override
    protected void onCreate(Bundle savedInstanceState) {
        try {
            super.onCreate(savedInstanceState);

            int startPageNumber;
            if ( savedInstanceState != null)
            {
                startPageNumber = savedInstanceState.getInt(PAGE_NUMBER_KEY);
//so on

Теперь он должен работать.


Если у вас все еще не ожидаемое поведение, попробуйте реализовать обработчик событий void onNewIntent(Intent intent), таким образом вы можете получить доступ к новому намерению, которое было вызвано для действия (что не то же самое, что просто вызов getIntent (), это всегда будет возвращать первое намерение, которое начал свою деятельность.

@Override
protected void onNewIntent(Intent intent) {
    int startPageNumber;

    if (intent != null) {
        startPageNumber = intent.getExtras().getInt(PAGE_NUMBER_KEY);
    } else {
        startPageNumber = 0;
    }
}
person Yuliia Ashomok    schedule 08.06.2016

Я думаю, вам нужно обновить Intent, когда вы получите новый, переопределив onNewIntent(Intent) в своей деятельности. Добавьте в свою деятельность следующее:

@Override
public void onNewIntent(Intent newIntent) {
    this.setIntent(newIntent);

    // Now getIntent() returns the updated Intent
    isNextWeek = getIntent().getBooleanExtra(IS_NEXT_WEEK, false);        
}

Изменить:

Это необходимо только в том случае, если ваша деятельность уже была запущена на момент получения намерения. Если ваша деятельность начата (а не просто возобновлена) по намерению, значит, проблема в другом месте, и мое предложение не может ее исправить.

person Vikram    schedule 03.08.2013
comment
это появляется также, если деятельность закрывается, а затем открывается с уведомлением. - person maysi; 05.08.2013

Следующий код должен работать: -

int icon = R.drawable.icon;
String message = "hello";
long when = System.currentTimeMillis();
NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
Notification notification = new Notification(icon, message, when);

Intent notificationIntent = new Intent(context, MainActivity.class);
notificationIntent.putExtra("isNexWeek", true);
notificationIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
PendingIntent pIntent = PendingIntent.getActivity(context, 0, notificationIntent, 0);
notification.setLatestEventInfo(context, title, message, pIntent);
notification.flags |= Notification.FLAG_AUTO_CANCEL;
notificationManager.notify(0, notification);

В MainActivity onCreate:

if (getIntent().getExtras() != null && getIntent().getExtras().containsKey("isNextWeek")) {
        boolean isNextWeek = getIntent().getExtras().getBoolean("isNextWeek");
}
person Haris ur Rehman    schedule 03.08.2013
comment
new Notification(icon, message, when); устарел - person maysi; 04.08.2013
comment
Все равно сделать это без CLEAR_TOP? - person richardaum; 26.06.2015