Search code examples
androidandroid-intentwidgetandroid-widgetandroid-pendingintent

Android widget PendingIntent stop working when app is killed


I have been looking for a solution for this problem for a week by now.

When my app is running in background, the onclicks event on the widget work as expected. But when the application is closed (killed by task manager), the widget's PendingIntents stop working.

How is it possible? I think I have created the widget provider correctly.

Something is missing?

Can someone help me?

Here is my code:

- compileSdk 31
- minSdk 23
- targetSdk 31
- gradle -> "com.android.tools.build:gradle:7.0.4"

Provider class:

public class GPWidgetProvider extends AppWidgetProvider {

    private static RemoteViews getRemoteViews(Context context) {

        RemoteViews views = new RemoteViews(context.getPackageName(), R.layout.widget);
        Intent intentHome = new Intent(context, Home.class);
        intentHome.setData(Uri.parse(intentHome.toUri(Intent.URI_INTENT_SCHEME)));
        intentHome.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
        PendingIntent homePendingIntent = PendingIntent.getActivity(context, 13, intentHome, PendingIntent.FLAG_IMMUTABLE | PendingIntent.FLAG_UPDATE_CURRENT);
        views.setOnClickPendingIntent(R.id.widget_image, homePendingIntent);

        return views;
    }

    @Override
    public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
        for (int appWidgetId : appWidgetIds) {
            RemoteViews views = getRemoteViews(context);
            appWidgetManager.updateAppWidget(appWidgetId, views);
        }
        super.onUpdate(context, appWidgetManager, appWidgetIds);
    }

    public static void updateWidget(Context context) {
        AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context);
        ComponentName widget = new ComponentName(context, GPWidgetProvider.class);
        int[] appWidgetIds = appWidgetManager.getAppWidgetIds(widget);

        for (int appWidgetId : appWidgetIds) {
            RemoteViews views = getRemoteViews(context);
            appWidgetManager.updateAppWidget(appWidgetId, views);
        }
    }
}

Manifest:

<receiver
        android:name="<myPackage>.GPWidgetProvider"
        android:enabled="true"
        android:exported="true">
    <intent-filter>
        <action android:name="android.appwidget.action.APPWIDGET_ENABLED" />
        <action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
        <action android:name="android.appwidget.action.APPWIDGET_DELETED" />
        <action android:name="android.appwidget.action.APPWIDGET_DISABLED" />
    </intent-filter>
    <meta-data
            android:name="android.appwidget.provider"
            android:resource="@xml/widget_info" />
</receiver>

Thanks in advance.


Solution

  • If an app is killed by e.g. the user force-stopping, all of the services, activities, notifications, and PendingIntents from the app are cancelled. You'll only have an opportunity to recover the next time your app runs (from activity launching, receiving broadcast, etc).

    This is why the system warns the user that apps may not behave properly if force-stopped.