diff --git a/src/com/android/launcher/Launcher.java b/src/com/android/launcher/Launcher.java index 7b7802e1f8..7dd341819a 100644 --- a/src/com/android/launcher/Launcher.java +++ b/src/com/android/launcher/Launcher.java @@ -168,6 +168,7 @@ public final class Launcher extends Activity implements View.OnClickListener, On private final BroadcastReceiver mApplicationsReceiver = new ApplicationsIntentReceiver(); private final ContentObserver mObserver = new FavoritesChangeObserver(); + private final ContentObserver mAppWidgetResetObserver = new AppWidgetResetObserver(); private LayoutInflater mInflater; @@ -826,6 +827,7 @@ public final class Launcher extends Activity implements View.OnClickListener, On sModel.abortLoaders(); getContentResolver().unregisterContentObserver(mObserver); + getContentResolver().unregisterContentObserver(mAppWidgetResetObserver); unregisterReceiver(mApplicationsReceiver); } @@ -1156,6 +1158,7 @@ public final class Launcher extends Activity implements View.OnClickListener, On private void registerContentObservers() { ContentResolver resolver = getContentResolver(); resolver.registerContentObserver(LauncherSettings.Favorites.CONTENT_URI, true, mObserver); + resolver.registerContentObserver(LauncherProvider.CONTENT_APPWIDGET_RESET_URI, true, mAppWidgetResetObserver); } @Override @@ -1221,6 +1224,16 @@ public final class Launcher extends Activity implements View.OnClickListener, On sModel.loadUserItems(false, this, false, false); } + /** + * When reset, we handle by calling {@link AppWidgetHost#startListening()} + * to make sure our callbacks are set correctly. + */ + private void onAppWidgetReset() { + if (mAppWidgetHost != null) { + mAppWidgetHost.startListening(); + } + } + void onDesktopItemsLoaded() { if (mDestroyed) return; bindDesktopItems(); @@ -1877,6 +1890,21 @@ public final class Launcher extends Activity implements View.OnClickListener, On } } + /** + * Receives notifications when the {@link AppWidgetHost} has been reset, + * usually only when the {@link LauncherProvider} database is first created. + */ + private class AppWidgetResetObserver extends ContentObserver { + public AppWidgetResetObserver() { + super(new Handler()); + } + + @Override + public void onChange(boolean selfChange) { + onAppWidgetReset(); + } + } + /** * Receives intents from other applications to change the wallpaper. */ diff --git a/src/com/android/launcher/LauncherProvider.java b/src/com/android/launcher/LauncherProvider.java index e63ef3084f..a27b746672 100644 --- a/src/com/android/launcher/LauncherProvider.java +++ b/src/com/android/launcher/LauncherProvider.java @@ -65,6 +65,14 @@ public class LauncherProvider extends ContentProvider { static final String TABLE_FAVORITES = "favorites"; static final String PARAMETER_NOTIFY = "notify"; + /** + * {@link Uri} triggered at any registered {@link ContentObserver} when + * {@link AppWidgetHost#deleteHost()} is called during database creation. + * Use this to recall {@link AppWidgetHost#startListening()} if needed. + */ + static final Uri CONTENT_APPWIDGET_RESET_URI = + Uri.parse("content://" + AUTHORITY + "/appWidgetReset"); + private SQLiteOpenHelper mOpenHelper; @Override @@ -176,6 +184,17 @@ public class LauncherProvider extends ContentProvider { mAppWidgetHost = new AppWidgetHost(context, Launcher.APPWIDGET_HOST_ID); } + /** + * Send notification that we've deleted the {@link AppWidgetHost}, + * probably as part of the initial database creation. The receiver may + * want to re-call {@link AppWidgetHost#startListening()} to ensure + * callbacks are correctly set. + */ + private void sendAppWidgetResetNotify() { + final ContentResolver resolver = mContext.getContentResolver(); + resolver.notifyChange(CONTENT_APPWIDGET_RESET_URI, null); + } + @Override public void onCreate(SQLiteDatabase db) { if (LOGD) Log.d(LOG_TAG, "creating new launcher database"); @@ -204,6 +223,7 @@ public class LauncherProvider extends ContentProvider { // Database was just created, so wipe any previous widgets if (mAppWidgetHost != null) { mAppWidgetHost.deleteHost(); + sendAppWidgetResetNotify(); } if (!convertDatabase(db)) {