Изменить настройки местоположения

Если вашему приложению требуется запрашивать местоположение или получать обновления разрешений, на устройстве необходимо включить соответствующие системные настройки, такие как GPS или сканирование Wi-Fi. Вместо того, чтобы напрямую включать такие службы, как GPS устройства, ваше приложение указывает требуемый уровень точности/энергопотребления и желаемый интервал обновления, а устройство автоматически вносит соответствующие изменения в системные настройки. Эти настройки определяются объектом данных LocationRequest .

В этом уроке показано, как использовать клиент настроек для проверки включенных настроек и отображения диалогового окна настроек местоположения, чтобы пользователь мог обновить свои настройки одним нажатием.

Настройка служб определения местоположения

Чтобы использовать службы определения местоположения, предоставляемые сервисами Google Play и поставщиком объединенного местоположения, подключите свое приложение с помощью клиента настроек , затем проверьте текущие настройки местоположения и предложите пользователю включить требуемые настройки при необходимости.

Приложения, функции которых используют службы определения местоположения, должны запрашивать разрешения на определение местоположения в зависимости от вариантов использования этих функций.

Настройте запрос местоположения

Для хранения параметров запросов к объединённому поставщику местоположения создайте объект LocationRequest . Параметры определяют уровень точности запросов местоположения. Подробную информацию обо всех доступных параметрах запроса местоположения см. в справочнике по классу LocationRequest . В этом уроке задаются интервал обновления, самый быстрый интервал обновления и приоритет, как описано ниже:

Интервал обновления
setIntervalMillis() — этот метод задаёт частоту (в миллисекундах), с которой ваше приложение предпочитает получать обновления местоположения. Обратите внимание, что обновления местоположения могут происходить немного быстрее или медленнее этой частоты для оптимизации расхода заряда батареи, или обновления могут отсутствовать вовсе (например, если устройство не подключено к сети).
Самый быстрый интервал обновления
setMinUpdateIntervalMillis() — этот метод устанавливает максимальную скорость (в миллисекундах), с которой ваше приложение может обрабатывать обновления местоположения. Если ваше приложение не получает обновления быстрее, чем указано в setInterval() , вам не нужно вызывать этот метод.
Приоритет

setPriority() — этот метод устанавливает приоритет запроса, давая службам определения местоположения Google Play чёткую подсказку о том, какие источники геолокации использовать. Поддерживаются следующие значения:

  • PRIORITY_BALANCED_POWER_ACCURACY — используйте этот параметр для запроса точности определения местоположения в пределах городского квартала, что составляет примерно 100 метров. Это считается низким уровнем точности и, вероятно, потребует меньше энергии. При использовании этого параметра службы определения местоположения, скорее всего, будут использовать данные Wi-Fi и вышки сотовой связи. Однако следует учитывать, что выбор поставщика геолокационных данных зависит от множества других факторов, например, от доступных источников.
  • PRIORITY_HIGH_ACCURACY — используйте этот параметр для запроса максимально точного местоположения. При использовании этого параметра службы геолокации с большей вероятностью будут использовать GPS для определения местоположения.
  • PRIORITY_LOW_POWER — используйте этот параметр, чтобы запросить точность на уровне города, что составляет примерно 10 километров. Это считается низким уровнем точности и, вероятно, потребует меньше энергии.
  • PRIORITY_PASSIVE — используйте этот параметр, если вам требуется незначительное влияние на энергопотребление, но вы хотите получать обновления местоположения, когда они доступны. При использовании этого параметра ваше приложение не будет запускать обновления местоположения, но будет получать данные о местоположении, полученные от других приложений.

Создайте запрос местоположения и задайте параметры, как показано в этом примере кода:

Котлин

  fun createLocationRequest() {
    val locationRequest = LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10000)
        .setMinUpdateIntervalMillis(5000)
        .build()
}

Ява

  protected void createLocationRequest() {
    LocationRequest locationRequest = new LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10000)
            .setMinUpdateIntervalMillis(5000)
            .build();
}

Приоритет PRIORITY_HIGH_ACCURACY в сочетании с разрешением ACCESS_FINE_LOCATION , заданным в манифесте приложения, и коротким интервалом обновления в 5000 миллисекунд (5 секунд) позволяет поставщику объединённого местоположения возвращать обновления местоположения с точностью до нескольких футов. Такой подход подходит для картографических приложений, отображающих местоположение в режиме реального времени.

Совет по производительности: если ваше приложение обращается к сети или выполняет другую длительную работу после получения обновления местоположения, уменьшите значение самого быстрого интервала. Это предотвратит получение приложением обновлений, которые оно не может использовать. После завершения длительной работы снова уменьшите значение самого быстрого интервала.

Получить текущие настройки местоположения

После подключения к сервисам Google Play и API служб определения местоположения вы можете получить текущие настройки местоположения устройства пользователя. Для этого создайте LocationSettingsRequest.Builder и добавьте один или несколько запросов местоположения. Следующий фрагмент кода показывает, как добавить запрос местоположения, созданный на предыдущем шаге:

Котлин

val builder = LocationSettingsRequest.Builder()
        .addLocationRequest(locationRequest)

Ява

LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
     .addLocationRequest(locationRequest);

Далее проверьте, удовлетворены ли текущие настройки местоположения:

Котлин

val builder = LocationSettingsRequest.Builder()

// ...

val client: SettingsClient = LocationServices.getSettingsClient(this)
val task: Task<LocationSettingsResponse> = client.checkLocationSettings(builder.build())

Ява

LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder();

// ...

SettingsClient client = LocationServices.getSettingsClient(this);
Task<LocationSettingsResponse> task = client.checkLocationSettings(builder.build());

После завершения Task ваше приложение может проверить настройки местоположения, просматривая код состояния объекта LocationSettingsResponse . Чтобы получить более подробную информацию о текущем состоянии соответствующих настроек местоположения, ваше приложение может вызвать метод getLocationSettingsStates() объекта LocationSettingsResponse .

Предложить пользователю изменить настройки местоположения

Чтобы определить, соответствуют ли настройки местоположения запросу, добавьте OnFailureListener к объекту Task , который проверяет настройки местоположения. Затем проверьте, является ли объект Exception , переданный методу onFailure() , экземпляром класса ResolvableApiException , что указывает на необходимость изменения настроек. Затем отобразите диалоговое окно, запрашивающее у пользователя разрешение на изменение настроек местоположения путем вызова startResolutionForResult() .

В следующем фрагменте кода показано, как определить, позволяют ли настройки местоположения пользователя службам определения местоположения создавать LocationRequest , а также как запросить у пользователя разрешение на изменение настроек местоположения при необходимости:

Котлин

task.addOnSuccessListener { locationSettingsResponse ->
    // All location settings are satisfied. The client can initialize
    // location requests here.
    // ...
}

task.addOnFailureListener { exception ->
    if (exception is ResolvableApiException){
        // Location settings are not satisfied, but this can be fixed
        // by showing the user a dialog.
        try {
            // Show the dialog by calling startResolutionForResult(),
            // and check the result in onActivityResult().
            exception.startResolutionForResult(this@MainActivity,
                    REQUEST_CHECK_SETTINGS)
        } catch (sendEx: IntentSender.SendIntentException) {
            // Ignore the error.
        }
    }
}

Ява

task.addOnSuccessListener(this, new OnSuccessListener<LocationSettingsResponse>() {
    @Override
    public void onSuccess(LocationSettingsResponse locationSettingsResponse) {
        // All location settings are satisfied. The client can initialize
        // location requests here.
        // ...
    }
});

task.addOnFailureListener(this, new OnFailureListener() {
    @Override
    public void onFailure(@NonNull Exception e) {
        if (e instanceof ResolvableApiException) {
            // Location settings are not satisfied, but this can be fixed
            // by showing the user a dialog.
            try {
                // Show the dialog by calling startResolutionForResult(),
                // and check the result in onActivityResult().
                ResolvableApiException resolvable = (ResolvableApiException) e;
                resolvable.startResolutionForResult(MainActivity.this,
                        REQUEST_CHECK_SETTINGS);
            } catch (IntentSender.SendIntentException sendEx) {
                // Ignore the error.
            }
        }
    }
});

В следующем уроке, «Запрос обновлений местоположения» , показано, как получать периодические обновления местоположения.