GooglePlayServicesUtil vs GoogleApiAvailable


102

Я намагаюся використовувати службу Google Play у своєму додатку Android. Як говориться в документі Google, нам потрібно перевірити, чи доступний API Google, перш ніж використовувати його. Я шукав якийсь спосіб перевірити це. Ось що я отримав:

private boolean checkPlayServices() {
int resultCode = GooglePlayServicesUtil.isGooglePlayServicesAvailable(this);
if (resultCode != ConnectionResult.SUCCESS) {
    if (GooglePlayServicesUtil.isUserRecoverableError(resultCode)) {
        GooglePlayServicesUtil.getErrorDialog(resultCode, this,
                PLAY_SERVICES_RESOLUTION_REQUEST).show();
    } else {
        Log.i(TAG, "This device is not supported.");
        finish();
    }
    return false;
}
return true;
}

Але коли я переходжу на сторінку Google Api GooglePlayServicesUtil, https://developers.google.com/android/reference/com/google/android/gms/common/GooglePlayServicesUtil

Я вважаю, що всі функції застарілі . Наприклад, метод

GooglePlayServicesUtil.isGooglePlayServicesAvailable (застаріло)

І Google рекомендує використовувати:

GoogleApiAvailable.isGooglePlayServicesAvailable .

Однак, коли я намагаюся використовувати GoogleApiAvailable.isGooglePlayServicesAvailable, я отримую повідомлення про помилку:

введіть тут опис зображення


де я можу знайти GoogleApiAvailable? Я не можу його знайти.
mcmillab

@mcmillab +1 Я оновив з 8.1.0 до 8.4.0 і GooglePlayServicesUtilбільше не працює (що здається поганою практикою для "незначного" оновлення), але я не бачу GoogleApiAvailabilityвикористовувати його як заміну.
spaaarky21

Під час оновлення до каси Firebase
Dawid Drozd

Відповіді:


203

Я знайшов рішення. У Росії GoogleApiAvailabilityвсі методи є публічними методами, тоді як у GooglePlayServicesUtilвсіх методах є статична загальнодоступна функція.

Отже, щоб використовувати GoogleApiAvailable, правильний спосіб:

private boolean checkPlayServices() {
    GoogleApiAvailability googleAPI = GoogleApiAvailability.getInstance();
    int result = googleAPI.isGooglePlayServicesAvailable(this);
    if(result != ConnectionResult.SUCCESS) {
        if(googleAPI.isUserResolvableError(result)) {
            googleAPI.getErrorDialog(this, result,
                    PLAY_SERVICES_RESOLUTION_REQUEST).show();
        }

        return false;
    }

    return true;
}

9
що таке: PLAY_SERVICES_RESOLUTION_REQUEST
Saman Sattari

12
private final static int PLAY_SERVICES_RESOLUTION_REQUEST = 9000;
Феррмоліна

7
Це довільне ціле число. Ви можете скласти значення.
Timmmm

4
Деякі вважають за краще встановити значення на щось понад 9000.
matthias_b_nz

12
Весь дизайн бібліотеки Служб Google Play - це цілий безлад. Це все недоліки, а також важко дотримуватися, крім того, відсутність документації.
mr5

64

Клас GooglePlayServicesUtil більше не слід використовувати!

Ось як можна використовувати натомість клас GoogleApiAvailable - коли, наприклад, потрібен GCM (або будь-яка інша служба Google):

public static final int REQUEST_GOOGLE_PLAY_SERVICES = 1972;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    if (savedInstanceState == null) {
        startRegistrationService();
    }
}

private void startRegistrationService() {
    GoogleApiAvailability api = GoogleApiAvailability.getInstance();
    int code = api.isGooglePlayServicesAvailable(this);
    if (code == ConnectionResult.SUCCESS) {
        onActivityResult(REQUEST_GOOGLE_PLAY_SERVICES, Activity.RESULT_OK, null);
    } else if (api.isUserResolvableError(code) &&
        api.showErrorDialogFragment(this, code, REQUEST_GOOGLE_PLAY_SERVICES)) {
        // wait for onActivityResult call (see below)
    } else {
        Toast.makeText(this, api.getErrorString(code), Toast.LENGTH_LONG).show();
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    switch(requestCode) {
        case REQUEST_GOOGLE_PLAY_SERVICES:
            if (resultCode == Activity.RESULT_OK) {
                Intent i = new Intent(this, RegistrationService.class); 
                startService(i); // OK, init GCM
            }
            break;

        default:
            super.onActivityResult(requestCode, resultCode, data);
    }
}

ОНОВЛЕННЯ:

REQUEST_GOOGLE_PLAY_SERVICES- ціла константа з довільним назвою та значенням, про яке можна посилатися у onActivityResult()способі.

Також дзвінок this.onActivityResult()у наведеному вище коді нормально (ви також телефонуєте super.onActivityResult()в іншому місці).


2
Чи можете ви вказати на джерело, яке стверджує, що "Клас GooglePlayServicesUtil більше не слід використовувати!". API служб Google Play настільки заплутаний.
Лъчезар

8
Усі способи в GooglePlayServicesUtil, позначені як устарені плюс рекомендації у верхній частині javadoc, щоб взяти GOOGLE_PLAY_SERVICES_PACKAGEконстанту з класу GoogleApiAvailable - це спосіб Google сказати вам: більше не використовуйте GooglePlayServicesUtilклас.
Олександр Фарбер

3
Що робити, якщо на пристрої встановлена ​​старіша версія сервісів Google Play, у якій GoogleApiAvailabilityклас не існує? Якщо ми посилаємося на клас статично, навіть у умовному виразі, чи не буде він збій додаток?
Кевін Крумвієде

6
@Kevin Krumwiede, GoogleApiAvailabilityє частиною клієнтської бібліотеки. Таким чином, його код збирається в додаток => Не хвилюйтеся з цього приводу.
WindRider

9
Ви не повинні викликати onActivityResult (). Він мається на увазі викликатися ззовні, коли інша діяльність повертає результат.
Яр

10

Вам доведеться користуватися GoogleApiAvailable натомість:

GoogleApiAvailability googleApiAvailability = GoogleApiAvailability.getInstance(); 
int errorCode = googleApiAvailability.isGooglePlayServicesAvailable(this);

thisявляє собою context.


9

Перевірте пристрій і переконайтеся, що він містить APK Google Play Services. Якщо це не так, виведіть діалогове вікно, яке дозволяє користувачам завантажувати APK з Google Play Store або вмикати його в системних налаштуваннях пристрою.

public static boolean checkPlayServices(Activity activity) {
    final int PLAY_SERVICES_RESOLUTION_REQUEST = 9000;
    GoogleApiAvailability apiAvailability = GoogleApiAvailability.getInstance();
    int resultCode = apiAvailability.isGooglePlayServicesAvailable(activity);
    if (resultCode != ConnectionResult.SUCCESS) {
        if (apiAvailability.isUserResolvableError(resultCode)) {
            apiAvailability.getErrorDialog(activity, resultCode, PLAY_SERVICES_RESOLUTION_REQUEST)
                    .show();
        } else {
            Logger.logE(TAG, "This device is not supported.");
        }
        return false;
    }
    return true;
}

0

Я додав це як розвагу в класі BaseActivity, який можна використовувати в усіх місцях

    fun checkGooglePlayServices(okAction : ()-> Unit , errorAction: (msg:String, isResolved:Boolean)-> Unit){
    val apiAvailability = GoogleApiAvailability.getInstance()
    val resultCode = apiAvailability.isGooglePlayServicesAvailable(this)
    if (resultCode != ConnectionResult.SUCCESS) {
        if (apiAvailability.isUserResolvableError(resultCode)) {
            apiAvailability.getErrorDialog(
                this,
                resultCode,
                PLAY_SERVICES_RESOLUTION_REQUEST
            ).show()
             // dialoe when click on ok should let user go to install/update play serices


            errorAction("dialog is shown" , true)

        } else {
          "checkGooglePlayServices  This device is not supported.".log(mTag)
            errorAction("This device is not supported",false)
        }
    }else{
        okAction()
    }
}

companion object {
    const val PLAY_SERVICES_RESOLUTION_REQUEST = 1425
}

використовувати його так

    (activity as? BaseActivity)?.checkGooglePlayServices({
        // ok so start map
        initializeMap()
    },
        { msg, isResolved ->
            if (!isResolved)
                context?.show(msg)

        }
    )

Або ви можете налаштувати його як хочете.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.