diff --git a/app/src/main/java/com/example/android/sunshine/app/MainActivity.java b/app/src/main/java/com/example/android/sunshine/app/MainActivity.java index 4960cfa..07068f5 100644 --- a/app/src/main/java/com/example/android/sunshine/app/MainActivity.java +++ b/app/src/main/java/com/example/android/sunshine/app/MainActivity.java @@ -15,8 +15,14 @@ */ package com.example.android.sunshine.app; +import android.app.AlertDialog; +import android.content.Context; import android.content.Intent; +import android.content.SharedPreferences; +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; import android.net.Uri; +import android.os.AsyncTask; import android.os.Bundle; import android.support.v7.app.ActionBarActivity; import android.util.Log; @@ -26,15 +32,28 @@ import android.view.MenuItem; import com.example.android.sunshine.app.sync.SunshineSyncAdapter; import com.google.android.gms.common.ConnectionResult; import com.google.android.gms.common.GooglePlayServicesUtil; +import com.google.android.gms.gcm.GoogleCloudMessaging; + +import java.io.IOException; +import java.util.concurrent.atomic.AtomicInteger; public class MainActivity extends ActionBarActivity implements ForecastFragment.Callback { private final String LOG_TAG = MainActivity.class.getSimpleName(); private static final String DETAILFRAGMENT_TAG = "DFTAG"; private final static int PLAY_SERVICES_RESOLUTION_REQUEST = 9000; + public static final String PROPERTY_REG_ID = "registration_id"; + private static final String PROPERTY_APP_VERSION = "appVersion"; + + /** + * Substitute you own sender ID here. This is the project number you got + * from the API Console. + */ + String SENDER_ID = "Your-Sender-ID"; private boolean mTwoPane; private String mLocation; + private GoogleCloudMessaging mGcm; @Override protected void onCreate(Bundle savedInstanceState) { @@ -66,12 +85,26 @@ public class MainActivity extends ActionBarActivity implements ForecastFragment. SunshineSyncAdapter.initializeSyncAdapter(this); - if (!checkPlayServices()) { - // this is where we could either prompt a user that they should install - // the latest version of Google Play Services, or add an error snackbar - // that some features won't be available. - } + // If Google Play Services is not available, some features, such as GCM-powered weather + // alerts, will not be available. + if (checkPlayServices()) { + mGcm = GoogleCloudMessaging.getInstance(this); + String regId = getRegistrationId(this); + if (SENDER_ID.equals("Your-Sender-ID")) { + new AlertDialog.Builder(this) + .setTitle("Needs Sender ID") + .setMessage("GCM will not function in Sunshine until you replace your Sender ID with a Sender ID from the Google Developers Console.") + .setPositiveButton(android.R.string.ok, null) + .create().show(); + } else if (regId.isEmpty()) { + registerInBackground(this); + } + } else { + Log.i(LOG_TAG, "No valid Google Play Services APK. Weather alerts will be disabled."); + // Store regID as null + storeRegistrationId(this, null); + } } @Override @@ -162,4 +195,113 @@ public class MainActivity extends ActionBarActivity implements ForecastFragment. } return true; } + + /** + * Gets the current registration ID for application on GCM service. + *
+ * If result is empty, the app needs to register. + * + * @return registration ID, or empty string if there is no existing + * registration ID. + */ + private String getRegistrationId(Context context) { + final SharedPreferences prefs = getGCMPreferences(context); + String registrationId = prefs.getString(PROPERTY_REG_ID, ""); + if (registrationId.isEmpty()) { + Log.i(LOG_TAG, "GCM Registration not found."); + return ""; + } + + // Check if app was updated; if so, it must clear the registration ID + // since the existing registration ID is not guaranteed to work with + // the new app version. + int registeredVersion = prefs.getInt(PROPERTY_APP_VERSION, Integer.MIN_VALUE); + int currentVersion = getAppVersion(context); + if (registeredVersion != currentVersion) { + Log.i(LOG_TAG, "App version changed."); + return ""; + } + return registrationId; + } + + /** + * @return Application's {@code SharedPreferences}. + */ + private SharedPreferences getGCMPreferences(Context context) { + // Sunshine persists the registration ID in shared preferences, but + // how you store the registration ID in your app is up to you. Just make sure + // that it is private! + return getSharedPreferences(MainActivity.class.getSimpleName(), Context.MODE_PRIVATE); + } + + /** + * @return Application's version code from the {@code PackageManager}. + */ + private static int getAppVersion(Context context) { + try { + PackageInfo packageInfo = context.getPackageManager() + .getPackageInfo(context.getPackageName(), 0); + return packageInfo.versionCode; + } catch (PackageManager.NameNotFoundException e) { + // Should never happen. WHAT DID YOU DO?!?! + throw new RuntimeException("Could not get package name: " + e); + } + } + + /** + * Registers the application with GCM servers asynchronously. + *
+ * Stores the registration ID and app versionCode in the application's
+ * shared preferences.
+ */
+ private void registerInBackground(final Context context) {
+ new AsyncTask