Чтобы уменьшить расход заряда батареи при использовании сервисов геолокации, выполните следующие действия:
Как удалить уведомления о местоположении
Часто батарея разряжается из-за того, что приложение продолжает получать данные о местоположении, когда они уже не нужны.
Это может произойти, если методы жизненного цикла onStart() или onResume() объекта activity содержат вызов requestlocationUpdates() без соответствующего вызова removeLocationUpdates() в методах жизненного цикла onPause() или onStop().
Чтобы лучше управлять жизненным циклом объектов activity в приложении, используйте компоненты, учитывающие жизненный цикл. Подробнее о том, как управлять жизненным циклом с помощью компонентов, учитывающих жизненный цикл…
Как настроить тайм-ауты
Чтобы избежать быстрого расхода батареи, установите разумное время ожидания, по истечении которого уведомления о местоположении должны прекратиться. Это позволяет избежать бесконечного обновления и защищает приложение в ситуациях, когда обновления запрашиваются, но не удаляются (например, из-за ошибки в коде).
Чтобы добавить время ожидания для запроса к поставщику объединенных геоданных, вызовите метод setDurationMillis(), который получает параметр, представляющий время в миллисекундах с момента последнего вызова метода. Вы также можете использовать метод, чтобы указать срок действия в виде продолжительности.
Чтобы добавить время ожидания в запрос местоположения геозоны, вызовите метод setExpirationDuration().
Пакетные запросы
Для всех остальных случаев используйте пакетные запросы. Используйте метод setIntervalMillis(), чтобы указать интервал, с которым должно определяться местоположение. Затем с помощью метода setMaxUpdateDelayMillis() задайте интервал, с которым данные о местоположении будут передаваться в приложение. Значение, передаваемое методу setMaxUpdateDelayMillis(), должно быть кратно значению, передаваемому методу setIntervalMillis(). Рассмотрим следующий запрос местоположения:
Kotlin
val request = LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10 * 60 * 1000)
.setMaxUpdateDelayMillis(60 * 60 * 1000)
.build()
Java
LocationRequest request = new LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10 * 60 * 1000)
.setMaxUpdateDelayMillis(60 * 60 * 1000)
.build();
В этом случае система вычисляет местоположение примерно каждые десять минут и передает пакет из примерно шести элементов данных о местоположении примерно каждый час. Вы по-прежнему будете получать уведомления о местоположении примерно каждые 10 минут, но заряд батареи будет расходоваться медленнее, потому что устройство будет выходить из спящего режима только раз в час.
Использовать пассивные уведомления о местоположении
В фоновом режиме рекомендуется ограничить частоту обновления данных о местоположении. В Android 8.0 (уровень API 26) это ограничение применяется принудительно, но мы рекомендуем разработчикам приложений для более ранних версий Android также по возможности ограничить доступ к данным о местоположении в фоновом режиме.
Вероятно, пока ваше приложение работает в фоновом режиме, другое приложение часто запрашивает данные о местоположении в активном режиме. Сервисы геолокации предоставляют эти обновления вашему приложению. Рассмотрим следующий запрос местоположения, который использует данные о местоположении:
Kotlin
val request = LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 15 * 60 * 1000)
.setMinUpdateIntervalMillis(2 * 60 * 1000)
.build()
Java
LocationRequest request = new LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 15 * 60 * 1000)
.setMinUpdateIntervalMillis(2 * 60 * 1000)
.build();
В предыдущем примере местоположение приложения вычисляется примерно каждые 15 минут. Если другие приложения запрашивают данные о местоположении, приложение получает их с максимальным интервалом в две минуты.
Хотя пассивное получение данных о местоположении не приводит к разрядке батареи, будьте особенно осторожны в случаях, когда получение данных о местоположении запускает ресурсоемкие операции ЦП или ввода-вывода. Чтобы минимизировать расход заряда батареи, интервал, указанный в setMinUpdateIntervalMillis(), не должен быть слишком маленьким.